Repository navigation
Refuse typed timestamp literals Snowflake rejects - #142
Merged
Merged
Conversation
Snowflake takes only DATE, TIME and TIMESTAMP as typed literals. It rejects TIMESTAMP_NTZ, TIMESTAMP_LTZ, TIMESTAMP_TZ, their spellings without underscores and DATETIME before a string with a syntax error (errno 1003), and with a precision as an unsupported literal (errno 2121), but the named-type literal rule read each as a cast that then converted. The parser now refuses them at the string, pointing to '...'::<type> or the TO_ function. The date-time constant form gains a negative neighbour for each, still to capture.
tslit-ex-00, the nine date-time-constant neighbours built at 2541bfd: seven syntax errors (1003/42000) and the two precision forms as compilation errors after parsing (2121/42601). Inventory equal, no changes, 0.0 credits.
… after parsing Snowflake parses TIMESTAMP_NTZ(3) '...' and TIMESTAMP_TZ(3) '...' and rejects them at compile time (2121, "Unsupported data type literal"), while the seven bare spellings are syntax errors (1003). The parser now refuses only the bare spellings; a listed type with parameters before a string parses as a cast, and the refusal pass rejects it as SQ0211 unsupported_type_literal with the same advice to write '...'::TIMESTAMP_NTZ or call TO_TIMESTAMP_NTZ. The two precision cases settle as accept with a semantic stage from import 171's receipts.
The case builder looked a receipt's setup text up by the pair of its SQL hash and setup digest in the reports' inputs. The run that recorded the 13 IPADDRESS and UUID temporary table cases lists no inputs for their SQL, so the builder fell back to the held setup and rewrote their recorded setup. The same setup text is listed under the same digest by other reports, and the digest names the text, so the lookup now uses the digest alone. A plain rebuild of the expressions family now reproduces the committed case file.
This was referenced Nov 7, 2026
SQ0211 matched any CAST to a listed timestamp type with a precision, so
CAST('...' AS DATETIME(3)), CAST('...' AS TIMESTAMPNTZ(3)) and the
TIMESTAMP_LTZ casts were refused although they are ordinary casts. A cast
now records whether it was written as a typed literal, TYPE '...', and
only those are refused. The flag is left out of the serialized tree, so
parse trees and coverage fingerprints are unchanged.
The DATETIME '...' syntax refusal checked only for the Snowflake dialect, so the polyglot-matching modes refused it too, where polyglot reads it as a datetime literal; polyglot's exact corpus check failed on test_bigquery_date_timezone_to_duckdb_476. It now uses the same gate as the other Snowflake syntax refusals.
kvlonge
added a commit
that referenced
this pull request
Nov 7, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Snowflake rejects a typed literal on a timestamp name other than
TIMESTAMP, but the parser read it as a cast and conversion went ahead. This PR makes each spelling fail in the same phase that Snowflake rejects it.TIMESTAMP_NTZ,TIMESTAMP_LTZ,TIMESTAMP_TZ,TIMESTAMPNTZ,TIMESTAMPLTZ,TIMESTAMPTZandDATETIMEbefore a string. The parser refuses these with SQ0001, with the caret at the string.TIMESTAMP_NTZ(3) '…'andTIMESTAMP_TZ(3) '…'. These parse as casts through the named-type rule, and the refusal pass rejects them as the new code SQ0211unsupported_type_literal.Both messages point to
'…'::TIMESTAMP_NTZorTO_TIMESTAMP_NTZ.TIMESTAMP '…'andDATE '…'are unchanged.Coverage:
sf.expressions.data-types-datetime.date-time-constantobligations o009–o017 and nine cases.accept, stagesemantic.syntax-coverage diffgains all nine obligations. It still lists the form as lost until its review is renewed, because the new obligations changed its definition.Separate commit: the case builder now finds a run-database receipt's setup by its digest alone. Before, a rebuild rewrote 13 IPADDRESS/UUID cases to the held setup, because their run lists no inputs for their SQL. The same bug made a rebuild move about 60
create-warehouseDDL cases off their recorded "d103 sweep" setup, which also made some settlements miss. With the fix, a plain rebuild ofexpressionsandddlreproduces the committed files, and #143 then only adds the pending settlements.With the digest-only lookup, the builder's
setup_reviewlist goes from empty to 16 cases: 14 ddl (alter-external-volume, alter-materialized-view, alter-restricted-session-scope, alter-semantic-view, alter-stream, alter-type, desc-transaction, show-mcp-servers) and 2 functions (system-resolve-python-packages). Their receipts disagree on whether the setup made a syntax error, so they keep the default setup. No committed file changes because of them, but they are new review work. On main the lookup found a recorded setup for only 2,746 receipts; it now finds 41,196.Review: auditor-expressions-016 (two commits from the auditor, bf97f06 and 615a5c2) renews the date-time-constant review at parser tree 90d18284. With it,
staleis empty andsyntax-coverage diff coverage/syntax/baseline.jsongains o009–o017 and loses no form.Follow-up, not in this PR: TIMESTAMP_LTZ(3), TIMESTAMPNTZ/LTZ/TZ(3), DATETIME(3), TIMESTAMP(3) and TIME(3) before a string have no receipts yet. They will be added as negative neighbours in the next import.