8000 fix(clickhouse): add support for DateTime64(precision, tz) and Tuples() by ogirardot · Pull Request #6060 · sqlfluff/sqlfluff · GitHub
[go: up one dir, main page]
More Web Proxy on the site http://driver.im/
Skip to content

fix(clickhouse): add support for DateTime64(precision, tz) and Tuples() #6060

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

Merged
merged 5 commits into from
Aug 11, 2024
Merged
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
61 changes: 59 additions & 2 deletions src/sqlfluff/dialects/dialect_clickhouse.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@
SegmentGenerator,
Sequence,
StringLexer,
StringParser,
SymbolSegment,
TypedParser,
)
Expand Down Expand Up @@ -328,15 +329,71 @@ class BracketedArguments(ansi.BracketedArguments):
Delimited(
OneOf(
# Dataypes like Nullable allow optional datatypes here.
Ref("DatatypeIdentifierSegment"),
Ref("NumericLiteralSegment"),
Ref("DatatypeSegment"),
),
# The brackets might be empty for some cases...
optional=True,
),
)


class DatatypeSegment(BaseSegment):
"""Support complex Clickhouse data types.

Complex data types are typically used in either DDL statements or as
the target type in casts.
"""

type = "data_type"
match_grammar = OneOf(
Sequence(
StringParser("NULLABLE", CodeSegment, type="data_type_identifier"),
Bracketed(Ref("DatatypeSegment")),
),
Ref("TupleTypeSegment"),
Ref("DatatypeIdentifierSegment"),
Ref("NumericLiteralSegment"),
Sequence(
StringParser("DATETIME64", CodeSegment, type="data_type_identifier"),
Bracketed(
Delimited(
Ref("NumericLiteralSegment"), # precision
Ref("QuotedLiteralSegment", optional=True), # timezone
# The brackets might be empty as well
optional=True,
),
optional=True,
),
),
)


class TupleTypeSegment(ansi.StructTypeSegment):
"""Expression to construct a Tuple datatype."""

match_grammar = Sequence(
"TUPLE",
Ref("TupleTypeSchemaSegment"), # Tuple() can't be empty
)


class TupleTypeSchemaSegment(BaseSegment):
"""Expression to construct the schema of a Tuple datatype."""

type = "tuple_type_schema"
match_grammar = Bracketed(
Delimited(
Sequence(
Ref("SingleIdentifierGrammar"),
Ref("DatatypeSegment"),
),
bracket_pairs_set="bracket_pairs",
),
bracket_pairs_set="bracket_pairs",
bracket_type="round",
)


