Coverage for /pythoncovmergedfiles/medio/medio/usr/local/lib/python3.11/site-packages/sqlalchemy/engine/interfaces.py: 83%

Shortcuts on this page

r m x   toggle line displays

j k   next/prev highlighted chunk

0   (zero) top of page

1   (one) first highlighted chunk

718 statements  

1# engine/interfaces.py 

2# Copyright (C) 2005-2026 the SQLAlchemy authors and contributors 

3# <see AUTHORS file> 

4# 

5# This module is part of SQLAlchemy and is released under 

6# the MIT License: https://www.opensource.org/licenses/mit-license.php 

7 

8"""Define core interfaces used by the engine system.""" 

9 

10from __future__ import annotations 

11 

12from enum import Enum 

13from typing import Any 

14from typing import Awaitable 

15from typing import Callable 

16from typing import ClassVar 

17from typing import Collection 

18from typing import Dict 

19from typing import Iterable 

20from typing import Iterator 

21from typing import List 

22from typing import Literal 

23from typing import Mapping 

24from typing import MutableMapping 

25from typing import Optional 

26from typing import Protocol 

27from typing import Sequence 

28from typing import Set 

29from typing import Tuple 

30from typing import Type 

31from typing import TYPE_CHECKING 

32from typing import TypedDict 

33from typing import TypeVar 

34from typing import Union 

35 

36from .. import util 

37from ..event import EventTarget 

38from ..pool import Pool 

39from ..pool import PoolProxiedConnection as PoolProxiedConnection 

40from ..sql.compiler import Compiled as Compiled 

41from ..sql.compiler import Compiled # noqa 

42from ..sql.compiler import TypeCompiler as TypeCompiler 

43from ..sql.compiler import TypeCompiler # noqa 

44from ..util import immutabledict 

45from ..util.concurrency import await_ 

46from ..util.typing import NotRequired 

47 

48if TYPE_CHECKING: 

49 from .base import Connection 

50 from .base import Engine 

51 from .cursor import CursorResult 

52 from .url import URL 

53 from ..connectors.asyncio import AsyncIODBAPIConnection 

54 from ..event import _ListenerFnType 

55 from ..event import dispatcher 

56 from ..exc import StatementError 

57 from ..sql import Executable 

58 from ..sql.compiler import _InsertManyValuesBatch 

59 from ..sql.compiler import AggregateOrderByStyle 

60 from ..sql.compiler import DDLCompiler 

61 from ..sql.compiler import IdentifierPreparer 

62 from ..sql.compiler import InsertmanyvaluesSentinelOpts 

63 from ..sql.compiler import Linting 

64 from ..sql.compiler import SQLCompiler 

65 from ..sql.elements import BindParameter 

66 from ..sql.elements import ClauseElement 

67 from ..sql.schema import Column 

68 from ..sql.schema import DefaultGenerator 

69 from ..sql.schema import SchemaItem 

70 from ..sql.schema import Sequence as Sequence_SchemaItem 

71 from ..sql.sqltypes import _JSON_VALUE 

72 from ..sql.sqltypes import Integer 

73 from ..sql.type_api import _TypeMemoDict 

74 from ..sql.type_api import TypeEngine 

75 from ..util.langhelpers import generic_fn_descriptor 

76 

77ConnectArgsType = Tuple[Sequence[str], MutableMapping[str, Any]] 

78 

79_T = TypeVar("_T", bound="Any") 

80 

81 

82class CacheStats(Enum): 

83 CACHE_HIT = 0 

84 CACHE_MISS = 1 

85 CACHING_DISABLED = 2 

86 NO_CACHE_KEY = 3 

87 NO_DIALECT_SUPPORT = 4 

88 

89 

90class ExecuteStyle(Enum): 

91 """indicates the :term:`DBAPI` cursor method that will be used to invoke 

92 a statement.""" 

93 

94 EXECUTE = 0 

95 """indicates cursor.execute() will be used""" 

96 

97 EXECUTEMANY = 1 

98 """indicates cursor.executemany() will be used.""" 

99 

100 INSERTMANYVALUES = 2 

101 """indicates cursor.execute() will be used with an INSERT where the 

102 VALUES expression will be expanded to accommodate for multiple 

103 parameter sets 

104 

105 .. seealso:: 

106 

107 :ref:`engine_insertmanyvalues` 

108 

109 """ 

110 

111 

112class DBAPIModule(Protocol): 

113 class Error(Exception): 

114 def __getattr__(self, key: str) -> Any: ... 

115 

116 class OperationalError(Error): 

117 pass 

118 

119 class InterfaceError(Error): 

120 pass 

121 

122 class IntegrityError(Error): 

123 pass 

124 

125 def __getattr__(self, key: str) -> Any: ... 

126 

127 

128class DBAPIConnection(Protocol): 

129 """protocol representing a :pep:`249` database connection. 

130 

131 .. versionadded:: 2.0 

132 

133 .. seealso:: 

134 

135 `Connection Objects <https://www.python.org/dev/peps/pep-0249/#connection-objects>`_ 

136 - in :pep:`249` 

137 

138 """ # noqa: E501 

139 

140 def close(self) -> None: ... 

141 

142 def commit(self) -> None: ... 

143 

144 def cursor(self, *args: Any, **kwargs: Any) -> DBAPICursor: ... 

145 

146 def rollback(self) -> None: ... 

147 

148 def __getattr__(self, key: str) -> Any: ... 

149 

150 def __setattr__(self, key: str, value: Any) -> None: ... 

151 

152 

153class DBAPIType(Protocol): 

154 """protocol representing a :pep:`249` database type. 

155 

156 .. versionadded:: 2.0 

157 

158 .. seealso:: 

159 

160 `Type Objects <https://www.python.org/dev/peps/pep-0249/#type-objects>`_ 

161 - in :pep:`249` 

162 

163 """ # noqa: E501 

164 

165 

166class DBAPICursor(Protocol): 

167 """protocol representing a :pep:`249` database cursor. 

168 

169 .. versionadded:: 2.0 

170 

171 .. seealso:: 

172 

173 `Cursor Objects <https://www.python.org/dev/peps/pep-0249/#cursor-objects>`_ 

174 - in :pep:`249` 

175 

176 """ # noqa: E501 

177 

178 @property 

179 def description( 

180 self, 

181 ) -> _DBAPICursorDescription: 

182 """The description attribute of the Cursor. 

183 

184 .. seealso:: 

185 

186 `cursor.description <https://www.python.org/dev/peps/pep-0249/#description>`_ 

187 - in :pep:`249` 

188 

189 

190 """ # noqa: E501 

191 ... 

192 

193 @property 

194 def rowcount(self) -> int: ... 

195 

196 arraysize: int 

197 

198 lastrowid: int 

199 

200 def close(self) -> None: ... 

201 

202 def execute( 

203 self, 

204 operation: Any, 

205 parameters: Optional[_DBAPISingleExecuteParams] = None, 

206 ) -> Any: ... 

207 

208 def executemany( 

209 self, 

210 operation: Any, 

211 parameters: _DBAPIMultiExecuteParams, 

212 ) -> Any: ... 

213 

214 def fetchone(self) -> Optional[Any]: ... 

215 

216 def fetchmany(self, size: int = ...) -> Sequence[Any]: ... 

217 

218 def fetchall(self) -> Sequence[Any]: ... 

219 

220 def setinputsizes(self, sizes: Sequence[Any]) -> None: ... 

221 

222 def setoutputsize(self, size: Any, column: Any) -> None: ... 

223 

224 def callproc( 

225 self, procname: str, parameters: Sequence[Any] = ... 

226 ) -> Any: ... 

227 

228 def nextset(self) -> Optional[bool]: ... 

229 

230 def __getattr__(self, key: str) -> Any: ... 

231 

232 

233_CoreSingleExecuteParams = Mapping[str, Any] 

234_MutableCoreSingleExecuteParams = MutableMapping[str, Any] 

235_CoreMultiExecuteParams = Sequence[_CoreSingleExecuteParams] 

236_CoreAnyExecuteParams = Union[ 

237 _CoreMultiExecuteParams, _CoreSingleExecuteParams 

238] 

239 

240_DBAPISingleExecuteParams = Union[Sequence[Any], _CoreSingleExecuteParams] 

241 

242_DBAPIMultiExecuteParams = Union[ 

243 Sequence[Sequence[Any]], _CoreMultiExecuteParams 

244] 

245_DBAPIAnyExecuteParams = Union[ 

246 _DBAPIMultiExecuteParams, _DBAPISingleExecuteParams 

247] 

248_DBAPICursorDescription = Sequence[ 

249 Tuple[ 

250 str, 

251 "DBAPIType", 

252 Optional[int], 

253 Optional[int], 

254 Optional[int], 

255 Optional[int], 

256 Optional[bool], 

257 ] 

258] 

259 

260_AnySingleExecuteParams = _DBAPISingleExecuteParams 

261_AnyMultiExecuteParams = _DBAPIMultiExecuteParams 

262_AnyExecuteParams = _DBAPIAnyExecuteParams 

263 

264CompiledCacheType = MutableMapping[Any, "Compiled"] 

265SchemaTranslateMapType = Mapping[Optional[str], Optional[str]] 

266 

267_ImmutableExecuteOptions = immutabledict[str, Any] 

268 

269_ParamStyle = Literal[ 

270 "qmark", "numeric", "named", "format", "pyformat", "numeric_dollar" 

271] 

272 

273_GenericSetInputSizesType = List[Tuple[str, Any, "TypeEngine[Any]"]] 

274 

275IsolationLevel = Literal[ 

276 "SERIALIZABLE", 

277 "REPEATABLE READ", 

278 "READ COMMITTED", 

279 "READ UNCOMMITTED", 

280 "AUTOCOMMIT", 

281] 

282 

283 

284class _CoreKnownExecutionOptions(TypedDict, total=False): 

285 compiled_cache: Optional[CompiledCacheType] 

286 logging_token: str 

287 isolation_level: IsolationLevel 

288 no_parameters: bool 

289 stream_results: bool 

290 max_row_buffer: int 

291 yield_per: int 

292 insertmanyvalues_page_size: int 

293 schema_translate_map: Optional[SchemaTranslateMapType] 

294 preserve_rowcount: bool 

295 driver_column_names: bool 

296 

297 

298_ExecuteOptions = immutabledict[str, Any] 

299CoreExecuteOptionsParameter = Union[ 

300 _CoreKnownExecutionOptions, Mapping[str, Any] 

301] 

302 

303 

304class ReflectedIdentity(TypedDict): 

305 """represent the reflected IDENTITY structure of a column, corresponding 

306 to the :class:`_schema.Identity` construct. 

307 

308 The :class:`.ReflectedIdentity` structure is part of the 

309 :class:`.ReflectedColumn` structure, which is returned by the 

310 :meth:`.Inspector.get_columns` method. 

311 

312 """ 

313 

314 always: bool 

315 """type of identity column""" 

316 

317 on_null: bool 

318 """indicates ON NULL""" 

319 

320 start: int 

321 """starting index of the sequence""" 

322 

323 increment: int 

324 """increment value of the sequence""" 

325 

326 minvalue: int 

327 """the minimum value of the sequence.""" 

328 

329 maxvalue: int 

330 """the maximum value of the sequence.""" 

331 

332 nominvalue: bool 

333 """no minimum value of the sequence.""" 

334 

335 nomaxvalue: bool 

336 """no maximum value of the sequence.""" 

337 

338 cycle: bool 

339 """allows the sequence to wrap around when the maxvalue 

340 or minvalue has been reached.""" 

341 

342 cache: Optional[int] 

343 """number of future values in the 

344 sequence which are calculated in advance.""" 

345 

346 order: bool 

347 """if true, renders the ORDER keyword.""" 

348 

349 

350class ReflectedComputed(TypedDict): 

351 """Represent the reflected elements of a computed column, corresponding 

352 to the :class:`_schema.Computed` construct. 

353 

354 The :class:`.ReflectedComputed` structure is part of the 

355 :class:`.ReflectedColumn` structure, which is returned by the 

356 :meth:`.Inspector.get_columns` method. 

357 

358 """ 

359 

360 sqltext: str 

361 """the expression used to generate this column returned 

362 as a string SQL expression""" 

363 

364 persisted: NotRequired[bool] 

365 """indicates if the value is stored in the table or computed on demand""" 

366 

367 

368class ReflectedColumn(TypedDict): 

369 """Dictionary representing the reflected elements corresponding to 

370 a :class:`_schema.Column` object. 

371 

372 The :class:`.ReflectedColumn` structure is returned by the 

373 :class:`.Inspector.get_columns` method. 

374 

375 """ 

376 

377 name: str 

378 """column name""" 

379 

380 type: TypeEngine[Any] 

381 """column type represented as a :class:`.TypeEngine` instance.""" 

382 

383 nullable: bool 

384 """boolean flag if the column is NULL or NOT NULL""" 

385 

386 default: Optional[str] 

387 """column default expression as a SQL string""" 

388 

389 autoincrement: NotRequired[bool] 

390 """database-dependent autoincrement flag. 

391 

392 This flag indicates if the column has a database-side "autoincrement" 

393 flag of some kind. Within SQLAlchemy, other kinds of columns may 

394 also act as an "autoincrement" column without necessarily having 

395 such a flag on them. 

396 

397 See :paramref:`_schema.Column.autoincrement` for more background on 

398 "autoincrement". 

399 

400 """ 

401 

402 comment: NotRequired[Optional[str]] 

403 """comment for the column, if present. 

404 Only some dialects return this key 

405 """ 

406 

407 computed: NotRequired[ReflectedComputed] 

408 """indicates that this column is computed by the database. 

409 Only some dialects return this key. 

410 """ 

411 

412 identity: NotRequired[ReflectedIdentity] 

413 """indicates this column is an IDENTITY column. 

414 Only some dialects return this key. 

415 

416 .. versionadded:: 1.4 - added support for identity column reflection. 

417 """ 

418 

419 dialect_options: NotRequired[Dict[str, Any]] 

420 """Additional dialect-specific options detected for this reflected 

421 object""" 

422 

423 

424class ReflectedConstraint(TypedDict): 

425 """Dictionary representing the reflected elements corresponding to 

426 :class:`.Constraint` 

427 

428 A base class for all constraints 

429 """ 

430 

431 name: Optional[str] 

432 """constraint name""" 

433 

434 comment: NotRequired[Optional[str]] 

435 """comment for the constraint, if present""" 

436 

437 

438class ReflectedCheckConstraint(ReflectedConstraint): 

439 """Dictionary representing the reflected elements corresponding to 

440 :class:`.CheckConstraint`. 

441 

442 The :class:`.ReflectedCheckConstraint` structure is returned by the 

443 :meth:`.Inspector.get_check_constraints` method. 

444 

445 """ 

446 

447 sqltext: str 

448 """the check constraint's SQL expression""" 

449 

450 dialect_options: NotRequired[Dict[str, Any]] 

451 """Additional dialect-specific options detected for this check constraint 

452 """ 

453 

454 

455class ReflectedUniqueConstraint(ReflectedConstraint): 

456 """Dictionary representing the reflected elements corresponding to 

457 :class:`.UniqueConstraint`. 

458 

459 The :class:`.ReflectedUniqueConstraint` structure is returned by the 

460 :meth:`.Inspector.get_unique_constraints` method. 

461 

462 """ 

463 

464 column_names: List[str] 

465 """column names which comprise the unique constraint""" 

466 

467 duplicates_index: NotRequired[Optional[str]] 

468 "Indicates if this unique constraint duplicates an index with this name" 

469 

470 dialect_options: NotRequired[Dict[str, Any]] 

471 """Additional dialect-specific options detected for this unique 

472 constraint""" 

473 

474 

475class ReflectedPrimaryKeyConstraint(ReflectedConstraint): 

476 """Dictionary representing the reflected elements corresponding to 

477 :class:`.PrimaryKeyConstraint`. 

478 

479 The :class:`.ReflectedPrimaryKeyConstraint` structure is returned by the 

480 :meth:`.Inspector.get_pk_constraint` method. 

481 

482 """ 

