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

704 statements  

1# engine/interfaces.py 

2# Copyright (C) 2005-2025 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 Mapping 

23from typing import MutableMapping 

24from typing import Optional 

25from typing import Protocol 

26from typing import Sequence 

27from typing import Set 

28from typing import Tuple 

29from typing import Type 

30from typing import TYPE_CHECKING 

31from typing import TypedDict 

32from typing import TypeVar 

33from typing import Union 

34 

35from .. import util 

36from ..event import EventTarget 

37from ..pool import Pool 

38from ..pool import PoolProxiedConnection as PoolProxiedConnection 

39from ..sql.compiler import Compiled as Compiled 

40from ..sql.compiler import Compiled # noqa 

41from ..sql.compiler import TypeCompiler as TypeCompiler 

42from ..sql.compiler import TypeCompiler # noqa 

43from ..util import immutabledict 

44from ..util.concurrency import await_ 

45from ..util.typing import Literal 

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 DDLCompiler 

60 from ..sql.compiler import IdentifierPreparer 

61 from ..sql.compiler import InsertmanyvaluesSentinelOpts 

62 from ..sql.compiler import Linting 

63 from ..sql.compiler import SQLCompiler 

64 from ..sql.elements import BindParameter 

65 from ..sql.elements import ClauseElement 

66 from ..sql.schema import Column 

67 from ..sql.schema import DefaultGenerator 

68 from ..sql.schema import SchemaItem 

69 from ..sql.schema import Sequence as Sequence_SchemaItem 

70 from ..sql.sqltypes import Integer 

71 from ..sql.type_api import _TypeMemoDict 

72 from ..sql.type_api import TypeEngine 

73 from ..util.langhelpers import generic_fn_descriptor 

74 

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

76 

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

78 

79 

80class CacheStats(Enum): 

81 CACHE_HIT = 0 

82 CACHE_MISS = 1 

83 CACHING_DISABLED = 2 

84 NO_CACHE_KEY = 3 

85 NO_DIALECT_SUPPORT = 4 

86 

87 

88class ExecuteStyle(Enum): 

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

90 a statement.""" 

91 

92 EXECUTE = 0 

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

94 

95 EXECUTEMANY = 1 

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

97 

98 INSERTMANYVALUES = 2 

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

100 VALUES expression will be expanded to accommodate for multiple 

101 parameter sets 

102 

103 .. seealso:: 

104 

105 :ref:`engine_insertmanyvalues` 

106 

107 """ 

108 

109 

110class DBAPIModule(Protocol): 

111 class Error(Exception): 

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

113 

114 class OperationalError(Error): 

115 pass 

116 

117 class InterfaceError(Error): 

118 pass 

119 

120 class IntegrityError(Error): 

121 pass 

122 

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

124 

125 

126class DBAPIConnection(Protocol): 

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

128 

129 .. versionadded:: 2.0 

130 

131 .. seealso:: 

132 

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

134 - in :pep:`249` 

135 

136 """ # noqa: E501 

137 

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

139 

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

141 

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

143 

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

145 

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

147 

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

149 

150 

151class DBAPIType(Protocol): 

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

153 

154 .. versionadded:: 2.0 

155 

156 .. seealso:: 

157 

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

159 - in :pep:`249` 

160 

161 """ # noqa: E501 

162 

163 

164class DBAPICursor(Protocol): 

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

166 

167 .. versionadded:: 2.0 

168 

169 .. seealso:: 

170 

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

172 - in :pep:`249` 

173 

174 """ # noqa: E501 

175 

176 @property 

177 def description( 

178 self, 

179 ) -> _DBAPICursorDescription: 

180 """The description attribute of the Cursor. 

181 

182 .. seealso:: 

183 

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

185 - in :pep:`249` 

186 

187 

188 """ # noqa: E501 

189 ... 

190 

191 @property 

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

193 

194 arraysize: int 

195 

196 lastrowid: int 

197 

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

199 

200 def execute( 

201 self, 

202 operation: Any, 

203 parameters: Optional[_DBAPISingleExecuteParams] = None, 

204 ) -> Any: ... 

205 

206 def executemany( 

207 self, 

208 operation: Any, 

209 parameters: _DBAPIMultiExecuteParams, 

210 ) -> Any: ... 

211 

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

213 

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

215 

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

217 

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

219 

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

221 

222 def callproc( 

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

224 ) -> Any: ... 

225 

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

227 

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

229 

230 

231_CoreSingleExecuteParams = Mapping[str, Any] 

232_MutableCoreSingleExecuteParams = MutableMapping[str, Any] 

233_CoreMultiExecuteParams = Sequence[_CoreSingleExecuteParams] 

234_CoreAnyExecuteParams = Union[ 

235 _CoreMultiExecuteParams, _CoreSingleExecuteParams 

236] 

237 

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

239 

240_DBAPIMultiExecuteParams = Union[ 

241 Sequence[Sequence[Any]], _CoreMultiExecuteParams 

242] 

243_DBAPIAnyExecuteParams = Union[ 

244 _DBAPIMultiExecuteParams, _DBAPISingleExecuteParams 

245] 

246_DBAPICursorDescription = Sequence[ 

247 Tuple[ 

248 str, 

249 "DBAPIType", 

250 Optional[int], 

251 Optional[int], 

252 Optional[int], 

253 Optional[int], 

254 Optional[bool], 

255 ] 

256] 

257 

258_AnySingleExecuteParams = _DBAPISingleExecuteParams 

259_AnyMultiExecuteParams = _DBAPIMultiExecuteParams 

260_AnyExecuteParams = _DBAPIAnyExecuteParams 

261 

262CompiledCacheType = MutableMapping[Any, "Compiled"] 

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

264 

265_ImmutableExecuteOptions = immutabledict[str, Any] 

266 

267_ParamStyle = Literal[ 

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

269] 

270 

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

272 

273IsolationLevel = Literal[ 

274 "SERIALIZABLE", 

275 "REPEATABLE READ", 

276 "READ COMMITTED", 

277 "READ UNCOMMITTED", 

278 "AUTOCOMMIT", 

279] 

280 

281 

282class _CoreKnownExecutionOptions(TypedDict, total=False): 

283 compiled_cache: Optional[CompiledCacheType] 

284 logging_token: str 

285 isolation_level: IsolationLevel 

286 no_parameters: bool 

287 stream_results: bool 

288 max_row_buffer: int 

289 yield_per: int 

290 insertmanyvalues_page_size: int 

291 schema_translate_map: Optional[SchemaTranslateMapType] 

292 preserve_rowcount: bool 

293 driver_column_names: bool 

294 

295 

296_ExecuteOptions = immutabledict[str, Any] 

297CoreExecuteOptionsParameter = Union[ 

298 _CoreKnownExecutionOptions, Mapping[str, Any] 

299] 

300 

301 

302class ReflectedIdentity(TypedDict): 

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

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

305 

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

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

308 :meth:`.Inspector.get_columns` method. 

309 

310 """ 

311 

312 always: bool 

313 """type of identity column""" 

314 

315 on_null: bool 

316 """indicates ON NULL""" 

317 

318 start: int 

319 """starting index of the sequence""" 

320 

321 increment: int 

322 """increment value of the sequence""" 

323 

324 minvalue: int 

325 """the minimum value of the sequence.""" 

326 

327 maxvalue: int 

328 """the maximum value of the sequence.""" 

329 

330 nominvalue: bool 

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

332 

333 nomaxvalue: bool 

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

335 

336 cycle: bool 

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

338 or minvalue has been reached.""" 

339 

340 cache: Optional[int] 

341 """number of future values in the 

342 sequence which are calculated in advance.""" 

343 

344 order: bool 

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

346 

347 

348class ReflectedComputed(TypedDict): 

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

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

351 

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

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

354 :meth:`.Inspector.get_columns` method. 

355 

356 """ 

357 

358 sqltext: str 

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

360 as a string SQL expression""" 

361 

362 persisted: NotRequired[bool] 

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

364 

365 

366class ReflectedColumn(TypedDict): 

367 """Dictionary representing the reflected elements corresponding to 

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

369 

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

371 :class:`.Inspector.get_columns` method. 

372 

373 """ 

374 

375 name: str 

376 """column name""" 

377 

378 type: TypeEngine[Any] 

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

380 

381 nullable: bool 

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

383 

384 default: Optional[str] 

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

386 

387 autoincrement: NotRequired[bool] 

388 """database-dependent autoincrement flag. 

389 

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

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

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

393 such a flag on them. 

394 

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

396 "autoincrement". 

397 

398 """ 

399 

400 comment: NotRequired[Optional[str]] 

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

402 Only some dialects return this key 

403 """ 

404 

405 computed: NotRequired[ReflectedComputed] 

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

407 Only some dialects return this key. 

408 """ 

409 

410 identity: NotRequired[ReflectedIdentity] 

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

412 Only some dialects return this key. 

413 

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

415 """ 

416 

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

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

419 object""" 

420 

421 

422class ReflectedConstraint(TypedDict): 

423 """Dictionary representing the reflected elements corresponding to 

424 :class:`.Constraint` 

425 

426 A base class for all constraints 

427 """ 

428 

429 name: Optional[str] 

430 """constraint name""" 

431 

432 comment: NotRequired[Optional[str]] 

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

434 

435 

436class ReflectedCheckConstraint(ReflectedConstraint): 

437 """Dictionary representing the reflected elements corresponding to 

438 :class:`.CheckConstraint`. 

439 

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

441 :meth:`.Inspector.get_check_constraints` method. 

442 

443 """ 

444 

445 sqltext: str 

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

447 

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

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

450 """ 

451 

452 

453class ReflectedUniqueConstraint(ReflectedConstraint): 

454 """Dictionary representing the reflected elements corresponding to 

455 :class:`.UniqueConstraint`. 

456 

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

458 :meth:`.Inspector.get_unique_constraints` method. 

459 

460 """ 

461 

462 column_names: List[str] 

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

464 

465 duplicates_index: NotRequired[Optional[str]] 

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

467 

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

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

