sqlspec 0.16.2__tar.gz → 0.17.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.

Potentially problematic release.


This version of sqlspec might be problematic. Click here for more details.

Files changed (312) hide show
  1. {sqlspec-0.16.2 → sqlspec-0.17.0}/Makefile +2 -2
  2. {sqlspec-0.16.2 → sqlspec-0.17.0}/PKG-INFO +1 -1
  3. {sqlspec-0.16.2 → sqlspec-0.17.0}/pyproject.toml +1 -1
  4. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/__init__.py +11 -1
  5. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/_sql.py +16 -412
  6. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/aiosqlite/__init__.py +11 -1
  7. sqlspec-0.17.0/sqlspec/adapters/aiosqlite/config.py +225 -0
  8. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/aiosqlite/driver.py +21 -10
  9. sqlspec-0.17.0/sqlspec/adapters/aiosqlite/pool.py +492 -0
  10. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/duckdb/__init__.py +2 -0
  11. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/duckdb/config.py +11 -235
  12. sqlspec-0.17.0/sqlspec/adapters/duckdb/pool.py +243 -0
  13. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/sqlite/__init__.py +2 -0
  14. sqlspec-0.17.0/sqlspec/adapters/sqlite/config.py +129 -0
  15. sqlspec-0.16.2/sqlspec/adapters/sqlite/config.py → sqlspec-0.17.0/sqlspec/adapters/sqlite/pool.py +2 -102
  16. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/base.py +147 -26
  17. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/__init__.py +6 -0
  18. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_parsing_utils.py +27 -0
  19. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_join_operations.py +115 -1
  20. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_select_operations.py +307 -3
  21. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_where_clause.py +60 -11
  22. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/compiler.py +7 -5
  23. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/driver/_common.py +9 -1
  24. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/loader.py +27 -54
  25. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/storage/registry.py +2 -2
  26. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/typing.py +53 -99
  27. sqlspec-0.17.0/tests/fixtures/asset_maintenance.sql +12 -0
  28. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/oracle.ddl.sql +1 -0
  29. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_aiosqlite/conftest.py +22 -0
  30. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_aiosqlite/test_pooling.py +4 -4
  31. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_sqlite/test_pooling.py +9 -6
  32. sqlspec-0.17.0/tests/unit/test_adapters/test_aiosqlite/__init__.py +1 -0
  33. sqlspec-0.17.0/tests/unit/test_adapters/test_aiosqlite/test_pool.py +811 -0
  34. sqlspec-0.17.0/tests/unit/test_adapters/test_sqlite/__init__.py +1 -0
  35. sqlspec-0.17.0/tests/unit/test_adapters/test_sqlite/test_pool.py +493 -0
  36. sqlspec-0.17.0/tests/unit/test_base_sql_integration.py +318 -0
  37. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_builder/test_parameter_naming.py +109 -0
  38. sqlspec-0.17.0/tests/unit/test_loader/test_fixtures_directory_loading.py +691 -0
  39. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_loader/test_sql_file_loader.py +49 -32
  40. sqlspec-0.17.0/tests/unit/test_parsing_utils.py +133 -0
  41. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_sql_factory.py +60 -0
  42. {sqlspec-0.16.2 → sqlspec-0.17.0}/uv.lock +12 -11
  43. sqlspec-0.16.2/sqlspec/adapters/aiosqlite/config.py +0 -253
  44. {sqlspec-0.16.2 → sqlspec-0.17.0}/.gitignore +0 -0
  45. {sqlspec-0.16.2 → sqlspec-0.17.0}/.pre-commit-config.yaml +0 -0
  46. {sqlspec-0.16.2 → sqlspec-0.17.0}/CONTRIBUTING.rst +0 -0
  47. {sqlspec-0.16.2 → sqlspec-0.17.0}/LICENSE +0 -0
  48. {sqlspec-0.16.2 → sqlspec-0.17.0}/NOTICE +0 -0
  49. {sqlspec-0.16.2 → sqlspec-0.17.0}/README.md +0 -0
  50. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/__main__.py +0 -0
  51. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/__metadata__.py +0 -0
  52. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/_serialization.py +0 -0
  53. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/_typing.py +0 -0
  54. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/__init__.py +0 -0
  55. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/adbc/__init__.py +0 -0
  56. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/adbc/_types.py +0 -0
  57. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/adbc/config.py +0 -0
  58. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/adbc/driver.py +0 -0
  59. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/aiosqlite/_types.py +0 -0
  60. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncmy/__init__.py +0 -0
  61. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncmy/_types.py +0 -0
  62. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncmy/config.py +0 -0
  63. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncmy/driver.py +0 -0
  64. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncpg/__init__.py +0 -0
  65. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncpg/_types.py +0 -0
  66. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncpg/config.py +0 -0
  67. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/asyncpg/driver.py +0 -0
  68. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/bigquery/__init__.py +0 -0
  69. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/bigquery/_types.py +0 -0
  70. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/bigquery/config.py +0 -0
  71. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/bigquery/driver.py +0 -0
  72. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/duckdb/_types.py +0 -0
  73. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/duckdb/driver.py +0 -0
  74. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/oracledb/__init__.py +0 -0
  75. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/oracledb/_types.py +0 -0
  76. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/oracledb/config.py +0 -0
  77. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/oracledb/driver.py +0 -0
  78. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psqlpy/__init__.py +0 -0
  79. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psqlpy/_types.py +0 -0
  80. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psqlpy/config.py +0 -0
  81. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psqlpy/driver.py +0 -0
  82. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psycopg/__init__.py +0 -0
  83. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psycopg/_types.py +0 -0
  84. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psycopg/config.py +0 -0
  85. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/psycopg/driver.py +0 -0
  86. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/sqlite/_types.py +0 -0
  87. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/adapters/sqlite/driver.py +0 -0
  88. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_base.py +0 -0
  89. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_column.py +0 -0
  90. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_ddl.py +0 -0
  91. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_ddl_utils.py +0 -0
  92. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_delete.py +0 -0
  93. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_insert.py +0 -0
  94. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_merge.py +0 -0
  95. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_select.py +0 -0
  96. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/_update.py +0 -0
  97. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/__init__.py +0 -0
  98. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_cte_and_set_ops.py +0 -0
  99. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_delete_operations.py +0 -0
  100. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_insert_operations.py +0 -0
  101. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_merge_operations.py +0 -0
  102. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_order_limit_operations.py +0 -0
  103. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_pivot_operations.py +0 -0
  104. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/builder/mixins/_update_operations.py +0 -0
  105. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/cli.py +0 -0
  106. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/config.py +0 -0
  107. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/__init__.py +0 -0
  108. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/cache.py +0 -0
  109. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/filters.py +0 -0
  110. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/hashing.py +0 -0
  111. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/parameters.py +0 -0
  112. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/result.py +0 -0
  113. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/splitter.py +0 -0
  114. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/core/statement.py +0 -0
  115. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/driver/__init__.py +0 -0
  116. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/driver/_async.py +0 -0
  117. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/driver/_sync.py +0 -0
  118. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/driver/mixins/__init__.py +0 -0
  119. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/driver/mixins/_result_tools.py +0 -0
  120. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/driver/mixins/_sql_translator.py +0 -0
  121. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/exceptions.py +0 -0
  122. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/__init__.py +0 -0
  123. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/aiosql/__init__.py +0 -0
  124. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/aiosql/adapter.py +0 -0
  125. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/litestar/__init__.py +0 -0
  126. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/litestar/_utils.py +0 -0
  127. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/litestar/cli.py +0 -0
  128. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/litestar/config.py +0 -0
  129. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/litestar/handlers.py +0 -0
  130. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/litestar/plugin.py +0 -0
  131. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/extensions/litestar/providers.py +0 -0
  132. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/migrations/__init__.py +0 -0
  133. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/migrations/base.py +0 -0
  134. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/migrations/commands.py +0 -0
  135. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/migrations/loaders.py +0 -0
  136. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/migrations/runner.py +0 -0
  137. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/migrations/tracker.py +0 -0
  138. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/migrations/utils.py +0 -0
  139. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/protocols.py +0 -0
  140. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/py.typed +0 -0
  141. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/storage/__init__.py +0 -0
  142. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/storage/backends/__init__.py +0 -0
  143. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/storage/backends/base.py +0 -0
  144. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/storage/backends/fsspec.py +0 -0
  145. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/storage/backends/obstore.py +0 -0
  146. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/storage/capabilities.py +0 -0
  147. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/__init__.py +0 -0
  148. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/correlation.py +0 -0
  149. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/deprecation.py +0 -0
  150. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/fixtures.py +0 -0
  151. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/logging.py +0 -0
  152. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/module_loader.py +0 -0
  153. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/serializers.py +0 -0
  154. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/singleton.py +0 -0
  155. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/sync_tools.py +0 -0
  156. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/text.py +0 -0
  157. {sqlspec-0.16.2 → sqlspec-0.17.0}/sqlspec/utils/type_guards.py +0 -0
  158. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/__init__.py +0 -0
  159. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/conftest.py +0 -0
  160. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/__init__.py +0 -0
  161. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/ddls-mysql-collection.sql +0 -0
  162. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/ddls-postgres-collection.sql +0 -0
  163. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/example_usage.py +0 -0
  164. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/init.sql +0 -0
  165. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-config.sql +0 -0
  166. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-data_types.sql +0 -0
  167. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-database_details.sql +0 -0
  168. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-engines.sql +0 -0
  169. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-hostname.sql +0 -0
  170. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-plugins.sql +0 -0
  171. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-process_list.sql +0 -0
  172. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-resource-groups.sql +0 -0
  173. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-schema_objects.sql +0 -0
  174. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-table_details.sql +0 -0
  175. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/collection-users.sql +0 -0
  176. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/mysql/init.sql +0 -0
  177. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-applications.sql +0 -0
  178. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-aws_extension_dependency.sql +0 -0
  179. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-aws_oracle_exists.sql +0 -0
  180. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-bg_writer_stats.sql +0 -0
  181. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-calculated_metrics.sql +0 -0
  182. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-data_types.sql +0 -0
  183. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-database_details.sql +0 -0
  184. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-extensions.sql +0 -0
  185. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-index_details.sql +0 -0
  186. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-pglogical-details.sql +0 -0
  187. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-privileges.sql +0 -0
  188. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-replication_slots.sql +0 -0
  189. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-replication_stats.sql +0 -0
  190. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-schema_details.sql +0 -0
  191. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-schema_objects.sql +0 -0
  192. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-settings.sql +0 -0
  193. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-source_details.sql +0 -0
  194. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/collection-table_details.sql +0 -0
  195. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/extended-collection-all-databases.sql +0 -0
  196. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/postgres/init.sql +0 -0
  197. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/readiness-check.sql +0 -0
  198. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/fixtures/sql_utils.py +0 -0
  199. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/__init__.py +0 -0
  200. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/conftest.py +0 -0
  201. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/__init__.py +0 -0
  202. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/__init__.py +0 -0
  203. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/conftest.py +0 -0
  204. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/test_adbc_arrow_features.py +0 -0
  205. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/test_adbc_backends.py +0 -0
  206. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/test_adbc_connection.py +0 -0
  207. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/test_adbc_driver.py +0 -0
  208. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/test_adbc_edge_cases.py +0 -0
  209. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_adbc/test_adbc_results.py +0 -0
  210. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_aiosqlite/__init__.py +0 -0
  211. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_aiosqlite/test_connection.py +0 -0
  212. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_aiosqlite/test_driver.py +0 -0
  213. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncmy/__init__.py +0 -0
  214. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncmy/conftest.py +0 -0
  215. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncmy/test_asyncmy_features.py +0 -0
  216. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncmy/test_config.py +0 -0
  217. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncmy/test_driver.py +0 -0
  218. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncmy/test_parameter_styles.py +0 -0
  219. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncpg/__init__.py +0 -0
  220. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncpg/conftest.py +0 -0
  221. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncpg/test_connection.py +0 -0
  222. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncpg/test_driver.py +0 -0
  223. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncpg/test_execute_many.py +0 -0
  224. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_asyncpg/test_parameter_styles.py +0 -0
  225. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_bigquery/__init__.py +0 -0
  226. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_bigquery/conftest.py +0 -0
  227. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_bigquery/test_bigquery_features.py +0 -0
  228. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_bigquery/test_config.py +0 -0
  229. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_bigquery/test_connection.py +0 -0
  230. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_bigquery/test_driver.py +0 -0
  231. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_bigquery/test_parameter_styles.py +0 -0
  232. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/__init__.py +0 -0
  233. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/test_connection.py +0 -0
  234. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/test_driver.py +0 -0
  235. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/test_execute_many.py +0 -0
  236. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/test_mixed_parameter_styles.py +0 -0
  237. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/test_parameter_styles.py +0 -0
  238. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/test_pooling.py +0 -0
  239. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_duckdb/utils.py +0 -0
  240. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/__init__.py +0 -0
  241. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/conftest.py +0 -0
  242. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/test_connection.py +0 -0
  243. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/test_driver_async.py +0 -0
  244. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/test_driver_sync.py +0 -0
  245. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/test_execute_many.py +0 -0
  246. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/test_oracle_features.py +0 -0
  247. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_oracledb/test_parameter_styles.py +0 -0
  248. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psqlpy/__init__.py +0 -0
  249. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psqlpy/conftest.py +0 -0
  250. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psqlpy/test_connection.py +0 -0
  251. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psqlpy/test_driver.py +0 -0
  252. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psqlpy/test_parameter_styles.py +0 -0
  253. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psqlpy/test_psqlpy_features.py +0 -0
  254. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psycopg/__init__.py +0 -0
  255. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psycopg/conftest.py +0 -0
  256. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psycopg/test_async_copy.py +0 -0
  257. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psycopg/test_connection.py +0 -0
  258. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psycopg/test_driver.py +0 -0
  259. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psycopg/test_execute_many.py +0 -0
  260. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_psycopg/test_parameter_styles.py +0 -0
  261. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_sqlite/__init__.py +0 -0
  262. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_sqlite/conftest.py +0 -0
  263. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_sqlite/test_driver.py +0 -0
  264. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_sqlite/test_parameter_styles.py +0 -0
  265. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_adapters/test_sqlite/test_query_mixin.py +0 -0
  266. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_loader/__init__.py +0 -0
  267. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_loader/test_file_system_loading.py +0 -0
  268. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_migrations/__init__.py +0 -0
  269. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/integration/test_migrations/test_migration_execution.py +0 -0
  270. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/conftest.py +0 -0
  271. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_adapters/__init__.py +0 -0
  272. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_adapters/conftest.py +0 -0
  273. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_adapters/test_adapter_implementations.py +0 -0
  274. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_adapters/test_async_adapters.py +0 -0
  275. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_adapters/test_sync_adapters.py +0 -0
  276. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_base/__init__.py +0 -0
  277. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_base/test_sqlspec_class.py +0 -0
  278. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_builder/__init__.py +0 -0
  279. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_builder/test_insert_builder.py +0 -0
  280. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_builder_parameter_naming.py +0 -0
  281. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_core/test_cache.py +0 -0
  282. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_core/test_compiler.py +0 -0
  283. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_core/test_filters.py +0 -0
  284. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_core/test_hashing.py +0 -0
  285. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_core/test_parameters.py +0 -0
  286. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_core/test_result.py +0 -0
  287. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_core/test_statement.py +0 -0
  288. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_loader/__init__.py +0 -0
  289. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_loader/test_cache_integration.py +0 -0
  290. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_loader/test_loading_patterns.py +0 -0
  291. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_migrations/__init__.py +0 -0
  292. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_migrations/test_migration.py +0 -0
  293. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_migrations/test_migration_execution.py +0 -0
  294. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_migrations/test_migration_runner.py +0 -0
  295. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/__init__.py +0 -0
  296. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_correlation.py +0 -0
  297. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_deprecation.py +0 -0
  298. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_fixtures.py +0 -0
  299. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_logging.py +0 -0
  300. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_module_loader.py +0 -0
  301. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_serializers.py +0 -0
  302. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_singleton.py +0 -0
  303. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_sync_tools.py +0 -0
  304. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_text.py +0 -0
  305. {sqlspec-0.16.2 → sqlspec-0.17.0}/tests/unit/test_utils/test_type_guards.py +0 -0
  306. {sqlspec-0.16.2 → sqlspec-0.17.0}/tools/__init__.py +0 -0
  307. {sqlspec-0.16.2 → sqlspec-0.17.0}/tools/build_docs.py +0 -0
  308. {sqlspec-0.16.2 → sqlspec-0.17.0}/tools/local-infra.sh +0 -0
  309. {sqlspec-0.16.2 → sqlspec-0.17.0}/tools/pypi_readme.py +0 -0
  310. {sqlspec-0.16.2 → sqlspec-0.17.0}/tools/sphinx_ext/__init__.py +0 -0
  311. {sqlspec-0.16.2 → sqlspec-0.17.0}/tools/sphinx_ext/changelog.py +0 -0
  312. {sqlspec-0.16.2 → sqlspec-0.17.0}/tools/sphinx_ext/missing_references.py +0 -0
