SQL: Don't allow inexact fields for MIN/MAX (#39563)

MIN/MAX on strings are supported and are implemented with
TopAggs FIRST/LAST respectively, but they cannot operate on
`text` fields without underlying `keyword` fields => inexact.

Follows: #39427
This commit is contained in:
Marios Trivyzas 2019-03-04 15:29:10 +01:00
parent 52ecf18dc4
commit c72a7998f5
No known key found for this signature in database
GPG Key ID: 8817B46B0CF36A3F
3 changed files with 16 additions and 2 deletions

View File

@ -13,6 +13,7 @@ import org.elasticsearch.xpack.sql.type.DataType;
import java.util.List; import java.util.List;
import static org.elasticsearch.xpack.sql.expression.TypeResolutions.isExact;
import static org.elasticsearch.xpack.sql.expression.TypeResolutions.isNumericOrDate; import static org.elasticsearch.xpack.sql.expression.TypeResolutions.isNumericOrDate;
/** /**
@ -47,7 +48,7 @@ public class Max extends NumericAggregate implements EnclosedAgg {
@Override @Override
protected TypeResolution resolveType() { protected TypeResolution resolveType() {
if (field().dataType().isString()) { if (field().dataType().isString()) {
return TypeResolution.TYPE_RESOLVED; return isExact(field(), sourceText(), ParamOrdinal.DEFAULT);
} else { } else {
return isNumericOrDate(field(), sourceText(), ParamOrdinal.DEFAULT); return isNumericOrDate(field(), sourceText(), ParamOrdinal.DEFAULT);
} }

View File

@ -13,6 +13,7 @@ import org.elasticsearch.xpack.sql.type.DataType;
import java.util.List; import java.util.List;
import static org.elasticsearch.xpack.sql.expression.TypeResolutions.isExact;
import static org.elasticsearch.xpack.sql.expression.TypeResolutions.isNumericOrDate; import static org.elasticsearch.xpack.sql.expression.TypeResolutions.isNumericOrDate;
/** /**
@ -50,7 +51,7 @@ public class Min extends NumericAggregate implements EnclosedAgg {
@Override @Override
protected TypeResolution resolveType() { protected TypeResolution resolveType() {
if (field().dataType().isString()) { if (field().dataType().isString()) {
return TypeResolution.TYPE_RESOLVED; return isExact(field(), sourceText(), ParamOrdinal.DEFAULT);
} else { } else {
return isNumericOrDate(field(), sourceText(), ParamOrdinal.DEFAULT); return isNumericOrDate(field(), sourceText(), ParamOrdinal.DEFAULT);
} }

View File

@ -717,6 +717,18 @@ public class VerifierErrorMessagesTests extends ESTestCase {
error("SELECT FIRST(int) FROM test GROUP BY text HAVING FIRST(int) > 10")); error("SELECT FIRST(int) FROM test GROUP BY text HAVING FIRST(int) > 10"));
} }
public void testMinOnInexactUnsupported() {
assertEquals("1:8: [MIN(text)] cannot operate on field of data type [text]: " +
"No keyword/multi-field defined exact matches for [text]; define one or use MATCH/QUERY instead",
error("SELECT MIN(text) FROM test"));
}
public void testMaxOnInexactUnsupported() {
assertEquals("1:8: [MAX(text)] cannot operate on field of data type [text]: " +
"No keyword/multi-field defined exact matches for [text]; define one or use MATCH/QUERY instead",
error("SELECT MAX(text) FROM test"));
}
public void testMinOnKeywordGroupByHavingUnsupported() { public void testMinOnKeywordGroupByHavingUnsupported() {
assertEquals("1:52: HAVING filter is unsupported for function [MIN(keyword)]", assertEquals("1:52: HAVING filter is unsupported for function [MIN(keyword)]",
error("SELECT MIN(keyword) FROM test GROUP BY text HAVING MIN(keyword) > 10")); error("SELECT MIN(keyword) FROM test GROUP BY text HAVING MIN(keyword) > 10"));