470 constraint""" 

471 

472 

473class ReflectedPrimaryKeyConstraint(ReflectedConstraint): 

474 """Dictionary representing the reflected elements corresponding to 

475 :class:`.PrimaryKeyConstraint`. 

476 

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

478 :meth:`.Inspector.get_pk_constraint` method. 

479 

480 """ 

481 

482 constrained_columns: List[str] 

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

484 

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

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

487 

488 

489class ReflectedForeignKeyConstraint(ReflectedConstraint): 

490 """Dictionary representing the reflected elements corresponding to 

491 :class:`.ForeignKeyConstraint`. 

492 

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

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

495 

496 """ 

497 

498 constrained_columns: List[str] 

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

500 

501 referred_schema: Optional[str] 

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

503 

504 referred_table: str 

505 """name of the table being referred""" 

506 

507 referred_columns: List[str] 

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

509 

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

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

512 

513 

514class ReflectedIndex(TypedDict): 

515 """Dictionary representing the reflected elements corresponding to 

516 :class:`.Index`. 

517 

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

519 :meth:`.Inspector.get_indexes` method. 

520 

521 """ 

522 

523 name: Optional[str] 

524 """index name""" 

525 

526 column_names: List[Optional[str]] 

527 """column names which the index references. 

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

529 returned in the ``expressions`` list. 

530 """ 

531 

532 expressions: NotRequired[List[str]] 

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

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

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

536 """ 

537 

538 unique: bool 

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

540 

541 duplicates_constraint: NotRequired[Optional[str]] 

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

543 

544 include_columns: NotRequired[List[str]] 

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

546 

547 .. deprecated:: 2.0 

548 

549 Legacy value, will be replaced with 

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

551 

552 """ 

553 

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

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

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

557 ``nulls_last``. 

558 """ 

559 

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

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

562 

563 

564class ReflectedTableComment(TypedDict): 

565 """Dictionary representing the reflected comment corresponding to 

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

567 

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

569 :meth:`.Inspector.get_table_comment` method. 

570 

571 """ 

572 

573 text: Optional[str] 

574 """text of the comment""" 

575 

576 

577class BindTyping(Enum): 

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

579 bound parameters in a statement to the database driver. 

580 

581 .. versionadded:: 2.0 

582 

583 """ 

584 

585 NONE = 1 

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

587 

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

589 SQL Server. 

590 

591 """ 

592 

593 SETINPUTSIZES = 2 

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

595 

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

597 the SQLAlchemy dialect has the appropriate infrastructure for that dialect 

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

599 optional support for SQL Server using pyodbc. 

600 

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

602 method for certain datatypes using include/exclude lists. 

603 

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

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

606 

607 """ 

608 

609 RENDER_CASTS = 3 

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

611 

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

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

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

615 aren't. 

616 

617 When RENDER_CASTS is used, the compiler will invoke the 

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

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

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

621 

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

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

624 :attr:`.InsertmanyvaluesSentinelOpts.USE_INSERT_FROM_SELECT` and 

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

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

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

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

629 

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

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

632 

633 

634 """ 

635 

636 

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

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

639 

640 

641class Dialect(EventTarget): 

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

643 

644 Any aspect of metadata definition, SQL query generation, 

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

646 between databases is defined under the general category of the 

647 Dialect. The Dialect acts as a factory for other 

648 database-specific object implementations including 

649 ExecutionContext, Compiled, DefaultGenerator, and TypeEngine. 

650 

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

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

653 descendant class. 

654 

655 """ 

656 

657 CACHE_HIT = CacheStats.CACHE_HIT 

658 CACHE_MISS = CacheStats.CACHE_MISS 

659 CACHING_DISABLED = CacheStats.CACHING_DISABLED 

660 NO_CACHE_KEY = CacheStats.NO_CACHE_KEY 

661 NO_DIALECT_SUPPORT = CacheStats.NO_DIALECT_SUPPORT 

662 

663 dispatch: dispatcher[Dialect] 

664 

665 name: str 

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

667 (i.e. 'sqlite') 

668 """ 

669 

670 driver: str 

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

672 

673 dialect_description: str 

674 

675 dbapi: Optional[DBAPIModule] 

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

677 

678 SQLAlchemy dialects import DBAPI modules using the classmethod 

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

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

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

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

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

684 the DBAPI module to this attribute. 

685 

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

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

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

689 contents. 

690 

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

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

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

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

695 

696 """ 

697 

698 @util.non_memoized_property 

699 def loaded_dbapi(self) -> DBAPIModule: 

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

701 DBAPI was set up. 

702 

703 .. versionadded:: 2.0 

704 

705 """ 

706 raise NotImplementedError() 

707 

708 positional: bool 

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

710 

711 paramstyle: str 

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

713 paramstyles). 

714 """ 

715 

716 compiler_linting: Linting 

717 

718 statement_compiler: Type[SQLCompiler] 

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

720 

721 ddl_compiler: Type[DDLCompiler] 

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

723 

724 type_compiler_cls: ClassVar[Type[TypeCompiler]] 

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

726 

727 .. versionadded:: 2.0 

728 

729 """ 

730 

731 type_compiler_instance: TypeCompiler 

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

733 objects 

734 

735 .. versionadded:: 2.0 

736 

737 """ 

738 

739 type_compiler: Any 

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

741 TypeCompiler instance at the instance level. 

742 

743 Refer to type_compiler_instance instead. 

744 

745 """ 

746 

747 preparer: Type[IdentifierPreparer] 

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

749 quote identifiers. 

750 """ 

751 

752 identifier_preparer: IdentifierPreparer 

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

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

755 

756 """ 

757 

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

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

760 

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

762 typically populated during the initial connection to the database. 

763 """ 

764 

765 default_schema_name: Optional[str] 

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

767 supporting dialects, and is typically populated during the 

768 initial connection to the database. 

769 

770 """ 

771 

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

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

774 default_isolation_level: Optional[IsolationLevel] 

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

776 

777 skip_autocommit_rollback: bool 

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

779 parameter was set. 

780 

781 .. versionadded:: 2.0.43 

782 

783 """ 

784 

785 # create_engine() -> isolation_level currently goes here 

786 _on_connect_isolation_level: Optional[IsolationLevel] 

787 

788 execution_ctx_cls: Type[ExecutionContext] 

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

790 

791 execute_sequence_format: Union[ 

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

793 ] 

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

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

796 

797 supports_alter: bool 

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

799 generating foreign key constraints in certain circumstances 

800 """ 

801 

802 max_identifier_length: int 

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

804 max_index_name_length: Optional[int] 

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

806 ``max_identifier_length``.""" 

807 max_constraint_name_length: Optional[int] 

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

809 ``max_identifier_length``.""" 

810 

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

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

813 

814 server_side_cursors: bool 

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

816 side cursors by default""" 

817 

818 supports_sane_rowcount: bool 

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

820 ``UPDATE`` and ``DELETE`` statements. 

821 """ 

822 

823 supports_sane_multi_rowcount: bool 

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

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

826 executemany. 

827 """ 

828 

829 supports_empty_insert: bool 

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

831 columns in it. 

832 

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

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

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

836 

837 """ 

838 

839 supports_default_values: bool 

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

841 

842 supports_default_metavalue: bool 

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

844 

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

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

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

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

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

850 

851 """ 

852 

853 default_metavalue_token: str = "DEFAULT" 

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

855 parenthesis. 

856 

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

858 

859 """ 

860 

861 supports_multivalues_insert: bool 

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

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

864 

865 """ 

866 

867 insert_executemany_returning: bool 

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

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

870 

871 """ 

872 

873 insert_executemany_returning_sort_by_parameter_order: bool 

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

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

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

877 parameter being set. 

878 

879 """ 

880 

881 update_executemany_returning: bool 

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

883 

884 delete_executemany_returning: bool 

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

886 

887 use_insertmanyvalues: bool 

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

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

890 

891 In practice, setting this to True means: 

892 

893 if ``supports_multivalues_insert``, ``insert_returning`` and 

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

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

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

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

898 INSERT statement to have multiple VALUES clauses, also executing 

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

900 of rows are given. 

901 

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

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

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

905 with RETURNING" support and also does not support 

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

907 that don't support RETURNING will not report 

908 ``insert_executemany_returning`` as True. 

909 

910 .. versionadded:: 2.0 

911 

912 .. seealso:: 

913 

914 :ref:`engine_insertmanyvalues` 

915 

916 """ 

917 

918 use_insertmanyvalues_wo_returning: bool 

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

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

921 

922 .. versionadded:: 2.0 

923 

924 .. seealso:: 

925 

926 :ref:`engine_insertmanyvalues` 

927 

928 """ 

929 

930 insertmanyvalues_implicit_sentinel: InsertmanyvaluesSentinelOpts 

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

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

933 for INSERTed rows. 

934 

935 .. versionadded:: 2.0.10 

936 

937 .. seealso:: 

938 

939 :ref:`engine_insertmanyvalues_returning_order` 

940 

941 """ 

942 

943 insertmanyvalues_page_size: int 

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

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

946 

947 The default dialect defaults this to 1000. 

948 

949 .. versionadded:: 2.0 

950 

951 .. seealso:: 

952 

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

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

955 

956 """ # noqa: E501 

957 

958 insertmanyvalues_max_parameters: int 

959 """Alternate to insertmanyvalues_page_size, will additionally limit 

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

961 

962 

963 """ 

964 

965 preexecute_autoincrement_sequences: bool 

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

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

968 

969 This is currently oriented towards PostgreSQL when the 

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

971 object. 

972 

973 """ 

974 

975 insert_returning: bool 

976 """if the dialect supports RETURNING with INSERT 

977 

978 .. versionadded:: 2.0 

979 

980 """ 

981 

982 update_returning: bool 

983 """if the dialect supports RETURNING with UPDATE 

984 

985 .. versionadded:: 2.0 

986 

987 """ 

988 

989 update_returning_multifrom: bool 

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

991 

992 .. versionadded:: 2.0 

993 

994 """ 

995 

996 delete_returning: bool 

997 """if the dialect supports RETURNING with DELETE 

998 

999 .. versionadded:: 2.0 