@@ -219,7 +219,7 @@ check-all: lint test-all coverage ## Run all checks (lint, test
219
219
  .PHONY: docs-clean
220
220
  docs-clean: ## Clean documentation build
221
221
  @echo "${INFO} Cleaning documentation build assets... 🧹"
222
- @rm -rf docs/_build >/dev/null 2>&1
222
+ @rm -rf docs/_build
223
223
  @echo "${OK} Documentation assets cleaned"
224
224
 
225
225
  .PHONY: docs-serve
@@ -230,7 +230,7 @@ docs-serve: docs-clean ## Serve documentation locall
230
230
  .PHONY: docs
231
231
  docs: docs-clean ## Build documentation
232
232
  @echo "${INFO} Building documentation... 📝"
233
- @uv run sphinx-build -M html docs docs/_build/ -E -a -j auto -W --keep-going >/dev/null 2>&1
233
+ @uv run sphinx-build -M html docs docs/_build/ -E -a -j auto -W --keep-going
234
234
  @echo "${OK} Documentation built successfully"
235
235
 
236
236
  .PHONY: docs-linkcheck
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: sqlspec
3
- Version: 0.16.2
3
+ Version: 0.17.0
4
4
  Summary: SQL Experiments in Python
5
5
  Project-URL: Discord, https://discord.gg/litestar