483 

484 constrained_columns: List[str] 

485 """column names which comprise the primary key""" 

486 

487 dialect_options: NotRequired[Dict[str, Any]] 

488 """Additional dialect-specific options detected for this primary key""" 

489 

490 

491class ReflectedForeignKeyConstraint(ReflectedConstraint): 

492 """Dictionary representing the reflected elements corresponding to 

493 :class:`.ForeignKeyConstraint`. 

494 

495 The :class:`.ReflectedForeignKeyConstraint` structure is returned by 

496 the :meth:`.Inspector.get_foreign_keys` method. 

497 

498 """ 

499 

500 constrained_columns: List[str] 

501 """local column names which comprise the foreign key""" 

502 

503 referred_schema: Optional[str] 

504 """schema name of the table being referred""" 

505 

506 referred_table: str 

507 """name of the table being referred""" 

508 

509 referred_columns: List[str] 

510 """referred column names that correspond to ``constrained_columns``""" 

511 

512 options: NotRequired[Dict[str, Any]] 

513 """Additional options detected for this foreign key constraint""" 

514 

515 

516class ReflectedIndex(TypedDict): 

517 """Dictionary representing the reflected elements corresponding to 

518 :class:`.Index`. 

519 

520 The :class:`.ReflectedIndex` structure is returned by the 

521 :meth:`.Inspector.get_indexes` method. 

522 

523 """ 

524 

525 name: Optional[str] 

526 """index name""" 

527 

528 column_names: List[Optional[str]] 

529 """column names which the index references. 

530 An element of this list is ``None`` if it's an expression and is 

531 returned in the ``expressions`` list. 

532 """ 

533 

534 expressions: NotRequired[List[str]] 

535 """Expressions that compose the index. This list, when present, contains 

536 both plain column names (that are also in ``column_names``) and 

537 expressions (that are ``None`` in ``column_names``). 

538 """ 

539 

540 unique: bool 

541 """whether or not the index has a unique flag""" 

542 

543 duplicates_constraint: NotRequired[Optional[str]] 

544 "Indicates if this index mirrors a constraint with this name" 

545 

546 include_columns: NotRequired[List[str]] 

547 """columns to include in the INCLUDE clause for supporting databases. 

548 

549 .. deprecated:: 2.0 

550 

551 Legacy value, will be replaced with 

552 ``index_dict["dialect_options"]["<dialect name>_include"]`` 

553 

554 """ 

555 

556 column_sorting: NotRequired[Dict[str, Tuple[str]]] 

557 """optional dict mapping column names or expressions to tuple of sort 

558 keywords, which may include ``asc``, ``desc``, ``nulls_first``, 

559 ``nulls_last``. 

560 """ 

561 

562 dialect_options: NotRequired[Dict[str, Any]] 

563 """Additional dialect-specific options detected for this index""" 

564 

565 

566class ReflectedTableComment(TypedDict): 

567 """Dictionary representing the reflected comment corresponding to 

568 the :attr:`_schema.Table.comment` attribute. 

569 

570 The :class:`.ReflectedTableComment` structure is returned by the 

571 :meth:`.Inspector.get_table_comment` method. 

572 

573 """ 

574 

575 text: Optional[str] 

576 """text of the comment""" 

577 

578 

579class BindTyping(Enum): 

580 """Define different methods of passing typing information for 

581 bound parameters in a statement to the database driver. 

582 

583 .. versionadded:: 2.0 

584 

585 """ 

586 

587 NONE = 1 

588 """No steps are taken to pass typing information to the database driver. 

589 

590 This is the default behavior for databases such as SQLite, MySQL / MariaDB, 

591 SQL Server. 

592 

593 """ 

594 

595 SETINPUTSIZES = 2 

596 """Use the pep-249 setinputsizes method. 

597 

598 This is only implemented for DBAPIs that support this method and for which 

599 the SQLAlchemy dialect has the appropriate infrastructure for that dialect 

600 set up. Current dialects include python-oracledb, cx_Oracle as well as 

601 optional support for SQL Server using pyodbc. 

602 

603 When using setinputsizes, dialects also have a means of only using the 

604 method for certain datatypes using include/exclude lists. 

605 

606 When SETINPUTSIZES is used, the :meth:`.Dialect.do_set_input_sizes` method 

607 is called for each statement executed which has bound parameters. 

608 

609 """ 

610 

611 RENDER_CASTS = 3 

612 """Render casts or other directives in the SQL string. 

613 

614 This method is used for all PostgreSQL dialects, including asyncpg, 

615 pg8000, psycopg, psycopg2. Dialects which implement this can choose 

616 which kinds of datatypes are explicitly cast in SQL statements and which 

617 aren't. 

618 

619 When RENDER_CASTS is used, the compiler will invoke the 

620 :meth:`.SQLCompiler.render_bind_cast` method for the rendered 

621 string representation of each :class:`.BindParameter` object whose 

622 dialect-level type sets the :attr:`.TypeEngine.render_bind_cast` attribute. 

623 

624 The :meth:`.SQLCompiler.render_bind_cast` is also used to render casts 

625 for one form of "insertmanyvalues" query, when both 

626 :attr:`.InsertmanyvaluesSentinelOpts.USE_INSERT_FROM_SELECT` and 

627 :attr:`.InsertmanyvaluesSentinelOpts.RENDER_SELECT_COL_CASTS` are set, 

628 where the casts are applied to the intermediary columns e.g. 

629 "INSERT INTO t (a, b, c) SELECT p0::TYP, p1::TYP, p2::TYP " 

630 "FROM (VALUES (?, ?), (?, ?), ...)". 

631 

632 .. versionadded:: 2.0.10 - :meth:`.SQLCompiler.render_bind_cast` is now 

633 used within some elements of the "insertmanyvalues" implementation. 

634 

635 

636 """ 

637 

638 

639VersionInfoType = Tuple[Union[int, str], ...] 

640TableKey = Tuple[Optional[str], str] 

641 

642 

643class Dialect(EventTarget): 

644 """Define the behavior of a specific database and DB-API combination. 

645 

646 Any aspect of metadata definition, SQL query generation, 

647 execution, result-set handling, or anything else which varies 

648 between databases is defined under the general category of the 

649 Dialect. The Dialect acts as a factory for other 

650 database-specific object implementations including 

651 ExecutionContext, Compiled, DefaultGenerator, and TypeEngine. 

652 

653 .. note:: Third party dialects should not subclass :class:`.Dialect` 

654 directly. Instead, subclass :class:`.default.DefaultDialect` or 

655 descendant class. 

656 

657 """ 

658 

659 CACHE_HIT = CacheStats.CACHE_HIT 

660 CACHE_MISS = CacheStats.CACHE_MISS 

661 CACHING_DISABLED = CacheStats.CACHING_DISABLED 

662 NO_CACHE_KEY = CacheStats.NO_CACHE_KEY 

663 NO_DIALECT_SUPPORT = CacheStats.NO_DIALECT_SUPPORT 

664 

665 dispatch: dispatcher[Dialect] 

666 

667 name: str 

668 """identifying name for the dialect from a DBAPI-neutral point of view 

669 (i.e. 'sqlite') 

670 """ 

671 

672 driver: str 

673 """identifying name for the dialect's DBAPI""" 

674 

675 dialect_description: str 

676 

677 dbapi: Optional[DBAPIModule] 

678 """A reference to the DBAPI module object itself. 

679 

680 SQLAlchemy dialects import DBAPI modules using the classmethod 

681 :meth:`.Dialect.import_dbapi`. The rationale is so that any dialect 

682 module can be imported and used to generate SQL statements without the 

683 need for the actual DBAPI driver to be installed. Only when an 

684 :class:`.Engine` is constructed using :func:`.create_engine` does the 

685 DBAPI get imported; at that point, the creation process will assign 

686 the DBAPI module to this attribute. 

687 

688 Dialects should therefore implement :meth:`.Dialect.import_dbapi` 

689 which will import the necessary module and return it, and then refer 

690 to ``self.dbapi`` in dialect code in order to refer to the DBAPI module 

691 contents. 

692 

693 .. versionchanged:: The :attr:`.Dialect.dbapi` attribute is exclusively 

694 used as the per-:class:`.Dialect`-instance reference to the DBAPI 

695 module. The previous not-fully-documented ``.Dialect.dbapi()`` 

696 classmethod is deprecated and replaced by :meth:`.Dialect.import_dbapi`. 

697 

698 """ 

699 

700 @util.non_memoized_property 

701 def loaded_dbapi(self) -> DBAPIModule: 

702 """same as .dbapi, but is never None; will raise an error if no 

703 DBAPI was set up. 

704 

705 .. versionadded:: 2.0 

706 

707 """ 

708 raise NotImplementedError() 

709 

710 positional: bool 

711 """True if the paramstyle for this Dialect is positional.""" 

712 

713 paramstyle: str 

714 """the paramstyle to be used (some DB-APIs support multiple 

715 paramstyles). 

716 """ 

717 

718 compiler_linting: Linting 

719 

720 statement_compiler: Type[SQLCompiler] 

721 """a :class:`.Compiled` class used to compile SQL statements""" 

722 

723 ddl_compiler: Type[DDLCompiler] 

724 """a :class:`.Compiled` class used to compile DDL statements""" 

725 

726 type_compiler_cls: ClassVar[Type[TypeCompiler]] 

727 """a :class:`.Compiled` class used to compile SQL type objects 

728 

729 .. versionadded:: 2.0 

730 

731 """ 

732 

733 type_compiler_instance: TypeCompiler 

734 """instance of a :class:`.Compiled` class used to compile SQL type 

735 objects 

736 

737 .. versionadded:: 2.0 

738 

739 """ 

740 

741 type_compiler: Any 

742 """legacy; this is a TypeCompiler class at the class level, a 

743 TypeCompiler instance at the instance level. 

744 

745 Refer to type_compiler_instance instead. 

746 

747 """ 

748 

749 preparer: Type[IdentifierPreparer] 

750 """a :class:`.IdentifierPreparer` class used to 

751 quote identifiers. 

752 """ 

753 

754 identifier_preparer: IdentifierPreparer 

755 """This element will refer to an instance of :class:`.IdentifierPreparer` 

756 once a :class:`.DefaultDialect` has been constructed. 

757 

758 """ 

759 

760 server_version_info: Optional[Tuple[Any, ...]] 

761 """a tuple containing a version number for the DB backend in use. 

762 

763 This value is only available for supporting dialects, and is 

764 typically populated during the initial connection to the database. 

765 """ 

766 

767 default_schema_name: Optional[str] 

768 """the name of the default schema. This value is only available for 

769 supporting dialects, and is typically populated during the 

770 initial connection to the database. 

771 

772 """ 

773 

774 # NOTE: this does not take into effect engine-level isolation level. 

775 # not clear if this should be changed, seems like it should 

776 default_isolation_level: Optional[IsolationLevel] 

777 """the isolation that is implicitly present on new connections""" 

778 

779 skip_autocommit_rollback: bool 

780 """Whether or not the :paramref:`.create_engine.skip_autocommit_rollback` 

781 parameter was set. 

782 

783 .. versionadded:: 2.0.43 

784 

785 """ 

786 

787 # create_engine() -> isolation_level currently goes here 

788 _on_connect_isolation_level: Optional[IsolationLevel] 

789 

790 execution_ctx_cls: Type[ExecutionContext] 

791 """a :class:`.ExecutionContext` class used to handle statement execution""" 

792 

793 execute_sequence_format: Union[ 

794 Type[Tuple[Any, ...]], Type[Tuple[List[Any]]] 

795 ] 

796 """either the 'tuple' or 'list' type, depending on what cursor.execute() 

797 accepts for the second argument (they vary).""" 

798 

799 supports_alter: bool 

800 """``True`` if the database supports ``ALTER TABLE`` - used only for 

801 generating foreign key constraints in certain circumstances 

802 """ 

803 

804 max_identifier_length: int 

805 """The maximum length of identifier names.""" 

806 max_index_name_length: Optional[int] 

807 """The maximum length of index names if different from 

808 ``max_identifier_length``.""" 

809 max_constraint_name_length: Optional[int] 

810 """The maximum length of constraint names if different from 

811 ``max_identifier_length``.""" 

812 

813 supports_server_side_cursors: Union[generic_fn_descriptor[bool], bool] 

814 """indicates if the dialect supports server side cursors""" 

815 

816 server_side_cursors: bool 

817 """deprecated; indicates if the dialect should attempt to use server 

818 side cursors by default""" 

819 

820 supports_sane_rowcount: bool 

821 """Indicate whether the dialect properly implements rowcount for 

822 ``UPDATE`` and ``DELETE`` statements. 

823 """ 

824 

825 supports_sane_multi_rowcount: bool 

826 """Indicate whether the dialect properly implements rowcount for 

827 ``UPDATE`` and ``DELETE`` statements when executed via 

828 executemany. 

829 """ 

830 

831 supports_empty_insert: bool 

832 """dialect supports INSERT () VALUES (), i.e. a plain INSERT with no 

833 columns in it. 

834 

835 This is not usually supported; an "empty" insert is typically 

836 suited using either "INSERT..DEFAULT VALUES" or 

837 "INSERT ... (col) VALUES (DEFAULT)". 

838 

839 """ 

840 

841 supports_default_values: bool 

842 """dialect supports INSERT... DEFAULT VALUES syntax""" 

843 

844 supports_default_metavalue: bool 

845 """dialect supports INSERT...(col) VALUES (DEFAULT) syntax. 

846 

847 Most databases support this in some way, e.g. SQLite supports it using 

848 ``VALUES (NULL)``. MS SQL Server supports the syntax also however 

849 is the only included dialect where we have this disabled, as 

850 MSSQL does not support the field for the IDENTITY column, which is 

851 usually where we like to make use of the feature. 

852 

853 """ 

854 

855 default_metavalue_token: str = "DEFAULT" 

856 """for INSERT... VALUES (DEFAULT) syntax, the token to put in the 

857 parenthesis. 

858 

859 E.g. for SQLite this is the keyword "NULL". 

860 

861 """ 

862 

863 supports_multivalues_insert: bool 

864 """Target database supports INSERT...VALUES with multiple value 

865 sets, i.e. INSERT INTO table (cols) VALUES (...), (...), (...), ... 

866 

867 """ 

868 

869 _json_serializer: Callable[[_JSON_VALUE], str] | None 

870 

871 _json_deserializer: Callable[[str], _JSON_VALUE] | None 

872 

873 supports_native_json_serialization: bool 

874 """target dialect includes a native JSON serializer, eliminating 

875 the need to use json.dumps() for JSON data 

876 

877 .. versionadded:: 2.1 

878 

879 """ 

880 

881 supports_native_json_deserialization: bool 

882 """target dialect includes a native JSON deserializer, eliminating 

883 the need to use json.loads() for JSON data 

884 

885 .. versionadded:: 2.1 

886 

887 """ 

888 

889 dialect_injects_custom_json_deserializer: bool 

890 """target dialect, when given a custom _json_deserializer, needs to 

891 inject this handler at the connection/cursor level, rather than 

892 having JSON data returned as a string to be handled by the type 

893 

894 ..versionadded:: 2.1 

895 

896 """ 

897 

898 aggregate_order_by_style: AggregateOrderByStyle 

899 """Style of ORDER BY supported for arbitrary aggregate functions 

900 

901 .. versionadded:: 2.1 

902 

903 """ 

904 

905 insert_executemany_returning: bool 

906 """dialect / driver / database supports some means of providing 

907 INSERT...RETURNING support when dialect.do_executemany() is used. 

908 

909 """ 

910 

911 insert_executemany_returning_sort_by_parameter_order: bool 

912 """dialect / driver / database supports some means of providing 

913 INSERT...RETURNING support when dialect.do_executemany() is used 

914 along with the :paramref:`_dml.Insert.returning.sort_by_parameter_order` 

915 parameter being set. 

916 

917 """ 