1000 

1001 """ 

1002 

1003 delete_returning_multifrom: bool 

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

1005 

1006 .. versionadded:: 2.0 

1007 

1008 """ 

1009 

1010 favor_returning_over_lastrowid: bool 

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

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

1013 

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

1015 

1016 """ 

1017 

1018 supports_identity_columns: bool 

1019 """target database supports IDENTITY""" 

1020 

1021 cte_follows_insert: bool 

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

1023 the CTE to be below the INSERT""" 

1024 

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

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

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

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

1029 dialect instance itself. 

1030 """ 

1031 

1032 supports_sequences: bool 

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

1034 

1035 sequences_optional: bool 

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

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

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

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

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

1041 other backends. 

1042 """ 

1043 

1044 default_sequence_base: int 

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

1046 a CREATE SEQUENCE DDL statement. 

1047 

1048 """ 

1049 

1050 supports_native_enum: bool 

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

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

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

1054 """ 

1055 

1056 supports_native_boolean: bool 

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

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

1059 constraint when that type is used. 

1060 """ 

1061 

1062 supports_native_decimal: bool 

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

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

1065 

1066 supports_native_uuid: bool 

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

1068 driver for SQL UUID datatypes. 

1069 

1070 .. versionadded:: 2.0 

1071 

1072 """ 

1073 

1074 returns_native_bytes: bool 

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

1076 driver for SQL "binary" datatypes. 

1077 

1078 .. versionadded:: 2.0.11 

1079 

1080 """ 

1081 

1082 construct_arguments: Optional[ 

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

1084 ] = None 

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

1086 constructs, typically schema items. 

1087 

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

1089 

1090 construct_arguments = [ 

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

1092 ] 

1093 

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

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

1096 ``postgresql_using``, ``postgresql_where``, nad ``postgresql_ops``. 

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

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

1099 

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

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

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

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

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

1105 feature continue to function in the old way. 

1106 

1107 .. seealso:: 

1108 

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

1110 :attr:`.DefaultDialect.construct_arguments` 

1111 

1112 

1113 """ 

1114 

1115 reflection_options: Sequence[str] = () 

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

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

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

1119 

1120 Current example is "oracle_resolve_synonyms" in the Oracle Database 

1121 dialects. 

1122 

1123 """ 

1124 

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

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

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

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

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

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

1131 majority of cases this dictionary is empty. 

1132 """ 

1133 

1134 supports_comments: bool 

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

1136 

1137 inline_comments: bool 

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

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

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

1141 

1142 supports_constraint_comments: bool 

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

1144 

1145 .. versionadded:: 2.0 

1146 """ 

1147 

1148 _has_events = False 

1149 

1150 supports_statement_cache: bool = True 

1151 """indicates if this dialect supports caching. 

1152 

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

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

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

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

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

1158 compliant with SQL statement caching. 

1159 

1160 .. versionadded:: 1.4.5 

1161 

1162 .. seealso:: 

1163 

1164 :ref:`engine_thirdparty_caching` 

1165 

1166 """ 

1167 

1168 _supports_statement_cache: bool 

1169 """internal evaluation for supports_statement_cache""" 

1170 

1171 bind_typing = BindTyping.NONE 

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

1173 driver for bound parameters. 

1174 

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

1176 

1177 .. versionadded:: 2.0 

1178 

1179 """ 

1180 

1181 is_async: bool 

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

1183 

1184 has_terminate: bool 

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

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

1187 

1188 engine_config_types: Mapping[str, Any] 

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

1190 type conversion functions. 

1191 

1192 """ 

1193 

1194 label_length: Optional[int] 

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

1196 

1197 include_set_input_sizes: Optional[Set[Any]] 

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

1199 automatic cursor.setinputsizes() calls. 

1200 

1201 This is only used if bind_typing is BindTyping.SET_INPUT_SIZES 

1202 

1203 """ 

1204 

1205 exclude_set_input_sizes: Optional[Set[Any]] 

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

1207 automatic cursor.setinputsizes() calls. 

1208 

1209 This is only used if bind_typing is BindTyping.SET_INPUT_SIZES 

1210 

1211 """ 

1212 

1213 supports_simple_order_by_label: bool 

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

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

1216 

1217 div_is_floordiv: bool 

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

1219 

1220 tuple_in_values: bool 

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

1222 

1223 _bind_typing_render_casts: bool 

1224 

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

1226 

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

1228 raise NotImplementedError() 

1229 

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

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

1232 

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

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

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

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

1237 ``connect()`` function. 

1238 

1239 The method typically makes use of the 

1240 :meth:`.URL.translate_connect_args` 

1241 method in order to generate a dictionary of options. 

1242 

1243 The default implementation is:: 

1244 

1245 def create_connect_args(self, url): 

1246 opts = url.translate_connect_args() 

1247 opts.update(url.query) 

1248 return ([], opts) 

1249 

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

1251 

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

1253 :meth:`.Dialect.connect` method. 

1254 

1255 .. seealso:: 

1256 

1257 :meth:`.URL.translate_connect_args` 

1258 

1259 """ 

1260 

1261 raise NotImplementedError() 

1262 

1263 @classmethod 

1264 def import_dbapi(cls) -> DBAPIModule: 

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

1266 

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

1268 instance variable to a constructed dialect under the name 

1269 ``.dbapi``. 

1270 

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

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

1273 which would be replaced at dialect instantiation time by the 

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

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

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

1277 

1278 """ 

1279 raise NotImplementedError() 

1280 

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

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

1283 

1284 Dialect classes will usually use the 

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

1286 accomplish this. 

1287 

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

1289 contain no dialect-instance state. 

1290 

1291 """ 

1292 

1293 raise NotImplementedError() 

1294 

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

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

1297 connection. 

1298 

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

1300 other properties. 

1301 

1302 The connection passed here is a SQLAlchemy Connection object, 

1303 with full capabilities. 

1304 

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

1306 super(). 

1307 

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

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

1310 

1311 """ 

1312 

1313 if TYPE_CHECKING: 

1314 

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

1316 

1317 def get_columns( 

1318 self, 

1319 connection: Connection, 

1320 table_name: str, 

1321 schema: Optional[str] = None, 

1322 **kw: Any, 

1323 ) -> List[ReflectedColumn]: 

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

1325 

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

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

1328 information as a list of dictionaries 

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

1330 

1331 This is an internal dialect method. Applications should use 

1332 :meth:`.Inspector.get_columns`. 

1333 

1334 """ 

1335 

1336 raise NotImplementedError() 

1337 