6
6
  Project-URL: Issue, https://github.com/litestar-org/sqlspec/issues/
@@ -13,7 +13,7 @@ maintainers = [{ name = "Litestar Developers", email = "hello@litestar.dev" }]
13
13
  name = "sqlspec"
14
14
  readme = "README.md"
15
15
  requires-python = ">=3.9, <4.0"
16
- version = "0.16.2"
16
+ version = "0.17.0"
17
17
 
18
18
  [project.urls]
19
19
  Discord = "https://discord.gg/litestar"
@@ -34,7 +34,16 @@ from sqlspec.core import (
34
34
  from sqlspec.core import filters as filters
35
35
  from sqlspec.driver import AsyncDriverAdapterBase, ExecutionResult, SyncDriverAdapterBase
36
36
  from sqlspec.loader import SQLFile, SQLFileLoader
37
- from sqlspec.typing import ConnectionT, DictRow, ModelDTOT, ModelT, RowT, StatementParameters, SupportedSchemaModel
37
+ from sqlspec.typing import (
38
+ ConnectionT,
39
+ DictRow,
40
+ ModelDTOT,
41
+ ModelT,
42
+ PoolT,
43
+ RowT,
44
+ StatementParameters,
45
+ SupportedSchemaModel,
46
+ )
38
47
 
39
48
  __all__ = (
40
49
  "SQL",
@@ -60,6 +69,7 @@ __all__ = (
60
69
  "ParameterProcessor",
61
70
  "ParameterStyle",
62
71
  "ParameterStyleConfig",
72
+ "PoolT",
63
73
  "QueryBuilder",
64
74
  "RowT",
65
75
  "SQLFactory",
@@ -4,10 +4,9 @@ Provides both statement builders (select, insert, update, etc.) and column expre
4
4
  """
5
5
 
6
6
  import logging
7
- from typing import TYPE_CHECKING, Any, Optional, Union, cast
7
+ from typing import TYPE_CHECKING, Any, Optional, Union
8
8
 
9
9
  import sqlglot
10
- from mypy_extensions import trait
11
10
  from sqlglot import exp
12
11
  from sqlglot.dialects.dialect import DialectType
13
12
  from sqlglot.errors import ParseError as SQLGlotParseError
@@ -34,10 +33,11 @@ from sqlspec.builder import (
34
33
  Truncate,
35
34
  Update,
36
35
  )
36
+ from sqlspec.builder.mixins._join_operations import JoinBuilder
37
+ from sqlspec.builder.mixins._select_operations import Case, SubqueryBuilder, WindowFunctionBuilder
37
38
  from sqlspec.exceptions import SQLBuilderError
38
39
 
39
40
  if TYPE_CHECKING:
40
- from sqlspec.builder._column import ColumnExpression
41
41
  from sqlspec.core.statement import SQL
42
42
 
43
43
  __all__ = (
@@ -179,7 +179,7 @@ class SQLFactory:
179
179
  # Statement Builders
180
180
  # ===================
181
181
  def select(
182
- self, *columns_or_sql: Union[str, exp.Expression, Column, "SQL"], dialect: DialectType = None
182
+ self, *columns_or_sql: Union[str, exp.Expression, Column, "SQL", "Case"], dialect: DialectType = None
183
183
  ) -> "Select":
184
184
  builder_dialect = dialect or self.dialect
185
185
  if len(columns_or_sql) == 1 and isinstance(columns_or_sql[0], str):
@@ -223,7 +223,10 @@ class SQLFactory:
223
223
  if self._looks_like_sql(table_or_sql):
224
224
  detected = self.detect_sql_type(table_or_sql, dialect=builder_dialect)
225
225
  if detected != "UPDATE":
226
- msg = f"sql.update() expects UPDATE statement, got {detected}. Use sql.{detected.lower()}() if a dedicated builder exists."
226
+ msg = (
227
+ f"sql.update() expects UPDATE statement, got {detected}. "
228
+ f"Use sql.{detected.lower()}() if a dedicated builder exists."
229
+ )
227
230
  raise SQLBuilderError(msg)
228
231
  return self._populate_update_from_sql(builder, table_or_sql)
229
232
  return builder.table(table_or_sql)
@@ -235,7 +238,10 @@ class SQLFactory:
235
238
  if table_or_sql and self._looks_like_sql(table_or_sql):
236
239
  detected = self.detect_sql_type(table_or_sql, dialect=builder_dialect)
237
240
  if detected != "DELETE":
238
- msg = f"sql.delete() expects DELETE statement, got {detected}. Use sql.{detected.lower()}() if a dedicated builder exists."
241
+ msg = (
242
+ f"sql.delete() expects DELETE statement, got {detected}. "
243
+ f"Use sql.{detected.lower()}() if a dedicated builder exists."
244
+ )
239
245
  raise SQLBuilderError(msg)
240
246
  return self._populate_delete_from_sql(builder, table_or_sql)
241
247
  return builder
@@ -247,7 +253,10 @@ class SQLFactory:
247
253
  if self._looks_like_sql(table_or_sql):
248
254
  detected = self.detect_sql_type(table_or_sql, dialect=builder_dialect)
249
255
  if detected != "MERGE":
250
- msg = f"sql.merge() expects MERGE statement, got {detected}. Use sql.{detected.lower()}() if a dedicated builder exists."
256
+ msg = (
257
+ f"sql.merge() expects MERGE statement, got {detected}. "
258
+ f"Use sql.{detected.lower()}() if a dedicated builder exists."
259
+ )
251
260
  raise SQLBuilderError(msg)
252
261
  return self._populate_merge_from_sql(builder, table_or_sql)
253
262
  return builder.into(table_or_sql)
@@ -1373,410 +1382,5 @@ class SQLFactory:
1373
1382
  return exp.Window(this=func_expr, **over_args)
1374
1383
 
1375
1384
 
1376
- @trait
1377
- class Case:
1378
- """Builder for CASE expressions using the SQL factory.
1379
-
1380
- Example:
1381
- ```python
1382
- from sqlspec import sql
1383
-
1384
- case_expr = (
1385
- sql.case()
1386
- .when(sql.age < 18, "Minor")
1387
- .when(sql.age < 65, "Adult")
1388
- .else_("Senior")
1389
- .end()
1390
- )
1391
- ```
1392
- """
1393
-
1394
- def __init__(self) -> None:
1395
- """Initialize the CASE expression builder."""
1396
- self._conditions: list[exp.If] = []
1397
- self._default: Optional[exp.Expression] = None
1398
-
1399
- def __eq__(self, other: object) -> "ColumnExpression": # type: ignore[override]
1400
- """Equal to (==) - convert to expression then compare."""
1401
- from sqlspec.builder._column import ColumnExpression
1402
-
1403
- case_expr = exp.Case(ifs=self._conditions, default=self._default)
1404
- if other is None:
1405
- return ColumnExpression(exp.Is(this=case_expr, expression=exp.Null()))
1406
- return ColumnExpression(exp.EQ(this=case_expr, expression=exp.convert(other)))
1407
-
1408
- def __hash__(self) -> int:
1409
- """Make Case hashable."""
1410
- return hash(id(self))
1411
-
1412
- def when(self, condition: Union[str, exp.Expression], value: Union[str, exp.Expression, Any]) -> "Case":
1413
- """Add a WHEN clause.
1414
-
1415
- Args:
1416
- condition: Condition to test.
1417
- value: Value to return if condition is true.
1418
-
1419
- Returns:
1420
- Self for method chaining.
1421
- """
1422
- cond_expr = exp.maybe_parse(condition) or exp.column(condition) if isinstance(condition, str) else condition
1423
- val_expr = SQLFactory._to_literal(value)
1424
-
1425
- # SQLGlot uses exp.If for CASE WHEN clauses, not exp.When
1426
- when_clause = exp.If(this=cond_expr, true=val_expr)
1427
- self._conditions.append(when_clause)
1428
- return self
1429
-
1430
- def else_(self, value: Union[str, exp.Expression, Any]) -> "Case":
1431
- """Add an ELSE clause.
1432
-
1433
- Args:
1434
- value: Default value to return.
1435
-
1436
- Returns:
1437
- Self for method chaining.
1438
- """
1439
- self._default = SQLFactory._to_literal(value)
1440
- return self
1441
-
1442
- def end(self) -> exp.Expression:
1443
- """Complete the CASE expression.
1444
-
1445
- Returns:
1446
- Complete CASE expression.
1447
- """
1448
- return exp.Case(ifs=self._conditions, default=self._default)
1449
-
1450
- def as_(self, alias: str) -> exp.Alias:
1451
- """Complete the CASE expression with an alias.
1452
-
1453
- Args:
1454
- alias: Alias name for the CASE expression.
1455
-
1456
- Returns:
1457
- Aliased CASE expression.
1458
- """
1459
- case_expr = exp.Case(ifs=self._conditions, default=self._default)
1460
- return cast("exp.Alias", exp.alias_(case_expr, alias))
1461
-
1462
-
1463
- @trait
1464
- class WindowFunctionBuilder:
1465
- """Builder for window functions with fluent syntax.
1466
-
1467
- Example:
1468
- ```python
1469
- from sqlspec import sql
1470
-
1471
- # sql.row_number_.partition_by("department").order_by("salary")
1472
- window_func = (
1473
- sql.row_number_.partition_by("department")
1474
- .order_by("salary")
1475
- .as_("row_num")
1476
- )
1477
- ```
1478
- """
1479
-
1480
- def __init__(self, function_name: str) -> None:
1481
- """Initialize the window function builder.
1482
-
1483
- Args:
1484
- function_name: Name of the window function (row_number, rank, etc.)
1485
- """
1486
- self._function_name = function_name
1487
- self._partition_by_cols: list[exp.Expression] = []
1488
- self._order_by_cols: list[exp.Expression] = []
1489
- self._alias: Optional[str] = None
1490
-
1491
- def __eq__(self, other: object) -> "ColumnExpression": # type: ignore[override]
1492
- """Equal to (==) - convert to expression then compare."""
1493
- from sqlspec.builder._column import ColumnExpression
1494
-
1495
- window_expr = self._build_expression()
1496
- if other is None:
1497
- return ColumnExpression(exp.Is(this=window_expr, expression=exp.Null()))
1498
- return ColumnExpression(exp.EQ(this=window_expr, expression=exp.convert(other)))
1499
-
1500
- def __hash__(self) -> int:
1501
- """Make WindowFunctionBuilder hashable."""
1502
- return hash(id(self))
1503
-
1504
- def partition_by(self, *columns: Union[str, exp.Expression]) -> "WindowFunctionBuilder":
1505
- """Add PARTITION BY clause.
1506
-
1507
- Args:
1508
- *columns: Columns to partition by.
1509
-
1510
- Returns:
1511
- Self for method chaining.
1512
- """
1513
- for col in columns:
1514
- col_expr = exp.column(col) if isinstance(col, str) else col
1515
- self._partition_by_cols.append(col_expr)
1516
- return self
1517
-
1518
- def order_by(self, *columns: Union[str, exp.Expression]) -> "WindowFunctionBuilder":
1519
- """Add ORDER BY clause.
1520
-
1521
- Args:
1522
- *columns: Columns to order by.
1523
-
1524
- Returns:
1525
- Self for method chaining.
1526
- """
1527
- for col in columns:
1528
- if isinstance(col, str):
1529
- col_expr = exp.column(col).asc()
1530
- self._order_by_cols.append(col_expr)
1531
- else:
1532
- # Convert to ordered expression
1533
- self._order_by_cols.append(exp.Ordered(this=col, desc=False))
1534
- return self
1535
-
1536
- def as_(self, alias: str) -> exp.Alias:
1537
- """Complete the window function with an alias.
1538
-
1539
- Args:
1540
- alias: Alias name for the window function.
1541
-
1542
- Returns:
1543
- Aliased window function expression.
1544
- """
1545
- window_expr = self._build_expression()
1546
- return cast("exp.Alias", exp.alias_(window_expr, alias))
1547
-
1548
- def build(self) -> exp.Expression:
1549
- """Complete the window function without an alias.
1550
-
1551
- Returns:
1552
- Window function expression.
1553
- """
1554
- return self._build_expression()
1555
-
1556
- def _build_expression(self) -> exp.Expression:
1557
- """Build the complete window function expression."""
1558
- # Create the function expression
1559
- func_expr = exp.Anonymous(this=self._function_name.upper(), expressions=[])
1560
-
1561
- # Build the OVER clause arguments
1562
- over_args: dict[str, Any] = {}
1563
-
1564
- if self._partition_by_cols:
1565
- over_args["partition_by"] = self._partition_by_cols
1566
-
1567
- if self._order_by_cols:
1568
- over_args["order"] = exp.Order(expressions=self._order_by_cols)
1569
-
1570
- return exp.Window(this=func_expr, **over_args)
1571
-
1572
-
1573
- @trait
1574
- class SubqueryBuilder:
1575
- """Builder for subquery operations with fluent syntax.
1576
-
1577
- Example:
1578
- ```python
1579
- from sqlspec import sql
1580
-
1581
- # sql.exists_(subquery)
1582
- exists_check = sql.exists_(
1583
- sql.select("1")
1584
- .from_("orders")
1585
- .where_eq("user_id", sql.users.id)
1586
- )
1587
-
1588
- # sql.in_(subquery)
1589
- in_check = sql.in_(
1590
- sql.select("category_id")
1591
- .from_("categories")
1592
- .where_eq("active", True)
1593
- )
1594
- ```
1595
- """
1596
-
1597
- def __init__(self, operation: str) -> None:
1598
- """Initialize the subquery builder.
1599
-
1600
- Args:
1601
- operation: Type of subquery operation (exists, in, any, all)
1602
- """
1603
- self._operation = operation
1604
-
1605
- def __eq__(self, other: object) -> "ColumnExpression": # type: ignore[override]
1606
- """Equal to (==) - not typically used but needed for type consistency."""
1607
- from sqlspec.builder._column import ColumnExpression
1608
-
1609
- # SubqueryBuilder doesn't have a direct expression, so this is a placeholder
1610
- # In practice, this shouldn't be called as subqueries are used differently
1611
- placeholder_expr = exp.Literal.string(f"subquery_{self._operation}")
1612
- if other is None:
1613
- return ColumnExpression(exp.Is(this=placeholder_expr, expression=exp.Null()))
1614
- return ColumnExpression(exp.EQ(this=placeholder_expr, expression=exp.convert(other)))
1615
-
1616
- def __hash__(self) -> int:
1617
- """Make SubqueryBuilder hashable."""
1618
- return hash(id(self))
1619
-
1620
- def __call__(self, subquery: Union[str, exp.Expression, Any]) -> exp.Expression:
1621
- """Build the subquery expression.
1622
-
1623
- Args:
1624
- subquery: The subquery - can be a SQL string, SelectBuilder, or expression
1625
-
1626
- Returns:
1627
- The subquery expression (EXISTS, IN, ANY, ALL, etc.)
1628
- """
1629
- subquery_expr: exp.Expression
1630
- if isinstance(subquery, str):
1631
- # Parse as SQL
1632
- parsed: Optional[exp.Expression] = exp.maybe_parse(subquery)
1633
- if not parsed:
1634
- msg = f"Could not parse subquery SQL: {subquery}"
1635
- raise SQLBuilderError(msg)
1636
- subquery_expr = parsed
1637
- elif hasattr(subquery, "build") and callable(getattr(subquery, "build", None)):
1638
- # It's a query builder - build it to get the SQL and parse
1639
- built_query = subquery.build() # pyright: ignore[reportAttributeAccessIssue]
1640
- subquery_expr = exp.maybe_parse(built_query.sql)
1641
- if not subquery_expr:
1642
- msg = f"Could not parse built query: {built_query.sql}"
1643
- raise SQLBuilderError(msg)
1644
- elif isinstance(subquery, exp.Expression):
1645
- subquery_expr = subquery
1646
- else:
1647
- # Try to convert to expression
1648
- parsed = exp.maybe_parse(str(subquery))
1649
- if not parsed:
1650
- msg = f"Could not convert subquery to expression: {subquery}"
1651
- raise SQLBuilderError(msg)
1652
- subquery_expr = parsed
1653
-
1654
- # Build the appropriate expression based on operation
1655
- if self._operation == "exists":
1656
- return exp.Exists(this=subquery_expr)
1657
- if self._operation == "in":
1658
- # For IN, we create a subquery that can be used with WHERE column IN (subquery)
1659
- return exp.In(expressions=[subquery_expr])
1660
- if self._operation == "any":
1661
- return exp.Any(this=subquery_expr)
1662
- if self._operation == "all":
1663
- return exp.All(this=subquery_expr)
1664
- msg = f"Unknown subquery operation: {self._operation}"
1665
- raise SQLBuilderError(msg)
1666
-
1667
-
1668
- @trait
1669
- class JoinBuilder:
1670
- """Builder for JOIN operations with fluent syntax.
1671
-
1672
- Example:
1673
- ```python
1674
- from sqlspec import sql
1675
-
1676
- # sql.left_join_("posts").on("users.id = posts.user_id")
1677
- join_clause = sql.left_join_("posts").on(
1678
- "users.id = posts.user_id"
1679
- )
1680
-
1681
- # Or with query builder
1682
- query = (
1683
- sql.select("users.name", "posts.title")
1684
- .from_("users")
1685
- .join(
1686
- sql.left_join_("posts").on(
1687
- "users.id = posts.user_id"
1688
- )
1689
- )
1690
- )
1691
- ```
1692
- """
1693
-
1694
- def __init__(self, join_type: str) -> None:
1695
- """Initialize the join builder.
1696
-
1697
- Args:
1698
- join_type: Type of join (inner, left, right, full, cross)
1699
- """
1700
- self._join_type = join_type.upper()
1701
- self._table: Optional[Union[str, exp.Expression]] = None
1702
- self._condition: Optional[exp.Expression] = None
1703
- self._alias: Optional[str] = None
1704
-
1705
- def __eq__(self, other: object) -> "ColumnExpression": # type: ignore[override]
1706
- """Equal to (==) - not typically used but needed for type consistency."""
1707
- from sqlspec.builder._column import ColumnExpression
1708
-
1709
- # JoinBuilder doesn't have a direct expression, so this is a placeholder
1710
- # In practice, this shouldn't be called as joins are used differently
1711
- placeholder_expr = exp.Literal.string(f"join_{self._join_type.lower()}")
1712
- if other is None:
1713
- return ColumnExpression(exp.Is(this=placeholder_expr, expression=exp.Null()))
1714
- return ColumnExpression(exp.EQ(this=placeholder_expr, expression=exp.convert(other)))
1715
-
1716
- def __hash__(self) -> int:
1717
- """Make JoinBuilder hashable."""
1718
- return hash(id(self))
1719
-
1720
- def __call__(self, table: Union[str, exp.Expression], alias: Optional[str] = None) -> "JoinBuilder":
1721
- """Set the table to join.
1722
-
1723
- Args:
1724
- table: Table name or expression to join
1725
- alias: Optional alias for the table
1726
-
1727
- Returns:
1728
- Self for method chaining
1729
- """
1730
- self._table = table
1731
- self._alias = alias
1732
- return self
1733
-
1734
- def on(self, condition: Union[str, exp.Expression]) -> exp.Expression:
1735
- """Set the join condition and build the JOIN expression.
1736
-
1737
- Args:
1738
- condition: JOIN condition (e.g., "users.id = posts.user_id")
1739
-
1740
- Returns:
1741
- Complete JOIN expression
1742
- """
1743
- if not self._table:
1744
- msg = "Table must be set before calling .on()"
1745
- raise SQLBuilderError(msg)
1746
-
1747
- # Parse the condition
1748
- condition_expr: exp.Expression
1749
- if isinstance(condition, str):
1750
- parsed: Optional[exp.Expression] = exp.maybe_parse(condition)
1751
- condition_expr = parsed or exp.condition(condition)
1752
- else:
1753
- condition_expr = condition
1754
-
1755
- # Build table expression
1756
- table_expr: exp.Expression
1757
- if isinstance(self._table, str):
1758
- table_expr = exp.to_table(self._table)
1759
- if self._alias:
1760
- table_expr = exp.alias_(table_expr, self._alias)
1761
- else:
1762
- table_expr = self._table
1763
- if self._alias:
1764
- table_expr = exp.alias_(table_expr, self._alias)
1765
-
1766
- # Create the appropriate join type using same pattern as existing JoinClauseMixin
1767
- if self._join_type == "INNER JOIN":
1768
- return exp.Join(this=table_expr, on=condition_expr)
1769
- if self._join_type == "LEFT JOIN":
1770
- return exp.Join(this=table_expr, on=condition_expr, side="LEFT")
1771
- if self._join_type == "RIGHT JOIN":
1772
- return exp.Join(this=table_expr, on=condition_expr, side="RIGHT")
1773
- if self._join_type == "FULL JOIN":
1774
- return exp.Join(this=table_expr, on=condition_expr, side="FULL", kind="OUTER")
1775
- if self._join_type == "CROSS JOIN":
1776
- # CROSS JOIN doesn't use ON condition
1777
- return exp.Join(this=table_expr, kind="CROSS")
1778
- return exp.Join(this=table_expr, on=condition_expr)
1779
-
1780
-
1781
1385
  # Create a default SQL factory instance
1782
1386
  sql = SQLFactory()
@@ -1,19 +1,29 @@
1
1
  from sqlspec.adapters.aiosqlite._types import AiosqliteConnection
2
- from sqlspec.adapters.aiosqlite.config import AiosqliteConfig, AiosqliteConnectionParams, AiosqliteConnectionPool
2
+ from sqlspec.adapters.aiosqlite.config import AiosqliteConfig, AiosqliteConnectionParams, AiosqlitePoolParams
3
3
  from sqlspec.adapters.aiosqlite.driver import (
4
4
  AiosqliteCursor,
5
5
  AiosqliteDriver,
6
6
  AiosqliteExceptionHandler,
7
7
  aiosqlite_statement_config,
8
8
  )
9
+ from sqlspec.adapters.aiosqlite.pool import (
10
+ AiosqliteConnectionPool,
11
+ AiosqliteConnectTimeoutError,
12
+ AiosqlitePoolClosedError,
13
+ AiosqlitePoolConnection,
14
+ )
9
15
 
10
16
  __all__ = (
11
17
  "AiosqliteConfig",
18
+ "AiosqliteConnectTimeoutError",
12
19
  "AiosqliteConnection",
13
20
  "AiosqliteConnectionParams",
14
21
  "AiosqliteConnectionPool",
15
22
  "AiosqliteCursor",
16
23
  "AiosqliteDriver",
17
24
  "AiosqliteExceptionHandler",
25
+ "AiosqlitePoolClosedError",
26
+ "AiosqlitePoolConnection",
27
+ "AiosqlitePoolParams",
18
28
  "aiosqlite_statement_config",
19
29
  )