918 

919 update_executemany_returning: bool 

920 """dialect supports UPDATE..RETURNING with executemany.""" 

921 

922 delete_executemany_returning: bool 

923 """dialect supports DELETE..RETURNING with executemany.""" 

924 

925 use_insertmanyvalues: bool 

926 """if True, indicates "insertmanyvalues" functionality should be used 

927 to allow for ``insert_executemany_returning`` behavior, if possible. 

928 

929 In practice, setting this to True means: 

930 

931 if ``supports_multivalues_insert``, ``insert_returning`` and 

932 ``use_insertmanyvalues`` are all True, the SQL compiler will produce 

933 an INSERT that will be interpreted by the :class:`.DefaultDialect` 

934 as an :attr:`.ExecuteStyle.INSERTMANYVALUES` execution that allows 

935 for INSERT of many rows with RETURNING by rewriting a single-row 

936 INSERT statement to have multiple VALUES clauses, also executing 

937 the statement multiple times for a series of batches when large numbers 

938 of rows are given. 

939 

940 The parameter is False for the default dialect, and is set to True for 

941 SQLAlchemy internal dialects SQLite, MySQL/MariaDB, PostgreSQL, SQL Server. 

942 It remains at False for Oracle Database, which provides native "executemany 

943 with RETURNING" support and also does not support 

944 ``supports_multivalues_insert``. For MySQL/MariaDB, those MySQL dialects 

945 that don't support RETURNING will not report 

946 ``insert_executemany_returning`` as True. 

947 

948 .. versionadded:: 2.0 

949 

950 .. seealso:: 

951 

952 :ref:`engine_insertmanyvalues` 

953 

954 """ 

955 

956 use_insertmanyvalues_wo_returning: bool 

957 """if True, and use_insertmanyvalues is also True, INSERT statements 

958 that don't include RETURNING will also use "insertmanyvalues". 

959 

960 .. versionadded:: 2.0 

961 

962 .. seealso:: 

963 

964 :ref:`engine_insertmanyvalues` 

965 

966 """ 

967 

968 insertmanyvalues_implicit_sentinel: InsertmanyvaluesSentinelOpts 

969 """Options indicating the database supports a form of bulk INSERT where 

970 the autoincrement integer primary key can be reliably used as an ordering 

971 for INSERTed rows. 

972 

973 .. versionadded:: 2.0.10 

974 

975 .. seealso:: 

976 

977 :ref:`engine_insertmanyvalues_returning_order` 

978 

979 """ 

980 

981 insertmanyvalues_page_size: int 

982 """Number of rows to render into an individual INSERT..VALUES() statement 

983 for :attr:`.ExecuteStyle.INSERTMANYVALUES` executions. 

984 

985 The default dialect defaults this to 1000. 

986 

987 .. versionadded:: 2.0 

988 

989 .. seealso:: 

990 

991 :paramref:`_engine.Connection.execution_options.insertmanyvalues_page_size` - 

992 execution option available on :class:`_engine.Connection`, statements 

993 

994 """ # noqa: E501 

995 

996 insertmanyvalues_max_parameters: int 

997 """Alternate to insertmanyvalues_page_size, will additionally limit 

998 page size based on number of parameters total in the statement. 

999 

1000 

1001 """ 

1002 

1003 preexecute_autoincrement_sequences: bool 

1004 """True if 'implicit' primary key functions must be executed separately 

1005 in order to get their value, if RETURNING is not used. 

1006 

1007 This is currently oriented towards PostgreSQL when the 

1008 ``implicit_returning=False`` parameter is used on a :class:`.Table` 

1009 object. 

1010 

1011 """ 

1012 

1013 insert_returning: bool 

1014 """if the dialect supports RETURNING with INSERT 

1015 

1016 .. versionadded:: 2.0 

1017 

1018 """ 

1019 

1020 update_returning: bool 

1021 """if the dialect supports RETURNING with UPDATE 

1022 

1023 .. versionadded:: 2.0 

1024 

1025 """ 

1026 

1027 update_returning_multifrom: bool 

1028 """if the dialect supports RETURNING with UPDATE..FROM 

1029 

1030 .. versionadded:: 2.0 

1031 

1032 """ 

1033 

1034 delete_returning: bool 

1035 """if the dialect supports RETURNING with DELETE 

1036 

1037 .. versionadded:: 2.0 

1038 

1039 """ 

1040 

1041 delete_returning_multifrom: bool 

1042 """if the dialect supports RETURNING with DELETE..FROM 

1043 

1044 .. versionadded:: 2.0 

1045 

1046 """ 

1047 

1048 favor_returning_over_lastrowid: bool 

1049 """for backends that support both a lastrowid and a RETURNING insert 

1050 strategy, favor RETURNING for simple single-int pk inserts. 

1051 

1052 cursor.lastrowid tends to be more performant on most backends. 

1053 

1054 """ 

1055 

1056 supports_identity_columns: bool 

1057 """target database supports IDENTITY""" 

1058 

1059 cte_follows_insert: bool 

1060 """target database, when given a CTE with an INSERT statement, needs 

1061 the CTE to be below the INSERT""" 

1062 

1063 colspecs: MutableMapping[Type[TypeEngine[Any]], Type[TypeEngine[Any]]] 

1064 """A dictionary of TypeEngine classes from sqlalchemy.types mapped 

1065 to subclasses that are specific to the dialect class. This 

1066 dictionary is class-level only and is not accessed from the 

1067 dialect instance itself. 

1068 """ 

1069 

1070 supports_sequences: bool 

1071 """Indicates if the dialect supports CREATE SEQUENCE or similar.""" 

1072 

1073 sequences_optional: bool 

1074 """If True, indicates if the :paramref:`_schema.Sequence.optional` 

1075 parameter on the :class:`_schema.Sequence` construct 

1076 should signal to not generate a CREATE SEQUENCE. Applies only to 

1077 dialects that support sequences. Currently used only to allow PostgreSQL 

1078 SERIAL to be used on a column that specifies Sequence() for usage on 

1079 other backends. 

1080 """ 

1081 

1082 default_sequence_base: int 

1083 """the default value that will be rendered as the "START WITH" portion of 

1084 a CREATE SEQUENCE DDL statement. 

1085 

1086 """ 

1087 

1088 supports_native_enum: bool 

1089 """Indicates if the dialect supports a native ENUM construct. 

1090 This will prevent :class:`_types.Enum` from generating a CHECK 

1091 constraint when that type is used in "native" mode. 

1092 """ 

1093 

1094 supports_native_boolean: bool 

1095 """Indicates if the dialect supports a native boolean construct. 

1096 This will prevent :class:`_types.Boolean` from generating a CHECK 

1097 constraint when that type is used. 

1098 """ 

1099 

1100 supports_native_decimal: bool 

1101 """indicates if Decimal objects are handled and returned for precision 

1102 numeric types, or if floats are returned""" 

1103 

1104 supports_native_uuid: bool 

1105 """indicates if Python UUID() objects are handled natively by the 

1106 driver for SQL UUID datatypes. 

1107 

1108 .. versionadded:: 2.0 

1109 

1110 """ 

1111 

1112 returns_native_bytes: bool 

1113 """indicates if Python bytes() objects are returned natively by the 

1114 driver for SQL "binary" datatypes. 

1115 

1116 .. versionadded:: 2.0.11 

1117 

1118 """ 

1119 

1120 construct_arguments: Optional[ 

1121 List[Tuple[Type[Union[SchemaItem, ClauseElement]], Mapping[str, Any]]] 

1122 ] = None 

1123 """Optional set of argument specifiers for various SQLAlchemy 

1124 constructs, typically schema items. 

1125 

1126 To implement, establish as a series of tuples, as in:: 

1127 

1128 construct_arguments = [ 

1129 (schema.Index, {"using": False, "where": None, "ops": None}), 

1130 ] 

1131 

1132 If the above construct is established on the PostgreSQL dialect, 

1133 the :class:`.Index` construct will now accept the keyword arguments 

1134 ``postgresql_using``, ``postgresql_where``, and ``postgresql_ops``. 

1135 Any other argument specified to the constructor of :class:`.Index` 

1136 which is prefixed with ``postgresql_`` will raise :class:`.ArgumentError`. 

1137 

1138 A dialect which does not include a ``construct_arguments`` member will 

1139 not participate in the argument validation system. For such a dialect, 

1140 any argument name is accepted by all participating constructs, within 

1141 the namespace of arguments prefixed with that dialect name. The rationale 

1142 here is so that third-party dialects that haven't yet implemented this 

1143 feature continue to function in the old way. 

1144 

1145 .. seealso:: 

1146 

1147 :class:`.DialectKWArgs` - implementing base class which consumes 

1148 :attr:`.DefaultDialect.construct_arguments` 

1149 

1150 

1151 """ 

1152 

1153 reflection_options: Sequence[str] = () 

1154 """Sequence of string names indicating keyword arguments that can be 

1155 established on a :class:`.Table` object which will be passed as 

1156 "reflection options" when using :paramref:`.Table.autoload_with`. 

1157 

1158 Current example is "oracle_resolve_synonyms" in the Oracle Database 

1159 dialects. 

1160 

1161 """ 

1162 

1163 dbapi_exception_translation_map: Mapping[str, str] = util.EMPTY_DICT 

1164 """A dictionary of names that will contain as values the names of 

1165 pep-249 exceptions ("IntegrityError", "OperationalError", etc) 

1166 keyed to alternate class names, to support the case where a 

1167 DBAPI has exception classes that aren't named as they are 

1168 referred to (e.g. IntegrityError = MyException). In the vast 

1169 majority of cases this dictionary is empty. 

1170 """ 

1171 

1172 supports_comments: bool 

1173 """Indicates the dialect supports comment DDL on tables and columns.""" 

1174 

1175 inline_comments: bool 

1176 """Indicates the dialect supports comment DDL that's inline with the 

1177 definition of a Table or Column. If False, this implies that ALTER must 

1178 be used to set table and column comments.""" 

1179 

1180 supports_constraint_comments: bool 

1181 """Indicates if the dialect supports comment DDL on constraints. 

1182 

1183 .. versionadded:: 2.0 

1184 """ 

1185 

1186 _has_events = False 

1187 

1188 supports_statement_cache: bool = True 

1189 """indicates if this dialect supports caching. 

1190 

1191 All dialects that are compatible with statement caching should set this 

1192 flag to True directly on each dialect class and subclass that supports 

1193 it. SQLAlchemy tests that this flag is locally present on each dialect 

1194 subclass before it will use statement caching. This is to provide 

1195 safety for legacy or new dialects that are not yet fully tested to be 

1196 compliant with SQL statement caching. 

1197 

1198 .. versionadded:: 1.4.5 

1199 

1200 .. seealso:: 

1201 

1202 :ref:`engine_thirdparty_caching` 

1203 

1204 """ 

1205 

1206 _supports_statement_cache: bool 

1207 """internal evaluation for supports_statement_cache""" 

1208 

1209 bind_typing = BindTyping.NONE 

1210 """define a means of passing typing information to the database and/or 

1211 driver for bound parameters. 

1212 

1213 See :class:`.BindTyping` for values. 

1214 

1215 .. versionadded:: 2.0 

1216 

1217 """ 

1218 

1219 is_async: bool 

1220 """Whether or not this dialect is intended for asyncio use.""" 

1221 

1222 has_terminate: bool 

1223 """Whether or not this dialect has a separate "terminate" implementation 

1224 that does not block or require awaiting.""" 

1225 

1226 engine_config_types: Mapping[str, Any] 

1227 """a mapping of string keys that can be in an engine config linked to 

1228 type conversion functions. 

1229 

1230 """ 

1231 

1232 label_length: Optional[int] 

1233 """optional user-defined max length for SQL labels""" 

1234 

1235 include_set_input_sizes: Optional[Set[Any]] 

1236 """set of DBAPI type objects that should be included in 

1237 automatic cursor.setinputsizes() calls. 

1238 

1239 This is only used if bind_typing is BindTyping.SET_INPUT_SIZES 

1240 

1241 """ 

1242 

1243 exclude_set_input_sizes: Optional[Set[Any]] 

1244 """set of DBAPI type objects that should be excluded in 

1245 automatic cursor.setinputsizes() calls. 

1246 

1247 This is only used if bind_typing is BindTyping.SET_INPUT_SIZES 

1248 

1249 """ 

1250 

1251 supports_simple_order_by_label: bool 

1252 """target database supports ORDER BY <labelname>, where <labelname> 

1253 refers to a label in the columns clause of the SELECT""" 

1254 

1255 div_is_floordiv: bool 

1256 """target database treats the / division operator as "floor division" """ 

1257 

1258 tuple_in_values: bool 

1259 """target database supports tuple IN, i.e. (x, y) IN ((q, p), (r, z))""" 

1260 

1261 requires_name_normalize: bool 

1262 """Indicates symbol names are returned by the database in 

1263 UPPERCASED if they are case insensitive within the database. 

1264 If this is True, the methods normalize_name() 

1265 and denormalize_name() must be provided. 

1266 """ 

1267 

1268 _bind_typing_render_casts: bool 

1269 

1270 _type_memos: MutableMapping[TypeEngine[Any], _TypeMemoDict] 

1271 

1272 def _builtin_onconnect(self) -> Optional[_ListenerFnType]: 

1273 raise NotImplementedError() 

1274 

1275 def create_connect_args(self, url: URL) -> ConnectArgsType: 

1276 """Build DB-API compatible connection arguments. 

1277 

1278 Given a :class:`.URL` object, returns a tuple 

1279 consisting of a ``(*args, **kwargs)`` suitable to send directly 

1280 to the dbapi's connect function. The arguments are sent to the 

1281 :meth:`.Dialect.connect` method which then runs the DBAPI-level 

1282 ``connect()`` function. 

1283 

1284 The method typically makes use of the 

1285 :meth:`.URL.translate_connect_args` 

1286 method in order to generate a dictionary of options. 

1287 

1288 The default implementation is:: 

1289 

1290 def create_connect_args(self, url): 

1291 opts = url.translate_connect_args() 

1292 opts.update(url.query) 

1293 return ([], opts) 

1294 

1295 :param url: a :class:`.URL` object 

1296 

1297 :return: a tuple of ``(*args, **kwargs)`` which will be passed to the 

1298 :meth:`.Dialect.connect` method. 

1299 

1300 .. seealso:: 

1301 

1302 :meth:`.URL.translate_connect_args` 

1303 

1304 """ 

1305 

1306 raise NotImplementedError() 

1307 

1308 @classmethod 

1309 def import_dbapi(cls) -> DBAPIModule: 

1310 """Import the DBAPI module that is used by this dialect. 

1311 

1312 The Python module object returned here will be assigned as an 

1313 instance variable to a constructed dialect under the name 

1314 ``.dbapi``. 

1315 

1316 .. versionchanged:: 2.0 The :meth:`.Dialect.import_dbapi` class 

1317 method is renamed from the previous method ``.Dialect.dbapi()``, 

1318 which would be replaced at dialect instantiation time by the 

1319 DBAPI module itself, thus using the same name in two different ways. 

1320 If a ``.Dialect.dbapi()`` classmethod is present on a third-party 

1321 dialect, it will be used and a deprecation warning will be emitted. 

1322 

1323 """ 

1324 raise NotImplementedError() 

1325 

1326 def type_descriptor(self, typeobj: TypeEngine[_T]) -> TypeEngine[_T]: 

1327 """Transform a generic type to a dialect-specific type. 

1328 

1329 Dialect classes will usually use the 

1330 :func:`_types.adapt_type` function in the types module to 

1331 accomplish this. 

1332 

1333 The returned result is cached *per dialect class* so can 

1334 contain no dialect-instance state. 

1335 

1336 """ 

1337 

1338 raise NotImplementedError() 

1339 

1340 def initialize(self, connection: Connection) -> None: 