1338 def get_multi_columns( 

1339 self, 

1340 connection: Connection, 

1341 *, 

1342 schema: Optional[str] = None, 

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

1344 **kw: Any, 

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

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

1347 given ``schema``. 

1348 

1349 This is an internal dialect method. Applications should use 

1350 :meth:`.Inspector.get_multi_columns`. 

1351 

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

1353 implementation that will call the single table method for 

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

1355 :meth:`Dialect.get_view_names` or 

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

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

1358 implementation should implement this method. 

1359 

1360 .. versionadded:: 2.0 

1361 

1362 """ 

1363 

1364 raise NotImplementedError() 

1365 

1366 def get_pk_constraint( 

1367 self, 

1368 connection: Connection, 

1369 table_name: str, 

1370 schema: Optional[str] = None, 

1371 **kw: Any, 

1372 ) -> ReflectedPrimaryKeyConstraint: 

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

1374 table_name`. 

1375 

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

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

1378 key information as a dictionary corresponding to the 

1379 :class:`.ReflectedPrimaryKeyConstraint` dictionary. 

1380 

1381 This is an internal dialect method. Applications should use 

1382 :meth:`.Inspector.get_pk_constraint`. 

1383 

1384 """ 

1385 raise NotImplementedError() 

1386 

1387 def get_multi_pk_constraint( 

1388 self, 

1389 connection: Connection, 

1390 *, 

1391 schema: Optional[str] = None, 

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

1393 **kw: Any, 

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

1395 """Return information about primary key constraints in 

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

1397 

1398 This is an internal dialect method. Applications should use 

1399 :meth:`.Inspector.get_multi_pk_constraint`. 

1400 

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

1402 implementation that will call the single table method for 

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

1404 :meth:`Dialect.get_view_names` or 

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

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

1407 implementation should implement this method. 

1408 

1409 .. versionadded:: 2.0 

1410 

1411 """ 

1412 raise NotImplementedError() 

1413 

1414 def get_foreign_keys( 

1415 self, 

1416 connection: Connection, 

1417 table_name: str, 

1418 schema: Optional[str] = None, 

1419 **kw: Any, 

1420 ) -> List[ReflectedForeignKeyConstraint]: 

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

1422 

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

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

1425 key information as a list of dicts corresponding to the 

1426 :class:`.ReflectedForeignKeyConstraint` dictionary. 

1427 

1428 This is an internal dialect method. Applications should use 

1429 :meth:`_engine.Inspector.get_foreign_keys`. 

1430 """ 

1431 

1432 raise NotImplementedError() 

1433 

1434 def get_multi_foreign_keys( 

1435 self, 

1436 connection: Connection, 

1437 *, 

1438 schema: Optional[str] = None, 

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

1440 **kw: Any, 

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

1442 """Return information about foreign_keys in all tables 

1443 in the given ``schema``. 

1444 

1445 This is an internal dialect method. Applications should use 

1446 :meth:`_engine.Inspector.get_multi_foreign_keys`. 

1447 

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

1449 implementation that will call the single table method for 

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

1451 :meth:`Dialect.get_view_names` or 

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

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

1454 implementation should implement this method. 

1455 

1456 .. versionadded:: 2.0 

1457 

1458 """ 

1459 

1460 raise NotImplementedError() 

1461 

1462 def get_table_names( 

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

1464 ) -> List[str]: 

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

1466 

1467 This is an internal dialect method. Applications should use 

1468 :meth:`_engine.Inspector.get_table_names`. 

1469 

1470 """ 

1471 

1472 raise NotImplementedError() 

1473 

1474 def get_temp_table_names( 

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

1476 ) -> List[str]: 

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

1478 if supported by the underlying backend. 

1479 

1480 This is an internal dialect method. Applications should use 

1481 :meth:`_engine.Inspector.get_temp_table_names`. 

1482 

1483 """ 

1484 

1485 raise NotImplementedError() 

1486 

1487 def get_view_names( 

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

1489 ) -> List[str]: 

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

1491 database. 

1492 

1493 This is an internal dialect method. Applications should use 

1494 :meth:`_engine.Inspector.get_view_names`. 

1495 

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

1497 

1498 """ 

1499 

1500 raise NotImplementedError() 

1501 

1502 def get_materialized_view_names( 

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

1504 ) -> List[str]: 

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

1506 database. 

1507 

1508 This is an internal dialect method. Applications should use 

1509 :meth:`_engine.Inspector.get_materialized_view_names`. 

1510 

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

1512 

1513 .. versionadded:: 2.0 

1514 

1515 """ 

1516 

1517 raise NotImplementedError() 

1518 

1519 def get_sequence_names( 

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

1521 ) -> List[str]: 

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

1523 

1524 This is an internal dialect method. Applications should use 

1525 :meth:`_engine.Inspector.get_sequence_names`. 

1526 

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

1528 

1529 .. versionadded:: 1.4 

1530 """ 

1531 

1532 raise NotImplementedError() 

1533 

1534 def get_temp_view_names( 

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

1536 ) -> List[str]: 

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

1538 if supported by the underlying backend. 

1539 

1540 This is an internal dialect method. Applications should use 

1541 :meth:`_engine.Inspector.get_temp_view_names`. 

1542 

1543 """ 

1544 

1545 raise NotImplementedError() 

1546 

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

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

1549 

1550 This is an internal dialect method. Applications should use 

1551 :meth:`_engine.Inspector.get_schema_names`. 

1552 """ 

1553 raise NotImplementedError() 

1554 

1555 def get_view_definition( 

1556 self, 

1557 connection: Connection, 

1558 view_name: str, 

1559 schema: Optional[str] = None, 

1560 **kw: Any, 

1561 ) -> str: 

1562 """Return plain or materialized view definition. 

1563 

1564 This is an internal dialect method. Applications should use 

1565 :meth:`_engine.Inspector.get_view_definition`. 

1566 

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

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

1569 definition. 

1570 """ 

1571 

1572 raise NotImplementedError() 

1573 

1574 def get_indexes( 

1575 self, 

1576 connection: Connection, 

1577 table_name: str, 

1578 schema: Optional[str] = None, 

1579 **kw: Any, 

1580 ) -> List[ReflectedIndex]: 

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

1582 

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

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

1585 information as a list of dictionaries corresponding to the 

1586 :class:`.ReflectedIndex` dictionary. 

1587 

1588 This is an internal dialect method. Applications should use 

1589 :meth:`.Inspector.get_indexes`. 

1590 """ 

1591 

1592 raise NotImplementedError() 

1593 

1594 def get_multi_indexes( 

1595 self, 

1596 connection: Connection, 

1597 *, 

1598 schema: Optional[str] = None, 

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

1600 **kw: Any, 

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

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

1603 in the given ``schema``. 

1604 

1605 This is an internal dialect method. Applications should use 

1606 :meth:`.Inspector.get_multi_indexes`. 

1607 

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

1609 implementation that will call the single table method for 

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

1611 :meth:`Dialect.get_view_names` or 

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

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

1614 implementation should implement this method. 

1615 

1616 .. versionadded:: 2.0 

1617 

1618 """ 

1619 

1620 raise NotImplementedError() 

1621 

1622 def get_unique_constraints( 

1623 self, 

1624 connection: Connection, 

1625 table_name: str, 

1626 schema: Optional[str] = None, 

1627 **kw: Any, 

1628 ) -> List[ReflectedUniqueConstraint]: 

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

1630 

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

1632 unique constraint information as a list of dicts corresponding 

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

1634 

1635 This is an internal dialect method. Applications should use 

1636 :meth:`.Inspector.get_unique_constraints`. 

1637 """ 

1638 

1639 raise NotImplementedError() 

1640 

1641 def get_multi_unique_constraints( 

1642 self, 

1643 connection: Connection, 

1644 *, 

1645 schema: Optional[str] = None, 

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

1647 **kw: Any, 

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

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

1650 in the given ``schema``. 

1651 

1652 This is an internal dialect method. Applications should use 

1653 :meth:`.Inspector.get_multi_unique_constraints`. 

1654 

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

1656 implementation that will call the single table method for 

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

1658 :meth:`Dialect.get_view_names` or 

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

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

1661 implementation should implement this method. 

1662 

1663 .. versionadded:: 2.0 

1664 

1665 """ 

1666 

1667 raise NotImplementedError() 

1668 

1669 def get_check_constraints( 

1670 self, 

1671 connection: Connection, 

1672 table_name: str, 

1673 schema: Optional[str] = None, 

1674 **kw: Any, 

1675 ) -> List[ReflectedCheckConstraint]: 

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

1677 

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

1679 check constraint information as a list of dicts corresponding 

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

1681 

1682 This is an internal dialect method. Applications should use 

1683 :meth:`.Inspector.get_check_constraints`. 

1684 

1685 """ 

1686 

1687 raise NotImplementedError() 

1688 

1689 def get_multi_check_constraints( 

1690 self, 

1691 connection: Connection, 

1692 *, 

1693 schema: Optional[str] = None, 

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

1695 **kw: Any, 

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

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

1698 in the given ``schema``. 

1699 

1700 This is an internal dialect method. Applications should use 

1701 :meth:`.Inspector.get_multi_check_constraints`. 

1702 

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

1704 implementation that will call the single table method for 

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

1706 :meth:`Dialect.get_view_names` or 

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

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

1709 implementation should implement this method. 

1710 

1711 .. versionadded:: 2.0 

1712 

1713 """ 

1714 

1715 raise NotImplementedError() 

1716 

1717 def get_table_options( 

1718 self, 

1719 connection: Connection, 

1720 table_name: str, 

1721 schema: Optional[str] = None, 

1722 **kw: Any, 

1723 ) -> Dict[str, Any]: 

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

1725 was created. 

1726 

1727 This is an internal dialect method. Applications should use 

1728 :meth:`_engine.Inspector.get_table_options`. 

1729 """ 

1730 raise NotImplementedError() 

1731 

1732 def get_multi_table_options( 

1733 self, 

1734 connection: Connection, 

1735 *, 

1736 schema: Optional[str] = None, 

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

1738 **kw: Any, 

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

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

1741 given schema were created. 

1742 

1743 This is an internal dialect method. Applications should use 

1744 :meth:`_engine.Inspector.get_multi_table_options`. 

1745 

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

1747 implementation that will call the single table method for 

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

1749 :meth:`Dialect.get_view_names` or 

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

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

1752 implementation should implement this method. 

1753 

1754 .. versionadded:: 2.0 

1755 

1756 """ 

1757 raise NotImplementedError() 

1758 

1759 def get_table_comment( 

1760 self, 

1761 connection: Connection, 

1762 table_name: str, 

1763 schema: Optional[str] = None, 

1764 **kw: Any, 

1765 ) -> ReflectedTableComment: 

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

1767 

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

1769 table comment information as a dictionary corresponding to the 

1770 :class:`.ReflectedTableComment` dictionary. 

1771 

1772 This is an internal dialect method. Applications should use 

1773 :meth:`.Inspector.get_table_comment`. 

1774 

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

1776 comments. 

1777 

1778 """ 

1779 

1780 raise NotImplementedError() 

1781 

1782 def get_multi_table_comment( 

1783 self, 

1784 connection: Connection, 

1785 *, 

1786 schema: Optional[str] = None, 

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

1788 **kw: Any, 

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

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

1791 in the given ``schema``. 

1792 

1793 This is an internal dialect method. Applications should use 

1794 :meth:`_engine.Inspector.get_multi_table_comment`. 

1795 

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

1797 implementation that will call the single table method for 

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

1799 :meth:`Dialect.get_view_names` or 

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

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

1802 implementation should implement this method. 

1803 

1804 .. versionadded:: 2.0 

1805 

1806 """ 

1807 

1808 raise NotImplementedError() 

1809 

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

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

1812 case insensitive. 

1813 

1814 This method is only used if the dialect defines 

1815 requires_name_normalize=True. 

1816 

1817 """ 

1818 raise NotImplementedError() 

1819 

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

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

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

1823 

1824 This method is only used if the dialect defines 

1825 requires_name_normalize=True. 

1826 

1827 """ 

1828 raise NotImplementedError() 

1829 

1830 def has_table( 

1831 self, 

1832 connection: Connection, 

1833 table_name: str, 

1834 schema: Optional[str] = None, 

1835 **kw: Any, 

1836 ) -> bool: 

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

1838 or view in the database. 

1839 

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

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

1842 database, False otherwise. 

1843 

1844 This method serves as the underlying implementation of the 

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

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

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

1848 

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

1850 published so that third-party dialects may provide an 

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

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

1853 

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

1855 formally supports checking for additional table-like objects: 

1856 

1857 * any type of views (plain or materialized) 

1858 * temporary tables of any kind 

1859 

1860 Previously, these two checks were not formally specified and 

1861 different dialects would vary in their behavior. The dialect 

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

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

1864 or temporary tables should seek to support locating these objects 

1865 for full compliance. 

1866 

1867 """ 

1868 

1869 raise NotImplementedError() 

1870 

1871 def has_index( 

1872 self, 

1873 connection: Connection, 

1874 table_name: str, 

1875 index_name: str, 

1876 schema: Optional[str] = None, 

1877 **kw: Any, 

1878 ) -> bool: 

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

1880 

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

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

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

1884 

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

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

1887 however dialects can implement a more performant version. 

1888 

1889 This is an internal dialect method. Applications should use 

1890 :meth:`_engine.Inspector.has_index`. 

1891 

1892 .. versionadded:: 1.4 

1893 

1894 """ 

1895 

1896 raise NotImplementedError() 

1897 

1898 def has_sequence( 

1899 self, 

1900 connection: Connection, 

1901 sequence_name: str, 

1902 schema: Optional[str] = None, 

1903 **kw: Any, 

1904 ) -> bool: 

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

1906 

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

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

1909 the database, ``False`` otherwise. 

1910 

1911 This is an internal dialect method. Applications should use 

1912 :meth:`_engine.Inspector.has_sequence`. 

1913 """ 

1914 

1915 raise NotImplementedError() 

1916 

1917 def has_schema( 

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

1919 ) -> bool: 

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

1921 

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

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

1924 given exists, ``False`` otherwise. 

1925 

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

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

1928 :meth:`.Dialect.get_schema_names`, 

1929 however dialects can implement a more performant version. 

1930 

1931 This is an internal dialect method. Applications should use 

1932 :meth:`_engine.Inspector.has_schema`. 

1933 

1934 .. versionadded:: 2.0 

1935 

1936 """ 

1937 

1938 raise NotImplementedError() 

1939 

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

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

1942 

1943 This is used by the default implementation to populate the 

1944 "server_version_info" attribute and is called exactly 

1945 once upon first connect. 

1946 

1947 """ 

1948 

1949 raise NotImplementedError() 

1950 

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

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

1953 the given connection. 

1954 

1955 This is used by the default implementation to populate the 

1956 "default_schema_name" attribute and is called exactly 

1957 once upon first connect. 

1958 

1959 """ 

1960 

1961 raise NotImplementedError() 

1962 

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

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

1965 DB-API connection. 

1966 

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

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

1969 DBAPIs that might need additional help in this area. 

1970 

1971 :param dbapi_connection: a DBAPI connection, typically 

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

1973 

1974 """ 

1975 

1976 raise NotImplementedError() 

1977 

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

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

1980 a DB-API connection. 

1981 

1982 :param dbapi_connection: a DBAPI connection, typically 

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

1984 

1985 """ 

1986 

1987 raise NotImplementedError() 

1988 

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

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

1991 DB-API connection. 

1992 

1993 :param dbapi_connection: a DBAPI connection, typically 

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

1995 

1996 """ 

1997 

1998 raise NotImplementedError() 

1999 

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

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

2002 much as possible to not block, given a DBAPI 

2003 connection. 

2004 

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

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

2007 

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

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

2010 

2011 .. versionadded:: 1.4.41 

2012 

2013 """ 

2014 

2015 raise NotImplementedError() 

2016 

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

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

2019 connection. 

2020 

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

2022 when a connection has been 

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

2024 capacity of the pool. 

2025 

2026 """ 

2027 

2028 raise NotImplementedError() 

2029 

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

2031 raise NotImplementedError() 

2032 

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

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

2035 usable.""" 

2036 raise NotImplementedError() 

2037 

2038 def do_set_input_sizes( 

2039 self, 

2040 cursor: DBAPICursor, 

2041 list_of_tuples: _GenericSetInputSizesType, 

2042 context: ExecutionContext, 

2043 ) -> Any: 

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

2045 

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

2047 set to the 

2048 :attr:`.BindTyping.SETINPUTSIZES` value. 

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

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

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

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

2053 

2054 .. versionadded:: 1.4 

2055 

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

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

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

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

2060 appropriately. 

2061 

2062 

2063 """ 

2064 raise NotImplementedError() 

2065 

2066 def create_xid(self) -> Any: 

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

2068 

2069 This id will be passed to do_begin_twophase(), 

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

2071 unspecified. 

2072 """ 

2073 

2074 raise NotImplementedError() 

2075 

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

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

2078 

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

2080 :param name: savepoint name. 

2081 

2082 """ 

2083 

2084 raise NotImplementedError() 

2085 

2086 def do_rollback_to_savepoint( 

2087 self, connection: Connection, name: str 

2088 ) -> None: 

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

2090 

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

2092 :param name: savepoint name. 

2093 

2094 """ 

2095 

2096 raise NotImplementedError() 

2097 

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

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

2100 

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

2102 :param name: savepoint name. 

2103 """ 

2104 

2105 raise NotImplementedError() 

2106 

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

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

2109 

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

2111 :param xid: xid 

2112 

2113 """ 

2114 

2115 raise NotImplementedError() 

2116 

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

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

2119 

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

2121 :param xid: xid 

2122 

2123 """ 

2124 

2125 raise NotImplementedError() 

2126 

2127 def do_rollback_twophase( 

2128 self, 

2129 connection: Connection, 

2130 xid: Any, 

2131 is_prepared: bool = True, 

2132 recover: bool = False, 

2133 ) -> None: 

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

2135 

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

2137 :param xid: xid 

2138 :param is_prepared: whether or not 

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

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

2141 

2142 """ 

2143 

2144 raise NotImplementedError() 

2145 

2146 def do_commit_twophase( 

2147 self, 

2148 connection: Connection, 

2149 xid: Any, 

2150 is_prepared: bool = True, 

2151 recover: bool = False, 

2152 ) -> None: 

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

2154 

2155 

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

2157 :param xid: xid 

2158 :param is_prepared: whether or not 

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

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

2161 

2162 """ 

2163 

2164 raise NotImplementedError() 

2165 

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

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

2168 identifiers on the given connection. 

2169 

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

2171 

2172 """ 

2173 

2174 raise NotImplementedError() 

2175 

2176 def _deliver_insertmanyvalues_batches( 

2177 self, 

2178 connection: Connection, 

2179 cursor: DBAPICursor, 

2180 statement: str, 

2181 parameters: _DBAPIMultiExecuteParams, 

2182 generic_setinputsizes: Optional[_GenericSetInputSizesType], 

2183 context: ExecutionContext, 

2184 ) -> Iterator[_InsertManyValuesBatch]: 

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

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

2187 feature. 

2188 

2189 """ 

2190 raise NotImplementedError() 

2191 

2192 def do_executemany( 

2193 self, 

2194 cursor: DBAPICursor, 

2195 statement: str, 

2196 parameters: _DBAPIMultiExecuteParams, 

2197 context: Optional[ExecutionContext] = None, 

2198 ) -> None: 

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

2200 parameters)``.""" 

2201 

2202 raise NotImplementedError() 

2203 

2204 def do_execute( 

2205 self, 

2206 cursor: DBAPICursor, 

2207 statement: str, 

2208 parameters: Optional[_DBAPISingleExecuteParams], 

2209 context: Optional[ExecutionContext] = None, 

2210 ) -> None: 

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

2212 parameters)``.""" 

2213 

2214 raise NotImplementedError() 

2215 

2216 def do_execute_no_params( 

2217 self, 

2218 cursor: DBAPICursor, 

2219 statement: str, 

2220 context: Optional[ExecutionContext] = None, 

2221 ) -> None: 

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

2223 

2224 The parameter collection should not be sent. 

2225 

2226 """ 

2227 

2228 raise NotImplementedError() 

2229 

2230 def is_disconnect( 

2231 self, 

2232 e: DBAPIModule.Error, 

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

2234 cursor: Optional[DBAPICursor], 

2235 ) -> bool: 

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

2237 connection""" 

2238 

2239 raise NotImplementedError() 

2240 

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

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

2243 

2244 The default implementation of this method is:: 

2245 

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

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

2248 

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

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

2251 

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

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

2254 DBAPI. 

2255 

2256 

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

2258 :meth:`.Dialect.create_connect_args` method 

2259 

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

2261 :meth:`.Dialect.create_connect_args` method. 

2262 

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

2264 level ``.connect()`` function. 

2265 

2266 .. seealso:: 

2267 

2268 :meth:`.Dialect.create_connect_args` 

2269 

2270 :meth:`.Dialect.on_connect` 

2271 

2272 """ 

2273 raise NotImplementedError() 

2274 

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

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

2277 

2278 This method is a new hook that supersedes the 

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

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

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

2282 compatibility with existing dialects. There is no deprecation 

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

2284 

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

2286 DBAPI connection itself. The inner callable has no 

2287 return value. 

2288 

2289 E.g.:: 

2290 

2291 class MyDialect(default.DefaultDialect): 

2292 # ... 

2293 

2294 def on_connect_url(self, url): 

2295 def do_on_connect(connection): 

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

2297 

2298 return do_on_connect 

2299 

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

2301 isolation modes, Unicode modes, etc. 

2302 

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

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

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

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

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

2308 replaced by plugins. 

2309 

2310 .. note:: 

2311 

2312 The default implementation of 

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

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

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

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

2317 it directly from here. 

2318 

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

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

2321 

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

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

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

2325 

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

2327 argument, or None. 

2328 

2329 .. seealso:: 

2330 

2331 :meth:`_engine.Dialect.on_connect` 

2332 

2333 """ 

2334 return self.on_connect() 

2335 

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

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

2338 

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

2340 DBAPI connection itself. The inner callable has no 

2341 return value. 

2342 

2343 E.g.:: 

2344 

2345 class MyDialect(default.DefaultDialect): 

2346 # ... 

2347 

2348 def on_connect(self): 

2349 def do_on_connect(connection): 

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

2351 

2352 return do_on_connect 

2353 

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

2355 isolation modes, Unicode modes, etc. 

2356 

2357 The "do_on_connect" callable is invoked by using the 

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

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

2360 callable. 

2361 

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

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

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

2365 

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

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

2368 the connect args. Dialects can implement on_connect_url instead 

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

2370 connection in order to get additional context. 

2371 

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

2373 

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

2375 argument, or None. 

2376 

2377 .. seealso:: 

2378 

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

2380 itself to be controlled. 

2381 

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

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

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

2385 

2386 """ 

2387 return None 

2388 

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

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

2391 

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

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

2394 :class:`_engine.Engine` 

2395 isolation level facilities; these APIs should be preferred for 

2396 most typical use cases. 

2397 

2398 .. seealso:: 

2399 

2400 :meth:`_engine.Connection.get_isolation_level` 

2401 - view current level 

2402 

2403 :attr:`_engine.Connection.default_isolation_level` 

2404 - view default level 

2405 

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

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

2408 

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

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

2411 

2412 """ 

2413 

2414 raise NotImplementedError() 

2415 

2416 def set_isolation_level( 

2417 self, dbapi_connection: DBAPIConnection, level: IsolationLevel 

2418 ) -> None: 

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

2420 

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

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

2423 :class:`_engine.Engine` 

2424 isolation level facilities; these APIs should be preferred for 

2425 most typical use cases. 

2426 

2427 If the dialect also implements the 

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

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

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

2431 

2432 .. seealso:: 

2433 

2434 :meth:`_engine.Connection.get_isolation_level` 

2435 - view current level 

2436 

2437 :attr:`_engine.Connection.default_isolation_level` 

2438 - view default level 

2439 

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

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

2442 

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

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

2445 

2446 """ 

2447 

2448 raise NotImplementedError() 

2449 

2450 def get_isolation_level( 

2451 self, dbapi_connection: DBAPIConnection 

2452 ) -> IsolationLevel: 

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

2454 

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

2456 the corresponding 

2457 DBAPI connection may be procured using the 

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

2459 

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

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

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

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

2464 

2465 

2466 .. seealso:: 

2467 

2468 :meth:`_engine.Connection.get_isolation_level` 

2469 - view current level 

2470 

2471 :attr:`_engine.Connection.default_isolation_level` 

2472 - view default level 

2473 

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

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

2476 

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

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

2479 

2480 

2481 """ 

2482 

2483 raise NotImplementedError() 

2484 

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

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

2487 

2488 :param dbapi_connection: a DBAPI connection object 

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

2490 :rtype: bool 

2491 

2492 This method inspects the given DBAPI connection to determine 

2493 whether autocommit mode is currently enabled. The specific 

2494 mechanism for detecting autocommit varies by database dialect 

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

2496 round trips. 

2497 

2498 .. note:: 

2499 

2500 Not all dialects support autocommit detection. Dialects 

2501 that do not support this feature will raise 

2502 :exc:`NotImplementedError`. 

2503 

2504 """ 

2505 raise NotImplementedError( 

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

2507 ) 

2508 

2509 def get_default_isolation_level( 

2510 self, dbapi_conn: DBAPIConnection 

2511 ) -> IsolationLevel: 

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

2513 a default isolation level if one cannot be retrieved. 

2514 

2515 This method may only raise NotImplementedError and 

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

2517 first connect. 

2518 

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

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

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

2522 

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

2524 method unless overridden by a dialect. 

2525 

2526 """ 

2527 raise NotImplementedError() 

2528 

2529 def get_isolation_level_values( 

2530 self, dbapi_conn: DBAPIConnection 

2531 ) -> Sequence[IsolationLevel]: 

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

2533 by this dialect. 

2534 

2535 The available names should use the following conventions: 

2536 

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

2538 names but these are normalized into UPPERCASE before being passed 

2539 along to the dialect. 

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

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

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

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

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

2545 ``READ COMMITTED``, ``REPEATABLE READ``, ``SERIALIZABLE`` 

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

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

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

2549 are named in UPPERCASE and use spaces not underscores. 

2550 

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

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

2553 :class:`_exc.ArgumentError`. 

2554 

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

2556 the dialect needs to interrogate the connection itself to determine 

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

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

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

2560 

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

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

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

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

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

2566 not yet be implementing this method. 

2567 

2568 .. versionadded:: 2.0 

2569 

2570 """ 

2571 raise NotImplementedError() 

2572 

2573 def _assert_and_set_isolation_level( 

2574 self, dbapi_conn: DBAPIConnection, level: IsolationLevel 

2575 ) -> None: 

2576 raise NotImplementedError() 

2577 

2578 @classmethod 

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

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

2581 

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

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

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

2585 the actual dialect to be used. 

2586 

2587 By default this just returns the cls. 

2588 

2589 """ 

2590 return cls 

2591 

2592 @classmethod 

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

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

2595 an async engine. 

2596 

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

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

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

2600 ``psycopg`` driver. 

2601 

2602 .. versionadded:: 2 

2603 

2604 .. seealso:: 

2605 

2606 :meth:`.Dialect.get_dialect_cls` 

2607 

2608 """ 

2609 return cls.get_dialect_cls(url) 

2610 

2611 @classmethod 

2612 def load_provisioning(cls) -> None: 

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

2614 

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

2616 provisioning followers, this method should initiate that process. 

2617 

2618 A typical implementation would be:: 

2619 

2620 @classmethod 

2621 def load_provisioning(cls): 

2622 __import__("mydialect.provision") 

2623 

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

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

2626 attribute:: 

2627 

2628 @classmethod 

2629 def load_provisioning(cls): 

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

2631 try: 

2632 __import__(package + ".provision") 

2633 except ImportError: 

2634 pass 

2635 

2636 """ 

2637 

2638 @classmethod 

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

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

2641 :class:`_engine.Engine`. 

2642 

2643 If the dialect returned a different class from the 

2644 :meth:`.get_dialect_cls` 

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

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

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

2648 

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

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

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

2652 

2653 """ 

2654 

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

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

2657 package. 

2658 

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

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

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

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

2663 connection-like object as returned by the driver. 

2664 

2665 .. versionadded:: 1.4.24 

2666 

2667 """ 

2668 raise NotImplementedError() 

2669 

2670 def set_engine_execution_options( 

2671 self, engine: Engine, opts: CoreExecuteOptionsParameter 

2672 ) -> None: 

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

2674 

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

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

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

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

2679 connection. 

2680 

2681 """ 

2682 raise NotImplementedError() 

2683 

2684 def set_connection_execution_options( 

2685 self, connection: Connection, opts: CoreExecuteOptionsParameter 

2686 ) -> None: 

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

2688 

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

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

2691 execution option. Dialects can intercept various execution options 

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

2693 

2694 .. versionadded:: 1.4 

2695 

2696 """ 

2697 raise NotImplementedError() 

2698 

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

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

2701 raise NotImplementedError() 

2702 

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

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

2705 

2706 

2707class CreateEnginePlugin: 

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

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

2710 

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

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

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

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

2715 :class:`_engine.CreateEnginePlugin` include: 

2716 

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

2718 number of checkouts and/or time spent with statements 

2719 

2720 * connectivity plugins such as proxies 

2721 

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

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

2724 

2725 

2726 import logging 

2727 

2728 from sqlalchemy.engine import CreateEnginePlugin 

2729 from sqlalchemy import event 

2730 

2731 

2732 class LogCursorEventsPlugin(CreateEnginePlugin): 

2733 def __init__(self, url, kwargs): 

2734 # consume the parameter "log_cursor_logging_name" from the 

2735 # URL query 

2736 logging_name = url.query.get( 

2737 "log_cursor_logging_name", "log_cursor" 

2738 ) 

2739 

2740 self.log = logging.getLogger(logging_name) 

2741 

2742 def update_url(self, url): 

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

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

2745 

2746 def engine_created(self, engine): 

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

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

2749 

2750 def _log_event( 

2751 self, 

2752 conn, 

2753 cursor, 

2754 statement, 

2755 parameters, 

2756 context, 

2757 executemany, 

2758 ): 

2759 

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

2761 

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

2763 of dialects:: 

2764 

2765 entry_points = { 

2766 "sqlalchemy.plugins": [ 

2767 "log_cursor_plugin = myapp.plugins:LogCursorEventsPlugin" 

2768 ] 

2769 } 

2770 

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

2772 URL as in:: 

2773 

2774 from sqlalchemy import create_engine 

2775 

2776 engine = create_engine( 

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

2778 "plugin=log_cursor_plugin&log_cursor_logging_name=mylogger" 

2779 ) 

2780 

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

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

2783 in the URL:: 

2784 

2785 engine = create_engine( 

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

2787 "plugin=plugin_one&plugin=plugin_twp&plugin=plugin_three" 

2788 ) 

2789 

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

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

2792 

2793 engine = create_engine( 

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

2795 ) 

2796 

2797 A plugin may consume plugin-specific arguments from the 

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

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

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

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

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

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

2804 

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

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

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

2808 should be consumed by implementing the 

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

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

2811 

2812 class MyPlugin(CreateEnginePlugin): 

2813 def __init__(self, url, kwargs): 

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

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

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

2817 

2818 def update_url(self, url): 

2819 return url.difference_update_query( 

2820 ["my_argument_one", "my_argument_two"] 

2821 ) 

2822 

2823 Arguments like those illustrated above would be consumed from a 

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

2825 

2826 from sqlalchemy import create_engine 

2827 

2828 engine = create_engine( 

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

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

2831 my_argument_three="bat", 

2832 ) 

2833 

2834 .. versionchanged:: 1.4 

2835 

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

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

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

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

2840 is invoked after the plugin is constructed. 

2841 

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

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

2844 method to detect which version is running:: 

2845 

2846 class MyPlugin(CreateEnginePlugin): 

2847 def __init__(self, url, kwargs): 

2848 if hasattr(CreateEnginePlugin, "update_url"): 

2849 # detect the 1.4 API 

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

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

2852 else: 

2853 # detect the 1.3 and earlier API - mutate the 

2854 # URL directly 

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

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

2857 

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

2859 

2860 def update_url(self, url): 

2861 # this method is only called in the 1.4 version 

2862 return url.difference_update_query( 

2863 ["my_argument_one", "my_argument_two"] 

2864 ) 

2865 

2866 .. seealso:: 

2867 

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

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

2870 

2871 

2872 When the engine creation process completes and produces the 

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

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

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

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

2877 

2878 """ # noqa: E501 

2879 

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

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

2882 

2883 The plugin object is instantiated individually for each call 

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

2885 Engine` will be 

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

2887 corresponding to this URL. 

2888 

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

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

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

2892 from the :meth:`_engine.CreateEnginePlugin.update_url` method. 

2893 

2894 .. versionchanged:: 1.4 

2895 

2896 The :class:`_engine.URL` object is now immutable, so a 

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

2898 :class:`_engine.URL` object should implement the 

2899 :meth:`_engine.CreateEnginePlugin.update_url` method. 

2900 

2901 :param kwargs: The keyword arguments passed to 

2902 :func:`_sa.create_engine`. 

2903 

2904 """ 

2905 self.url = url 

2906 

2907 def update_url(self, url: URL) -> URL: 

2908 """Update the :class:`_engine.URL`. 

2909 

2910 A new :class:`_engine.URL` should be returned. This method is 

2911 typically used to consume configuration arguments from the 

2912 :class:`_engine.URL` which must be removed, as they will not be 

2913 recognized by the dialect. The 

2914 :meth:`_engine.URL.difference_update_query` method is available 

2915 to remove these arguments. See the docstring at 

2916 :class:`_engine.CreateEnginePlugin` for an example. 

2917 

2918 

2919 .. versionadded:: 1.4 

2920 

2921 """ 

2922 raise NotImplementedError() 

2923 

2924 def handle_dialect_kwargs( 

2925 self, dialect_cls: Type[Dialect], dialect_args: Dict[str, Any] 

2926 ) -> None: 

2927 """parse and modify dialect kwargs""" 

2928 

2929 def handle_pool_kwargs( 

2930 self, pool_cls: Type[Pool], pool_args: Dict[str, Any] 

2931 ) -> None: 

2932 """parse and modify pool kwargs""" 

2933 

2934 def engine_created(self, engine: Engine) -> None: 

2935 """Receive the :class:`_engine.Engine` 

2936 object when it is fully constructed. 

2937 

2938 The plugin may make additional changes to the engine, such as 

2939 registering engine or connection pool events. 

2940 

2941 """ 

2942 

2943 

2944class ExecutionContext: 

2945 """A messenger object for a Dialect that corresponds to a single 

2946 execution. 

2947 

2948 """ 

2949 

2950 engine: Engine 

2951 """engine which the Connection is associated with""" 

2952 

2953 connection: Connection 

2954 """Connection object which can be freely used by default value 

2955 generators to execute SQL. This Connection should reference the 

2956 same underlying connection/transactional resources of 

2957 root_connection.""" 

2958 

2959 root_connection: Connection 

2960 """Connection object which is the source of this ExecutionContext.""" 

2961 

2962 dialect: Dialect 

2963 """dialect which created this ExecutionContext.""" 

2964 

2965 cursor: DBAPICursor 

2966 """DB-API cursor procured from the connection""" 

2967 

2968 compiled: Optional[Compiled] 

2969 """if passed to constructor, sqlalchemy.engine.base.Compiled object 

2970 being executed""" 

2971 

2972 statement: str 

2973 """string version of the statement to be executed. Is either 

2974 passed to the constructor, or must be created from the 

2975 sql.Compiled object by the time pre_exec() has completed.""" 

2976 

2977 invoked_statement: Optional[Executable] 

2978 """The Executable statement object that was given in the first place. 

2979 

2980 This should be structurally equivalent to compiled.statement, but not 

2981 necessarily the same object as in a caching scenario the compiled form 

2982 will have been extracted from the cache. 

2983 

2984 """ 

2985 

2986 parameters: _AnyMultiExecuteParams 

2987 """bind parameters passed to the execute() or exec_driver_sql() methods. 

2988 

2989 These are always stored as a list of parameter entries. A single-element 

2990 list corresponds to a ``cursor.execute()`` call and a multiple-element 

2991 list corresponds to ``cursor.executemany()``, except in the case 

2992 of :attr:`.ExecuteStyle.INSERTMANYVALUES` which will use 

2993 ``cursor.execute()`` one or more times. 

2994 

2995 """ 

2996 

2997 no_parameters: bool 

2998 """True if the execution style does not use parameters""" 

2999 

3000 isinsert: bool 

3001 """True if the statement is an INSERT.""" 

3002 

3003 isupdate: bool 

3004 """True if the statement is an UPDATE.""" 

3005 

3006 execute_style: ExecuteStyle 

3007 """the style of DBAPI cursor method that will be used to execute 

3008 a statement. 

3009 

3010 .. versionadded:: 2.0 

3011 

3012 """ 

3013 

3014 executemany: bool 

3015 """True if the context has a list of more than one parameter set. 

3016 

3017 Historically this attribute links to whether ``cursor.execute()`` or 

3018 ``cursor.executemany()`` will be used. It also can now mean that 

3019 "insertmanyvalues" may be used which indicates one or more 

3020 ``cursor.execute()`` calls. 

3021 

3022 """ 

3023 

3024 prefetch_cols: util.generic_fn_descriptor[Optional[Sequence[Column[Any]]]] 

3025 """a list of Column objects for which a client-side default 

3026 was fired off. Applies to inserts and updates.""" 

3027 

3028 postfetch_cols: util.generic_fn_descriptor[Optional[Sequence[Column[Any]]]] 

3029 """a list of Column objects for which a server-side default or 

3030 inline SQL expression value was fired off. Applies to inserts 

3031 and updates.""" 

3032 

3033 execution_options: _ExecuteOptions 

3034 """Execution options associated with the current statement execution""" 

3035 

3036 @classmethod 

3037 def _init_ddl( 

3038 cls, 

3039 dialect: Dialect, 

3040 connection: Connection, 

3041 dbapi_connection: PoolProxiedConnection, 

3042 execution_options: _ExecuteOptions, 

3043 compiled_ddl: DDLCompiler, 

3044 ) -> ExecutionContext: 

3045 raise NotImplementedError() 

3046 

3047 @classmethod 

3048 def _init_compiled( 

3049 cls, 

3050 dialect: Dialect, 

3051 connection: Connection, 

3052 dbapi_connection: PoolProxiedConnection, 

3053 execution_options: _ExecuteOptions, 

3054 compiled: SQLCompiler, 

3055 parameters: _CoreMultiExecuteParams, 

3056 invoked_statement: Executable, 

3057 extracted_parameters: Optional[Sequence[BindParameter[Any]]], 

3058 cache_hit: CacheStats = CacheStats.CACHING_DISABLED, 

3059 ) -> ExecutionContext: 

3060 raise NotImplementedError() 

3061 

3062 @classmethod 

3063 def _init_statement( 

3064 cls, 

3065 dialect: Dialect, 

3066 connection: Connection, 

3067 dbapi_connection: PoolProxiedConnection, 

3068 execution_options: _ExecuteOptions, 

3069 statement: str, 

3070 parameters: _DBAPIMultiExecuteParams, 

3071 ) -> ExecutionContext: 

3072 raise NotImplementedError() 

3073 

3074 @classmethod 

3075 def _init_default( 

3076 cls, 

3077 dialect: Dialect, 

3078 connection: Connection, 

3079 dbapi_connection: PoolProxiedConnection, 

3080 execution_options: _ExecuteOptions, 

3081 ) -> ExecutionContext: 

3082 raise NotImplementedError() 

3083 

3084 def _exec_default( 

3085 self, 

3086 column: Optional[Column[Any]], 

3087 default: DefaultGenerator, 

3088 type_: Optional[TypeEngine[Any]], 

3089 ) -> Any: 

3090 raise NotImplementedError() 

3091 

3092 def _prepare_set_input_sizes( 

3093 self, 

3094 ) -> Optional[List[Tuple[str, Any, TypeEngine[Any]]]]: 

3095 raise NotImplementedError() 

3096 

3097 def _get_cache_stats(self) -> str: 

3098 raise NotImplementedError() 

3099 

3100 def _setup_result_proxy(self) -> CursorResult[Any]: 

3101 raise NotImplementedError() 

3102 

3103 def fire_sequence(self, seq: Sequence_SchemaItem, type_: Integer) -> int: 

3104 """given a :class:`.Sequence`, invoke it and return the next int 

3105 value""" 

3106 raise NotImplementedError() 

3107 

3108 def create_cursor(self) -> DBAPICursor: 

3109 """Return a new cursor generated from this ExecutionContext's 

3110 connection. 

3111 

3112 Some dialects may wish to change the behavior of 

3113 connection.cursor(), such as postgresql which may return a PG 

3114 "server side" cursor. 

3115 """ 

3116 

3117 raise NotImplementedError() 

3118 

3119 def pre_exec(self) -> None: 

3120 """Called before an execution of a compiled statement. 

3121 

3122 If a compiled statement was passed to this ExecutionContext, 

3123 the `statement` and `parameters` datamembers must be 

3124 initialized after this statement is complete. 

3125 """ 

3126 

3127 raise NotImplementedError() 

3128 

3129 def get_out_parameter_values( 

3130 self, out_param_names: Sequence[str] 

3131 ) -> Sequence[Any]: 

3132 """Return a sequence of OUT parameter values from a cursor. 

3133 

3134 For dialects that support OUT parameters, this method will be called 

3135 when there is a :class:`.SQLCompiler` object which has the 

3136 :attr:`.SQLCompiler.has_out_parameters` flag set. This flag in turn 

3137 will be set to True if the statement itself has :class:`.BindParameter` 

3138 objects that have the ``.isoutparam`` flag set which are consumed by 

3139 the :meth:`.SQLCompiler.visit_bindparam` method. If the dialect 

3140 compiler produces :class:`.BindParameter` objects with ``.isoutparam`` 

3141 set which are not handled by :meth:`.SQLCompiler.visit_bindparam`, it 

3142 should set this flag explicitly. 

3143 

3144 The list of names that were rendered for each bound parameter 

3145 is passed to the method. The method should then return a sequence of 

3146 values corresponding to the list of parameter objects. Unlike in 

3147 previous SQLAlchemy versions, the values can be the **raw values** from 

3148 the DBAPI; the execution context will apply the appropriate type 

3149 handler based on what's present in self.compiled.binds and update the 

3150 values. The processed dictionary will then be made available via the 

3151 ``.out_parameters`` collection on the result object. Note that 

3152 SQLAlchemy 1.4 has multiple kinds of result object as part of the 2.0 

3153 transition. 

3154 

3155 .. versionadded:: 1.4 - added 

3156 :meth:`.ExecutionContext.get_out_parameter_values`, which is invoked 

3157 automatically by the :class:`.DefaultExecutionContext` when there 

3158 are :class:`.BindParameter` objects with the ``.isoutparam`` flag 

3159 set. This replaces the practice of setting out parameters within 

3160 the now-removed ``get_result_proxy()`` method. 

3161 

3162 """ 

3163 raise NotImplementedError() 

3164 

3165 def post_exec(self) -> None: 

3166 """Called after the execution of a compiled statement. 

3167 

3168 If a compiled statement was passed to this ExecutionContext, 

3169 the `last_insert_ids`, `last_inserted_params`, etc. 

3170 datamembers should be available after this method completes. 

3171 """ 

3172 

3173 raise NotImplementedError() 

3174 

3175 def handle_dbapi_exception(self, e: BaseException) -> None: 

3176 """Receive a DBAPI exception which occurred upon execute, result 

3177 fetch, etc.""" 

3178 

3179 raise NotImplementedError() 

3180 

3181 def lastrow_has_defaults(self) -> bool: 

3182 """Return True if the last INSERT or UPDATE row contained 

3183 inlined or database-side defaults. 

3184 """ 

3185 

3186 raise NotImplementedError() 

3187 

3188 def get_rowcount(self) -> Optional[int]: 

3189 """Return the DBAPI ``cursor.rowcount`` value, or in some 

3190 cases an interpreted value. 

3191 

3192 See :attr:`_engine.CursorResult.rowcount` for details on this. 

3193 

3194 """ 

3195 

3196 raise NotImplementedError() 

3197 

3198 def fetchall_for_returning(self, cursor: DBAPICursor) -> Sequence[Any]: 

3199 """For a RETURNING result, deliver cursor.fetchall() from the 

3200 DBAPI cursor. 

3201 

3202 This is a dialect-specific hook for dialects that have special 

3203 considerations when calling upon the rows delivered for a 

3204 "RETURNING" statement. Default implementation is 

3205 ``cursor.fetchall()``. 

3206 

3207 This hook is currently used only by the :term:`insertmanyvalues` 

3208 feature. Dialects that don't set ``use_insertmanyvalues=True`` 

3209 don't need to consider this hook. 

3210 

3211 .. versionadded:: 2.0.10 

3212 

3213 """ 

3214 raise NotImplementedError() 

3215 

3216 

3217class ConnectionEventsTarget(EventTarget): 

3218 """An object which can accept events from :class:`.ConnectionEvents`. 

3219 

3220 Includes :class:`_engine.Connection` and :class:`_engine.Engine`. 

3221 

3222 .. versionadded:: 2.0 

3223 

3224 """ 

3225 

3226 dispatch: dispatcher[ConnectionEventsTarget] 

3227 

3228 

3229Connectable = ConnectionEventsTarget 

3230 

3231 

3232class ExceptionContext: 

3233 """Encapsulate information about an error condition in progress. 

3234 

3235 This object exists solely to be passed to the 

3236 :meth:`_events.DialectEvents.handle_error` event, 

3237 supporting an interface that 

3238 can be extended without backwards-incompatibility. 

3239 

3240 

3241 """ 

3242 

3243 __slots__ = () 

3244 

3245 dialect: Dialect 

3246 """The :class:`_engine.Dialect` in use. 

3247 

3248 This member is present for all invocations of the event hook. 

3249 

3250 .. versionadded:: 2.0 

3251 

3252 """ 

3253 

3254 connection: Optional[Connection] 

3255 """The :class:`_engine.Connection` in use during the exception. 

3256 

3257 This member is present, except in the case of a failure when 

3258 first connecting. 

3259 

3260 .. seealso:: 

3261 

3262 :attr:`.ExceptionContext.engine` 

3263 

3264 

3265 """ 

3266 

3267 engine: Optional[Engine] 

3268 """The :class:`_engine.Engine` in use during the exception. 

3269 

3270 This member is present in all cases except for when handling an error 

3271 within the connection pool "pre-ping" process. 

3272 

3273 """ 

3274 

3275 cursor: Optional[DBAPICursor] 

3276 """The DBAPI cursor object. 

3277 

3278 May be None. 

3279 

3280 """ 

3281 

3282 statement: Optional[str] 

3283 """String SQL statement that was emitted directly to the DBAPI. 

3284 

3285 May be None. 

3286 

3287 """ 

3288 

3289 parameters: Optional[_DBAPIAnyExecuteParams] 

3290 """Parameter collection that was emitted directly to the DBAPI. 

3291 

3292 May be None. 

3293 

3294 """ 

3295 

3296 original_exception: BaseException 

3297 """The exception object which was caught. 

3298 

3299 This member is always present. 

3300 

3301 """ 

3302 

3303 sqlalchemy_exception: Optional[StatementError] 

3304 """The :class:`sqlalchemy.exc.StatementError` which wraps the original, 

3305 and will be raised if exception handling is not circumvented by the event. 

3306 

3307 May be None, as not all exception types are wrapped by SQLAlchemy. 

3308 For DBAPI-level exceptions that subclass the dbapi's Error class, this 

3309 field will always be present. 

3310 

3311 """ 

3312 

3313 chained_exception: Optional[BaseException] 

3314 """The exception that was returned by the previous handler in the 

3315 exception chain, if any. 

3316 

3317 If present, this exception will be the one ultimately raised by 

3318 SQLAlchemy unless a subsequent handler replaces it. 

3319 

3320 May be None. 

3321 

3322 """ 

3323 

3324 execution_context: Optional[ExecutionContext] 

3325 """The :class:`.ExecutionContext` corresponding to the execution 

3326 operation in progress. 

3327 

3328 This is present for statement execution operations, but not for 

3329 operations such as transaction begin/end. It also is not present when 

3330 the exception was raised before the :class:`.ExecutionContext` 

3331 could be constructed. 

3332 

3333 Note that the :attr:`.ExceptionContext.statement` and 

3334 :attr:`.ExceptionContext.parameters` members may represent a 

3335 different value than that of the :class:`.ExecutionContext`, 

3336 potentially in the case where a 

3337 :meth:`_events.ConnectionEvents.before_cursor_execute` event or similar 

3338 modified the statement/parameters to be sent. 

3339 

3340 May be None. 

3341 

3342 """ 

3343 

3344 is_disconnect: bool 

3345 """Represent whether the exception as occurred represents a "disconnect" 

3346 condition. 

3347 

3348 This flag will always be True or False within the scope of the 

3349 :meth:`_events.DialectEvents.handle_error` handler. 

3350 

3351 SQLAlchemy will defer to this flag in order to determine whether or not 

3352 the connection should be invalidated subsequently. That is, by 

3353 assigning to this flag, a "disconnect" event which then results in 

3354 a connection and pool invalidation can be invoked or prevented by 

3355 changing this flag. 

3356 

3357 

3358 .. note:: The pool "pre_ping" handler enabled using the 

3359 :paramref:`_sa.create_engine.pool_pre_ping` parameter does **not** 

3360 consult this event before deciding if the "ping" returned false, 

3361 as opposed to receiving an unhandled error. For this use case, the 

3362 :ref:`legacy recipe based on engine_connect() may be used 

3363 <pool_disconnects_pessimistic_custom>`. A future API allow more 

3364 comprehensive customization of the "disconnect" detection mechanism 

3365 across all functions. 

3366 

3367 """ 

3368 

3369 invalidate_pool_on_disconnect: bool 

3370 """Represent whether all connections in the pool should be invalidated 

3371 when a "disconnect" condition is in effect. 

3372 

3373 Setting this flag to False within the scope of the 

3374 :meth:`_events.DialectEvents.handle_error` 

3375 event will have the effect such 

3376 that the full collection of connections in the pool will not be 

3377 invalidated during a disconnect; only the current connection that is the 

3378 subject of the error will actually be invalidated. 

3379 

3380 The purpose of this flag is for custom disconnect-handling schemes where 

3381 the invalidation of other connections in the pool is to be performed 

3382 based on other conditions, or even on a per-connection basis. 

3383 

3384 """ 

3385 

3386 is_pre_ping: bool 

3387 """Indicates if this error is occurring within the "pre-ping" step 

3388 performed when :paramref:`_sa.create_engine.pool_pre_ping` is set to 

3389 ``True``. In this mode, the :attr:`.ExceptionContext.engine` attribute 

3390 will be ``None``. The dialect in use is accessible via the 

3391 :attr:`.ExceptionContext.dialect` attribute. 

3392 

3393 .. versionadded:: 2.0.5 

3394 

3395 """ 

3396 

3397 

3398class AdaptedConnection: 

3399 """Interface of an adapted connection object to support the DBAPI protocol. 

3400 

3401 Used by asyncio dialects to provide a sync-style pep-249 facade on top 

3402 of the asyncio connection/cursor API provided by the driver. 

3403 

3404 .. versionadded:: 1.4.24 

3405 

3406 """ 

3407 

3408 __slots__ = ("_connection",) 

3409 

3410 _connection: AsyncIODBAPIConnection 

3411 

3412 @property 

3413 def driver_connection(self) -> Any: 

3414 """The connection object as returned by the driver after a connect.""" 

3415 return self._connection 

3416 

3417 def run_async(self, fn: Callable[[Any], Awaitable[_T]]) -> _T: 

3418 """Run the awaitable returned by the given function, which is passed 

3419 the raw asyncio driver connection. 

3420 

3421 This is used to invoke awaitable-only methods on the driver connection 

3422 within the context of a "synchronous" method, like a connection 

3423 pool event handler. 

3424 

3425 E.g.:: 

3426 

3427 engine = create_async_engine(...) 

3428 

3429 

3430 @event.listens_for(engine.sync_engine, "connect") 

3431 def register_custom_types( 

3432 dbapi_connection, # ... 

3433 ): 

3434 dbapi_connection.run_async( 

3435 lambda connection: connection.set_type_codec( 

3436 "MyCustomType", encoder, decoder, ... 

3437 ) 

3438 ) 

3439 

3440 .. versionadded:: 1.4.30 

3441 

3442 .. seealso:: 

3443 

3444 :ref:`asyncio_events_run_async` 

3445 

3446 """ 

3447 return await_(fn(self._connection)) 

3448 

3449 def __repr__(self) -> str: 

3450 return "<AdaptedConnection %s>" % self._connection