class ArrayJoinClauseSegment(BaseSegment):
"""[LEFT] ARRAY JOIN does not support Join conditions and doesn't work as real JOIN.

Expand Down
3 changes: 3 additions & 0 deletions src/sqlfluff/dialects/dialect_clickhouse_keywords.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,8 @@
"DATABASE",
"DATABASES",
"DATE",
"DATETIME32",
"DATETIME64",
"DAY",
"DEDUPLICATE",
"DEFAULT",
Expand Down Expand Up @@ -180,6 +182,7 @@
"TRIM",
"TRUNCATE",
"TTL",
"TUPLE",
"TYPE",
"UNFREEZE",
"UPDATE",
Expand Down
10 changes: 5 additions & 5 deletions test/fixtures/dialects/clickhouse/create_table.yml
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
# computed by SQLFluff when running the tests. Please run
# `python test/generate_parse_fixture_yml.py` to generate them after adding or
# altering SQL files.
_hash: 74dc79622bd7e71234949b6e8a3f21f986e80cf3f4bff8e8c591b233fdc26510
_hash: 0d8c06d7b85df995a48a26ffd92efdb9082f25001adda4393383ef373b2dd2b9
file:
- statement:
create_table_statement:
Expand Down Expand Up @@ -507,11 +507,11 @@ file:
naked_identifier: s
data_type:
data_type_identifier: Nullable
bracketed_arguments:
bracketed:
start_bracket: (
bracketed:
start_bracket: (
data_type:
data_type_identifier: String
end_bracket: )
end_bracket: )
- end_bracket: )
- engine:
- keyword: ENGINE
Expand Down
9 changes: 9 additions & 0 deletions test/fixtures/dialects/clickhouse/datetime64_precision.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
SELECT '2024-01-01'::DateTime64 as datetime;

SELECT '2024-01-01'::DateTime64() as datetime;

SELECT '2024-01-01'::DateTime64(3) as datetime;

SELECT '2024-01-01'::DateTime64(3, 'Europe/Paris') as datetime;

SELECT '2024-01-01'::DateTime64(6) as datetime;
99 changes: 99 additions & 0 deletions test/fixtures/dialects/clickhouse/datetime64_precision.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
# YML test files are auto-generated from SQL files and should not be edited by
# hand. To help enforce this, the "hash" field in the file must match a hash
# computed by SQLFluff when running the tests. Please run
# `python test/generate_parse_fixture_yml.py` to generate them after adding or
# altering SQL files.
_hash: 21229aedcf3c2f7bbc08f000918f35e29eb04cad440579c2cc54c485feafb031
file:
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
quoted_literal: "'2024-01-01'"
casting_operator: '::'
data_type:
data_type_identifier: DateTime64
alias_expression:
keyword: as
naked_identifier: datetime
- statement_terminator: ;
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
quoted_literal: "'2024-01-01'"
casting_operator: '::'
data_type:
data_type_identifier: DateTime64
bracketed:
start_bracket: (
end_bracket: )
alias_expression:
keyword: as
naked_identifier: datetime
- statement_terminator: ;
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
quoted_literal: "'2024-01-01'"
casting_operator: '::'
data_type:
data_type_identifier: DateTime64
bracketed:
start_bracket: (
numeric_literal: '3'
end_bracket: )
alias_expression:
keyword: as
naked_identifier: datetime
- statement_terminator: ;
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
quoted_literal: "'2024-01-01'"
casting_operator: '::'
data_type:
data_type_identifier: DateTime64
bracketed:
start_bracket: (
numeric_literal: '3'
comma: ','
quoted_literal: "'Europe/Paris'"
end_bracket: )
alias_expression:
keyword: as
naked_identifier: datetime
- statement_terminator: ;
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
quoted_literal: "'2024-01-01'"
casting_operator: '::'
data_type:
data_type_identifier: DateTime64
bracketed:
start_bracket: (
numeric_literal: '6'
end_bracket: )
alias_expression:
keyword: as
naked_identifier: datetime
- statement_terminator: ;
5 changes: 5 additions & 0 deletions test/fixtures/dialects/clickhouse/tuple_datatype.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
SELECT (1, 'two', '2024-01-01')::Tuple(id Int64, name String, created_at Date32) as struct;

SELECT (1, 'two', '2024-01-01')::Tuple(`id` Int64, `name` String, `created_at` Date32) as struct;

SELECT (1, 'two', '2024-01-01')::`Tuple(id Int64, name String, created_at Date32)` as struct;
111 changes: 111 additions & 0 deletions test/fixtures/dialects/clickhouse/tuple_datatype.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,111 @@
# YML test files are auto-generated from SQL files and should not be edited by
# hand. To help enforce this, the "hash" field in the file must match a hash
# computed by SQLFluff when running the tests. Please run
# `python test/generate_parse_fixture_yml.py` to generate them after adding or
# altering SQL files.
_hash: 932b62c5844873fe012d2c850c255ac21b107d5261ba67f85277e37098d9fe13
file:
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
bracketed:
- start_bracket: (
- numeric_literal: '1'
- comma: ','
- column_reference:
quoted_identifier: "'two'"
- comma: ','
- column_reference:
quoted_identifier: "'2024-01-01'"
- end_bracket: )
casting_operator: '::'
data_type:
struct_type:
keyword: Tuple
tuple_type_schema:
bracketed:
- start_bracket: (
- naked_identifier: id
- data_type:
data_type_identifier: Int64
- comma: ','
- naked_identifier: name
- data_type:
data_type_identifier: String
- comma: ','
- naked_identifier: created_at
- data_type:
data_type_identifier: Date32
- end_bracket: )
alias_expression:
keyword: as
naked_identifier: struct
- statement_terminator: ;
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
bracketed:
- start_bracket: (
- numeric_literal: '1'
- comma: ','
- column_reference:
quoted_identifier: "'two'"
- comma: ','
- column_reference:
quoted_identifier: "'2024-01-01'"
- end_bracket: )
casting_operator: '::'
data_type:
struct_type:
keyword: Tuple
tuple_type_schema:
bracketed:
- start_bracket: (
- quoted_identifier: '`id`'
- data_type:
data_type_identifier: Int64
- comma: ','
- quoted_identifier: '`name`'
- data_type:
data_type_identifier: String
- comma: ','
- quoted_identifier: '`created_at`'
- data_type:
data_type_identifier: Date32
- end_bracket: )
alias_expression:
keyword: as
naked_identifier: struct
- statement_terminator: ;
- statement:
select_statement:
select_clause:
keyword: SELECT
select_clause_element:
expression:
cast_expression:
bracketed:
- start_bracket: (
- numeric_literal: '1'
- comma: ','
- column_reference:
quoted_identifier: "'two'"
- comma: ','
- column_reference:
quoted_identifier: "'2024-01-01'"
- end_bracket: )
casting_operator: '::'
data_type:
quoted_identifier: '`Tuple(id Int64, name String, created_at Date32)`'
alias_expression:
keyword: as
naked_identifier: struct
- statement_terminator: ;
Loading
0