sqlglot 30.25.0__tar.gz → 30.26.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (340) hide show
  1. {sqlglot-30.25.0 → sqlglot-30.26.0}/CHANGELOG.md +108 -0
  2. {sqlglot-30.25.0 → sqlglot-30.26.0}/Makefile +1 -1
  3. {sqlglot-30.25.0/sqlglot.egg-info → sqlglot-30.26.0}/PKG-INFO +4 -4
  4. {sqlglot-30.25.0 → sqlglot-30.26.0}/pyproject.toml +1 -1
  5. {sqlglot-30.25.0 → sqlglot-30.26.0}/setup.py +1 -1
  6. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/_version.py +3 -3
  7. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/bigquery.py +1 -0
  8. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/dialect.py +40 -4
  9. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/hive.py +1 -0
  10. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/oracle.py +1 -0
  11. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/snowflake.py +41 -58
  12. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/spark2.py +1 -0
  13. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/sqlite.py +1 -0
  14. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/core.py +4 -0
  15. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/properties.py +4 -0
  16. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generator.py +60 -4
  17. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/duckdb.py +39 -7
  18. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/postgres.py +32 -9
  19. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/tsql.py +1 -0
  20. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/annotate_types.py +93 -87
  21. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/resolver.py +3 -1
  22. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/scope.py +7 -2
  23. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/unnest_subqueries.py +5 -0
  24. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parser.py +61 -15
  25. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/clickhouse.py +1 -4
  26. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/duckdb.py +14 -1
  27. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/mysql.py +8 -0
  28. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/oracle.py +5 -0
  29. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/postgres.py +23 -0
  30. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/snowflake.py +37 -16
  31. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/spark.py +1 -1
  32. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/bigquery.py +6 -4
  33. {sqlglot-30.25.0 → sqlglot-30.26.0/sqlglot.egg-info}/PKG-INFO +4 -4
  34. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot.egg-info/requires.txt +3 -3
  35. sqlglot-30.26.0/sqlglot.egg-info/scm_version.json +8 -0
  36. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglotc/pyproject.toml +2 -2
  37. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_bigquery.py +19 -0
  38. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_clickhouse.py +8 -0
  39. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_dialect.py +133 -0
  40. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_duckdb.py +75 -3
  41. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_mysql.py +49 -2
  42. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_oracle.py +10 -0
  43. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_postgres.py +45 -0
  44. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_snowflake.py +193 -7
  45. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_spark.py +29 -0
  46. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_tsql.py +5 -0
  47. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/annotate_types.sql +111 -0
  48. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/pretty.sql +20 -0
  49. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_optimizer.py +216 -0
  50. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_transpile.py +4 -0
  51. sqlglot-30.25.0/sqlglot.egg-info/scm_version.json +0 -8
  52. {sqlglot-30.25.0 → sqlglot-30.26.0}/.gitignore +0 -0
  53. {sqlglot-30.25.0 → sqlglot-30.26.0}/.gitmodules +0 -0
  54. {sqlglot-30.25.0 → sqlglot-30.26.0}/.gitpod.yml +0 -0
  55. {sqlglot-30.25.0 → sqlglot-30.26.0}/.pre-commit-config.yaml +0 -0
  56. {sqlglot-30.25.0 → sqlglot-30.26.0}/AGENTS.md +0 -0
  57. {sqlglot-30.25.0 → sqlglot-30.26.0}/CLAUDE.md +0 -0
  58. {sqlglot-30.25.0 → sqlglot-30.26.0}/CONTRIBUTING.md +0 -0
  59. {sqlglot-30.25.0 → sqlglot-30.26.0}/LICENSE +0 -0
  60. {sqlglot-30.25.0 → sqlglot-30.26.0}/MANIFEST.in +0 -0
  61. {sqlglot-30.25.0 → sqlglot-30.26.0}/README.md +0 -0
  62. {sqlglot-30.25.0 → sqlglot-30.26.0}/setup.cfg +0 -0
  63. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/__init__.py +0 -0
  64. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/__main__.py +0 -0
  65. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/_typing.py +0 -0
  66. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/anonymize.py +0 -0
  67. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/__init__.py +0 -0
  68. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/athena.py +0 -0
  69. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/clickhouse.py +0 -0
  70. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/databricks.py +0 -0
  71. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/dax.py +0 -0
  72. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/doris.py +0 -0
  73. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/dremio.py +0 -0
  74. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/drill.py +0 -0
  75. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/druid.py +0 -0
  76. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/duckdb.py +0 -0
  77. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/dune.py +0 -0
  78. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/exasol.py +0 -0
  79. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/fabric.py +0 -0
  80. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/materialize.py +0 -0
  81. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/mysql.py +0 -0
  82. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/postgres.py +0 -0
  83. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/presto.py +0 -0
  84. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/prql.py +0 -0
  85. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/redshift.py +0 -0
  86. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/risingwave.py +0 -0
  87. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/singlestore.py +0 -0
  88. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/solr.py +0 -0
  89. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/spark.py +0 -0
  90. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/starrocks.py +0 -0
  91. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/tableau.py +0 -0
  92. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/teradata.py +0 -0
  93. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/trino.py +0 -0
  94. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/dialects/tsql.py +0 -0
  95. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/diff.py +0 -0
  96. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/errors.py +0 -0
  97. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/executor/__init__.py +0 -0
  98. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/executor/context.py +0 -0
  99. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/executor/env.py +0 -0
  100. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/executor/python.py +0 -0
  101. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/executor/table.py +0 -0
  102. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/__init__.py +0 -0
  103. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/aggregate.py +0 -0
  104. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/array.py +0 -0
  105. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/builders.py +0 -0
  106. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/constraints.py +0 -0
  107. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/datatypes.py +0 -0
  108. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/ddl.py +0 -0
  109. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/dml.py +0 -0
  110. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/functions.py +0 -0
  111. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/json.py +0 -0
  112. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/math.py +0 -0
  113. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/query.py +0 -0
  114. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/string.py +0 -0
  115. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/expressions/temporal.py +0 -0
  116. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/__init__.py +0 -0
  117. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/athena.py +0 -0
  118. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/bigquery.py +0 -0
  119. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/clickhouse.py +0 -0
  120. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/databricks.py +0 -0
  121. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/dax.py +0 -0
  122. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/doris.py +0 -0
  123. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/dremio.py +0 -0
  124. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/drill.py +0 -0
  125. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/druid.py +0 -0
  126. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/dune.py +0 -0
  127. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/exasol.py +0 -0
  128. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/fabric.py +0 -0
  129. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/hive.py +0 -0
  130. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/materialize.py +0 -0
  131. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/mysql.py +0 -0
  132. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/oracle.py +0 -0
  133. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/presto.py +0 -0
  134. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/prql.py +0 -0
  135. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/python.py +0 -0
  136. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/redshift.py +0 -0
  137. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/risingwave.py +0 -0
  138. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/singlestore.py +0 -0
  139. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/snowflake.py +0 -0
  140. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/solr.py +0 -0
  141. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/spark.py +0 -0
  142. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/spark2.py +0 -0
  143. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/sqlite.py +0 -0
  144. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/starrocks.py +0 -0
  145. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/tableau.py +0 -0
  146. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/teradata.py +0 -0
  147. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/generators/trino.py +0 -0
  148. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/helper.py +0 -0
  149. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/jsonpath.py +0 -0
  150. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/lineage.py +0 -0
  151. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/__init__.py +0 -0
  152. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/canonicalize.py +0 -0
  153. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/canonicalize_internal_names.py +0 -0
  154. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/eliminate_ctes.py +0 -0
  155. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/eliminate_joins.py +0 -0
  156. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/eliminate_subqueries.py +0 -0
  157. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/helpers.py +0 -0
  158. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/isolate_table_selects.py +0 -0
  159. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/journal.py +0 -0
  160. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/merge_subqueries.py +0 -0
  161. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/normalize.py +0 -0
  162. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/normalize_identifiers.py +0 -0
  163. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/optimize_joins.py +0 -0
  164. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/optimizer.py +0 -0
  165. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/pushdown_predicates.py +0 -0
  166. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/pushdown_projections.py +0 -0
  167. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/qualify.py +0 -0
  168. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/qualify_columns.py +0 -0
  169. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/qualify_tables.py +0 -0
  170. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/optimizer/simplify.py +0 -0
  171. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/__init__.py +0 -0
  172. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/athena.py +0 -0
  173. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/base.py +0 -0
  174. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/bigquery.py +0 -0
  175. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/databricks.py +0 -0
  176. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/dax.py +0 -0
  177. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/doris.py +0 -0
  178. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/dremio.py +0 -0
  179. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/drill.py +0 -0
  180. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/druid.py +0 -0
  181. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/dune.py +0 -0
  182. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/exasol.py +0 -0
  183. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/fabric.py +0 -0
  184. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/hive.py +0 -0
  185. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/materialize.py +0 -0
  186. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/presto.py +0 -0
  187. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/prql.py +0 -0
  188. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/redshift.py +0 -0
  189. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/risingwave.py +0 -0
  190. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/singlestore.py +0 -0
  191. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/solr.py +0 -0
  192. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/spark2.py +0 -0
  193. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/sqlite.py +0 -0
  194. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/starrocks.py +0 -0
  195. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/tableau.py +0 -0
  196. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/teradata.py +0 -0
  197. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/trino.py +0 -0
  198. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/parsers/tsql.py +0 -0
  199. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/planner.py +0 -0
  200. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/py.typed +0 -0
  201. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/schema.py +0 -0
  202. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/serde.py +0 -0
  203. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/time.py +0 -0
  204. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/tokenizer_core.py +0 -0
  205. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/tokens.py +0 -0
  206. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/transforms.py +0 -0
  207. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/trie.py +0 -0
  208. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/__init__.py +0 -0
  209. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/clickhouse.py +0 -0
  210. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/databricks.py +0 -0
  211. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/duckdb.py +0 -0
  212. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/hive.py +0 -0
  213. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/mysql.py +0 -0
  214. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/postgres.py +0 -0
  215. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/presto.py +0 -0
  216. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/redshift.py +0 -0
  217. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/snowflake.py +0 -0
  218. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/spark.py +0 -0
  219. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/spark2.py +0 -0
  220. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot/typing/tsql.py +0 -0
  221. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot.egg-info/SOURCES.txt +0 -0
  222. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot.egg-info/dependency_links.txt +0 -0
  223. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot.egg-info/scm_file_list.json +0 -0
  224. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot.egg-info/top_level.txt +0 -0
  225. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglot.png +0 -0
  226. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglotc/MANIFEST.in +0 -0
  227. {sqlglot-30.25.0 → sqlglot-30.26.0}/sqlglotc/setup.py +0 -0
  228. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/__init__.py +0 -0
  229. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/__init__.py +0 -0
  230. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_athena.py +0 -0
  231. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_databricks.py +0 -0
  232. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_dax.py +0 -0
  233. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_doris.py +0 -0
  234. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_dremio.py +0 -0
  235. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_drill.py +0 -0
  236. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_druid.py +0 -0
  237. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_dune.py +0 -0
  238. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_exasol.py +0 -0
  239. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_fabric.py +0 -0
  240. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_hive.py +0 -0
  241. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_materialize.py +0 -0
  242. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_pipe_syntax.py +0 -0
  243. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_presto.py +0 -0
  244. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_prql.py +0 -0
  245. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_redshift.py +0 -0
  246. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_risingwave.py +0 -0
  247. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_singlestore.py +0 -0
  248. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_solr.py +0 -0
  249. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_sqlite.py +0 -0
  250. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_starrocks.py +0 -0
  251. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_tableau.py +0 -0
  252. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_teradata.py +0 -0
  253. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/dialects/test_trino.py +0 -0
  254. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/identity.sql +0 -0
  255. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/jsonpath/LICENSE +0 -0
  256. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/jsonpath/cts.json +0 -0
  257. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/annotate_functions.sql +0 -0
  258. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/canonicalize.sql +0 -0
  259. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/canonicalize_internal_names.sql +0 -0
  260. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/eliminate_ctes.sql +0 -0
  261. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/eliminate_joins.sql +0 -0
  262. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/eliminate_subqueries.sql +0 -0
  263. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/isolate_table_selects.sql +0 -0
  264. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/merge_subqueries.sql +0 -0
  265. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/normalize.sql +0 -0
  266. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/normalize_identifiers.sql +0 -0
  267. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/optimize_joins.sql +0 -0
  268. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/optimizer.sql +0 -0
  269. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/pushdown_cte_alias_columns.sql +0 -0
  270. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/pushdown_predicates.sql +0 -0
  271. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/pushdown_projections.sql +0 -0
  272. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/qualify_columns.sql +0 -0
  273. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/qualify_columns__invalid.sql +0 -0
  274. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/qualify_columns__with_invisible.sql +0 -0
  275. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/qualify_columns_ddl.sql +0 -0
  276. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/qualify_tables.sql +0 -0
  277. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/quote_identifiers.sql +0 -0
  278. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/simplify.sql +0 -0
  279. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/call_center.csv.gz +0 -0
  280. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/catalog_page.csv.gz +0 -0
  281. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/catalog_returns.csv.gz +0 -0
  282. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/catalog_sales.csv.gz +0 -0
  283. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/customer.csv.gz +0 -0
  284. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/customer_address.csv.gz +0 -0
  285. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/customer_demographics.csv.gz +0 -0
  286. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/date_dim.csv.gz +0 -0
  287. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/household_demographics.csv.gz +0 -0
  288. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/income_band.csv.gz +0 -0
  289. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/inventory.csv.gz +0 -0
  290. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/item.csv.gz +0 -0
  291. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/promotion.csv.gz +0 -0
  292. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/reason.csv.gz +0 -0
  293. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/ship_mode.csv.gz +0 -0
  294. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/store.csv.gz +0 -0
  295. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/store_returns.csv.gz +0 -0
  296. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/store_sales.csv.gz +0 -0
  297. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/time_dim.csv.gz +0 -0
  298. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/tpc-ds.sql +0 -0
  299. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/warehouse.csv.gz +0 -0
  300. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/web_page.csv.gz +0 -0
  301. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/web_returns.csv.gz +0 -0
  302. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/web_sales.csv.gz +0 -0
  303. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-ds/web_site.csv.gz +0 -0
  304. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/customer.csv.gz +0 -0
  305. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/lineitem.csv.gz +0 -0
  306. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/nation.csv.gz +0 -0
  307. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/orders.csv.gz +0 -0
  308. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/part.csv.gz +0 -0
  309. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/partsupp.csv.gz +0 -0
  310. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/region.csv.gz +0 -0
  311. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/supplier.csv.gz +0 -0
  312. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/tpc-h/tpc-h.sql +0 -0
  313. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/optimizer/unnest_subqueries.sql +0 -0
  314. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/fixtures/partial.sql +0 -0
  315. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/gen_fixtures.py +0 -0
  316. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/helpers.py +0 -0
  317. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/leakcheck.py +0 -0
  318. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/sqlglot/__init__.py +0 -0
  319. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_anonymize.py +0 -0
  320. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_build.py +0 -0
  321. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_dialect_entry_points.py +0 -0
  322. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_dialect_imports.py +0 -0
  323. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_diff.py +0 -0
  324. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_docs.py +0 -0
  325. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_errors.py +0 -0
  326. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_executor.py +0 -0
  327. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_expressions.py +0 -0
  328. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_generator.py +0 -0
  329. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_helper.py +0 -0
  330. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_integration_loader.py +0 -0
  331. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_jsonpath.py +0 -0
  332. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_lineage.py +0 -0
  333. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_parser.py +0 -0
  334. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_schema.py +0 -0
  335. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_serde.py +0 -0
  336. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_sqlglotc.py +0 -0
  337. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_time.py +0 -0
  338. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_tokens.py +0 -0
  339. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_transforms.py +0 -0
  340. {sqlglot-30.25.0 → sqlglot-30.26.0}/tests/test_typing.py +0 -0
