What happens
Parsing everyday statements in the Trino dialect panics instead of producing a parse tree or a clean error.
let dialect = kind_to_dialect(&DialectKind::Trino, None).unwrap();
let lexer = Lexer::from(&dialect);
let parser = Parser::from(&dialect);
let tokens = lexer.lex(&tables, "create table".to_string());
parser.parse(&tables, &tokens.0).unwrap(); // panics
create table panics with Grammar refers to 'TRANSIENT' which was not found in the dialect (grammar.rs:133)
insert into t values (1) panics with Grammar refers to 'OVERWRITE' which was not found in the dialect (grammar.rs:145)
alter table t ... reaches the same panic for SEQUENCE
I hit these while fuzzing the parser across dialects, and confirmed each by lexing and parsing the string above through the public pipeline.
Root cause
trino.rs builds Trino from ansi::raw_dialect(), then clears the keyword sets and repopulates them from TRINO_UNRESERVED_KEYWORDS / TRINO_RESERVED_KEYWORDS:
trino_dialect.sets_mut("unreserved_keywords").clear();
trino_dialect.update_keywords_set_from_multiline_string("unreserved_keywords", TRINO_UNRESERVED_KEYWORDS);
The inherited ANSI grammar still contains Ref::keyword("TRANSIENT"), Ref::keyword("OVERWRITE") and Ref::keyword("SEQUENCE") (from TemporaryTransientGrammar, InsertStatementSegment, and the alter/sequence grammar). Dialect::expand only creates a library entry for a keyword that is present in a keyword set, so these references resolve to nothing and Dialect::ref takes its None arm and panics. Trino does not override those statement segments, so the ANSI grammar with these refs is used as is.
The tricky part, and why I did not just send a PR
The obvious quick fix, adding TRANSIENT, OVERWRITE, SEQUENCE to Trino's keyword sets, would be wrong. Trino does not support transient tables, INSERT OVERWRITE, or sequences, so registering those keywords would make the parser accept syntax that is not valid Trino.
I can see a few real fixes, and which one you want is a dialect design call, so I would rather ask than guess:
- Override
CreateTableStatementSegment, InsertStatementSegment and the alter/sequence grammar in Trino to drop the unsupported keyword references, matching what Trino actually accepts (and SQLFluff's Trino dialect).
- Make
Dialect::ref degrade gracefully when a grammar references a keyword that is not in the dialect's sets, so an optional keyword simply does not match rather than crashing. This would also guard any other dialect against the same class of panic, though it changes core behavior and might hide genuine dialect misconfigurations.
Happy to put up a PR for whichever direction you prefer.
What happens
Parsing everyday statements in the Trino dialect panics instead of producing a parse tree or a clean error.
create tablepanics withGrammar refers to 'TRANSIENT' which was not found in the dialect(grammar.rs:133)insert into t values (1)panics withGrammar refers to 'OVERWRITE' which was not found in the dialect(grammar.rs:145)alter table t ...reaches the same panic forSEQUENCEI hit these while fuzzing the parser across dialects, and confirmed each by lexing and parsing the string above through the public pipeline.
Root cause
trino.rsbuilds Trino fromansi::raw_dialect(), then clears the keyword sets and repopulates them fromTRINO_UNRESERVED_KEYWORDS/TRINO_RESERVED_KEYWORDS:The inherited ANSI grammar still contains
Ref::keyword("TRANSIENT"),Ref::keyword("OVERWRITE")andRef::keyword("SEQUENCE")(fromTemporaryTransientGrammar,InsertStatementSegment, and the alter/sequence grammar).Dialect::expandonly creates a library entry for a keyword that is present in a keyword set, so these references resolve to nothing andDialect::reftakes itsNonearm and panics. Trino does not override those statement segments, so the ANSI grammar with these refs is used as is.The tricky part, and why I did not just send a PR
The obvious quick fix, adding
TRANSIENT,OVERWRITE,SEQUENCEto Trino's keyword sets, would be wrong. Trino does not support transient tables,INSERT OVERWRITE, or sequences, so registering those keywords would make the parser accept syntax that is not valid Trino.I can see a few real fixes, and which one you want is a dialect design call, so I would rather ask than guess:
CreateTableStatementSegment,InsertStatementSegmentand the alter/sequence grammar in Trino to drop the unsupported keyword references, matching what Trino actually accepts (and SQLFluff's Trino dialect).Dialect::refdegrade gracefully when a grammar references a keyword that is not in the dialect's sets, so an optional keyword simply does not match rather than crashing. This would also guard any other dialect against the same class of panic, though it changes core behavior and might hide genuine dialect misconfigurations.Happy to put up a PR for whichever direction you prefer.