1341 """Called during strategized creation of the dialect with a 

1342 connection. 

1343 

1344 Allows dialects to configure options based on server version info or 

1345 other properties. 

1346 

1347 The connection passed here is a SQLAlchemy Connection object, 

1348 with full capabilities. 

1349 

1350 The initialize() method of the base dialect should be called via 

1351 super(). 

1352 

1353 .. note:: as of SQLAlchemy 1.4, this method is called **before** 

1354 any :meth:`_engine.Dialect.on_connect` hooks are called. 

1355 

1356 """ 

1357 

1358 if TYPE_CHECKING: 

1359 

1360 def _overrides_default(self, method_name: str) -> bool: ... 

1361 

1362 def get_columns( 

1363 self, 

1364 connection: Connection, 

1365 table_name: str, 

1366 schema: Optional[str] = None, 

1367 **kw: Any, 

1368 ) -> List[ReflectedColumn]: 

1369 """Return information about columns in ``table_name``. 

1370 

1371 Given a :class:`_engine.Connection`, a string 

1372 ``table_name``, and an optional string ``schema``, return column 

1373 information as a list of dictionaries 

1374 corresponding to the :class:`.ReflectedColumn` dictionary. 

1375 

1376 This is an internal dialect method. Applications should use 

1377 :meth:`.Inspector.get_columns`. 

1378 

1379 """ 

1380 

1381 raise NotImplementedError() 

1382 

1383 def get_multi_columns( 

1384 self, 

1385 connection: Connection, 

1386 *, 

1387 schema: Optional[str] = None, 

1388 filter_names: Optional[Collection[str]] = None, 

1389 **kw: Any, 

1390 ) -> Iterable[Tuple[TableKey, List[ReflectedColumn]]]: 

1391 """Return information about columns in all tables in the 

1392 given ``schema``. 

1393 

1394 This is an internal dialect method. Applications should use 

1395 :meth:`.Inspector.get_multi_columns`. 

1396 

1397 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1398 implementation that will call the single table method for 

1399 each object returned by :meth:`Dialect.get_table_names`, 

1400 :meth:`Dialect.get_view_names` or 

1401 :meth:`Dialect.get_materialized_view_names` depending on the 

1402 provided ``kind``. Dialects that want to support a faster 

1403 implementation should implement this method. 

1404 

1405 .. versionadded:: 2.0 

1406 

1407 """ 

1408 

1409 raise NotImplementedError() 

1410 

1411 def get_pk_constraint( 

1412 self, 

1413 connection: Connection, 

1414 table_name: str, 

1415 schema: Optional[str] = None, 

1416 **kw: Any, 

1417 ) -> ReflectedPrimaryKeyConstraint: 

1418 """Return information about the primary key constraint on 

1419 table_name`. 

1420 

1421 Given a :class:`_engine.Connection`, a string 

1422 ``table_name``, and an optional string ``schema``, return primary 

1423 key information as a dictionary corresponding to the 

1424 :class:`.ReflectedPrimaryKeyConstraint` dictionary. 

1425 

1426 This is an internal dialect method. Applications should use 

1427 :meth:`.Inspector.get_pk_constraint`. 

1428 

1429 """ 

1430 raise NotImplementedError() 

1431 

1432 def get_multi_pk_constraint( 

1433 self, 

1434 connection: Connection, 

1435 *, 

1436 schema: Optional[str] = None, 

1437 filter_names: Optional[Collection[str]] = None, 

1438 **kw: Any, 

1439 ) -> Iterable[Tuple[TableKey, ReflectedPrimaryKeyConstraint]]: 

1440 """Return information about primary key constraints in 

1441 all tables in the given ``schema``. 

1442 

1443 This is an internal dialect method. Applications should use 

1444 :meth:`.Inspector.get_multi_pk_constraint`. 

1445 

1446 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1447 implementation that will call the single table method for 

1448 each object returned by :meth:`Dialect.get_table_names`, 

1449 :meth:`Dialect.get_view_names` or 

1450 :meth:`Dialect.get_materialized_view_names` depending on the 

1451 provided ``kind``. Dialects that want to support a faster 

1452 implementation should implement this method. 

1453 

1454 .. versionadded:: 2.0 

1455 

1456 """ 

1457 raise NotImplementedError() 

1458 

1459 def get_foreign_keys( 

1460 self, 

1461 connection: Connection, 

1462 table_name: str, 

1463 schema: Optional[str] = None, 

1464 **kw: Any, 

1465 ) -> List[ReflectedForeignKeyConstraint]: 

1466 """Return information about foreign_keys in ``table_name``. 

1467 

1468 Given a :class:`_engine.Connection`, a string 

1469 ``table_name``, and an optional string ``schema``, return foreign 

1470 key information as a list of dicts corresponding to the 

1471 :class:`.ReflectedForeignKeyConstraint` dictionary. 

1472 

1473 This is an internal dialect method. Applications should use 

1474 :meth:`_engine.Inspector.get_foreign_keys`. 

1475 """ 

1476 

1477 raise NotImplementedError() 

1478 

1479 def get_multi_foreign_keys( 

1480 self, 

1481 connection: Connection, 

1482 *, 

1483 schema: Optional[str] = None, 

1484 filter_names: Optional[Collection[str]] = None, 

1485 **kw: Any, 

1486 ) -> Iterable[Tuple[TableKey, List[ReflectedForeignKeyConstraint]]]: 

1487 """Return information about foreign_keys in all tables 

1488 in the given ``schema``. 

1489 

1490 This is an internal dialect method. Applications should use 

1491 :meth:`_engine.Inspector.get_multi_foreign_keys`. 

1492 

1493 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1494 implementation that will call the single table method for 

1495 each object returned by :meth:`Dialect.get_table_names`, 

1496 :meth:`Dialect.get_view_names` or 

1497 :meth:`Dialect.get_materialized_view_names` depending on the 

1498 provided ``kind``. Dialects that want to support a faster 

1499 implementation should implement this method. 

1500 

1501 .. versionadded:: 2.0 

1502 

1503 """ 

1504 

1505 raise NotImplementedError() 

1506 

1507 def get_table_names( 

1508 self, connection: Connection, schema: Optional[str] = None, **kw: Any 

1509 ) -> List[str]: 

1510 """Return a list of table names for ``schema``. 

1511 

1512 This is an internal dialect method. Applications should use 

1513 :meth:`_engine.Inspector.get_table_names`. 

1514 

1515 """ 

1516 

1517 raise NotImplementedError() 

1518 

1519 def get_temp_table_names( 

1520 self, connection: Connection, schema: Optional[str] = None, **kw: Any 

1521 ) -> List[str]: 

1522 """Return a list of temporary table names on the given connection, 

1523 if supported by the underlying backend. 

1524 

1525 This is an internal dialect method. Applications should use 

1526 :meth:`_engine.Inspector.get_temp_table_names`. 

1527 

1528 """ 

1529 

1530 raise NotImplementedError() 

1531 

1532 def get_view_names( 

1533 self, connection: Connection, schema: Optional[str] = None, **kw: Any 

1534 ) -> List[str]: 

1535 """Return a list of all non-materialized view names available in the 

1536 database. 

1537 

1538 This is an internal dialect method. Applications should use 

1539 :meth:`_engine.Inspector.get_view_names`. 

1540 

1541 :param schema: schema name to query, if not the default schema. 

1542 

1543 """ 

1544 

1545 raise NotImplementedError() 

1546 

1547 def get_materialized_view_names( 

1548 self, connection: Connection, schema: Optional[str] = None, **kw: Any 

1549 ) -> List[str]: 

1550 """Return a list of all materialized view names available in the 

1551 database. 

1552 

1553 This is an internal dialect method. Applications should use 

1554 :meth:`_engine.Inspector.get_materialized_view_names`. 

1555 

1556 :param schema: schema name to query, if not the default schema. 

1557 

1558 .. versionadded:: 2.0 

1559 

1560 """ 

1561 

1562 raise NotImplementedError() 

1563 

1564 def get_sequence_names( 

1565 self, connection: Connection, schema: Optional[str] = None, **kw: Any 

1566 ) -> List[str]: 

1567 """Return a list of all sequence names available in the database. 

1568 

1569 This is an internal dialect method. Applications should use 

1570 :meth:`_engine.Inspector.get_sequence_names`. 

1571 

1572 :param schema: schema name to query, if not the default schema. 

1573 

1574 .. versionadded:: 1.4 

1575 """ 

1576 

1577 raise NotImplementedError() 

1578 

1579 def get_temp_view_names( 

1580 self, connection: Connection, schema: Optional[str] = None, **kw: Any 

1581 ) -> List[str]: 

1582 """Return a list of temporary view names on the given connection, 

1583 if supported by the underlying backend. 

1584 

1585 This is an internal dialect method. Applications should use 

1586 :meth:`_engine.Inspector.get_temp_view_names`. 

1587 

1588 """ 

1589 

1590 raise NotImplementedError() 

1591 

1592 def get_schema_names(self, connection: Connection, **kw: Any) -> List[str]: 

1593 """Return a list of all schema names available in the database. 

1594 

1595 This is an internal dialect method. Applications should use 

1596 :meth:`_engine.Inspector.get_schema_names`. 

1597 """ 

1598 raise NotImplementedError() 

1599 

1600 def get_view_definition( 

1601 self, 

1602 connection: Connection, 

1603 view_name: str, 

1604 schema: Optional[str] = None, 

1605 **kw: Any, 

1606 ) -> str: 

1607 """Return plain or materialized view definition. 

1608 

1609 This is an internal dialect method. Applications should use 

1610 :meth:`_engine.Inspector.get_view_definition`. 

1611 

1612 Given a :class:`_engine.Connection`, a string 

1613 ``view_name``, and an optional string ``schema``, return the view 

1614 definition. 

1615 """ 

1616 

1617 raise NotImplementedError() 

1618 

1619 def get_indexes( 

1620 self, 

1621 connection: Connection, 

1622 table_name: str, 

1623 schema: Optional[str] = None, 

1624 **kw: Any, 

1625 ) -> List[ReflectedIndex]: 

1626 """Return information about indexes in ``table_name``. 

1627 

1628 Given a :class:`_engine.Connection`, a string 

1629 ``table_name`` and an optional string ``schema``, return index 

1630 information as a list of dictionaries corresponding to the 

1631 :class:`.ReflectedIndex` dictionary. 

1632 

1633 This is an internal dialect method. Applications should use 

1634 :meth:`.Inspector.get_indexes`. 

1635 """ 

1636 

1637 raise NotImplementedError() 

1638 

1639 def get_multi_indexes( 

1640 self, 

1641 connection: Connection, 

1642 *, 

1643 schema: Optional[str] = None, 

1644 filter_names: Optional[Collection[str]] = None, 

1645 **kw: Any, 

1646 ) -> Iterable[Tuple[TableKey, List[ReflectedIndex]]]: 

1647 """Return information about indexes in in all tables 

1648 in the given ``schema``. 

1649 

1650 This is an internal dialect method. Applications should use 

1651 :meth:`.Inspector.get_multi_indexes`. 

1652 

1653 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1654 implementation that will call the single table method for 

1655 each object returned by :meth:`Dialect.get_table_names`, 

1656 :meth:`Dialect.get_view_names` or 

1657 :meth:`Dialect.get_materialized_view_names` depending on the 

1658 provided ``kind``. Dialects that want to support a faster 

1659 implementation should implement this method. 

1660 

1661 .. versionadded:: 2.0 

1662 

1663 """ 

1664 

1665 raise NotImplementedError() 

1666 

1667 def get_unique_constraints( 

1668 self, 

1669 connection: Connection, 

1670 table_name: str, 

1671 schema: Optional[str] = None, 

1672 **kw: Any, 

1673 ) -> List[ReflectedUniqueConstraint]: 

1674 r"""Return information about unique constraints in ``table_name``. 

1675 

1676 Given a string ``table_name`` and an optional string ``schema``, return 

1677 unique constraint information as a list of dicts corresponding 

1678 to the :class:`.ReflectedUniqueConstraint` dictionary. 

1679 

1680 This is an internal dialect method. Applications should use 

1681 :meth:`.Inspector.get_unique_constraints`. 

1682 """ 

1683 

1684 raise NotImplementedError() 

1685 

1686 def get_multi_unique_constraints( 

1687 self, 

1688 connection: Connection, 

1689 *, 

1690 schema: Optional[str] = None, 

1691 filter_names: Optional[Collection[str]] = None, 

1692 **kw: Any, 

1693 ) -> Iterable[Tuple[TableKey, List[ReflectedUniqueConstraint]]]: 

1694 """Return information about unique constraints in all tables 

1695 in the given ``schema``. 

1696 

1697 This is an internal dialect method. Applications should use 

1698 :meth:`.Inspector.get_multi_unique_constraints`. 

1699 

1700 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1701 implementation that will call the single table method for 

1702 each object returned by :meth:`Dialect.get_table_names`, 

1703 :meth:`Dialect.get_view_names` or 

1704 :meth:`Dialect.get_materialized_view_names` depending on the 

1705 provided ``kind``. Dialects that want to support a faster 

1706 implementation should implement this method. 

1707 

1708 .. versionadded:: 2.0 

1709 

1710 """ 

1711 

1712 raise NotImplementedError() 

1713 

1714 def get_check_constraints( 

1715 self, 

1716 connection: Connection, 

1717 table_name: str, 

1718 schema: Optional[str] = None, 

1719 **kw: Any, 

1720 ) -> List[ReflectedCheckConstraint]: 

1721 r"""Return information about check constraints in ``table_name``. 

1722 

1723 Given a string ``table_name`` and an optional string ``schema``, return 

1724 check constraint information as a list of dicts corresponding 

1725 to the :class:`.ReflectedCheckConstraint` dictionary. 

1726 

1727 This is an internal dialect method. Applications should use 

1728 :meth:`.Inspector.get_check_constraints`. 

1729 

1730 """ 

1731 

1732 raise NotImplementedError() 

1733 

1734 def get_multi_check_constraints( 

1735 self, 

1736 connection: Connection, 

1737 *, 

1738 schema: Optional[str] = None, 

1739 filter_names: Optional[Collection[str]] = None, 

1740 **kw: Any, 

1741 ) -> Iterable[Tuple[TableKey, List[ReflectedCheckConstraint]]]: 

1742 """Return information about check constraints in all tables 

1743 in the given ``schema``. 

1744 

1745 This is an internal dialect method. Applications should use 

1746 :meth:`.Inspector.get_multi_check_constraints`. 

1747 

1748 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1749 implementation that will call the single table method for 

1750 each object returned by :meth:`Dialect.get_table_names`, 

1751 :meth:`Dialect.get_view_names` or 

1752 :meth:`Dialect.get_materialized_view_names` depending on the 

1753 provided ``kind``. Dialects that want to support a faster 

1754 implementation should implement this method. 

1755 

1756 .. versionadded:: 2.0 

1757 

1758 """ 

1759 

1760 raise NotImplementedError() 

1761 

1762 def get_table_options( 

1763 self, 

1764 connection: Connection, 

1765 table_name: str, 

1766 schema: Optional[str] = None, 

1767 **kw: Any, 

1768 ) -> Dict[str, Any]: 

1769 """Return a dictionary of options specified when ``table_name`` 

1770 was created. 

1771 

1772 This is an internal dialect method. Applications should use 

1773 :meth:`_engine.Inspector.get_table_options`. 

1774 """ 

1775 raise NotImplementedError() 

1776 

1777 def get_multi_table_options( 

1778 self, 

1779 connection: Connection, 

1780 *, 

1781 schema: Optional[str] = None, 

1782 filter_names: Optional[Collection[str]] = None, 

1783 **kw: Any, 

1784 ) -> Iterable[Tuple[TableKey, Dict[str, Any]]]: 

1785 """Return a dictionary of options specified when the tables in the 

1786 given schema were created. 

1787 

1788 This is an internal dialect method. Applications should use 

1789 :meth:`_engine.Inspector.get_multi_table_options`. 

1790 

1791 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1792 implementation that will call the single table method for 

1793 each object returned by :meth:`Dialect.get_table_names`, 

1794 :meth:`Dialect.get_view_names` or 

1795 :meth:`Dialect.get_materialized_view_names` depending on the 

1796 provided ``kind``. Dialects that want to support a faster 

1797 implementation should implement this method. 

1798 

1799 .. versionadded:: 2.0 

1800 

1801 """ 

