sqlspec 0.14.0__py3-none-any.whl → 0.15.0__py3-none-any.whl
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.
- sqlspec/__init__.py +50 -25
- sqlspec/__main__.py +12 -0
- sqlspec/__metadata__.py +1 -3
- sqlspec/_serialization.py +1 -2
- sqlspec/_sql.py +256 -120
- sqlspec/_typing.py +278 -142
- sqlspec/adapters/adbc/__init__.py +4 -3
- sqlspec/adapters/adbc/_types.py +12 -0
- sqlspec/adapters/adbc/config.py +115 -248
- sqlspec/adapters/adbc/driver.py +462 -353
- sqlspec/adapters/aiosqlite/__init__.py +18 -3
- sqlspec/adapters/aiosqlite/_types.py +13 -0
- sqlspec/adapters/aiosqlite/config.py +199 -129
- sqlspec/adapters/aiosqlite/driver.py +230 -269
- sqlspec/adapters/asyncmy/__init__.py +18 -3
- sqlspec/adapters/asyncmy/_types.py +12 -0
- sqlspec/adapters/asyncmy/config.py +80 -168
- sqlspec/adapters/asyncmy/driver.py +260 -225
- sqlspec/adapters/asyncpg/__init__.py +19 -4
- sqlspec/adapters/asyncpg/_types.py +17 -0
- sqlspec/adapters/asyncpg/config.py +82 -181
- sqlspec/adapters/asyncpg/driver.py +285 -383
- sqlspec/adapters/bigquery/__init__.py +17 -3
- sqlspec/adapters/bigquery/_types.py +12 -0
- sqlspec/adapters/bigquery/config.py +191 -258
- sqlspec/adapters/bigquery/driver.py +474 -646
- sqlspec/adapters/duckdb/__init__.py +14 -3
- sqlspec/adapters/duckdb/_types.py +12 -0
- sqlspec/adapters/duckdb/config.py +415 -351
- sqlspec/adapters/duckdb/driver.py +343 -413
- sqlspec/adapters/oracledb/__init__.py +19 -5
- sqlspec/adapters/oracledb/_types.py +14 -0
- sqlspec/adapters/oracledb/config.py +123 -379
- sqlspec/adapters/oracledb/driver.py +507 -560
- sqlspec/adapters/psqlpy/__init__.py +13 -3
- sqlspec/adapters/psqlpy/_types.py +11 -0
- sqlspec/adapters/psqlpy/config.py +93 -254
- sqlspec/adapters/psqlpy/driver.py +505 -234
- sqlspec/adapters/psycopg/__init__.py +19 -5
- sqlspec/adapters/psycopg/_types.py +17 -0
- sqlspec/adapters/psycopg/config.py +143 -403
- sqlspec/adapters/psycopg/driver.py +706 -872
- sqlspec/adapters/sqlite/__init__.py +14 -3
- sqlspec/adapters/sqlite/_types.py +11 -0
- sqlspec/adapters/sqlite/config.py +202 -118
- sqlspec/adapters/sqlite/driver.py +264 -303
- sqlspec/base.py +105 -9
- sqlspec/{statement/builder → builder}/__init__.py +12 -14
- sqlspec/{statement/builder → builder}/_base.py +120 -55
- sqlspec/{statement/builder → builder}/_column.py +17 -6
- sqlspec/{statement/builder → builder}/_ddl.py +46 -79
- sqlspec/{statement/builder → builder}/_ddl_utils.py +5 -10
- sqlspec/{statement/builder → builder}/_delete.py +6 -25
- sqlspec/{statement/builder → builder}/_insert.py +6 -64
- sqlspec/builder/_merge.py +56 -0
- sqlspec/{statement/builder → builder}/_parsing_utils.py +3 -10
- sqlspec/{statement/builder → builder}/_select.py +11 -56
- sqlspec/{statement/builder → builder}/_update.py +12 -18
- sqlspec/{statement/builder → builder}/mixins/__init__.py +10 -14
- sqlspec/{statement/builder → builder}/mixins/_cte_and_set_ops.py +48 -59
- sqlspec/{statement/builder → builder}/mixins/_insert_operations.py +22 -16
- sqlspec/{statement/builder → builder}/mixins/_join_operations.py +1 -3
- sqlspec/{statement/builder → builder}/mixins/_merge_operations.py +3 -5
- sqlspec/{statement/builder → builder}/mixins/_order_limit_operations.py +3 -3
- sqlspec/{statement/builder → builder}/mixins/_pivot_operations.py +4 -8
- sqlspec/{statement/builder → builder}/mixins/_select_operations.py +21 -36
- sqlspec/{statement/builder → builder}/mixins/_update_operations.py +3 -14
- sqlspec/{statement/builder → builder}/mixins/_where_clause.py +52 -79
- sqlspec/cli.py +4 -5
- sqlspec/config.py +180 -133
- sqlspec/core/__init__.py +63 -0
- sqlspec/core/cache.py +873 -0
- sqlspec/core/compiler.py +396 -0
- sqlspec/core/filters.py +828 -0
- sqlspec/core/hashing.py +310 -0
- sqlspec/core/parameters.py +1209 -0
- sqlspec/core/result.py +664 -0
- sqlspec/{statement → core}/splitter.py +321 -191
- sqlspec/core/statement.py +651 -0
- sqlspec/driver/__init__.py +7 -10
- sqlspec/driver/_async.py +387 -176
- sqlspec/driver/_common.py +527 -289
- sqlspec/driver/_sync.py +390 -172
- sqlspec/driver/mixins/__init__.py +2 -19
- sqlspec/driver/mixins/_result_tools.py +168 -0
- sqlspec/driver/mixins/_sql_translator.py +6 -3
- sqlspec/exceptions.py +5 -252
- sqlspec/extensions/aiosql/adapter.py +93 -96
- sqlspec/extensions/litestar/config.py +0 -1
- sqlspec/extensions/litestar/handlers.py +15 -26
- sqlspec/extensions/litestar/plugin.py +16 -14
- sqlspec/extensions/litestar/providers.py +17 -52
- sqlspec/loader.py +424 -105
- sqlspec/migrations/__init__.py +12 -0
- sqlspec/migrations/base.py +92 -68
- sqlspec/migrations/commands.py +24 -106
- sqlspec/migrations/loaders.py +402 -0
- sqlspec/migrations/runner.py +49 -51
- sqlspec/migrations/tracker.py +31 -44
- sqlspec/migrations/utils.py +64 -24
- sqlspec/protocols.py +7 -183
- sqlspec/storage/__init__.py +1 -1
- sqlspec/storage/backends/base.py +37 -40
- sqlspec/storage/backends/fsspec.py +136 -112
- sqlspec/storage/backends/obstore.py +138 -160
- sqlspec/storage/capabilities.py +5 -4
- sqlspec/storage/registry.py +57 -106
- sqlspec/typing.py +136 -115
- sqlspec/utils/__init__.py +2 -3
- sqlspec/utils/correlation.py +0 -3
- sqlspec/utils/deprecation.py +6 -6
- sqlspec/utils/fixtures.py +6 -6
- sqlspec/utils/logging.py +0 -2
- sqlspec/utils/module_loader.py +7 -12
- sqlspec/utils/singleton.py +0 -1
- sqlspec/utils/sync_tools.py +16 -37
- sqlspec/utils/text.py +12 -51
- sqlspec/utils/type_guards.py +443 -232
- {sqlspec-0.14.0.dist-info → sqlspec-0.15.0.dist-info}/METADATA +7 -2
- sqlspec-0.15.0.dist-info/RECORD +134 -0
- sqlspec-0.15.0.dist-info/entry_points.txt +2 -0
- sqlspec/driver/connection.py +0 -207
- sqlspec/driver/mixins/_cache.py +0 -114
- sqlspec/driver/mixins/_csv_writer.py +0 -91
- sqlspec/driver/mixins/_pipeline.py +0 -508
- sqlspec/driver/mixins/_query_tools.py +0 -796
- sqlspec/driver/mixins/_result_utils.py +0 -138
- sqlspec/driver/mixins/_storage.py +0 -912
- sqlspec/driver/mixins/_type_coercion.py +0 -128
- sqlspec/driver/parameters.py +0 -138
- sqlspec/statement/__init__.py +0 -21
- sqlspec/statement/builder/_merge.py +0 -95
- sqlspec/statement/cache.py +0 -50
- sqlspec/statement/filters.py +0 -625
- sqlspec/statement/parameters.py +0 -996
- sqlspec/statement/pipelines/__init__.py +0 -210
- sqlspec/statement/pipelines/analyzers/__init__.py +0 -9
- sqlspec/statement/pipelines/analyzers/_analyzer.py +0 -646
- sqlspec/statement/pipelines/context.py +0 -115
- sqlspec/statement/pipelines/transformers/__init__.py +0 -7
- sqlspec/statement/pipelines/transformers/_expression_simplifier.py +0 -88
- sqlspec/statement/pipelines/transformers/_literal_parameterizer.py +0 -1247
- sqlspec/statement/pipelines/transformers/_remove_comments_and_hints.py +0 -76
- sqlspec/statement/pipelines/validators/__init__.py +0 -23
- sqlspec/statement/pipelines/validators/_dml_safety.py +0 -290
- sqlspec/statement/pipelines/validators/_parameter_style.py +0 -370
- sqlspec/statement/pipelines/validators/_performance.py +0 -714
- sqlspec/statement/pipelines/validators/_security.py +0 -967
- sqlspec/statement/result.py +0 -435
- sqlspec/statement/sql.py +0 -1774
- sqlspec/utils/cached_property.py +0 -25
- sqlspec/utils/statement_hashing.py +0 -203
- sqlspec-0.14.0.dist-info/RECORD +0 -143
- sqlspec-0.14.0.dist-info/entry_points.txt +0 -2
- /sqlspec/{statement/builder → builder}/mixins/_delete_operations.py +0 -0
- {sqlspec-0.14.0.dist-info → sqlspec-0.15.0.dist-info}/WHEEL +0 -0
- {sqlspec-0.14.0.dist-info → sqlspec-0.15.0.dist-info}/licenses/LICENSE +0 -0
- {sqlspec-0.14.0.dist-info → sqlspec-0.15.0.dist-info}/licenses/NOTICE +0 -0
sqlspec/config.py
CHANGED
|
@@ -1,21 +1,17 @@
|
|
|
1
1
|
from abc import ABC, abstractmethod
|
|
2
|
-
from
|
|
3
|
-
from typing import TYPE_CHECKING, Any, ClassVar, Generic, Optional, TypeVar, Union
|
|
2
|
+
from typing import TYPE_CHECKING, Any, Callable, ClassVar, Generic, Optional, TypeVar, Union
|
|
4
3
|
|
|
5
|
-
from
|
|
4
|
+
from typing_extensions import NotRequired, TypedDict
|
|
5
|
+
|
|
6
|
+
from sqlspec.core.parameters import ParameterStyle, ParameterStyleConfig
|
|
7
|
+
from sqlspec.core.statement import StatementConfig
|
|
6
8
|
from sqlspec.utils.logging import get_logger
|
|
7
9
|
|
|
8
10
|
if TYPE_CHECKING:
|
|
9
11
|
from collections.abc import Awaitable
|
|
10
12
|
from contextlib import AbstractAsyncContextManager, AbstractContextManager
|
|
11
13
|
|
|
12
|
-
from
|
|
13
|
-
|
|
14
|
-
from sqlspec.driver import AsyncDriverAdapterProtocol, SyncDriverAdapterProtocol
|
|
15
|
-
from sqlspec.statement.result import StatementResult
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
StatementResultType = Union["StatementResult[dict[str, Any]]", "StatementResult[Any]"]
|
|
14
|
+
from sqlspec.driver import AsyncDriverAdapterBase, SyncDriverAdapterBase
|
|
19
15
|
|
|
20
16
|
|
|
21
17
|
__all__ = (
|
|
@@ -24,10 +20,9 @@ __all__ = (
|
|
|
24
20
|
"ConfigT",
|
|
25
21
|
"DatabaseConfigProtocol",
|
|
26
22
|
"DriverT",
|
|
27
|
-
"
|
|
23
|
+
"LifecycleConfig",
|
|
28
24
|
"NoPoolAsyncConfig",
|
|
29
25
|
"NoPoolSyncConfig",
|
|
30
|
-
"StatementResultType",
|
|
31
26
|
"SyncConfigT",
|
|
32
27
|
"SyncDatabaseConfig",
|
|
33
28
|
)
|
|
@@ -38,74 +33,59 @@ ConfigT = TypeVar(
|
|
|
38
33
|
"ConfigT",
|
|
39
34
|
bound="Union[Union[AsyncDatabaseConfig[Any, Any, Any], NoPoolAsyncConfig[Any, Any]], SyncDatabaseConfig[Any, Any, Any], NoPoolSyncConfig[Any, Any]]",
|
|
40
35
|
)
|
|
41
|
-
|
|
36
|
+
|
|
37
|
+
# Define TypeVars for Generic classes
|
|
38
|
+
ConnectionT = TypeVar("ConnectionT")
|
|
39
|
+
PoolT = TypeVar("PoolT")
|
|
40
|
+
DriverT = TypeVar("DriverT", bound="Union[SyncDriverAdapterBase, AsyncDriverAdapterBase]")
|
|
42
41
|
|
|
43
42
|
logger = get_logger("config")
|
|
44
43
|
|
|
45
44
|
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
"""Protocol defining the interface for database configurations."""
|
|
45
|
+
class LifecycleConfig(TypedDict, total=False):
|
|
46
|
+
"""Universal lifecycle hooks for all adapters.
|
|
49
47
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
supports_native_arrow_import: "ClassVar[bool]" = field(init=False, default=False)
|
|
53
|
-
supports_native_arrow_export: "ClassVar[bool]" = field(init=False, default=False)
|
|
54
|
-
supports_native_parquet_import: "ClassVar[bool]" = field(init=False, default=False)
|
|
55
|
-
supports_native_parquet_export: "ClassVar[bool]" = field(init=False, default=False)
|
|
56
|
-
connection_type: "type[ConnectionT]" = field(init=False, repr=False, hash=False, compare=False)
|
|
57
|
-
driver_type: "type[DriverT]" = field(init=False, repr=False, hash=False, compare=False)
|
|
58
|
-
pool_instance: "Optional[PoolT]" = field(default=None)
|
|
59
|
-
default_row_type: "type[Any]" = field(init=False)
|
|
60
|
-
migration_config: "dict[str, Any]" = field(default_factory=dict)
|
|
61
|
-
"""Migration configuration settings."""
|
|
62
|
-
_dialect: "DialectType" = field(default=None, init=False, repr=False, hash=False, compare=False)
|
|
63
|
-
|
|
64
|
-
# Adapter-level cache configuration
|
|
65
|
-
enable_adapter_cache: bool = field(default=True)
|
|
66
|
-
"""Enable adapter-level SQL compilation caching."""
|
|
67
|
-
adapter_cache_size: int = field(default=500)
|
|
68
|
-
"""Maximum number of compiled SQL statements to cache per adapter."""
|
|
69
|
-
enable_prepared_statements: bool = field(default=False)
|
|
70
|
-
"""Enable prepared statement pooling for supported databases."""
|
|
71
|
-
prepared_statement_cache_size: int = field(default=100)
|
|
72
|
-
"""Maximum number of prepared statements to maintain."""
|
|
73
|
-
|
|
74
|
-
supported_parameter_styles: "ClassVar[tuple[str, ...]]" = ()
|
|
75
|
-
"""Parameter styles supported by this database adapter (e.g., ('qmark', 'named_colon'))."""
|
|
76
|
-
|
|
77
|
-
default_parameter_style: "ClassVar[str]" = "none"
|
|
78
|
-
"""The preferred/native parameter style for this database."""
|
|
48
|
+
Each hook accepts a list of callables to support multiple handlers.
|
|
49
|
+
"""
|
|
79
50
|
|
|
80
|
-
|
|
81
|
-
|
|
51
|
+
on_connection_create: NotRequired[list[Callable[[Any], None]]]
|
|
52
|
+
on_connection_destroy: NotRequired[list[Callable[[Any], None]]]
|
|
53
|
+
on_pool_create: NotRequired[list[Callable[[Any], None]]]
|
|
54
|
+
on_pool_destroy: NotRequired[list[Callable[[Any], None]]]
|
|
55
|
+
on_session_start: NotRequired[list[Callable[[Any], None]]]
|
|
56
|
+
on_session_end: NotRequired[list[Callable[[Any], None]]]
|
|
57
|
+
on_query_start: NotRequired[list[Callable[[str, dict], None]]]
|
|
58
|
+
on_query_complete: NotRequired[list[Callable[[str, dict, Any], None]]]
|
|
59
|
+
on_error: NotRequired[list[Callable[[Exception, str, dict], None]]]
|
|
82
60
|
|
|
83
|
-
@property
|
|
84
|
-
def dialect(self) -> "DialectType":
|
|
85
|
-
"""Get the SQL dialect type lazily.
|
|
86
61
|
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
dynamic dialect detection (e.g., ADBC which supports multiple databases),
|
|
90
|
-
it can override _get_dialect() to provide custom logic.
|
|
62
|
+
class DatabaseConfigProtocol(ABC, Generic[ConnectionT, PoolT, DriverT]):
|
|
63
|
+
"""Protocol defining the interface for database configurations."""
|
|
91
64
|
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
65
|
+
__slots__ = ("driver_features", "migration_config", "pool_instance", "statement_config")
|
|
66
|
+
driver_type: "ClassVar[type[Any]]"
|
|
67
|
+
connection_type: "ClassVar[type[Any]]"
|
|
68
|
+
is_async: "ClassVar[bool]" = False
|
|
69
|
+
supports_connection_pooling: "ClassVar[bool]" = False
|
|
70
|
+
supports_native_arrow_import: "ClassVar[bool]" = False
|
|
71
|
+
supports_native_arrow_export: "ClassVar[bool]" = False
|
|
72
|
+
supports_native_parquet_import: "ClassVar[bool]" = False
|
|
73
|
+
supports_native_parquet_export: "ClassVar[bool]" = False
|
|
74
|
+
statement_config: "StatementConfig"
|
|
75
|
+
pool_instance: "Optional[PoolT]"
|
|
76
|
+
migration_config: "dict[str, Any]"
|
|
98
77
|
|
|
99
|
-
def
|
|
100
|
-
|
|
78
|
+
def __hash__(self) -> int:
|
|
79
|
+
return id(self)
|
|
101
80
|
|
|
102
|
-
|
|
103
|
-
|
|
81
|
+
def __eq__(self, other: object) -> bool:
|
|
82
|
+
if not isinstance(other, type(self)):
|
|
83
|
+
return False
|
|
84
|
+
return bool(self.pool_instance == other.pool_instance and self.migration_config == other.migration_config)
|
|
104
85
|
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
""
|
|
108
|
-
return self.driver_type.dialect
|
|
86
|
+
def __repr__(self) -> str:
|
|
87
|
+
parts = ", ".join([f"pool_instance={self.pool_instance!r}", f"migration_config={self.migration_config!r}"])
|
|
88
|
+
return f"{type(self).__name__}({parts})"
|
|
109
89
|
|
|
110
90
|
@abstractmethod
|
|
111
91
|
def create_connection(self) -> "Union[ConnectionT, Awaitable[ConnectionT]]":
|
|
@@ -126,12 +106,6 @@ class DatabaseConfigProtocol(ABC, Generic[ConnectionT, PoolT, DriverT]):
|
|
|
126
106
|
"""Provide a database session context manager."""
|
|
127
107
|
raise NotImplementedError
|
|
128
108
|
|
|
129
|
-
@property
|
|
130
|
-
@abstractmethod
|
|
131
|
-
def connection_config_dict(self) -> "dict[str, Any]":
|
|
132
|
-
"""Return the connection configuration as a dict."""
|
|
133
|
-
raise NotImplementedError
|
|
134
|
-
|
|
135
109
|
@abstractmethod
|
|
136
110
|
def create_pool(self) -> "Union[PoolT, Awaitable[PoolT]]":
|
|
137
111
|
"""Create and return connection pool."""
|
|
@@ -159,46 +133,49 @@ class DatabaseConfigProtocol(ABC, Generic[ConnectionT, PoolT, DriverT]):
|
|
|
159
133
|
Returns:
|
|
160
134
|
Dictionary mapping type names to types.
|
|
161
135
|
"""
|
|
162
|
-
|
|
136
|
+
return {}
|
|
163
137
|
|
|
164
|
-
if hasattr(self, "driver_type") and self.driver_type:
|
|
165
|
-
namespace[self.driver_type.__name__] = self.driver_type
|
|
166
138
|
|
|
167
|
-
namespace[self.__class__.__name__] = self.__class__
|
|
168
|
-
|
|
169
|
-
if hasattr(self, "connection_type") and self.connection_type:
|
|
170
|
-
connection_type = self.connection_type
|
|
171
|
-
|
|
172
|
-
if hasattr(connection_type, "__args__"):
|
|
173
|
-
# It's a generic type, extract the actual types
|
|
174
|
-
for arg_type in connection_type.__args__: # type: ignore[attr-defined]
|
|
175
|
-
if arg_type and hasattr(arg_type, "__name__"):
|
|
176
|
-
namespace[arg_type.__name__] = arg_type
|
|
177
|
-
elif hasattr(connection_type, "__name__"):
|
|
178
|
-
# Regular type
|
|
179
|
-
namespace[connection_type.__name__] = connection_type
|
|
180
|
-
|
|
181
|
-
return namespace
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
@dataclass
|
|
185
139
|
class NoPoolSyncConfig(DatabaseConfigProtocol[ConnectionT, None, DriverT]):
|
|
186
140
|
"""Base class for a sync database configurations that do not implement a pool."""
|
|
187
141
|
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
142
|
+
__slots__ = ("connection_config",)
|
|
143
|
+
is_async: "ClassVar[bool]" = False
|
|
144
|
+
supports_connection_pooling: "ClassVar[bool]" = False
|
|
145
|
+
|
|
146
|
+
def __init__(
|
|
147
|
+
self,
|
|
148
|
+
*,
|
|
149
|
+
connection_config: Optional[dict[str, Any]] = None,
|
|
150
|
+
migration_config: "Optional[dict[str, Any]]" = None,
|
|
151
|
+
statement_config: "Optional[StatementConfig]" = None,
|
|
152
|
+
driver_features: "Optional[dict[str, Any]]" = None,
|
|
153
|
+
) -> None:
|
|
154
|
+
self.pool_instance = None
|
|
155
|
+
self.connection_config = connection_config or {}
|
|
156
|
+
self.migration_config: dict[str, Any] = migration_config if migration_config is not None else {}
|
|
157
|
+
|
|
158
|
+
if statement_config is None:
|
|
159
|
+
default_parameter_config = ParameterStyleConfig(
|
|
160
|
+
default_parameter_style=ParameterStyle.QMARK, supported_parameter_styles={ParameterStyle.QMARK}
|
|
161
|
+
)
|
|
162
|
+
self.statement_config = StatementConfig(dialect="sqlite", parameter_config=default_parameter_config)
|
|
163
|
+
else:
|
|
164
|
+
self.statement_config = statement_config
|
|
165
|
+
self.driver_features = driver_features or {}
|
|
191
166
|
|
|
192
167
|
def create_connection(self) -> ConnectionT:
|
|
193
|
-
"""Create
|
|
168
|
+
"""Create a database connection."""
|
|
194
169
|
raise NotImplementedError
|
|
195
170
|
|
|
196
171
|
def provide_connection(self, *args: Any, **kwargs: Any) -> "AbstractContextManager[ConnectionT]":
|
|
197
|
-
"""Provide connection
|
|
172
|
+
"""Provide a database connection context manager."""
|
|
198
173
|
raise NotImplementedError
|
|
199
174
|
|
|
200
|
-
def provide_session(
|
|
201
|
-
""
|
|
175
|
+
def provide_session(
|
|
176
|
+
self, *args: Any, statement_config: "Optional[StatementConfig]" = None, **kwargs: Any
|
|
177
|
+
) -> "AbstractContextManager[DriverT]":
|
|
178
|
+
"""Provide a database session context manager."""
|
|
202
179
|
raise NotImplementedError
|
|
203
180
|
|
|
204
181
|
def create_pool(self) -> None:
|
|
@@ -211,24 +188,47 @@ class NoPoolSyncConfig(DatabaseConfigProtocol[ConnectionT, None, DriverT]):
|
|
|
211
188
|
return None
|
|
212
189
|
|
|
213
190
|
|
|
214
|
-
@dataclass
|
|
215
191
|
class NoPoolAsyncConfig(DatabaseConfigProtocol[ConnectionT, None, DriverT]):
|
|
216
192
|
"""Base class for an async database configurations that do not implement a pool."""
|
|
217
193
|
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
194
|
+
__slots__ = ("connection_config",)
|
|
195
|
+
|
|
196
|
+
is_async: "ClassVar[bool]" = True
|
|
197
|
+
supports_connection_pooling: "ClassVar[bool]" = False
|
|
198
|
+
|
|
199
|
+
def __init__(
|
|
200
|
+
self,
|
|
201
|
+
*,
|
|
202
|
+
connection_config: "Optional[dict[str, Any]]" = None,
|
|
203
|
+
migration_config: "Optional[dict[str, Any]]" = None,
|
|
204
|
+
statement_config: "Optional[StatementConfig]" = None,
|
|
205
|
+
driver_features: "Optional[dict[str, Any]]" = None,
|
|
206
|
+
) -> None:
|
|
207
|
+
self.pool_instance = None
|
|
208
|
+
self.connection_config = connection_config or {}
|
|
209
|
+
self.migration_config: dict[str, Any] = migration_config if migration_config is not None else {}
|
|
210
|
+
|
|
211
|
+
if statement_config is None:
|
|
212
|
+
default_parameter_config = ParameterStyleConfig(
|
|
213
|
+
default_parameter_style=ParameterStyle.QMARK, supported_parameter_styles={ParameterStyle.QMARK}
|
|
214
|
+
)
|
|
215
|
+
self.statement_config = StatementConfig(dialect="sqlite", parameter_config=default_parameter_config)
|
|
216
|
+
else:
|
|
217
|
+
self.statement_config = statement_config
|
|
218
|
+
self.driver_features = driver_features or {}
|
|
221
219
|
|
|
222
220
|
async def create_connection(self) -> ConnectionT:
|
|
223
|
-
"""Create
|
|
221
|
+
"""Create a database connection."""
|
|
224
222
|
raise NotImplementedError
|
|
225
223
|
|
|
226
224
|
def provide_connection(self, *args: Any, **kwargs: Any) -> "AbstractAsyncContextManager[ConnectionT]":
|
|
227
|
-
"""Provide connection
|
|
225
|
+
"""Provide a database connection context manager."""
|
|
228
226
|
raise NotImplementedError
|
|
229
227
|
|
|
230
|
-
def provide_session(
|
|
231
|
-
""
|
|
228
|
+
def provide_session(
|
|
229
|
+
self, *args: Any, statement_config: "Optional[StatementConfig]" = None, **kwargs: Any
|
|
230
|
+
) -> "AbstractAsyncContextManager[DriverT]":
|
|
231
|
+
"""Provide a database session context manager."""
|
|
232
232
|
raise NotImplementedError
|
|
233
233
|
|
|
234
234
|
async def create_pool(self) -> None:
|
|
@@ -241,20 +241,38 @@ class NoPoolAsyncConfig(DatabaseConfigProtocol[ConnectionT, None, DriverT]):
|
|
|
241
241
|
return None
|
|
242
242
|
|
|
243
243
|
|
|
244
|
-
@dataclass
|
|
245
|
-
class GenericPoolConfig:
|
|
246
|
-
"""Generic Database Pool Configuration."""
|
|
247
|
-
|
|
248
|
-
|
|
249
|
-
@dataclass
|
|
250
244
|
class SyncDatabaseConfig(DatabaseConfigProtocol[ConnectionT, PoolT, DriverT]):
|
|
251
245
|
"""Generic Sync Database Configuration."""
|
|
252
246
|
|
|
253
|
-
|
|
254
|
-
|
|
247
|
+
__slots__ = ("pool_config",)
|
|
248
|
+
|
|
249
|
+
is_async: "ClassVar[bool]" = False
|
|
250
|
+
supports_connection_pooling: "ClassVar[bool]" = True
|
|
251
|
+
|
|
252
|
+
def __init__(
|
|
253
|
+
self,
|
|
254
|
+
*,
|
|
255
|
+
pool_config: "Optional[dict[str, Any]]" = None,
|
|
256
|
+
pool_instance: "Optional[PoolT]" = None,
|
|
257
|
+
migration_config: "Optional[dict[str, Any]]" = None,
|
|
258
|
+
statement_config: "Optional[StatementConfig]" = None,
|
|
259
|
+
driver_features: "Optional[dict[str, Any]]" = None,
|
|
260
|
+
) -> None:
|
|
261
|
+
self.pool_instance = pool_instance
|
|
262
|
+
self.pool_config = pool_config or {}
|
|
263
|
+
self.migration_config: dict[str, Any] = migration_config if migration_config is not None else {}
|
|
264
|
+
|
|
265
|
+
if statement_config is None:
|
|
266
|
+
default_parameter_config = ParameterStyleConfig(
|
|
267
|
+
default_parameter_style=ParameterStyle.QMARK, supported_parameter_styles={ParameterStyle.QMARK}
|
|
268
|
+
)
|
|
269
|
+
self.statement_config = StatementConfig(dialect="postgres", parameter_config=default_parameter_config)
|
|
270
|
+
else:
|
|
271
|
+
self.statement_config = statement_config
|
|
272
|
+
self.driver_features = driver_features or {}
|
|
255
273
|
|
|
256
274
|
def create_pool(self) -> PoolT:
|
|
257
|
-
"""Create
|
|
275
|
+
"""Create and return the connection pool.
|
|
258
276
|
|
|
259
277
|
Returns:
|
|
260
278
|
The created pool.
|
|
@@ -265,7 +283,7 @@ class SyncDatabaseConfig(DatabaseConfigProtocol[ConnectionT, PoolT, DriverT]):
|
|
|
265
283
|
return self.pool_instance
|
|
266
284
|
|
|
267
285
|
def close_pool(self) -> None:
|
|
268
|
-
"""Close
|
|
286
|
+
"""Close the connection pool."""
|
|
269
287
|
self._close_pool()
|
|
270
288
|
|
|
271
289
|
def provide_pool(self, *args: Any, **kwargs: Any) -> PoolT:
|
|
@@ -275,15 +293,17 @@ class SyncDatabaseConfig(DatabaseConfigProtocol[ConnectionT, PoolT, DriverT]):
|
|
|
275
293
|
return self.pool_instance
|
|
276
294
|
|
|
277
295
|
def create_connection(self) -> ConnectionT:
|
|
278
|
-
"""Create
|
|
296
|
+
"""Create a database connection."""
|
|
279
297
|
raise NotImplementedError
|
|
280
298
|
|
|
281
299
|
def provide_connection(self, *args: Any, **kwargs: Any) -> "AbstractContextManager[ConnectionT]":
|
|
282
|
-
"""Provide connection
|
|
300
|
+
"""Provide a database connection context manager."""
|
|
283
301
|
raise NotImplementedError
|
|
284
302
|
|
|
285
|
-
def provide_session(
|
|
286
|
-
""
|
|
303
|
+
def provide_session(
|
|
304
|
+
self, *args: Any, statement_config: "Optional[StatementConfig]" = None, **kwargs: Any
|
|
305
|
+
) -> "AbstractContextManager[DriverT]":
|
|
306
|
+
"""Provide a database session context manager."""
|
|
287
307
|
raise NotImplementedError
|
|
288
308
|
|
|
289
309
|
@abstractmethod
|
|
@@ -297,15 +317,40 @@ class SyncDatabaseConfig(DatabaseConfigProtocol[ConnectionT, PoolT, DriverT]):
|
|
|
297
317
|
raise NotImplementedError
|
|
298
318
|
|
|
299
319
|
|
|
300
|
-
@dataclass
|
|
301
320
|
class AsyncDatabaseConfig(DatabaseConfigProtocol[ConnectionT, PoolT, DriverT]):
|
|
302
321
|
"""Generic Async Database Configuration."""
|
|
303
322
|
|
|
304
|
-
|
|
305
|
-
|
|
323
|
+
__slots__ = ("pool_config",)
|
|
324
|
+
|
|
325
|
+
is_async: "ClassVar[bool]" = True
|
|
326
|
+
supports_connection_pooling: "ClassVar[bool]" = True
|
|
327
|
+
|
|
328
|
+
def __init__(
|
|
329
|
+
self,
|
|
330
|
+
*,
|
|
331
|
+
pool_config: "Optional[dict[str, Any]]" = None,
|
|
332
|
+
pool_instance: "Optional[PoolT]" = None,
|
|
333
|
+
migration_config: "Optional[dict[str, Any]]" = None,
|
|
334
|
+
statement_config: "Optional[StatementConfig]" = None,
|
|
335
|
+
driver_features: "Optional[dict[str, Any]]" = None,
|
|
336
|
+
) -> None:
|
|
337
|
+
self.pool_instance = pool_instance
|
|
338
|
+
self.pool_config = pool_config or {}
|
|
339
|
+
self.migration_config: dict[str, Any] = migration_config if migration_config is not None else {}
|
|
340
|
+
|
|
341
|
+
if statement_config is None:
|
|
342
|
+
self.statement_config = StatementConfig(
|
|
343
|
+
parameter_config=ParameterStyleConfig(
|
|
344
|
+
default_parameter_style=ParameterStyle.QMARK, supported_parameter_styles={ParameterStyle.QMARK}
|
|
345
|
+
),
|
|
346
|
+
dialect="postgres",
|
|
347
|
+
)
|
|
348
|
+
else:
|
|
349
|
+
self.statement_config = statement_config
|
|
350
|
+
self.driver_features = driver_features or {}
|
|
306
351
|
|
|
307
352
|
async def create_pool(self) -> PoolT:
|
|
308
|
-
"""Create
|
|
353
|
+
"""Create and return the connection pool.
|
|
309
354
|
|
|
310
355
|
Returns:
|
|
311
356
|
The created pool.
|
|
@@ -316,7 +361,7 @@ class AsyncDatabaseConfig(DatabaseConfigProtocol[ConnectionT, PoolT, DriverT]):
|
|
|
316
361
|
return self.pool_instance
|
|
317
362
|
|
|
318
363
|
async def close_pool(self) -> None:
|
|
319
|
-
"""Close
|
|
364
|
+
"""Close the connection pool."""
|
|
320
365
|
await self._close_pool()
|
|
321
366
|
|
|
322
367
|
async def provide_pool(self, *args: Any, **kwargs: Any) -> PoolT:
|
|
@@ -326,15 +371,17 @@ class AsyncDatabaseConfig(DatabaseConfigProtocol[ConnectionT, PoolT, DriverT]):
|
|
|
326
371
|
return self.pool_instance
|
|
327
372
|
|
|
328
373
|
async def create_connection(self) -> ConnectionT:
|
|
329
|
-
"""Create
|
|
374
|
+
"""Create a database connection."""
|
|
330
375
|
raise NotImplementedError
|
|
331
376
|
|
|
332
377
|
def provide_connection(self, *args: Any, **kwargs: Any) -> "AbstractAsyncContextManager[ConnectionT]":
|
|
333
|
-
"""Provide connection
|
|
378
|
+
"""Provide a database connection context manager."""
|
|
334
379
|
raise NotImplementedError
|
|
335
380
|
|
|
336
|
-
def provide_session(
|
|
337
|
-
""
|
|
381
|
+
def provide_session(
|
|
382
|
+
self, *args: Any, statement_config: "Optional[StatementConfig]" = None, **kwargs: Any
|
|
383
|
+
) -> "AbstractAsyncContextManager[DriverT]":
|
|
384
|
+
"""Provide a database session context manager."""
|
|
338
385
|
raise NotImplementedError
|
|
339
386
|
|
|
340
387
|
@abstractmethod
|
sqlspec/core/__init__.py
ADDED
|
@@ -0,0 +1,63 @@
|
|
|
1
|
+
"""SQLSpec Core Module - SQL Processing System.
|
|
2
|
+
|
|
3
|
+
This module provides the core SQL processing components including statement handling,
|
|
4
|
+
parameter processing, compilation, and result management.
|
|
5
|
+
|
|
6
|
+
Components:
|
|
7
|
+
- statement.py: SQL class with StatementConfig
|
|
8
|
+
- parameters.py: Parameter processing pipeline
|
|
9
|
+
- compiler.py: SQL compilation with caching
|
|
10
|
+
- result.py: Result classes for query execution
|
|
11
|
+
- filters.py: Statement filter system
|
|
12
|
+
- cache.py: Unified caching system
|
|
13
|
+
- splitter.py: SQL statement splitter
|
|
14
|
+
- hashing.py: Cache key generation
|
|
15
|
+
"""
|
|
16
|
+
|
|
17
|
+
from sqlspec.core import filters
|
|
18
|
+
from sqlspec.core.cache import CacheConfig, CacheStats, UnifiedCache, get_statement_cache
|
|
19
|
+
from sqlspec.core.compiler import OperationType, SQLProcessor
|
|
20
|
+
from sqlspec.core.filters import StatementFilter
|
|
21
|
+
from sqlspec.core.hashing import (
|
|
22
|
+
hash_expression,
|
|
23
|
+
hash_expression_node,
|
|
24
|
+
hash_optimized_expression,
|
|
25
|
+
hash_parameters,
|
|
26
|
+
hash_sql_statement,
|
|
27
|
+
)
|
|
28
|
+
from sqlspec.core.parameters import (
|
|
29
|
+
ParameterConverter,
|
|
30
|
+
ParameterProcessor,
|
|
31
|
+
ParameterStyle,
|
|
32
|
+
ParameterStyleConfig,
|
|
33
|
+
TypedParameter,
|
|
34
|
+
)
|
|
35
|
+
from sqlspec.core.result import ArrowResult, SQLResult, StatementResult
|
|
36
|
+
from sqlspec.core.statement import SQL, Statement, StatementConfig
|
|
37
|
+
|
|
38
|
+
__all__ = (
|
|
39
|
+
"SQL",
|
|
40
|
+
"ArrowResult",
|
|
41
|
+
"CacheConfig",
|
|
42
|
+
"CacheStats",
|
|
43
|
+
"OperationType",
|
|
44
|
+
"ParameterConverter",
|
|
45
|
+
"ParameterProcessor",
|
|
46
|
+
"ParameterStyle",
|
|
47
|
+
"ParameterStyleConfig",
|
|
48
|
+
"SQLProcessor",
|
|
49
|
+
"SQLResult",
|
|
50
|
+
"Statement",
|
|
51
|
+
"StatementConfig",
|
|
52
|
+
"StatementFilter",
|
|
53
|
+
"StatementResult",
|
|
54
|
+
"TypedParameter",
|
|
55
|
+
"UnifiedCache",
|
|
56
|
+
"filters",
|
|
57
|
+
"get_statement_cache",
|
|
58
|
+
"hash_expression",
|
|
59
|
+
"hash_expression_node",
|
|
60
|
+
"hash_optimized_expression",
|
|
61
|
+
"hash_parameters",
|
|
62
|
+
"hash_sql_statement",
|
|
63
|
+
)
|