Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[WIP] Parse invalid numbers and throw an error #24799

Open
wants to merge 2 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 34 additions & 3 deletions core/trino-grammar/src/main/antlr4/io/trino/grammar/sql/SqlBase.g4
Original file line number Diff line number Diff line change
Expand Up @@ -983,6 +983,7 @@ number
: MINUS? DECIMAL_VALUE #decimalLiteral
| MINUS? DOUBLE_VALUE #doubleLiteral
| MINUS? INTEGER_VALUE #integerLiteral
| MINUS? INVALID_NUMBER #invalidNumber
;

authorizationUser
Expand Down Expand Up @@ -1367,6 +1368,24 @@ DOUBLE_VALUE
| '.' DIGIT+ EXPONENT
;

INVALID_NUMBER
// Trailing underscore
: DIGIT ('_' | DIGIT)* '_'
| '0X' ('_' | HEX_DIGIT)* '_'
| '0O' ('_' | OCTAL_DIGIT)* '_'
| '0B' ('_' | BINARY_DIGIT)* '_'
// Consecutive underscores
| DECIMAL_INTEGER '__' ('_' | DIGIT)*
| HEXADECIMAL_INTEGER '__' ('_' | HEX_DIGIT)*
| OCTAL_INTEGER '__' ('_' | OCTAL_DIGIT)*
| BINARY_INTEGER '__' ('_' | BINARY_DIGIT)*
| DIGIT ('_' | DIGIT)* '.' DECIMAL_INTEGER '__' ('_' | DIGIT)*
// Underscore besides comma
| DIGIT ('_' | DIGIT)* '_' '.' ('_' | DIGIT)*
| DECIMAL_INTEGER '.' '_' ('_' | DIGIT)*
| '.' '_' ('_' | DIGIT)*
;

IDENTIFIER
: (LETTER | '_') (LETTER | DIGIT | '_')*
;
Expand All @@ -1388,15 +1407,15 @@ fragment DECIMAL_INTEGER
;

fragment HEXADECIMAL_INTEGER
: '0X' ('_'? (DIGIT | [A-F]))+
: '0X' ('_'? HEX_DIGIT)+
;

fragment OCTAL_INTEGER
: '0O' ('_'? [0-7])+
: '0O' ('_'? OCTAL_DIGIT)+
;

fragment BINARY_INTEGER
: '0B' ('_'? [01])+
: '0B' ('_'? BINARY_DIGIT)+
;

fragment EXPONENT
Expand All @@ -1407,6 +1426,18 @@ fragment DIGIT
: [0-9]
;

fragment HEX_DIGIT
: [0-9A-F]
;

fragment OCTAL_DIGIT
: [0-7]
;

fragment BINARY_DIGIT
: [01]
;

fragment LETTER
: [A-Z]
;
Expand Down
11 changes: 11 additions & 0 deletions core/trino-parser/src/main/java/io/trino/sql/parser/SqlParser.java
Original file line number Diff line number Diff line change
Expand Up @@ -235,6 +235,17 @@ public void exitDigitIdentifier(SqlBaseParser.DigitIdentifierContext context)
token.getCharPositionInLine() + 1);
}

@Override
public void exitInvalidNumber(SqlBaseParser.InvalidNumberContext context)
{
Token token = context.INVALID_NUMBER().getSymbol();
throw new ParsingException(
"numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point",
null,
token.getLine(),
token.getCharPositionInLine() + 1);
}

@Override
public void exitNonReserved(SqlBaseParser.NonReservedContext context)
{
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,16 @@ private static Stream<Arguments> expressions()
{
return Stream.of(
Arguments.of("", "line 1:1: mismatched input '<EOF>'. Expecting: <expression>"),
Arguments.of("1 + 1 x", "line 1:7: mismatched input 'x'. Expecting: '%', '*', '+', '-', '.', '/', 'AND', 'AT', 'OR', '[', '||', <EOF>, <predicate>"));
Arguments.of("1 + 1 x", "line 1:7: mismatched input 'x'. Expecting: '%', '*', '+', '-', '.', '/', 'AND', 'AT', 'OR', '[', '||', <EOF>, <predicate>"),
Arguments.of("1_", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("1__2", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("12_.", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("12._", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("12._34", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("12.3__4", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("0x_", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("0b_", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"),
Arguments.of("0o_", "line 1:1: numbers may not contain trailing underscores, consecutive underscores, or underscores besides the decimal point"));
}

private static Stream<Arguments> statements()
Expand Down Expand Up @@ -215,7 +224,7 @@ public void testPossibleExponentialBacktracking2()
"line 24:1: mismatched input 'GROUP'. Expecting: '%', ')', '*', '+', ',', '-', '.', '/', 'AND', 'AT', 'FILTER', 'IGNORE', 'OR', 'OVER', 'RESPECT', '[', '||', <predicate>");
}

@ParameterizedTest
@ParameterizedTest(name = "{index}: {0}")
@MethodSource("statements")
public void testStatement(String sql, String error)
{
Expand All @@ -224,7 +233,7 @@ public void testStatement(String sql, String error)
.hasMessage(error);
}

@ParameterizedTest
@ParameterizedTest(name = "{index}: {0}")
@MethodSource("expressions")
public void testExpression(String sql, String error)
{
Expand Down
Loading