1802 raise NotImplementedError() 

1803 

1804 def get_table_comment( 

1805 self, 

1806 connection: Connection, 

1807 table_name: str, 

1808 schema: Optional[str] = None, 

1809 **kw: Any, 

1810 ) -> ReflectedTableComment: 

1811 r"""Return the "comment" for the table identified by ``table_name``. 

1812 

1813 Given a string ``table_name`` and an optional string ``schema``, return 

1814 table comment information as a dictionary corresponding to the 

1815 :class:`.ReflectedTableComment` dictionary. 

1816 

1817 This is an internal dialect method. Applications should use 

1818 :meth:`.Inspector.get_table_comment`. 

1819 

1820 :raise: ``NotImplementedError`` for dialects that don't support 

1821 comments. 

1822 

1823 """ 

1824 

1825 raise NotImplementedError() 

1826 

1827 def get_multi_table_comment( 

1828 self, 

1829 connection: Connection, 

1830 *, 

1831 schema: Optional[str] = None, 

1832 filter_names: Optional[Collection[str]] = None, 

1833 **kw: Any, 

1834 ) -> Iterable[Tuple[TableKey, ReflectedTableComment]]: 

1835 """Return information about the table comment in all tables 

1836 in the given ``schema``. 

1837 

1838 This is an internal dialect method. Applications should use 

1839 :meth:`_engine.Inspector.get_multi_table_comment`. 

1840 

1841 .. note:: The :class:`_engine.DefaultDialect` provides a default 

1842 implementation that will call the single table method for 

1843 each object returned by :meth:`Dialect.get_table_names`, 

1844 :meth:`Dialect.get_view_names` or 

1845 :meth:`Dialect.get_materialized_view_names` depending on the 

1846 provided ``kind``. Dialects that want to support a faster 

1847 implementation should implement this method. 

1848 

1849 .. versionadded:: 2.0 

1850 

1851 """ 

1852 

1853 raise NotImplementedError() 

1854 

1855 def normalize_name(self, name: str) -> str: 

1856 """convert the given name to lowercase if it is detected as 

1857 case insensitive. 

1858 

1859 This method is only used if the dialect defines 

1860 requires_name_normalize=True. 

1861 

1862 """ 

1863 raise NotImplementedError() 

1864 

1865 def denormalize_name(self, name: str) -> str: 

1866 """convert the given name to a case insensitive identifier 

1867 for the backend if it is an all-lowercase name. 

1868 

1869 This method is only used if the dialect defines 

1870 requires_name_normalize=True. 

1871 

1872 """ 

1873 raise NotImplementedError() 

1874 

1875 def has_table( 

1876 self, 

1877 connection: Connection, 

1878 table_name: str, 

1879 schema: Optional[str] = None, 

1880 **kw: Any, 

1881 ) -> bool: 

1882 """For internal dialect use, check the existence of a particular table 

1883 or view in the database. 

1884 

1885 Given a :class:`_engine.Connection` object, a string table_name and 

1886 optional schema name, return True if the given table exists in the 

1887 database, False otherwise. 

1888 

1889 This method serves as the underlying implementation of the 

1890 public facing :meth:`.Inspector.has_table` method, and is also used 

1891 internally to implement the "checkfirst" behavior for methods like 

1892 :meth:`_schema.Table.create` and :meth:`_schema.MetaData.create_all`. 

1893 

1894 .. note:: This method is used internally by SQLAlchemy, and is 

1895 published so that third-party dialects may provide an 

1896 implementation. It is **not** the public API for checking for table 

1897 presence. Please use the :meth:`.Inspector.has_table` method. 

1898 

1899 .. versionchanged:: 2.0:: :meth:`_engine.Dialect.has_table` now 

1900 formally supports checking for additional table-like objects: 

1901 

1902 * any type of views (plain or materialized) 

1903 * temporary tables of any kind 

1904 

1905 Previously, these two checks were not formally specified and 

1906 different dialects would vary in their behavior. The dialect 

1907 testing suite now includes tests for all of these object types, 

1908 and dialects to the degree that the backing database supports views 

1909 or temporary tables should seek to support locating these objects 

1910 for full compliance. 

1911 

1912 """ 

1913 

1914 raise NotImplementedError() 

1915 

1916 def has_index( 

1917 self, 

1918 connection: Connection, 

1919 table_name: str, 

1920 index_name: str, 

1921 schema: Optional[str] = None, 

1922 **kw: Any, 

1923 ) -> bool: 

1924 """Check the existence of a particular index name in the database. 

1925 

1926 Given a :class:`_engine.Connection` object, a string 

1927 ``table_name`` and string index name, return ``True`` if an index of 

1928 the given name on the given table exists, ``False`` otherwise. 

1929 

1930 The :class:`.DefaultDialect` implements this in terms of the 

1931 :meth:`.Dialect.has_table` and :meth:`.Dialect.get_indexes` methods, 

1932 however dialects can implement a more performant version. 

1933 

1934 This is an internal dialect method. Applications should use 

1935 :meth:`_engine.Inspector.has_index`. 

1936 

1937 .. versionadded:: 1.4 

1938 

1939 """ 

1940 

1941 raise NotImplementedError() 

1942 

1943 def has_sequence( 

1944 self, 

1945 connection: Connection, 

1946 sequence_name: str, 

1947 schema: Optional[str] = None, 

1948 **kw: Any, 

1949 ) -> bool: 

1950 """Check the existence of a particular sequence in the database. 

1951 

1952 Given a :class:`_engine.Connection` object and a string 

1953 `sequence_name`, return ``True`` if the given sequence exists in 

1954 the database, ``False`` otherwise. 

1955 

1956 This is an internal dialect method. Applications should use 

1957 :meth:`_engine.Inspector.has_sequence`. 

1958 """ 

1959 

1960 raise NotImplementedError() 

1961 

1962 def has_schema( 

1963 self, connection: Connection, schema_name: str, **kw: Any 

1964 ) -> bool: 

1965 """Check the existence of a particular schema name in the database. 

1966 

1967 Given a :class:`_engine.Connection` object, a string 

1968 ``schema_name``, return ``True`` if a schema of the 

1969 given exists, ``False`` otherwise. 

1970 

1971 The :class:`.DefaultDialect` implements this by checking 

1972 the presence of ``schema_name`` among the schemas returned by 

1973 :meth:`.Dialect.get_schema_names`, 

1974 however dialects can implement a more performant version. 

1975 

1976 This is an internal dialect method. Applications should use 

1977 :meth:`_engine.Inspector.has_schema`. 

1978 

1979 .. versionadded:: 2.0 

1980 

1981 """ 

1982 

1983 raise NotImplementedError() 

1984 

1985 def _get_server_version_info(self, connection: Connection) -> Any: 

1986 """Retrieve the server version info from the given connection. 

1987 

1988 This is used by the default implementation to populate the 

1989 "server_version_info" attribute and is called exactly 

1990 once upon first connect. 

1991 

1992 """ 

1993 

1994 raise NotImplementedError() 

1995 

1996 def _get_default_schema_name(self, connection: Connection) -> str: 

1997 """Return the string name of the currently selected schema from 

1998 the given connection. 

1999 

2000 This is used by the default implementation to populate the 

2001 "default_schema_name" attribute and is called exactly 

2002 once upon first connect. 

2003 

2004 """ 

2005 

2006 raise NotImplementedError() 

2007 

2008 def do_begin(self, dbapi_connection: PoolProxiedConnection) -> None: 

2009 """Provide an implementation of ``connection.begin()``, given a 

2010 DB-API connection. 

2011 

2012 The DBAPI has no dedicated "begin" method and it is expected 

2013 that transactions are implicit. This hook is provided for those 

2014 DBAPIs that might need additional help in this area. 

2015 

2016 :param dbapi_connection: a DBAPI connection, typically 

2017 proxied within a :class:`.ConnectionFairy`. 

2018 

2019 """ 

2020 

2021 raise NotImplementedError() 

2022 

2023 def do_rollback(self, dbapi_connection: PoolProxiedConnection) -> None: 

2024 """Provide an implementation of ``connection.rollback()``, given 

2025 a DB-API connection. 

2026 

2027 :param dbapi_connection: a DBAPI connection, typically 

2028 proxied within a :class:`.ConnectionFairy`. 

2029 

2030 """ 

2031 

2032 raise NotImplementedError() 

2033 

2034 def do_commit(self, dbapi_connection: PoolProxiedConnection) -> None: 

2035 """Provide an implementation of ``connection.commit()``, given a 

2036 DB-API connection. 

2037 

2038 :param dbapi_connection: a DBAPI connection, typically 

2039 proxied within a :class:`.ConnectionFairy`. 

2040 

2041 """ 

2042 

2043 raise NotImplementedError() 

2044 

2045 def do_terminate(self, dbapi_connection: DBAPIConnection) -> None: 

2046 """Provide an implementation of ``connection.close()`` that tries as 

2047 much as possible to not block, given a DBAPI 

2048 connection. 

2049 

2050 In the vast majority of cases this just calls .close(), however 

2051 for some asyncio dialects may call upon different API features. 

2052 

2053 This hook is called by the :class:`_pool.Pool` 

2054 when a connection is being recycled or has been invalidated. 

2055 

2056 .. versionadded:: 1.4.41 

2057 

2058 """ 

2059 

2060 raise NotImplementedError() 

2061 

2062 def do_close(self, dbapi_connection: DBAPIConnection) -> None: 

2063 """Provide an implementation of ``connection.close()``, given a DBAPI 

2064 connection. 

2065 

2066 This hook is called by the :class:`_pool.Pool` 

2067 when a connection has been 

2068 detached from the pool, or is being returned beyond the normal 

2069 capacity of the pool. 

2070 

2071 """ 

2072 

2073 raise NotImplementedError() 

2074 

2075 def _do_ping_w_event(self, dbapi_connection: DBAPIConnection) -> bool: 

2076 raise NotImplementedError() 

2077 

2078 def do_ping(self, dbapi_connection: DBAPIConnection) -> bool: 

2079 """ping the DBAPI connection and return True if the connection is 

2080 usable.""" 

2081 raise NotImplementedError() 

2082 

2083 def do_set_input_sizes( 

2084 self, 

2085 cursor: DBAPICursor, 

2086 list_of_tuples: _GenericSetInputSizesType, 

2087 context: ExecutionContext, 

2088 ) -> Any: 

2089 """invoke the cursor.setinputsizes() method with appropriate arguments 

2090 

2091 This hook is called if the :attr:`.Dialect.bind_typing` attribute is 

2092 set to the 

2093 :attr:`.BindTyping.SETINPUTSIZES` value. 

2094 Parameter data is passed in a list of tuples (paramname, dbtype, 

2095 sqltype), where ``paramname`` is the key of the parameter in the 

2096 statement, ``dbtype`` is the DBAPI datatype and ``sqltype`` is the 

2097 SQLAlchemy type. The order of tuples is in the correct parameter order. 

2098 

2099 .. versionadded:: 1.4 

2100 

2101 .. versionchanged:: 2.0 - setinputsizes mode is now enabled by 

2102 setting :attr:`.Dialect.bind_typing` to 

2103 :attr:`.BindTyping.SETINPUTSIZES`. Dialects which accept 

2104 a ``use_setinputsizes`` parameter should set this value 

2105 appropriately. 

2106 

2107 

2108 """ 

2109 raise NotImplementedError() 

2110 

2111 def create_xid(self) -> Any: 

2112 """Create a two-phase transaction ID. 

2113 

2114 This id will be passed to do_begin_twophase(), 

2115 do_rollback_twophase(), do_commit_twophase(). Its format is 

2116 unspecified. 

2117 """ 

2118 

2119 raise NotImplementedError() 

2120 

2121 def do_savepoint(self, connection: Connection, name: str) -> None: 

2122 """Create a savepoint with the given name. 

2123 

2124 :param connection: a :class:`_engine.Connection`. 

2125 :param name: savepoint name. 

2126 

2127 """ 

2128 

2129 raise NotImplementedError() 

2130 

2131 def do_rollback_to_savepoint( 

2132 self, connection: Connection, name: str 

2133 ) -> None: 

2134 """Rollback a connection to the named savepoint. 

2135 

2136 :param connection: a :class:`_engine.Connection`. 

2137 :param name: savepoint name. 

2138 

2139 """ 

2140 

2141 raise NotImplementedError() 

2142 

2143 def do_release_savepoint(self, connection: Connection, name: str) -> None: 

2144 """Release the named savepoint on a connection. 

2145 

2146 :param connection: a :class:`_engine.Connection`. 

2147 :param name: savepoint name. 

2148 """ 

2149 

2150 raise NotImplementedError() 

2151 

2152 def do_begin_twophase(self, connection: Connection, xid: Any) -> None: 

2153 """Begin a two phase transaction on the given connection. 

2154 

2155 :param connection: a :class:`_engine.Connection`. 

2156 :param xid: xid 

2157 

2158 """ 

2159 

2160 raise NotImplementedError() 

2161 

2162 def do_prepare_twophase(self, connection: Connection, xid: Any) -> None: 

2163 """Prepare a two phase transaction on the given connection. 

2164 

2165 :param connection: a :class:`_engine.Connection`. 

2166 :param xid: xid 

2167 

2168 """ 

2169 

2170 raise NotImplementedError() 

2171 

2172 def do_rollback_twophase( 

2173 self, 

2174 connection: Connection, 

2175 xid: Any, 

2176 is_prepared: bool = True, 

2177 recover: bool = False, 

2178 ) -> None: 

2179 """Rollback a two phase transaction on the given connection. 

2180 

2181 :param connection: a :class:`_engine.Connection`. 

2182 :param xid: xid 

2183 :param is_prepared: whether or not 

2184 :meth:`.TwoPhaseTransaction.prepare` was called. 

2185 :param recover: if the recover flag was passed. 

2186 

2187 """ 

2188 

2189 raise NotImplementedError() 

2190 

2191 def do_commit_twophase( 

2192 self, 

2193 connection: Connection, 

2194 xid: Any, 

2195 is_prepared: bool = True, 

2196 recover: bool = False, 

2197 ) -> None: 

2198 """Commit a two phase transaction on the given connection. 

2199 

2200 

2201 :param connection: a :class:`_engine.Connection`. 

2202 :param xid: xid 

2203 :param is_prepared: whether or not 

2204 :meth:`.TwoPhaseTransaction.prepare` was called. 

2205 :param recover: if the recover flag was passed. 

2206 

2207 """ 

2208 

2209 raise NotImplementedError() 

2210 

2211 def do_recover_twophase(self, connection: Connection) -> List[Any]: 

2212 """Recover list of uncommitted prepared two phase transaction 

2213 identifiers on the given connection. 

2214 

2215 :param connection: a :class:`_engine.Connection`. 

2216 

2217 """ 

2218 

2219 raise NotImplementedError() 

2220 

2221 def _deliver_insertmanyvalues_batches( 

2222 self, 

2223 connection: Connection, 

2224 cursor: DBAPICursor, 

2225 statement: str, 

2226 parameters: _DBAPIMultiExecuteParams, 

2227 generic_setinputsizes: Optional[_GenericSetInputSizesType], 

2228 context: ExecutionContext, 

2229 ) -> Iterator[_InsertManyValuesBatch]: 

2230 """convert executemany parameters for an INSERT into an iterator 

2231 of statement/single execute values, used by the insertmanyvalues 

2232 feature. 

2233 

2234 """ 

2235 raise NotImplementedError() 

2236 

2237 def do_executemany( 

2238 self, 

2239 cursor: DBAPICursor, 

2240 statement: str, 

2241 parameters: _DBAPIMultiExecuteParams, 

2242 context: Optional[ExecutionContext] = None, 

2243 ) -> None: 