@@ -1,6 +1,113 @@
1
1
  Changelog
2
2
  =========
3
3
 
4
+ ## [v30.25.0] - 2026-10-26
5
+ ### :boom: BREAKING CHANGES
6
+ - due to [`c90a322`](https://github.com/tobymao/sqlglot/commit/c90a322c329d2b1003bf73b848f0d9e17f1a3d67) - support non-identifier column parts in compiled code *(PR [#8710](https://github.com/tobymao/sqlglot/pull/8710) by [@georgesittas](https://github.com/georgesittas))*:
7
+
8
+ support non-identifier column parts in compiled code (#8710)
9
+
10
+ - due to [`78b24a7`](https://github.com/tobymao/sqlglot/commit/78b24a744adb8d5dc0eb285f067087338b60f266) - transpile hex SHA2 hashes with ENCODE(..., 'hex') and parse SHA256 as a digest [CLAUDE] *(PR [#8764](https://github.com/tobymao/sqlglot/pull/8764) by [@vidigoat](https://github.com/vidigoat))*:
11
+
12
+ transpile hex SHA2 hashes with ENCODE(..., 'hex') and parse SHA256 as a digest [CLAUDE] (#8764)
13
+
14
+ - due to [`0e7b2da`](https://github.com/tobymao/sqlglot/commit/0e7b2da5d199388e84908aef13c53e535f1cf715) - preserve grouping when removing redundant casts *(PR [#8787](https://github.com/tobymao/sqlglot/pull/8787) by [@georgesittas](https://github.com/georgesittas))*:
15
+
16
+ preserve grouping when removing redundant casts (#8787)
17
+
18
+ - due to [`f0b4347`](https://github.com/tobymao/sqlglot/commit/f0b4347b84b71bfd406e2fe831656a6d03351110) - coerce `VALUES` column types across all rows *(PR [#8775](https://github.com/tobymao/sqlglot/pull/8775) by [@drzippie](https://github.com/drzippie))*:
19
+
20
+ coerce `VALUES` column types across all rows (#8775)
21
+
22
+ - due to [`9d2966e`](https://github.com/tobymao/sqlglot/commit/9d2966ed3f8a7f0d370846dbae1579b40ddc2924) - defer scope annotation until qualification is complete *(PR [#8696](https://github.com/tobymao/sqlglot/pull/8696) by [@georgesittas](https://github.com/georgesittas))*:
23
+
24
+ defer scope annotation until qualification is complete (#8696)
25
+
26
+
27
+ ### :sparkles: New Features
28
+ - [`a220ffb`](https://github.com/tobymao/sqlglot/commit/a220ffb98a2f0ba290ff09c75154a73f09ff57b1) - **duckdb**: support NEAREST joins *(PR [#8722](https://github.com/tobymao/sqlglot/pull/8722) by [@georgesittas](https://github.com/georgesittas))*
29
+ - [`5e0f716`](https://github.com/tobymao/sqlglot/commit/5e0f7169307a4c77fe4cd1eba484eed47d124c4e) - **optimizer**: back-project columns to single unknown-schema TVF *(PR [#8677](https://github.com/tobymao/sqlglot/pull/8677) by [@fivetran-kwoodbeck](https://github.com/fivetran-kwoodbeck))*
30
+ - [`43fbff2`](https://github.com/tobymao/sqlglot/commit/43fbff2037b3c4aa4459ca5bce111c6a1c0c1559) - **optimizer**: Fix positional renaming to have proper type *(PR [#8725](https://github.com/tobymao/sqlglot/pull/8725) by [@fivetran-amrutabhimsenayachit](https://github.com/fivetran-amrutabhimsenayachit))*
31
+ - [`1852fd3`](https://github.com/tobymao/sqlglot/commit/1852fd31961ac51afc38c923e33af84a447adced) - **starrocks**: parse blacklist and TRANSLATE TRINO statements as commands [CLAUDE] *(PR [#8732](https://github.com/tobymao/sqlglot/pull/8732) by [@nytai](https://github.com/nytai))*
32
+ - [`e3b3e23`](https://github.com/tobymao/sqlglot/commit/e3b3e23c644728be22e718b6ca838f753757592f) - **duckdb**: normalize explicit join types *(PR [#8759](https://github.com/tobymao/sqlglot/pull/8759) by [@georgesittas](https://github.com/georgesittas))*
33
+ - [`46af6e4`](https://github.com/tobymao/sqlglot/commit/46af6e468564c271f7cc748dda68a6d813a683f6) - **duckdb**: v2 [dis]connect statement *(commit by [@georgesittas](https://github.com/georgesittas))*
34
+ - [`c514be0`](https://github.com/tobymao/sqlglot/commit/c514be049b382191d6ba010c2af4765d9b8cca57) - **duckdb**: parse SQL trigger bodies *(PR [#8796](https://github.com/tobymao/sqlglot/pull/8796) by [@georgesittas](https://github.com/georgesittas))*
35
+
36
+ ### :bug: Bug Fixes
37
+ - [`67961af`](https://github.com/tobymao/sqlglot/commit/67961afbed7c986dfe26ab82db89a25814c1bdcb) - **optimizer**: preserve unresolved JSON paths during alias matching *(PR [#8693](https://github.com/tobymao/sqlglot/pull/8693) by [@georgesittas](https://github.com/georgesittas))*
38
+ - [`c90a322`](https://github.com/tobymao/sqlglot/commit/c90a322c329d2b1003bf73b848f0d9e17f1a3d67) - support non-identifier column parts in compiled code *(PR [#8710](https://github.com/tobymao/sqlglot/pull/8710) by [@georgesittas](https://github.com/georgesittas))*
39
+ - [`d335f89`](https://github.com/tobymao/sqlglot/commit/d335f8985e59ad986408604ce92733e6834f24eb) - **generator**: parenthesize CONCAT paths in JSON arrow operators [CLAUDE] *(PR [#8701](https://github.com/tobymao/sqlglot/pull/8701) by [@vidigoat](https://github.com/vidigoat))*
40
+ - [`e6c7d52`](https://github.com/tobymao/sqlglot/commit/e6c7d5275707635d7f5cbf08ba6f8095126ab669) - **parser**: parse the column list after an INSERT target alias as the INSERT's [CLAUDE] *(PR [#8712](https://github.com/tobymao/sqlglot/pull/8712) by [@vidigoat](https://github.com/vidigoat))*
41
+ - [`83479d0`](https://github.com/tobymao/sqlglot/commit/83479d061b1b92836cc41b6fdf266f575a72dc3f) - duckdb v2 compat *(PR [#8717](https://github.com/tobymao/sqlglot/pull/8717) by [@georgesittas](https://github.com/georgesittas))*
42
+ - [`092e29a`](https://github.com/tobymao/sqlglot/commit/092e29a82fdb153c6c1925627b0b4a7955398c9b) - **databricks**: preserve timestamp precision during SQL generation *(commit by [@georgesittas](https://github.com/georgesittas))*
43
+ - [`2b57c00`](https://github.com/tobymao/sqlglot/commit/2b57c00a114ad74f8d016f499b0cc97c7ffca9d5) - **sqlite**: parse multi-argument MAX/MIN as GREATEST/LEAST *(PR [#8734](https://github.com/tobymao/sqlglot/pull/8734) by [@vidigoat](https://github.com/vidigoat))*
44
+ - [`83c09cd`](https://github.com/tobymao/sqlglot/commit/83c09cdf3cdd42a6a28a9e7514fdef0a9e202d77) - **oracle**: allow non-reserved SAMPLE and MATCH_RECOGNIZE as identifiers [CLAUDE] *(PR [#8733](https://github.com/tobymao/sqlglot/pull/8733) by [@adrianlzt](https://github.com/adrianlzt))*
45
+ - :arrow_lower_right: *fixes issue [#8715](https://github.com/tobymao/sqlglot/issues/8715) opened by [@adrianlzt](https://github.com/adrianlzt)*
46
+ - [`069a751`](https://github.com/tobymao/sqlglot/commit/069a75175b3914ccaed99162eaae9b817482da48) - **clickhouse**: natural join [#8739](https://github.com/tobymao/sqlglot/pull/8739) *(commit by [@georgesittas](https://github.com/georgesittas))*
47
+ - [`a97d035`](https://github.com/tobymao/sqlglot/commit/a97d03579f530531451e773823d823404cb6bedd) - **duckdb**: keep the - end placeholder of a slice with a step [CLAUDE] *(PR [#8736](https://github.com/tobymao/sqlglot/pull/8736) by [@vidigoat](https://github.com/vidigoat))*
48
+ - [`30ceae5`](https://github.com/tobymao/sqlglot/commit/30ceae53a0049859d9fd36b2ec1336a9cad7d4d2) - **optimizer**: preserve semantics when unnesting subqueries in JOIN ON *(PR [#8742](https://github.com/tobymao/sqlglot/pull/8742) by [@georgesittas](https://github.com/georgesittas))*
49
+ - :arrow_lower_right: *fixes issue [#8737](https://github.com/tobymao/sqlglot/issues/8737) opened by [@DeepBuha06](https://github.com/DeepBuha06)*
50
+ - [`4678f6c`](https://github.com/tobymao/sqlglot/commit/4678f6cb67662b0156d942f603eee816abbfec5a) - **optimizer**: preserve row references and aliases during TVF inference *(PR [#8723](https://github.com/tobymao/sqlglot/pull/8723) by [@georgesittas](https://github.com/georgesittas))*
51
+ - [`8fb04fb`](https://github.com/tobymao/sqlglot/commit/8fb04fb3428d592ba785dfc75bff19cf29d6d198) - **sqlite**: normalize hexadecimal integer literals *(PR [#8744](https://github.com/tobymao/sqlglot/pull/8744) by [@georgesittas](https://github.com/georgesittas))*
52
+ - [`b994fa7`](https://github.com/tobymao/sqlglot/commit/b994fa759bb85182ae4a589c1d01973829236047) - **optimizer**: don't fold decimal division by zero [CLAUDE] *(PR [#8748](https://github.com/tobymao/sqlglot/pull/8748) by [@Debasishhh](https://github.com/Debasishhh))*
53
+ - :arrow_lower_right: *fixes issue [#8747](https://github.com/tobymao/sqlglot/issues/8747) opened by [@Debasishhh](https://github.com/Debasishhh)*
54
+ - [`dd71d36`](https://github.com/tobymao/sqlglot/commit/dd71d360f4ac49fc67b8a444b5c4c557e67298ea) - **duckdb**: keep the fraction of an interval written as one string [CLAUDE] *(PR [#8746](https://github.com/tobymao/sqlglot/pull/8746) by [@vidigoat](https://github.com/vidigoat))*
55
+ - [`7600123`](https://github.com/tobymao/sqlglot/commit/76001235539919787dfd05923c90d39b97122773) - **optimizer**: resolve Snowflake token-splitter columns and BigQuery pivot rows *(PR [#8745](https://github.com/tobymao/sqlglot/pull/8745) by [@georgesittas](https://github.com/georgesittas))*
56
+ - [`eb03a97`](https://github.com/tobymao/sqlglot/commit/eb03a9726f27ce33b2a899e2b70c52ba8e6de8ad) - **postgres**: transpile a case-insensitive regex flag to ~* [CLAUDE] *(PR [#8755](https://github.com/tobymao/sqlglot/pull/8755) by [@vidigoat](https://github.com/vidigoat))*
57
+ - [`a9f1309`](https://github.com/tobymao/sqlglot/commit/a9f1309cc7116a79008c9a2b6ab0a06ce6b6f4c7) - **optimizer**: rename right operand references when aligning UNION BY NAME *(PR [#8749](https://github.com/tobymao/sqlglot/pull/8749) by [@treysp](https://github.com/treysp))*
58
+ - [`e0ac5e4`](https://github.com/tobymao/sqlglot/commit/e0ac5e4e667146df9fce47fd3a449bdd19f4f8ea) - keep the last value of an exclusive series with a negative step [CLAUDE] *(PR [#8757](https://github.com/tobymao/sqlglot/pull/8757) by [@vidigoat](https://github.com/vidigoat))*
59
+ - [`f872c44`](https://github.com/tobymao/sqlglot/commit/f872c442af585d773247f623cd5878d17cda6850) - **optimizer**: preserve filtered and grouped CROSS JOIN inputs [CODEX] *(PR [#8756](https://github.com/tobymao/sqlglot/pull/8756) by [@Seraph-x](https://github.com/Seraph-x))*
60
+ - :arrow_lower_right: *fixes issue [#8754](https://github.com/tobymao/sqlglot/issues/8754) opened by [@hutiefang76](https://github.com/hutiefang76)*
61
+ - [`4aa189a`](https://github.com/tobymao/sqlglot/commit/4aa189a472639e7af442c8d794514ec3ab116995) - **duckdb**: decode the escapes of a Unicode string into its characters [CLAUDE] *(PR [#8758](https://github.com/tobymao/sqlglot/pull/8758) by [@vidigoat](https://github.com/vidigoat))*
62
+ - [`184557f`](https://github.com/tobymao/sqlglot/commit/184557f70dd6b606e76fb2592bd096e4667450eb) - **oracle**: parse JSON_VALUE RETURNING clause *(PR [#8762](https://github.com/tobymao/sqlglot/pull/8762) by [@madarwish007](https://github.com/madarwish007))*
63
+ - :arrow_lower_right: *fixes issue [#8761](https://github.com/tobymao/sqlglot/issues/8761) opened by [@madarwish007](https://github.com/madarwish007)*
64
+ - [`37f0963`](https://github.com/tobymao/sqlglot/commit/37f09630d14be44def882c8a2ef0666725a4d83a) - **optimizer**: GROUP BY ordinal interpretation in unnested subqueries *(PR [#8730](https://github.com/tobymao/sqlglot/pull/8730) by [@fivetran-kwoodbeck](https://github.com/fivetran-kwoodbeck))*
65
+ - [`4d7421e`](https://github.com/tobymao/sqlglot/commit/4d7421ee43612043f11574d98227319d5e1f9855) - **optimizer**: keep CROSS JOIN with LIMIT 1 and split the LEFT JOIN row check *(PR [#8760](https://github.com/tobymao/sqlglot/pull/8760) by [@geooo109](https://github.com/geooo109))*
66
+ - :arrow_lower_right: *fixes issue [#8750](https://github.com/tobymao/sqlglot/issues/8750) opened by [@wjjc1017](https://github.com/wjjc1017)*
67
+ - [`78b24a7`](https://github.com/tobymao/sqlglot/commit/78b24a744adb8d5dc0eb285f067087338b60f266) - **postgres**: transpile hex SHA2 hashes with ENCODE(..., 'hex') and parse SHA256 as a digest [CLAUDE] *(PR [#8764](https://github.com/tobymao/sqlglot/pull/8764) by [@vidigoat](https://github.com/vidigoat))*
68
+ - [`c068aef`](https://github.com/tobymao/sqlglot/commit/c068aefd6997c5d272af86fb560ee25d8d5a10d6) - **parser**: copy DataType node for each cast in _replace_lambda *(PR [#8780](https://github.com/tobymao/sqlglot/pull/8780) by [@Pyhroff](https://github.com/Pyhroff))*
69
+ - :arrow_lower_right: *fixes issue [#8777](https://github.com/tobymao/sqlglot/issues/8777) opened by [@olmaks](https://github.com/olmaks)*
70
+ - [`a8a7610`](https://github.com/tobymao/sqlglot/commit/a8a7610d5d4139fe14d2ea624652fdbdb5ba74b3) - **bigquery**: generate EXTRACT(DAYOFWEEK FROM ...) for DayOfWeek *(PR [#8778](https://github.com/tobymao/sqlglot/pull/8778) by [@JoeyTan21](https://github.com/JoeyTan21))*
71
+ - :arrow_lower_right: *fixes issue [#8767](https://github.com/tobymao/sqlglot/issues/8767) opened by [@JoeyTan21](https://github.com/JoeyTan21)*
72
+ - [`d375836`](https://github.com/tobymao/sqlglot/commit/d3758367d4205bc728738110363e82edb3be211b) - **generator**: escape text before quoting it in generated SQL *(PR [#8779](https://github.com/tobymao/sqlglot/pull/8779) by [@tobymao](https://github.com/tobymao))*
73
+ - [`8c5600a`](https://github.com/tobymao/sqlglot/commit/8c5600ad1fa322cbc11dcd93ee78cf5608efeda5) - **clickhouse**: parenthesize Contains under unary minus [CLAUDE] *(PR [#8782](https://github.com/tobymao/sqlglot/pull/8782) by [@ekut](https://github.com/ekut))*
74
+ - [`908809d`](https://github.com/tobymao/sqlglot/commit/908809d3c2b756d0c4e259c55e8e61ca9579ebd8) - **sqlite**: parse REAL and FLOAT as 8-byte DOUBLE [CLAUDE] *(PR [#8784](https://github.com/tobymao/sqlglot/pull/8784) by [@kennywu411-dev](https://github.com/kennywu411-dev))*
75
+ - [`bc1cd99`](https://github.com/tobymao/sqlglot/commit/bc1cd99a78974337a592662023e24231c2bf2a91) - **parser**: infinite loop issue *(PR [#8788](https://github.com/tobymao/sqlglot/pull/8788) by [@georgesittas](https://github.com/georgesittas))*
76
+ - :arrow_lower_right: *fixes issue [#8786](https://github.com/tobymao/sqlglot/issues/8786) opened by [@RaghavChamadiya](https://github.com/RaghavChamadiya)*
77
+ - [`0e7b2da`](https://github.com/tobymao/sqlglot/commit/0e7b2da5d199388e84908aef13c53e535f1cf715) - **optimizer**: preserve grouping when removing redundant casts *(PR [#8787](https://github.com/tobymao/sqlglot/pull/8787) by [@georgesittas](https://github.com/georgesittas))*
78
+ - [`f0b4347`](https://github.com/tobymao/sqlglot/commit/f0b4347b84b71bfd406e2fe831656a6d03351110) - **optimizer**: coerce `VALUES` column types across all rows *(PR [#8775](https://github.com/tobymao/sqlglot/pull/8775) by [@drzippie](https://github.com/drzippie))*
79
+ - [`5859d71`](https://github.com/tobymao/sqlglot/commit/5859d7146aca266f3fdfbff6f11a8eeffcb4ee78) - **duckdb**: keep every path of a multi-path JSON_EXTRACT [CLAUDE] *(PR [#8771](https://github.com/tobymao/sqlglot/pull/8771) by [@vidigoat](https://github.com/vidigoat))*
80
+ - [`bc7a5c4`](https://github.com/tobymao/sqlglot/commit/bc7a5c466e8dffe653c3fe04cb080cef1de1ad41) - **optimizer**: avoid unsafe `LEFT JOIN` elimination with `DISTINCT ON` *(PR [#8769](https://github.com/tobymao/sqlglot/pull/8769) by [@treysp](https://github.com/treysp))*
81
+ - :arrow_lower_right: *fixes issue [#8751](https://github.com/tobymao/sqlglot/issues/8751) opened by [@wjjc1017](https://github.com/wjjc1017)*
82
+ - [`33c7209`](https://github.com/tobymao/sqlglot/commit/33c72094fbe6d05382e560e1026780372640f79b) - **optimizer**: exclude semi/anti join RHS sources from column resolution *(PR [#8763](https://github.com/tobymao/sqlglot/pull/8763) by [@fivetran-amrutabhimsenayachit](https://github.com/fivetran-amrutabhimsenayachit))*
83
+ - [`634edd9`](https://github.com/tobymao/sqlglot/commit/634edd93bedaa5cb624098bb66fb99e07706f4ce) - **sqlite**: generate functions for temporal casts *(PR [#8793](https://github.com/tobymao/sqlglot/pull/8793) by [@georgesittas](https://github.com/georgesittas))*
84
+ - :arrow_lower_right: *fixes issue [#8791](https://github.com/tobymao/sqlglot/issues/8791) opened by [@kennywu411-dev](https://github.com/kennywu411-dev)*
85
+ - [`ebd5fb4`](https://github.com/tobymao/sqlglot/commit/ebd5fb4d74f6e849ef989c2a81ab8e69e0395569) - **duckdb**: drop the SQL/JSON clauses of JSON_ARRAY and JSON_OBJECT [CLAUDE] *(PR [#8794](https://github.com/tobymao/sqlglot/pull/8794) by [@vidigoat](https://github.com/vidigoat))*
86
+ - [`a357b7d`](https://github.com/tobymao/sqlglot/commit/a357b7d9be3d7c03ece213d53421d8a192b90a03) - **postgres**: support tablespace clauses in CREATE statements [CODEX] *(PR [#8792](https://github.com/tobymao/sqlglot/pull/8792) by [@georgesittas](https://github.com/georgesittas))*
87
+ - :arrow_lower_right: *fixes issue [#8776](https://github.com/tobymao/sqlglot/issues/8776) opened by [@cmodiano](https://github.com/cmodiano)*
88
+ - [`31918e9`](https://github.com/tobymao/sqlglot/commit/31918e9a2f249bb5cda263e644eb9c1b96be0c6d) - **duckdb**: preserve quoted variable names *(PR [#8795](https://github.com/tobymao/sqlglot/pull/8795) by [@georgesittas](https://github.com/georgesittas))*
89
+ - [`c5fe540`](https://github.com/tobymao/sqlglot/commit/c5fe5404f379d84798610ab23fb94980f26d2ff2) - **snowflake**: support MERGE ALL BY NAME *(PR [#8797](https://github.com/tobymao/sqlglot/pull/8797) by [@georgesittas](https://github.com/georgesittas))*
90
+ - :arrow_lower_right: *fixes issue [#8783](https://github.com/tobymao/sqlglot/issues/8783) opened by [@sai-sakalam](https://github.com/sai-sakalam)*
91
+ - [`114999a`](https://github.com/tobymao/sqlglot/commit/114999ae6787cbdb7ea630710b82ad2849711e08) - **optimizer**: avoid nested aggregates when unnesting scalar subqueries [CODEX] *(PR [#8798](https://github.com/tobymao/sqlglot/pull/8798) by [@georgesittas](https://github.com/georgesittas))*
92
+ - :arrow_lower_right: *fixes issue [#8790](https://github.com/tobymao/sqlglot/issues/8790) opened by [@kennywu411-dev](https://github.com/kennywu411-dev)*
93
+ - [`fb36fb7`](https://github.com/tobymao/sqlglot/commit/fb36fb7112ad71356fe81fd2cce9aa4733679e1d) - **optimizer**: annotate struct-valued subqueries and row references *(PR [#8694](https://github.com/tobymao/sqlglot/pull/8694) by [@georgesittas](https://github.com/georgesittas))*
94
+
95
+ ### :zap: Performance Improvements
96
+ - [`a2a8bb4`](https://github.com/tobymao/sqlglot/commit/a2a8bb4209e188c0ae78d9809ec3e27666c00f16) - **athena**: avoid tokenizing DML twice [CLAUDE] *(PR [#8709](https://github.com/tobymao/sqlglot/pull/8709) by [@masiljangajji](https://github.com/masiljangajji))*
97
+ - :arrow_lower_right: *addresses issue [#8708](https://github.com/tobymao/sqlglot/issues/8708) opened by [@masiljangajji](https://github.com/masiljangajji)*
98
+ - [`7c4e124`](https://github.com/tobymao/sqlglot/commit/7c4e124f21225a4b60d790cb6938d64bf2778d4a) - **optimizer**: cache positional column alias mappings [CODEX] *(PR [#8735](https://github.com/tobymao/sqlglot/pull/8735) by [@georgesittas](https://github.com/georgesittas))*
99
+
100
+ ### :recycle: Refactors
101
+ - [`65eb0f2`](https://github.com/tobymao/sqlglot/commit/65eb0f229a5d7af5e4d3ff9084d79362e5fc899a) - **duckdb**: drop unused Lambda colon arg *(PR [#8721](https://github.com/tobymao/sqlglot/pull/8721) by [@VaggelisD](https://github.com/VaggelisD))*
102
+ - [`2bf94d9`](https://github.com/tobymao/sqlglot/commit/2bf94d96359db584862dcf20b358f34cabc1661d) - **optimizer**: expand struct column paths using inferred types *(PR [#8695](https://github.com/tobymao/sqlglot/pull/8695) by [@georgesittas](https://github.com/georgesittas))*
103
+ - [`9d2966e`](https://github.com/tobymao/sqlglot/commit/9d2966ed3f8a7f0d370846dbae1579b40ddc2924) - **optimizer**: defer scope annotation until qualification is complete *(PR [#8696](https://github.com/tobymao/sqlglot/pull/8696) by [@georgesittas](https://github.com/georgesittas))*
104
+
105
+ ### :wrench: Chores
106
+ - [`9fedfa5`](https://github.com/tobymao/sqlglot/commit/9fedfa5f5ecb94f4ca290ee6373b1dd4feb120e2) - fix comments for insert table *(commit by [@geooo109](https://github.com/geooo109))*
107
+ - [`3377b95`](https://github.com/tobymao/sqlglot/commit/3377b95795837881a1ffe86c0ea6965084b195d7) - minimize insert table parser *(commit by [@geooo109](https://github.com/geooo109))*
108
+ - [`9075977`](https://github.com/tobymao/sqlglot/commit/90759771ddf61d8b53d729712c53870a3317f5ce) - suppress unsupported property warning in tests *(PR [#8724](https://github.com/tobymao/sqlglot/pull/8724) by [@treysp](https://github.com/treysp))*
109
+
110
+
4
111
  ## [v30.24.0] - 2026-10-20
5
112
  ### :boom: BREAKING CHANGES
6
113
  - due to [`094509a`](https://github.com/tobymao/sqlglot/commit/094509aad83fff575f1b4d198e4d03c21c432e58) - merge SortArray into ArraySort with explicit NULL ordering *(PR [#8643](https://github.com/tobymao/sqlglot/pull/8643) by [@tobymao](https://github.com/tobymao))*:
@@ -16385,3 +16492,4 @@ pip install "sqlglot[c]" # compiled — faster, but no subclassing
16385
16492
  [v30.22.0]: https://github.com/tobymao/sqlglot/compare/v30.21.0...v30.22.0
16386
16493
  [v30.23.0]: https://github.com/tobymao/sqlglot/compare/v30.22.0...v30.23.0
16387
16494
  [v30.24.0]: https://github.com/tobymao/sqlglot/compare/v30.23.0...v30.24.0
16495
+ [v30.25.0]: https://github.com/tobymao/sqlglot/compare/v30.24.0...v30.25.0
@@ -28,8 +28,8 @@ install-dev:
28
28
  @if [ -f sqlglot-integration-tests/Makefile ]; then \
29
29
  $(MAKE) -C sqlglot-integration-tests install; \
30
30
  fi
31
+ $(PIP) uninstall $(if $(UV),,-y) sqlglotc 2>/dev/null || true
31
32
  $(PIP) install -e ".[dev]"
32
- $(PIP) uninstall -y sqlglotc 2>/dev/null || true
33
33
  @if ! command -v gh >/dev/null 2>&1; then \
34
34
  echo ""; \
35
35
  echo "gh (GitHub CLI) is not installed. It is needed to auto-create PRs for integration tests."; \
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: sqlglot
3
- Version: 30.25.0
3
+ Version: 30.26.0
4
4
  Summary: An easily customizable SQL parser and transpiler
5
5
  Author-email: Toby Mao <toby.mao@gmail.com>
6
6
  License-Expression: MIT
@@ -21,7 +21,7 @@ Provides-Extra: dev
21
21
  Requires-Dist: duckdb>=0.6; extra == "dev"
22
22
  Requires-Dist: mypy>=2.4.0; python_version >= "3.10" and extra == "dev"
23
23
  Requires-Dist: mypy; python_version < "3.10" and extra == "dev"
24
- Requires-Dist: setuptools_scm; extra == "dev"
24
+ Requires-Dist: setuptools_scm>=10.2; extra == "dev"
25
25
  Requires-Dist: pandas; extra == "dev"
26
26
  Requires-Dist: pandas-stubs; extra == "dev"
27
27
  Requires-Dist: python-dateutil; extra == "dev"
@@ -34,10 +34,10 @@ Requires-Dist: types-pytz; extra == "dev"
34
34
  Requires-Dist: typing_extensions; extra == "dev"
35
35
  Requires-Dist: pyperf; extra == "dev"
36
36
  Provides-Extra: c
37
- Requires-Dist: sqlglotc==30.25.0; python_version >= "3.10" and extra == "c"
37
+ Requires-Dist: sqlglotc==30.26.0; python_version >= "3.10" and extra == "c"
38
38
  Provides-Extra: rs
39
39
  Requires-Dist: sqlglotrs==0.13.0; extra == "rs"
40
- Requires-Dist: sqlglotc==30.25.0; python_version >= "3.10" and extra == "rs"
40
+ Requires-Dist: sqlglotc==30.26.0; python_version >= "3.10" and extra == "rs"
41
41
  Dynamic: license-file
42
42
  Dynamic: provides-extra
43
43
 
@@ -23,7 +23,7 @@ Repository = "https://github.com/tobymao/sqlglot"
23
23
  Issues = "https://github.com/tobymao/sqlglot/issues"
24
24
 
25
25
  [build-system]
26
- requires = ["setuptools >= 61.0", "setuptools_scm"]
26
+ requires = ["setuptools >= 61.0", "setuptools_scm >= 10.2"]
27
27
  build-backend = "setuptools.build_meta"
28
28
 
29
29
  [tool.setuptools]
@@ -11,7 +11,7 @@ setup(
11
11
  # for py3.10+; on py3.9 just use upstream mypy for type checking.
12
12
  "mypy >= 2.4.0; python_version >= '3.10'",
13
13
  "mypy; python_version < '3.10'",
14
- "setuptools_scm",
14
+ "setuptools_scm >= 10.2",
15
15
  "pandas",
16
16
  "pandas-stubs",
17
17
  "python-dateutil",
@@ -18,7 +18,7 @@ version_tuple: tuple[int | str, ...]
18
18
  commit_id: str | None
19
19
  __commit_id__: str | None
20
20
 
21
- __version__ = version = '30.25.0'
22
- __version_tuple__ = version_tuple = (30, 25, 0)
21
+ __version__ = version = '30.26.0'
22
+ __version_tuple__ = version_tuple = (30, 26, 0)
23
23
 
24
- __commit_id__ = commit_id = 'g9d2966ed3'
24
+ __commit_id__ = commit_id = 'gb0842a1ee'
@@ -211,6 +211,7 @@ class BigQuery(Dialect):
211
211
  "TIMESTAMP": TokenType.TIMESTAMPTZ,
212
212
  "WHILE": TokenType.COMMAND,
213
213
  }
214
+ KEYWORDS.pop("ISNULL")
214
215
  KEYWORDS.pop("DIV")
215
216
  KEYWORDS.pop("VALUES")
216
217
  KEYWORDS.pop("/*+")
@@ -42,7 +42,15 @@ DATE_ADD_OR_DIFF = t.Union[
42
42
  exp.TsOrDsAdd,
43
43
  exp.TsOrDsDiff,
44
44
  ]
45
- DATE_ADD_OR_SUB = t.Union[exp.DateAdd, exp.TsOrDsAdd, exp.DateSub]
45
+ DATE_ADD_OR_SUB = t.Union[
46
+ exp.DateAdd,
47
+ exp.DateSub,
48
+ exp.DatetimeAdd,
49
+ exp.DatetimeSub,
50
+ exp.TimestampAdd,
51
+ exp.TimestampSub,
52
+ exp.TsOrDsAdd,
53
+ ]
46
54
  JSON_EXTRACT_TYPE = t.Union[
47
55
  exp.JSONExtract, exp.JSONExtractScalar, exp.JSONBExtract, exp.JSONBExtractScalar
48
56
  ]
@@ -804,6 +812,12 @@ class Dialect(metaclass=_Dialect):
804
812
  must be explicitly specified.
805
813
  """
806
814
 
815
+ INTERSECT_BINDS_TIGHTER_THAN_UNION_AND_EXCEPT = True
816
+ """
817
+ Whether INTERSECT binds more tightly than UNION and EXCEPT when a set operation chain isn't
818
+ parenthesized. If False, all set operations have equal precedence and associate left to right.
819
+ """
820
+
807
821
  CREATABLE_KIND_MAPPING: dict[str, str] = {}
808
822
  """
809
823
  Helper for dialects that use a different name for the same creatable kind. For example, the Clickhouse
@@ -2220,13 +2234,23 @@ def date_delta_sql(name: str, cast: bool = False) -> t.Callable[[Generator, DATE
2220
2234
  return _delta_sql
2221
2235
 
2222
2236
 
2237
+ def date_delta_to_binary_sql(self: Generator, expression: exp.Expr, binary: exp.Binary) -> str:
2238
+ parent = expression.parent
2239
+ if isinstance(parent, (exp.Binary, exp.Unary, exp.AtTimeZone)) and not (
2240
+ isinstance(parent, exp.Paren)
2241
+ or isinstance(parent, (exp.Add, exp.Sub))
2242
+ and parent.this is expression
2243
+ ):
2244
+ return self.sql(exp.paren(binary, copy=False))
2245
+ return self.sql(binary)
2246
+
2247
+
2223
2248
  def date_delta_to_binary_interval_op(
2224
2249
  cast: bool = True,
2225
2250
  ) -> t.Callable[[Generator, DATETIME_DELTA], str]:
2226
2251
  def date_delta_to_binary_interval_op_sql(self: Generator, expression: DATETIME_DELTA) -> str:
2227
2252
  this = expression.this
2228
2253
  unit = unit_to_var(expression)
2229
- op = "+" if isinstance(expression, DATETIME_ADD) else "-"
2230
2254
 
2231
2255
  to_type: exp.DATA_TYPE | None = None
2232
2256
  if cast:
@@ -2236,7 +2260,15 @@ def date_delta_to_binary_interval_op(
2236
2260
  # Cast string literals (i.e function parameters) to the appropriate type for +/- interval to work
2237
2261
  to_type = (
2238
2262
  exp.DType.DATETIME
2239
- if isinstance(expression, (exp.DatetimeAdd, exp.DatetimeSub))
2263
+ if isinstance(
2264
+ expression,
2265
+ (
2266
+ exp.DatetimeAdd,
2267
+ exp.DatetimeSub,
2268
+ exp.TimestampAdd,
2269
+ exp.TimestampSub,
2270
+ ),
2271
+ )
2240
2272
  else exp.DType.DATE
2241
2273
  )
2242
2274
 
@@ -2245,7 +2277,11 @@ def date_delta_to_binary_interval_op(
2245
2277
  expr = expression.expression
2246
2278
  interval = expr if isinstance(expr, exp.Interval) else exp.Interval(this=expr, unit=unit)
2247
2279
 
2248
- return f"{self.sql(this)} {op} {self.sql(interval)}"
2280
+ return date_delta_to_binary_sql(
2281
+ self,
2282
+ expression,
2283
+ this + interval if isinstance(expression, DATETIME_ADD) else this - interval,
2284
+ )
2249
2285
 
2250
2286
  return date_delta_to_binary_interval_op_sql
2251
2287
 
@@ -24,6 +24,7 @@ class Hive(Dialect):
24
24
  ARRAY_AGG_INCLUDES_NULLS = None
25
25
  REGEXP_EXTRACT_DEFAULT_GROUP = 1
26
26
  ALTER_TABLE_SUPPORTS_CASCADE = True
27
+ INTERSECT_BINDS_TIGHTER_THAN_UNION_AND_EXCEPT = False
27
28
 
28
29
  # https://spark.apache.org/docs/latest/sql-ref-identifier.html#description
29
30
  NORMALIZATION_STRATEGY = NormalizationStrategy.CASE_INSENSITIVE
@@ -21,6 +21,7 @@ class Oracle(Dialect):
21
21
  ON_CONDITION_EMPTY_BEFORE_ERROR = False
22
22
  ALTER_TABLE_ADD_REQUIRED_FOR_EACH_COLUMN = False
23
23
  DISABLES_ALIAS_REF_EXPANSION = True
24
+ INTERSECT_BINDS_TIGHTER_THAN_UNION_AND_EXCEPT = False
24
25
 
25
26
  # See section 8: https://docs.oracle.com/cd/A97630_01/server.920/a96540/sql_elements9a.htm
26
27
  NORMALIZATION_STRATEGY = NormalizationStrategy.UPPERCASE
@@ -1,5 +1,7 @@
1
1
  from __future__ import annotations
2
2
 
3
+ from itertools import product
4
+
3
5
  from sqlglot import exp, jsonpath, tokens
4
6
  from sqlglot.dialects.dialect import (
5
7
  Dialect,
@@ -47,68 +49,47 @@ class Snowflake(Dialect):
47
49
  INITCAP_DEFAULT_DELIMITER_CHARS = ' \t\n\r\f\v!?@"^#$&~_,.:;+\\-*%/|\\[\\](){}<>'
48
50
 
49
51
  INVERSE_TIME_MAPPING = {
52
+ "%d": "DD",
53
+ "%-d": "DD",
54
+ "%a": "DY",
50
55
  "T": "T", # in TIME_MAPPING we map '"T"' with the double quotes to 'T', and we want to prevent 'T' from being mapped back to '"T"' so that 'AUTO' doesn't become 'AU"T"O'
51
56
  }
52
57
 
53
58
  TIME_MAPPING = {
54
- "YYYY": "%Y",
55
- "yyyy": "%Y",
56
- "YY": "%y",
57
- "yy": "%y",
58
- "MMMM": "%B",
59
- "mmmm": "%B",
60
- "MON": "%b",
61
- "mon": "%b",
62
- "MM": "%m",
63
- "mm": "%m",
64
- "DD": "%d",
65
- "dd": "%-d",
66
- "DY": "%a",
67
- "dy": "%w",
68
- "HH24": "%H",
69
- "hh24": "%H",
70
- "HH12": "%I",
71
- "hh12": "%I",
72
- "MI": "%M",
73
- "mi": "%M",
74
- "SS": "%S",
75
- "ss": "%S",
76
- "FF": "%f_nine", # %f_ internal representation with precision specified
77
- "ff": "%f_nine",
78
- "FF0": "%f_zero",
79
- "ff0": "%f_zero",
80
- "FF1": "%f_one",
81
- "ff1": "%f_one",
82
- "FF2": "%f_two",
83
- "ff2": "%f_two",
84
- "FF3": "%f_three",
85
- "ff3": "%f_three",
86
- "FF4": "%f_four",
87
- "ff4": "%f_four",
88
- "FF5": "%f_five",
89
- "ff5": "%f_five",
90
- "FF6": "%f",
91
- "ff6": "%f",
92
- "FF7": "%f_seven",
93
- "ff7": "%f_seven",
94
- "FF8": "%f_eight",
95
- "ff8": "%f_eight",
96
- "FF9": "%f_nine",
97
- "ff9": "%f_nine",
98
- "TZHTZM": "%z",
99
- "tzhtzm": "%z",
100
- "TZH:TZM": "%:z", # internal representation for ±HH:MM
101
- "tzh:tzm": "%:z",
102
- "TZH": "%-z", # internal representation ±HH
103
- "tzh": "%-z",
104
- '"T"': "T", # remove the optional double quotes around the separator between the date and time
105
- # Seems like Snowflake treats AM/PM in the format string as equivalent,
106
- # only the time (stamp) value's AM/PM affects the output
107
- "AM": "%p",
108
- "am": "%p",
109
- "PM": "%p",
110
- "pm": "%p",
111
- }
59
+ "".join(chars): value
60
+ for key, value in {
61
+ "YYYY": "%Y",
62
+ "YY": "%y",
63
+ "MMMM": "%B",
64
+ "MON": "%b",
65
+ "MM": "%m",
66
+ "DD": "%d",
67
+ "DY": "%a",
68
+ "HH24": "%H",
69
+ "HH12": "%I",
70
+ "MI": "%M",
71
+ "SS": "%S",
72
+ "FF": "%f_nine", # %f_ internal representation with precision specified
73
+ "FF0": "%f_zero",
74
+ "FF1": "%f_one",
75
+ "FF2": "%f_two",
76
+ "FF3": "%f_three",
77
+ "FF4": "%f_four",
78
+ "FF5": "%f_five",
79
+ "FF6": "%f",
80
+ "FF7": "%f_seven",
81
+ "FF8": "%f_eight",
82
+ "FF9": "%f_nine",
83
+ "TZHTZM": "%z",
84
+ "TZH:TZM": "%:z", # internal representation for ±HH:MM
85
+ "TZH": "%-z", # internal representation ±HH
86
+ # Seems like Snowflake treats AM/PM in the format string as equivalent,
87
+ # only the time (stamp) value's AM/PM affects the output
88
+ "AM": "%p",
89
+ "PM": "%p",
90
+ }.items()
91
+ for chars in product(*zip(key.upper(), key.lower()))
92
+ } | {'"T"': "T"}
112
93
 
113
94
  DATE_PART_MAPPING = {
114
95
  **Dialect.DATE_PART_MAPPING,
@@ -189,6 +170,8 @@ class Snowflake(Dialect):
189
170
  "FLOAT": TokenType.DOUBLE,
190
171
  }
191
172
  KEYWORDS.pop("/*+")
173
+ KEYWORDS.pop("GLOB")
174
+ KEYWORDS.pop("RETURNING")
192
175
 
193
176
  SINGLE_TOKENS = {
194
177
  **tokens.Tokenizer.SINGLE_TOKENS,
@@ -9,6 +9,7 @@ from sqlglot.typing.spark2 import EXPRESSION_METADATA
9
9
 
10
10
  class Spark2(Hive):
11
11
  ALTER_TABLE_SUPPORTS_CASCADE = False
12
+ INTERSECT_BINDS_TIGHTER_THAN_UNION_AND_EXCEPT = True
12
13
 
13
14
  EXPRESSION_METADATA = EXPRESSION_METADATA.copy()
14
15
 
@@ -21,6 +21,7 @@ class SQLite(Dialect):
21
21
  USING_COLUMN_ORDER = UsingColumnOrder.IN_PLACE
22
22
  CONCAT_COALESCE = True
23
23
  CONCAT_WS_COALESCE = True
24
+ INTERSECT_BINDS_TIGHTER_THAN_UNION_AND_EXCEPT = False
24
25
 
25
26
  class Tokenizer(tokens.Tokenizer):
26
27
  IDENTIFIERS = ['"', ("[", "]"), "`"]
@@ -2108,6 +2108,10 @@ class Filter(Expression):
2108
2108
  arg_types = {"this": True, "expression": True}
2109
2109
 
2110
2110
 
2111
+ class Per(Expression):
2112
+ arg_types = {"this": True, "expressions": True}
2113
+
2114
+
2111
2115
  class Check(Expression):
2112
2116
  pass
2113
2117
 
@@ -107,6 +107,10 @@ class CopyGrantsProperty(Property):
107
107
  arg_types = {}
108
108
 
109
109
 
110
+ class CopyTagsProperty(Property):
111
+ arg_types = {}
112
+
113
+
110
114
  class DataBlocksizeProperty(Property):
111
115
  arg_types = {
112
116
  "size": False,
@@ -169,6 +169,7 @@ class Generator:
169
169
  "CONVERT", e.this, e.args["dest"], e.args.get("source")
170
170
  ),
171
171
  exp.CopyGrantsProperty: lambda *_: "COPY GRANTS",
172
+ exp.CopyTagsProperty: lambda *_: "COPY TAGS",
172
173
  exp.CredentialsProperty: lambda self, e: (
173
174
  f"CREDENTIALS=({self.expressions(e, 'expressions', sep=' ')})"
174
175
  ),
@@ -731,6 +732,7 @@ class Generator:
731
732
  exp.CollateProperty: exp.Properties.Location.POST_SCHEMA,
732
733
  exp.ComputeProperty: exp.Properties.Location.POST_CREATE,
733
734
  exp.CopyGrantsProperty: exp.Properties.Location.POST_SCHEMA,
735
+ exp.CopyTagsProperty: exp.Properties.Location.POST_SCHEMA,
734
736
  exp.Cluster: exp.Properties.Location.POST_SCHEMA,
735
737
  exp.ClusteredByProperty: exp.Properties.Location.POST_SCHEMA,
736
738
  exp.ClusterProperty: exp.Properties.Location.POST_SCHEMA,
@@ -1964,19 +1966,63 @@ class Generator:
1964
1966
  return self.sql(select)
1965
1967
 
1966
1968
  sqls: list[str] = []
1967
- stack: list[str | exp.Expr] = [expression]
1969
+ stack: list[str | exp.Expr | int | None] = [expression]
1970
+ depth = 0
1971
+ open_parens = ""
1968
1972
 
1969
1973
  while stack:
1970
1974
  node = stack.pop()
1971
1975
 
1972
- if isinstance(node, exp.SetOperation):
1976
+ if isinstance(node, int):
1977
+ # Closes a plain grouping opened below, restoring its depth
1978
+ depth = node
1979
+ sqls[-1] += self.sep("") + self.indent(")", level=depth, pad=0)
1980
+ elif isinstance(node, exp.SetOperation):
1973
1981
  stack.append(node.expression)
1974
1982
  stack.append(
1975
1983
  self.maybe_comment(
1976
1984
  self.set_operation(node), comments=node.comments, separated=True
1977
1985
  )
1978
1986
  )
1979
- stack.append(node.this)
1987
+ left = node.this
1988
+ if (
1989
+ not self.SET_OP_PARENTHESIZED_OPERANDS
1990
+ and not self.dialect.INTERSECT_BINDS_TIGHTER_THAN_UNION_AND_EXCEPT
1991
+ ):
1992
+ # Left grouping is implicit, so skip the `SELECT * FROM (...)` wrapper:
1993
+ # it renames duplicate columns and deepens recursion. Inner CTEs and
1994
+ # modifiers still need the wrapper.
1995
+ wrappers: list[exp.Subquery] = []
1996
+ inner = left
1997
+ while isinstance(inner, exp.Subquery) and inner.is_wrapper:
1998
+ wrappers.append(inner)
1999
+ inner = inner.this
2000
+
2001
+ if (
2002
+ isinstance(inner, exp.SetOperation)
2003
+ and not inner.args.get("with_")
2004
+ and not any(inner.args.get(key) for key in exp.QUERY_MODIFIERS)
2005
+ ):
2006
+ for wrapper in wrappers:
2007
+ inner.add_comments(wrapper.pop_comments())
2008
+ left = inner
2009
+ elif (
2010
+ self.SET_OP_PARENTHESIZED_OPERANDS
2011
+ and isinstance(left, exp.Subquery)
2012
+ and left.is_wrapper
2013
+ and not left.comments
2014
+ and isinstance(left.this, exp.SetOperation)
2015
+ and not left.this.args.get("with_")
2016
+ and not any(left.this.args.get(key) for key in exp.QUERY_MODIFIERS)
2017
+ ):
2018
+ # Write a plain grouping's parentheses here rather than recursing through
2019
+ # subquery_sql: left-to-right chains nest one grouping per INTERSECT, and
2020
+ # long ones would exhaust the stack. The depth pushed here marks the close.
2021
+ open_parens += self.indent("(", level=depth, pad=0) + self.sep("")
2022
+ stack.append(depth)
2023
+ depth += 1
2024
+ left = left.this
2025
+ stack.append(left)
1980
2026
  else:
1981
2027
  if (
1982
2028
  not self.SET_OP_LIMITS
@@ -1986,7 +2032,14 @@ class Generator:
1986
2032
  node = node.subquery(copy=False)
1987
2033
  if not self.SET_OP_PARENTHESIZED_OPERANDS:
1988
2034
  node = exp.select("*").from_(node, copy=False)
1989
- sqls.append(self.sql(node))
2035
+ elif (
2036
+ not self.SET_OP_PARENTHESIZED_OPERANDS
2037
+ and isinstance(node, exp.Subquery)
2038
+ and isinstance(node.unnest(), exp.SetOperation)
2039
+ ):
2040
+ node = exp.select("*").from_(node, copy=False)
2041
+ sqls.append(open_parens + self.indent(self.sql(node), level=depth, pad=0))
2042
+ open_parens = ""
1990
2043
 
1991
2044
  this = self.sep().join(sqls)
1992
2045
  this = self.query_modifiers(expression, this)
@@ -2014,6 +2067,9 @@ class Generator:
2014
2067
  where = self.sql(expression, "expression").strip()
2015
2068
  return f"{this} FILTER({where})"
2016
2069
 
2070
+ def per_sql(self, expression: exp.Per) -> str:
2071
+ return f"{self.sql(expression, 'this')} PER ({self.expressions(expression, flat=True)})"
2072
+
2017
2073
  def hint_sql(self, expression: exp.Hint) -> str:
2018
2074
  if not self.QUERY_HINTS:
2019
2075
  self.unsupported("Hints are not supported")