2244 """Provide an implementation of ``cursor.executemany(statement, 

2245 parameters)``.""" 

2246 

2247 raise NotImplementedError() 

2248 

2249 def do_execute( 

2250 self, 

2251 cursor: DBAPICursor, 

2252 statement: str, 

2253 parameters: Optional[_DBAPISingleExecuteParams], 

2254 context: Optional[ExecutionContext] = None, 

2255 ) -> None: 

2256 """Provide an implementation of ``cursor.execute(statement, 

2257 parameters)``.""" 

2258 

2259 raise NotImplementedError() 

2260 

2261 def do_execute_no_params( 

2262 self, 

2263 cursor: DBAPICursor, 

2264 statement: str, 

2265 context: Optional[ExecutionContext] = None, 

2266 ) -> None: 

2267 """Provide an implementation of ``cursor.execute(statement)``. 

2268 

2269 The parameter collection should not be sent. 

2270 

2271 """ 

2272 

2273 raise NotImplementedError() 

2274 

2275 def is_disconnect( 

2276 self, 

2277 e: DBAPIModule.Error, 

2278 connection: Optional[Union[PoolProxiedConnection, DBAPIConnection]], 

2279 cursor: Optional[DBAPICursor], 

2280 ) -> bool: 

2281 """Return True if the given DB-API error indicates an invalid 

2282 connection""" 

2283 

2284 raise NotImplementedError() 

2285 

2286 def connect(self, *cargs: Any, **cparams: Any) -> DBAPIConnection: 

2287 r"""Establish a connection using this dialect's DBAPI. 

2288 

2289 The default implementation of this method is:: 

2290 

2291 def connect(self, *cargs, **cparams): 

2292 return self.dbapi.connect(*cargs, **cparams) 

2293 

2294 The ``*cargs, **cparams`` parameters are generated directly 

2295 from this dialect's :meth:`.Dialect.create_connect_args` method. 

2296 

2297 This method may be used for dialects that need to perform programmatic 

2298 per-connection steps when a new connection is procured from the 

2299 DBAPI. 

2300 

2301 

2302 :param \*cargs: positional parameters returned from the 

2303 :meth:`.Dialect.create_connect_args` method 

2304 

2305 :param \*\*cparams: keyword parameters returned from the 

2306 :meth:`.Dialect.create_connect_args` method. 

2307 

2308 :return: a DBAPI connection, typically from the :pep:`249` module 

2309 level ``.connect()`` function. 

2310 

2311 .. seealso:: 

2312 

2313 :meth:`.Dialect.create_connect_args` 

2314 

2315 :meth:`.Dialect.on_connect` 

2316 

2317 """ 

2318 raise NotImplementedError() 

2319 

2320 def on_connect_url(self, url: URL) -> Optional[Callable[[Any], Any]]: 

2321 """return a callable which sets up a newly created DBAPI connection. 

2322 

2323 This method is a new hook that supersedes the 

2324 :meth:`_engine.Dialect.on_connect` method when implemented by a 

2325 dialect. When not implemented by a dialect, it invokes the 

2326 :meth:`_engine.Dialect.on_connect` method directly to maintain 

2327 compatibility with existing dialects. There is no deprecation 

2328 for :meth:`_engine.Dialect.on_connect` expected. 

2329 

2330 The callable should accept a single argument "conn" which is the 

2331 DBAPI connection itself. The inner callable has no 

2332 return value. 

2333 

2334 E.g.:: 

2335 

2336 class MyDialect(default.DefaultDialect): 

2337 # ... 

2338 

2339 def on_connect_url(self, url): 

2340 def do_on_connect(connection): 

2341 connection.execute("SET SPECIAL FLAGS etc") 

2342 

2343 return do_on_connect 

2344 

2345 This is used to set dialect-wide per-connection options such as 

2346 isolation modes, Unicode modes, etc. 

2347 

2348 This method differs from :meth:`_engine.Dialect.on_connect` in that 

2349 it is passed the :class:`_engine.URL` object that's relevant to the 

2350 connect args. Normally the only way to get this is from the 

2351 :meth:`_engine.Dialect.on_connect` hook is to look on the 

2352 :class:`_engine.Engine` itself, however this URL object may have been 

2353 replaced by plugins. 

2354 

2355 .. note:: 

2356 

2357 The default implementation of 

2358 :meth:`_engine.Dialect.on_connect_url` is to invoke the 

2359 :meth:`_engine.Dialect.on_connect` method. Therefore if a dialect 

2360 implements this method, the :meth:`_engine.Dialect.on_connect` 

2361 method **will not be called** unless the overriding dialect calls 

2362 it directly from here. 

2363 

2364 .. versionadded:: 1.4.3 added :meth:`_engine.Dialect.on_connect_url` 

2365 which normally calls into :meth:`_engine.Dialect.on_connect`. 

2366 

2367 :param url: a :class:`_engine.URL` object representing the 

2368 :class:`_engine.URL` that was passed to the 

2369 :meth:`_engine.Dialect.create_connect_args` method. 

2370 

2371 :return: a callable that accepts a single DBAPI connection as an 

2372 argument, or None. 

2373 

2374 .. seealso:: 

2375 

2376 :meth:`_engine.Dialect.on_connect` 

2377 

2378 """ 

2379 return self.on_connect() 

2380 

2381 def on_connect(self) -> Optional[Callable[[Any], None]]: 

2382 """return a callable which sets up a newly created DBAPI connection. 

2383 

2384 The callable should accept a single argument "conn" which is the 

2385 DBAPI connection itself. The inner callable has no 

2386 return value. 

2387 

2388 E.g.:: 

2389 

2390 class MyDialect(default.DefaultDialect): 

2391 # ... 

2392 

2393 def on_connect(self): 

2394 def do_on_connect(connection): 

2395 connection.execute("SET SPECIAL FLAGS etc") 

2396 

2397 return do_on_connect 

2398 

2399 This is used to set dialect-wide per-connection options such as 

2400 isolation modes, Unicode modes, etc. 

2401 

2402 The "do_on_connect" callable is invoked by using the 

2403 :meth:`_events.PoolEvents.connect` event 

2404 hook, then unwrapping the DBAPI connection and passing it into the 

2405 callable. 

2406 

2407 .. versionchanged:: 1.4 the on_connect hook is no longer called twice 

2408 for the first connection of a dialect. The on_connect hook is still 

2409 called before the :meth:`_engine.Dialect.initialize` method however. 

2410 

2411 .. versionchanged:: 1.4.3 the on_connect hook is invoked from a new 

2412 method on_connect_url that passes the URL that was used to create 

2413 the connect args. Dialects can implement on_connect_url instead 

2414 of on_connect if they need the URL object that was used for the 

2415 connection in order to get additional context. 

2416 

2417 If None is returned, no event listener is generated. 

2418 

2419 :return: a callable that accepts a single DBAPI connection as an 

2420 argument, or None. 

2421 

2422 .. seealso:: 

2423 

2424 :meth:`.Dialect.connect` - allows the DBAPI ``connect()`` sequence 

2425 itself to be controlled. 

2426 

2427 :meth:`.Dialect.on_connect_url` - supersedes 

2428 :meth:`.Dialect.on_connect` to also receive the 

2429 :class:`_engine.URL` object in context. 

2430 

2431 """ 

2432 return None 

2433 

2434 def reset_isolation_level(self, dbapi_connection: DBAPIConnection) -> None: 

2435 """Given a DBAPI connection, revert its isolation to the default. 

2436 

2437 Note that this is a dialect-level method which is used as part 

2438 of the implementation of the :class:`_engine.Connection` and 

2439 :class:`_engine.Engine` 

2440 isolation level facilities; these APIs should be preferred for 

2441 most typical use cases. 

2442 

2443 .. seealso:: 

2444 

2445 :meth:`_engine.Connection.get_isolation_level` 

2446 - view current level 

2447 

2448 :attr:`_engine.Connection.default_isolation_level` 

2449 - view default level 

2450 

2451 :paramref:`.Connection.execution_options.isolation_level` - 

2452 set per :class:`_engine.Connection` isolation level 

2453 

2454 :paramref:`_sa.create_engine.isolation_level` - 

2455 set per :class:`_engine.Engine` isolation level 

2456 

2457 """ 

2458 

2459 raise NotImplementedError() 

2460 

2461 def set_isolation_level( 

2462 self, dbapi_connection: DBAPIConnection, level: IsolationLevel 

2463 ) -> None: 

2464 """Given a DBAPI connection, set its isolation level. 

2465 

2466 Note that this is a dialect-level method which is used as part 

2467 of the implementation of the :class:`_engine.Connection` and 

2468 :class:`_engine.Engine` 

2469 isolation level facilities; these APIs should be preferred for 

2470 most typical use cases. 

2471 

2472 If the dialect also implements the 

2473 :meth:`.Dialect.get_isolation_level_values` method, then the given 

2474 level is guaranteed to be one of the string names within that sequence, 

2475 and the method will not need to anticipate a lookup failure. 

2476 

2477 .. seealso:: 

2478 

2479 :meth:`_engine.Connection.get_isolation_level` 

2480 - view current level 

2481 

2482 :attr:`_engine.Connection.default_isolation_level` 

2483 - view default level 

2484 

2485 :paramref:`.Connection.execution_options.isolation_level` - 

2486 set per :class:`_engine.Connection` isolation level 

2487 

2488 :paramref:`_sa.create_engine.isolation_level` - 

2489 set per :class:`_engine.Engine` isolation level 

2490 

2491 """ 

2492 

2493 raise NotImplementedError() 

2494 

2495 def get_isolation_level( 

2496 self, dbapi_connection: DBAPIConnection 

2497 ) -> IsolationLevel: 

2498 """Given a DBAPI connection, return its isolation level. 

2499 

2500 When working with a :class:`_engine.Connection` object, 

2501 the corresponding 

2502 DBAPI connection may be procured using the 

2503 :attr:`_engine.Connection.connection` accessor. 

2504 

2505 Note that this is a dialect-level method which is used as part 

2506 of the implementation of the :class:`_engine.Connection` and 

2507 :class:`_engine.Engine` isolation level facilities; 

2508 these APIs should be preferred for most typical use cases. 

2509 

2510 

2511 .. seealso:: 

2512 

2513 :meth:`_engine.Connection.get_isolation_level` 

2514 - view current level 

2515 

2516 :attr:`_engine.Connection.default_isolation_level` 

2517 - view default level 

2518 

2519 :paramref:`.Connection.execution_options.isolation_level` - 

2520 set per :class:`_engine.Connection` isolation level 

2521 

2522 :paramref:`_sa.create_engine.isolation_level` - 

2523 set per :class:`_engine.Engine` isolation level 

2524 

2525 

2526 """ 

2527 

2528 raise NotImplementedError() 

2529 

2530 def detect_autocommit_setting(self, dbapi_conn: DBAPIConnection) -> bool: 

2531 """Detect the current autocommit setting for a DBAPI connection. 

2532 

2533 :param dbapi_connection: a DBAPI connection object 

2534 :return: True if autocommit is enabled, False if disabled 

2535 :rtype: bool 

2536 

2537 This method inspects the given DBAPI connection to determine 

2538 whether autocommit mode is currently enabled. The specific 

2539 mechanism for detecting autocommit varies by database dialect 

2540 and DBAPI driver, however it should be done **without** network 

2541 round trips. 

2542 

2543 .. note:: 

2544 

2545 Not all dialects support autocommit detection. Dialects 

2546 that do not support this feature will raise 

2547 :exc:`NotImplementedError`. 

2548 

2549 """ 

2550 raise NotImplementedError( 

2551 "This dialect cannot detect autocommit on a DBAPI connection" 

2552 ) 

2553 

2554 def get_default_isolation_level( 

2555 self, dbapi_conn: DBAPIConnection 

2556 ) -> IsolationLevel: 

2557 """Given a DBAPI connection, return its isolation level, or 

2558 a default isolation level if one cannot be retrieved. 

2559 

2560 This method may only raise NotImplementedError and 

2561 **must not raise any other exception**, as it is used implicitly upon 

2562 first connect. 

2563 

2564 The method **must return a value** for a dialect that supports 

2565 isolation level settings, as this level is what will be reverted 

2566 towards when a per-connection isolation level change is made. 

2567 

2568 The method defaults to using the :meth:`.Dialect.get_isolation_level` 

2569 method unless overridden by a dialect. 

2570 

2571 """ 

2572 raise NotImplementedError() 

2573 

2574 def get_isolation_level_values( 

2575 self, dbapi_conn: DBAPIConnection 

2576 ) -> Sequence[IsolationLevel]: 

2577 """return a sequence of string isolation level names that are accepted 

2578 by this dialect. 

2579 

2580 The available names should use the following conventions: 

2581 

2582 * use UPPERCASE names. isolation level methods will accept lowercase 

2583 names but these are normalized into UPPERCASE before being passed 

2584 along to the dialect. 

2585 * separate words should be separated by spaces, not underscores, e.g. 

2586 ``REPEATABLE READ``. isolation level names will have underscores 

2587 converted to spaces before being passed along to the dialect. 

2588 * The names for the four standard isolation names to the extent that 

2589 they are supported by the backend should be ``READ UNCOMMITTED``, 

2590 ``READ COMMITTED``, ``REPEATABLE READ``, ``SERIALIZABLE`` 

2591 * if the dialect supports an autocommit option it should be provided 

2592 using the isolation level name ``AUTOCOMMIT``. 

2593 * Other isolation modes may also be present, provided that they 

2594 are named in UPPERCASE and use spaces not underscores. 

2595 

2596 This function is used so that the default dialect can check that 

2597 a given isolation level parameter is valid, else raises an 

2598 :class:`_exc.ArgumentError`. 

2599 

2600 A DBAPI connection is passed to the method, in the unlikely event that 

2601 the dialect needs to interrogate the connection itself to determine 

2602 this list, however it is expected that most backends will return 

2603 a hardcoded list of values. If the dialect supports "AUTOCOMMIT", 

2604 that value should also be present in the sequence returned. 

2605 

2606 The method raises ``NotImplementedError`` by default. If a dialect 

2607 does not implement this method, then the default dialect will not 

2608 perform any checking on a given isolation level value before passing 

2609 it onto the :meth:`.Dialect.set_isolation_level` method. This is 

2610 to allow backwards-compatibility with third party dialects that may 

2611 not yet be implementing this method. 

2612 

2613 .. versionadded:: 2.0 

2614 

2615 """ 

2616 raise NotImplementedError() 

2617 

2618 def _assert_and_set_isolation_level( 

2619 self, dbapi_conn: DBAPIConnection, level: IsolationLevel 

2620 ) -> None: 

2621 raise NotImplementedError() 

2622 

2623 @classmethod 

2624 def get_dialect_cls(cls, url: URL) -> Type[Dialect]: 

2625 """Given a URL, return the :class:`.Dialect` that will be used. 

2626 

2627 This is a hook that allows an external plugin to provide functionality 

2628 around an existing dialect, by allowing the plugin to be loaded 

2629 from the url based on an entrypoint, and then the plugin returns 

2630 the actual dialect to be used. 

2631 

2632 By default this just returns the cls. 

2633 

2634 """ 

2635 return cls 

2636 

2637 @classmethod 

2638 def get_async_dialect_cls(cls, url: URL) -> Type[Dialect]: 

2639 """Given a URL, return the :class:`.Dialect` that will be used by 

2640 an async engine. 

2641 

2642 By default this is an alias of :meth:`.Dialect.get_dialect_cls` and 

2643 just returns the cls. It may be used if a dialect provides 

2644 both a sync and async version under the same name, like the 

2645 ``psycopg`` driver. 

2646 

2647 .. versionadded:: 2 

2648 

2649 .. seealso:: 

2650 

2651 :meth:`.Dialect.get_dialect_cls` 

2652 

2653 """ 

2654 return cls.get_dialect_cls(url) 

2655 

2656 @classmethod 

2657 def load_provisioning(cls) -> None: 

2658 """set up the provision.py module for this dialect. 

2659 

2660 For dialects that include a provision.py module that sets up 

2661 provisioning followers, this method should initiate that process. 

2662 

2663 A typical implementation would be:: 

2664 

2665 @classmethod 

2666 def load_provisioning(cls): 

2667 __import__("mydialect.provision") 

2668 

2669 The default method assumes a module named ``provision.py`` inside 

2670 the owning package of the current dialect, based on the ``__module__`` 

2671 attribute:: 

2672 

2673 @classmethod 

2674 def load_provisioning(cls): 

2675 package = ".".join(cls.__module__.split(".")[0:-1]) 

2676 try: 

2677 __import__(package + ".provision") 

2678 except ImportError: 

2679 pass 

2680 

2681 """ 

2682 

2683 @classmethod 

2684 def engine_created(cls, engine: Engine) -> None: 

2685 """A convenience hook called before returning the final 

2686 :class:`_engine.Engine`. 

2687 

2688 If the dialect returned a different class from the 

2689 :meth:`.get_dialect_cls` 

2690 method, then the hook is called on both classes, first on 

2691 the dialect class returned by the :meth:`.get_dialect_cls` method and 

2692 then on the class on which the method was called. 

2693 

2694 The hook should be used by dialects and/or wrappers to apply special 

2695 events to the engine or its components. In particular, it allows 

2696 a dialect-wrapping class to apply dialect-level events. 

2697 

2698 """ 

2699 

2700 def get_driver_connection(self, connection: DBAPIConnection) -> Any: 

2701 """Returns the connection object as returned by the external driver 

2702 package. 

2703 

2704 For normal dialects that use a DBAPI compliant driver this call 

2705 will just return the ``connection`` passed as argument. 

2706 For dialects that instead adapt a non DBAPI compliant driver, like 

2707 when adapting an asyncio driver, this call will return the 

2708 connection-like object as returned by the driver. 

2709 

2710 .. versionadded:: 1.4.24 

2711 

2712 """ 

2713 raise NotImplementedError() 

2714 

2715 def set_engine_execution_options( 

2716 self, engine: Engine, opts: CoreExecuteOptionsParameter 

2717 ) -> None: 

2718 """Establish execution options for a given engine. 

2719 

2720 This is implemented by :class:`.DefaultDialect` to establish 

2721 event hooks for new :class:`.Connection` instances created 

2722 by the given :class:`.Engine` which will then invoke the 

2723 :meth:`.Dialect.set_connection_execution_options` method for that 

2724 connection. 

2725 

2726 """ 

2727 raise NotImplementedError() 

2728 

2729 def set_connection_execution_options( 

2730 self, connection: Connection, opts: CoreExecuteOptionsParameter 

2731 ) -> None: 

2732 """Establish execution options for a given connection. 

2733 

2734 This is implemented by :class:`.DefaultDialect` in order to implement 

2735 the :paramref:`_engine.Connection.execution_options.isolation_level` 

2736 execution option. Dialects can intercept various execution options 

2737 which may need to modify state on a particular DBAPI connection. 

2738 

2739 .. versionadded:: 1.4 

2740 

2741 """ 

2742 raise NotImplementedError() 

2743 

2744 def get_dialect_pool_class(self, url: URL) -> Type[Pool]: 

2745 """return a Pool class to use for a given URL""" 

2746 raise NotImplementedError() 

2747 

2748 def validate_identifier(self, ident: str) -> None: 

2749 """Validates an identifier name, raising an exception if invalid""" 

2750 

2751 

2752class CreateEnginePlugin: 

2753 """A set of hooks intended to augment the construction of an 

2754 :class:`_engine.Engine` object based on entrypoint names in a URL. 

2755 

2756 The purpose of :class:`_engine.CreateEnginePlugin` is to allow third-party 

2757 systems to apply engine, pool and dialect level event listeners without 

2758 the need for the target application to be modified; instead, the plugin 

2759 names can be added to the database URL. Target applications for 

2760 :class:`_engine.CreateEnginePlugin` include: 

2761 

2762 * connection and SQL performance tools, e.g. which use events to track 

2763 number of checkouts and/or time spent with statements 

2764 

2765 * connectivity plugins such as proxies 

2766 

2767 A rudimentary :class:`_engine.CreateEnginePlugin` that attaches a logger 

2768 to an :class:`_engine.Engine` object might look like:: 

2769 

2770 

2771 import logging 

2772 

2773 from sqlalchemy.engine import CreateEnginePlugin 

2774 from sqlalchemy import event 

2775 

2776 

2777 class LogCursorEventsPlugin(CreateEnginePlugin): 

2778 def __init__(self, url, kwargs): 

2779 # consume the parameter "log_cursor_logging_name" from the 

2780 # URL query 

2781 logging_name = url.query.get( 

2782 "log_cursor_logging_name", "log_cursor" 

2783 ) 

2784 

2785 self.log = logging.getLogger(logging_name) 

2786 

2787 def update_url(self, url): 

2788 "update the URL to one that no longer includes our parameters" 

2789 return url.difference_update_query(["log_cursor_logging_name"]) 

2790 

2791 def engine_created(self, engine): 

2792 "attach an event listener after the new Engine is constructed" 

2793 event.listen(engine, "before_cursor_execute", self._log_event) 

2794 

2795 def _log_event( 

2796 self, 

2797 conn, 

2798 cursor, 

2799 statement, 

2800 parameters, 

2801 context, 

2802 executemany, 

2803 ): 

2804 

2805 self.log.info("Plugin logged cursor event: %s", statement) 

2806 

2807 Plugins are registered using entry points in a similar way as that 

2808 of dialects:: 

2809 

2810 entry_points = { 

2811 "sqlalchemy.plugins": [ 

2812 "log_cursor_plugin = myapp.plugins:LogCursorEventsPlugin" 

2813 ] 

2814 } 

2815 

2816 A plugin that uses the above names would be invoked from a database 

2817 URL as in:: 

2818 

2819 from sqlalchemy import create_engine 

2820 

2821 engine = create_engine( 

2822 "mysql+pymysql://scott:tiger@localhost/test?" 

2823 "plugin=log_cursor_plugin&log_cursor_logging_name=mylogger" 

2824 ) 

2825 

2826 The ``plugin`` URL parameter supports multiple instances, so that a URL 

2827 may specify multiple plugins; they are loaded in the order stated 

2828 in the URL:: 

2829 

2830 engine = create_engine( 

2831 "mysql+pymysql://scott:tiger@localhost/test?" 

2832 "plugin=plugin_one&plugin=plugin_twp&plugin=plugin_three" 

2833 ) 

2834 

2835 The plugin names may also be passed directly to :func:`_sa.create_engine` 

2836 using the :paramref:`_sa.create_engine.plugins` argument:: 

2837 

2838 engine = create_engine( 

2839 "mysql+pymysql://scott:tiger@localhost/test", plugins=["myplugin"] 

2840 ) 

2841 

2842 A plugin may consume plugin-specific arguments from the 

2843 :class:`_engine.URL` object as well as the ``kwargs`` dictionary, which is 

2844 the dictionary of arguments passed to the :func:`_sa.create_engine` 

2845 call. "Consuming" these arguments includes that they must be removed 

2846 when the plugin initializes, so that the arguments are not passed along 

2847 to the :class:`_engine.Dialect` constructor, where they will raise an 

2848 :class:`_exc.ArgumentError` because they are not known by the dialect. 

2849 

2850 As of version 1.4 of SQLAlchemy, arguments should continue to be consumed 

2851 from the ``kwargs`` dictionary directly, by removing the values with a 

2852 method such as ``dict.pop``. Arguments from the :class:`_engine.URL` object 

2853 should be consumed by implementing the 

2854 :meth:`_engine.CreateEnginePlugin.update_url` method, returning a new copy 

2855 of the :class:`_engine.URL` with plugin-specific parameters removed:: 

2856 

2857 class MyPlugin(CreateEnginePlugin): 

2858 def __init__(self, url, kwargs): 

2859 self.my_argument_one = url.query["my_argument_one"] 

2860 self.my_argument_two = url.query["my_argument_two"] 

2861 self.my_argument_three = kwargs.pop("my_argument_three", None) 

2862 

2863 def update_url(self, url): 

2864 return url.difference_update_query( 

2865 ["my_argument_one", "my_argument_two"] 

2866 ) 

2867 

2868 Arguments like those illustrated above would be consumed from a 

2869 :func:`_sa.create_engine` call such as:: 

2870 

2871 from sqlalchemy import create_engine 

2872 

2873 engine = create_engine( 

2874 "mysql+pymysql://scott:tiger@localhost/test?" 

2875 "plugin=myplugin&my_argument_one=foo&my_argument_two=bar", 

2876 my_argument_three="bat", 

2877 ) 

2878 

2879 .. versionchanged:: 1.4 

2880 

2881 The :class:`_engine.URL` object is now immutable; a 

2882 :class:`_engine.CreateEnginePlugin` that needs to alter the 

2883 :class:`_engine.URL` should implement the newly added 

2884 :meth:`_engine.CreateEnginePlugin.update_url` method, which 

2885 is invoked after the plugin is constructed. 

2886 

2887 For migration, construct the plugin in the following way, checking 

2888 for the existence of the :meth:`_engine.CreateEnginePlugin.update_url` 

2889 method to detect which version is running:: 

2890 

2891 class MyPlugin(CreateEnginePlugin): 

2892 def __init__(self, url, kwargs): 

2893 if hasattr(CreateEnginePlugin, "update_url"): 

2894 # detect the 1.4 API 

2895 self.my_argument_one = url.query["my_argument_one"] 

2896 self.my_argument_two = url.query["my_argument_two"] 

2897 else: 

2898 # detect the 1.3 and earlier API - mutate the 

2899 # URL directly 

2900 self.my_argument_one = url.query.pop("my_argument_one") 

2901 self.my_argument_two = url.query.pop("my_argument_two") 

2902 

2903 self.my_argument_three = kwargs.pop("my_argument_three", None) 

2904 

2905 def update_url(self, url): 

2906 # this method is only called in the 1.4 version 

2907 return url.difference_update_query( 

2908 ["my_argument_one", "my_argument_two"] 

2909 ) 

2910 

2911 .. seealso:: 

2912 

2913 :ref:`change_5526` - overview of the :class:`_engine.URL` change which 

2914 also includes notes regarding :class:`_engine.CreateEnginePlugin`. 

2915 

2916 

2917 When the engine creation process completes and produces the 

2918 :class:`_engine.Engine` object, it is again passed to the plugin via the 

2919 :meth:`_engine.CreateEnginePlugin.engine_created` hook. In this hook, additional 

2920 changes can be made to the engine, most typically involving setup of 

2921 events (e.g. those defined in :ref:`core_event_toplevel`). 

2922 

2923 """ # noqa: E501 

2924 

2925 def __init__(self, url: URL, kwargs: Dict[str, Any]): 

2926 """Construct a new :class:`.CreateEnginePlugin`. 

2927 

2928 The plugin object is instantiated individually for each call 

2929 to :func:`_sa.create_engine`. A single :class:`_engine. 

2930 Engine` will be 

2931 passed to the :meth:`.CreateEnginePlugin.engine_created` method 

2932 corresponding to this URL. 

2933 

2934 :param url: the :class:`_engine.URL` object. The plugin may inspect 

2935 the :class:`_engine.URL` for arguments. Arguments used by the 

2936 plugin should be removed, by returning an updated :class:`_engine.URL` 

2937 from the :meth:`_engine.CreateEnginePlugin.update_url` method. 

2938 

2939 .. versionchanged:: 1.4 

2940 

2941 The :class:`_engine.URL` object is now immutable, so a 

2942 :class:`_engine.CreateEnginePlugin` that needs to alter the 

2943 :class:`_engine.URL` object should implement the 

2944 :meth:`_engine.CreateEnginePlugin.update_url` method. 

2945 

2946 :param kwargs: The keyword arguments passed to 

2947 :func:`_sa.create_engine`. 

2948 

2949 """ 

2950 self.url = url 

2951 

2952 def update_url(self, url: URL) -> URL: 

2953 """Update the :class:`_engine.URL`. 

2954 

2955 A new :class:`_engine.URL` should be returned. This method is 

2956 typically used to consume configuration arguments from the 

2957 :class:`_engine.URL` which must be removed, as they will not be 

2958 recognized by the dialect. The 

2959 :meth:`_engine.URL.difference_update_query` method is available 

2960 to remove these arguments. See the docstring at 

2961 :class:`_engine.CreateEnginePlugin` for an example. 

2962 

2963 

2964 .. versionadded:: 1.4 

2965 

2966 """ 

2967 raise NotImplementedError() 

2968 

2969 def handle_dialect_kwargs( 

2970 self, dialect_cls: Type[Dialect], dialect_args: Dict[str, Any] 

2971 ) -> None: 

2972 """parse and modify dialect kwargs""" 

2973 

2974 def handle_pool_kwargs( 

2975 self, pool_cls: Type[Pool], pool_args: Dict[str, Any] 

2976 ) -> None: 

2977 """parse and modify pool kwargs""" 

2978 

2979 def engine_created(self, engine: Engine) -> None: 

2980 """Receive the :class:`_engine.Engine` 

2981 object when it is fully constructed. 

2982 

2983 The plugin may make additional changes to the engine, such as 

2984 registering engine or connection pool events. 

2985 

2986 """ 

2987 

2988 

2989class ExecutionContext: 

2990 """A messenger object for a Dialect that corresponds to a single 

2991 execution. 

2992 

2993 """ 

2994 

2995 engine: Engine 

2996 """engine which the Connection is associated with""" 

2997 

2998 connection: Connection 

2999 """Connection object which can be freely used by default value 

3000 generators to execute SQL. This Connection should reference the 

3001 same underlying connection/transactional resources of 

3002 root_connection.""" 

3003 

3004 root_connection: Connection 

3005 """Connection object which is the source of this ExecutionContext.""" 

3006 

3007 dialect: Dialect 

3008 """dialect which created this ExecutionContext.""" 

3009 

3010 cursor: DBAPICursor 

3011 """DB-API cursor procured from the connection""" 

3012 

3013 compiled: Optional[Compiled] 

3014 """if passed to constructor, sqlalchemy.engine.base.Compiled object 

3015 being executed""" 

3016 

3017 statement: str 

3018 """string version of the statement to be executed. Is either 

3019 passed to the constructor, or must be created from the 

3020 sql.Compiled object by the time pre_exec() has completed.""" 

3021 

3022 invoked_statement: Optional[Executable] 

3023 """The Executable statement object that was given in the first place. 

3024 

3025 This should be structurally equivalent to compiled.statement, but not 

3026 necessarily the same object as in a caching scenario the compiled form 

3027 will have been extracted from the cache. 

3028 

3029 """ 

3030 

3031 parameters: _AnyMultiExecuteParams 

3032 """bind parameters passed to the execute() or exec_driver_sql() methods. 

3033 

3034 These are always stored as a list of parameter entries. A single-element 

3035 list corresponds to a ``cursor.execute()`` call and a multiple-element 

3036 list corresponds to ``cursor.executemany()``, except in the case 

3037 of :attr:`.ExecuteStyle.INSERTMANYVALUES` which will use 

3038 ``cursor.execute()`` one or more times. 

3039 

3040 """ 

3041 

3042 no_parameters: bool 

3043 """True if the execution style does not use parameters""" 

3044 

3045 isinsert: bool 

3046 """True if the statement is an INSERT.""" 

3047 

3048 isupdate: bool 

3049 """True if the statement is an UPDATE.""" 

3050 

3051 execute_style: ExecuteStyle 

3052 """the style of DBAPI cursor method that will be used to execute 

3053 a statement. 

3054 

3055 .. versionadded:: 2.0 

3056 

3057 """ 

3058 

3059 executemany: bool 

3060 """True if the context has a list of more than one parameter set. 

3061 

3062 Historically this attribute links to whether ``cursor.execute()`` or 

3063 ``cursor.executemany()`` will be used. It also can now mean that 

3064 "insertmanyvalues" may be used which indicates one or more 

3065 ``cursor.execute()`` calls. 

3066 

3067 """ 

3068 

3069 prefetch_cols: util.generic_fn_descriptor[Optional[Sequence[Column[Any]]]] 

3070 """a list of Column objects for which a client-side default 

3071 was fired off. Applies to inserts and updates.""" 

3072 

3073 postfetch_cols: util.generic_fn_descriptor[Optional[Sequence[Column[Any]]]] 

3074 """a list of Column objects for which a server-side default or 

3075 inline SQL expression value was fired off. Applies to inserts 

3076 and updates.""" 

3077 

3078 execution_options: _ExecuteOptions 

3079 """Execution options associated with the current statement execution""" 

3080 

3081 @classmethod 

3082 def _init_ddl( 

3083 cls, 

3084 dialect: Dialect, 

3085 connection: Connection, 

3086 dbapi_connection: PoolProxiedConnection, 

3087 execution_options: _ExecuteOptions, 

3088 compiled_ddl: DDLCompiler, 

3089 ) -> ExecutionContext: 

3090 raise NotImplementedError() 

3091 

3092 @classmethod 

3093 def _init_compiled( 

3094 cls, 

3095 dialect: Dialect, 

3096 connection: Connection, 

3097 dbapi_connection: PoolProxiedConnection, 

3098 execution_options: _ExecuteOptions, 

3099 compiled: SQLCompiler, 

3100 parameters: _CoreMultiExecuteParams, 

3101 invoked_statement: Executable, 

3102 extracted_parameters: Optional[Sequence[BindParameter[Any]]], 

3103 cache_hit: CacheStats = CacheStats.CACHING_DISABLED, 

3104 ) -> ExecutionContext: 

3105 raise NotImplementedError() 

3106 

3107 @classmethod 

3108 def _init_statement( 

3109 cls, 

3110 dialect: Dialect, 

3111 connection: Connection, 

3112 dbapi_connection: PoolProxiedConnection, 

3113 execution_options: _ExecuteOptions, 

3114 statement: str, 

3115 parameters: _DBAPIMultiExecuteParams, 

3116 ) -> ExecutionContext: 

3117 raise NotImplementedError() 

3118 

3119 @classmethod 

3120 def _init_default( 

3121 cls, 

3122 dialect: Dialect, 

3123 connection: Connection, 

3124 dbapi_connection: PoolProxiedConnection, 

3125 execution_options: _ExecuteOptions, 

3126 ) -> ExecutionContext: 

3127 raise NotImplementedError() 

3128 

3129 def _exec_default( 

3130 self, 

3131 column: Optional[Column[Any]], 

3132 default: DefaultGenerator, 

3133 type_: Optional[TypeEngine[Any]], 

3134 ) -> Any: 

3135 raise NotImplementedError() 

3136 

3137 def _prepare_set_input_sizes( 

3138 self, 

3139 ) -> Optional[List[Tuple[str, Any, TypeEngine[Any]]]]: 

3140 raise NotImplementedError() 

3141 

3142 def _get_cache_stats(self) -> str: 

3143 raise NotImplementedError() 

3144 

3145 def _setup_result_proxy(self) -> CursorResult[Any]: 

3146 raise NotImplementedError() 

3147 

3148 def fire_sequence(self, seq: Sequence_SchemaItem, type_: Integer) -> int: 

3149 """given a :class:`.Sequence`, invoke it and return the next int 

3150 value""" 

3151 raise NotImplementedError() 

3152 

3153 def create_cursor(self) -> DBAPICursor: 

3154 """Return a new cursor generated from this ExecutionContext's 

3155 connection. 

3156 

3157 Some dialects may wish to change the behavior of 

3158 connection.cursor(), such as postgresql which may return a PG 

3159 "server side" cursor. 

3160 """ 

3161 

3162 raise NotImplementedError() 

3163 

3164 def pre_exec(self) -> None: 

3165 """Called before an execution of a compiled statement. 

3166 

3167 If a compiled statement was passed to this ExecutionContext, 

3168 the `statement` and `parameters` datamembers must be 

3169 initialized after this statement is complete. 

3170 """ 

3171 

3172 raise NotImplementedError() 

3173 

3174 def get_out_parameter_values( 

3175 self, out_param_names: Sequence[str] 

3176 ) -> Sequence[Any]: 

3177 """Return a sequence of OUT parameter values from a cursor. 

3178 

3179 For dialects that support OUT parameters, this method will be called 

3180 when there is a :class:`.SQLCompiler` object which has the 

3181 :attr:`.SQLCompiler.has_out_parameters` flag set. This flag in turn 

3182 will be set to True if the statement itself has :class:`.BindParameter` 

3183 objects that have the ``.isoutparam`` flag set which are consumed by 

3184 the :meth:`.SQLCompiler.visit_bindparam` method. If the dialect 

3185 compiler produces :class:`.BindParameter` objects with ``.isoutparam`` 

3186 set which are not handled by :meth:`.SQLCompiler.visit_bindparam`, it 

3187 should set this flag explicitly. 

3188 

3189 The list of names that were rendered for each bound parameter 

3190 is passed to the method. The method should then return a sequence of 

3191 values corresponding to the list of parameter objects. Unlike in 

3192 previous SQLAlchemy versions, the values can be the **raw values** from 

3193 the DBAPI; the execution context will apply the appropriate type 

3194 handler based on what's present in self.compiled.binds and update the 

3195 values. The processed dictionary will then be made available via the 

3196 ``.out_parameters`` collection on the result object. Note that 

3197 SQLAlchemy 1.4 has multiple kinds of result object as part of the 2.0 

3198 transition. 

3199 

3200 .. versionadded:: 1.4 - added 

3201 :meth:`.ExecutionContext.get_out_parameter_values`, which is invoked 

3202 automatically by the :class:`.DefaultExecutionContext` when there 

3203 are :class:`.BindParameter` objects with the ``.isoutparam`` flag 

3204 set. This replaces the practice of setting out parameters within 

3205 the now-removed ``get_result_proxy()`` method. 

3206 

3207 """ 

3208 raise NotImplementedError() 

3209 

3210 def post_exec(self) -> None: 

3211 """Called after the execution of a compiled statement. 

3212 

3213 If a compiled statement was passed to this ExecutionContext, 

3214 the `last_insert_ids`, `last_inserted_params`, etc. 

3215 datamembers should be available after this method completes. 

3216 """ 

3217 

3218 raise NotImplementedError() 

3219 

3220 def handle_dbapi_exception(self, e: BaseException) -> None: 

3221 """Receive a DBAPI exception which occurred upon execute, result 

3222 fetch, etc.""" 

3223 

3224 raise NotImplementedError() 

3225 

3226 def lastrow_has_defaults(self) -> bool: 

3227 """Return True if the last INSERT or UPDATE row contained 

3228 inlined or database-side defaults. 

3229 """ 

3230 

3231 raise NotImplementedError() 

3232 

3233 def get_rowcount(self) -> Optional[int]: 

3234 """Return the DBAPI ``cursor.rowcount`` value, or in some 

3235 cases an interpreted value. 

3236 

3237 See :attr:`_engine.CursorResult.rowcount` for details on this. 

3238 

3239 """ 

3240 

3241 raise NotImplementedError() 

3242 

3243 def fetchall_for_returning(self, cursor: DBAPICursor) -> Sequence[Any]: 

3244 """For a RETURNING result, deliver cursor.fetchall() from the 

3245 DBAPI cursor. 

3246 

3247 This is a dialect-specific hook for dialects that have special 

3248 considerations when calling upon the rows delivered for a 

3249 "RETURNING" statement. Default implementation is 

3250 ``cursor.fetchall()``. 

3251 

3252 This hook is currently used only by the :term:`insertmanyvalues` 

3253 feature. Dialects that don't set ``use_insertmanyvalues=True`` 

3254 don't need to consider this hook. 

3255 

3256 .. versionadded:: 2.0.10 

3257 

3258 """ 

3259 raise NotImplementedError() 

3260 

3261 

3262class ConnectionEventsTarget(EventTarget): 

3263 """An object which can accept events from :class:`.ConnectionEvents`. 

3264 

3265 Includes :class:`_engine.Connection` and :class:`_engine.Engine`. 

3266 

3267 .. versionadded:: 2.0 

3268 

3269 """ 

3270 

3271 dispatch: dispatcher[ConnectionEventsTarget] 

3272 

3273 

3274Connectable = ConnectionEventsTarget 

3275 

3276 

3277class ExceptionContext: 

3278 """Encapsulate information about an error condition in progress. 

3279 

3280 This object exists solely to be passed to the 

3281 :meth:`_events.DialectEvents.handle_error` event, 

3282 supporting an interface that 

3283 can be extended without backwards-incompatibility. 

3284 

3285 

3286 """ 

3287 

3288 __slots__ = () 

3289 

3290 dialect: Dialect 

3291 """The :class:`_engine.Dialect` in use. 

3292 

3293 This member is present for all invocations of the event hook. 

3294 

3295 .. versionadded:: 2.0 

3296 

3297 """ 

3298 

3299 connection: Optional[Connection] 

3300 """The :class:`_engine.Connection` in use during the exception. 

3301 

3302 This member is present, except in the case of a failure when 

3303 first connecting. 

3304 

3305 .. seealso:: 

3306 

3307 :attr:`.ExceptionContext.engine` 

3308 

3309 

3310 """ 

3311 

3312 engine: Optional[Engine] 

3313 """The :class:`_engine.Engine` in use during the exception. 

3314 

3315 This member is present in all cases except for when handling an error 

3316 within the connection pool "pre-ping" process. 

3317 

3318 """ 

3319 

3320 cursor: Optional[DBAPICursor] 

3321 """The DBAPI cursor object. 

3322 

3323 May be None. 

3324 

3325 """ 

3326 

3327 statement: Optional[str] 

3328 """String SQL statement that was emitted directly to the DBAPI. 

3329 

3330 May be None. 

3331 

3332 """ 

3333 

3334 parameters: Optional[_DBAPIAnyExecuteParams] 

3335 """Parameter collection that was emitted directly to the DBAPI. 

3336 

3337 May be None. 

3338 

3339 """ 

3340 

3341 original_exception: BaseException 

3342 """The exception object which was caught. 

3343 

3344 This member is always present. 

3345 

3346 """ 

3347 

3348 sqlalchemy_exception: Optional[StatementError] 

3349 """The :class:`sqlalchemy.exc.StatementError` which wraps the original, 

3350 and will be raised if exception handling is not circumvented by the event. 

3351 

3352 May be None, as not all exception types are wrapped by SQLAlchemy. 

3353 For DBAPI-level exceptions that subclass the dbapi's Error class, this 

3354 field will always be present. 

3355 

3356 """ 

3357 

3358 chained_exception: Optional[BaseException] 

3359 """The exception that was returned by the previous handler in the 

3360 exception chain, if any. 

3361 

3362 If present, this exception will be the one ultimately raised by 

3363 SQLAlchemy unless a subsequent handler replaces it. 

3364 

3365 May be None. 

3366 

3367 """ 

3368 

3369 execution_context: Optional[ExecutionContext] 

3370 """The :class:`.ExecutionContext` corresponding to the execution 

3371 operation in progress. 

3372 

3373 This is present for statement execution operations, but not for 

3374 operations such as transaction begin/end. It also is not present when 

3375 the exception was raised before the :class:`.ExecutionContext` 

3376 could be constructed. 

3377 

3378 Note that the :attr:`.ExceptionContext.statement` and 

3379 :attr:`.ExceptionContext.parameters` members may represent a 

3380 different value than that of the :class:`.ExecutionContext`, 

3381 potentially in the case where a 

3382 :meth:`_events.ConnectionEvents.before_cursor_execute` event or similar 

3383 modified the statement/parameters to be sent. 

3384 

3385 May be None. 

3386 

3387 """ 

3388 

3389 is_disconnect: bool 

3390 """Represent whether the exception as occurred represents a "disconnect" 

3391 condition. 

3392 

3393 This flag will always be True or False within the scope of the 

3394 :meth:`_events.DialectEvents.handle_error` handler. 

3395 

3396 SQLAlchemy will defer to this flag in order to determine whether or not 

3397 the connection should be invalidated subsequently. That is, by 

3398 assigning to this flag, a "disconnect" event which then results in 

3399 a connection and pool invalidation can be invoked or prevented by 

3400 changing this flag. 

3401 

3402 

3403 .. note:: The pool "pre_ping" handler enabled using the 

3404 :paramref:`_sa.create_engine.pool_pre_ping` parameter does **not** 

3405 consult this event before deciding if the "ping" returned false, 

3406 as opposed to receiving an unhandled error. For this use case, the 

3407 :ref:`legacy recipe based on engine_connect() may be used 

3408 <pool_disconnects_pessimistic_custom>`. A future API allow more 

3409 comprehensive customization of the "disconnect" detection mechanism 

3410 across all functions. 

3411 

3412 """ 

3413 

3414 invalidate_pool_on_disconnect: bool 

3415 """Represent whether all connections in the pool should be invalidated 

3416 when a "disconnect" condition is in effect. 

3417 

3418 Setting this flag to False within the scope of the 

3419 :meth:`_events.DialectEvents.handle_error` 

3420 event will have the effect such 

3421 that the full collection of connections in the pool will not be 

3422 invalidated during a disconnect; only the current connection that is the 

3423 subject of the error will actually be invalidated. 

3424 

3425 The purpose of this flag is for custom disconnect-handling schemes where 

3426 the invalidation of other connections in the pool is to be performed 

3427 based on other conditions, or even on a per-connection basis. 

3428 

3429 """ 

3430 

3431 is_pre_ping: bool 

3432 """Indicates if this error is occurring within the "pre-ping" step 

3433 performed when :paramref:`_sa.create_engine.pool_pre_ping` is set to 

3434 ``True``. In this mode, the :attr:`.ExceptionContext.engine` attribute 

3435 will be ``None``. The dialect in use is accessible via the 

3436 :attr:`.ExceptionContext.dialect` attribute. 

3437 

3438 .. versionadded:: 2.0.5 

3439 

3440 """ 

3441 

3442 

3443class AdaptedConnection: 

3444 """Interface of an adapted connection object to support the DBAPI protocol. 

3445 

3446 Used by asyncio dialects to provide a sync-style pep-249 facade on top 

3447 of the asyncio connection/cursor API provided by the driver. 

3448 

3449 .. versionadded:: 1.4.24 

3450 

3451 """ 

3452 

3453 __slots__ = ("_connection",) 

3454 

3455 _connection: AsyncIODBAPIConnection 

3456 

3457 @property 

3458 def driver_connection(self) -> Any: 

3459 """The connection object as returned by the driver after a connect.""" 

3460 return self._connection 

3461 

3462 def run_async(self, fn: Callable[[Any], Awaitable[_T]]) -> _T: 

3463 """Run the awaitable returned by the given function, which is passed 

3464 the raw asyncio driver connection. 

3465 

3466 This is used to invoke awaitable-only methods on the driver connection 

3467 within the context of a "synchronous" method, like a connection 

3468 pool event handler. 

3469 

3470 E.g.:: 

3471 

3472 engine = create_async_engine(...) 

3473 

3474 

3475 @event.listens_for(engine.sync_engine, "connect") 

3476 def register_custom_types( 

3477 dbapi_connection, # ... 

3478 ): 

3479 dbapi_connection.run_async( 

3480 lambda connection: connection.set_type_codec( 

3481 "MyCustomType", encoder, decoder, ... 

3482 ) 

3483 ) 

3484 

3485 .. versionadded:: 1.4.30 

3486 

3487 .. seealso:: 

3488 

3489 :ref:`asyncio_events_run_async` 

3490 

3491 """ 

3492 return await_(fn(self._connection)) 

3493 

3494 def __repr__(self) -> str: 

3495 return "<AdaptedConnection %s>" % self._connection