原文:
docs.sqlalchemy.org/en/20/contents.html
2.0 更新日志
原文:
docs.sqlalchemy.org/en/20/changelog/changelog_20.html
2.0.30
无发布日期
orm
- [orm] [bug]
添加了新的属性
ORMExecuteState.is_from_statement
,用于检测形式为select().from_statement()
的语句,并且还增强了FromStatement
以设置ORMExecuteState.is_select
、ORMExecuteState.is_insert
、ORMExecuteState.is_update
和ORMExecuteState.is_delete
根据发送到Select.from_statement()
方法本身的元素。 References: #11220
engine
- [engine] [bug]
在
Connection.execution_options.logging_token
选项中修复了问题,当在已经记录了消息的连接上更改logging_token
的值时,不会更新以反映新的日志令牌。具体来说,这会阻止使用Session.connection()
来更改连接上的选项,因为 BEGIN 记录消息已经被发出。 References: #11210
打字
- [typing] [bug] [regression]
修复了由版本 2.0.29 中 PR #11055 引起的打字退化,该版本试图将
ParamSpec
添加到 asyncio 的run_sync()
方法中,使用AsyncConnection.run_sync()
与MetaData.reflect()
将会由于错误导致 mypy 失败。详细信息请参阅github.com/python/mypy/issues/17093
。由 Francisco R. Del Roio 提供的拉取请求。 References: #11200
杂项
- [bug] [test]
确保在测试中使用
subprocess.run
时正确初始化PYTHONPATH
变量。 References: #11268
2.0.29
发布日期:2024 年 3 月 23 日
orm
- [orm] [usecase]
增加了对PEP 695
TypeAliasType
构造以及 python 3.12 原生的type
关键字的支持,以便在使用这些构造链接到PEP 593Annotated
容器时,允许解析Annotated
在这些构造用于Mapped
类型容器时继续进行。 参考:#11130 - [orm] [bug]
修复了声明性问题,其中使用
Relationship
而不是Mapped
来定义关系会意外地为该属性引入“动态”关系加载策略。 参考:#10611 - [orm] [bug]
修复了在 ORM 注释声明中使用
mapped_column()
与mapped_column.index
或mapped_column.unique
设置为 False 时,会被具有该参数设置为True
的传入Annotated
元素覆盖的问题,即使直接的mapped_column()
元素更具体且应优先考虑。增强了协调布尔值的逻辑,以适应本地值为False
仍然优先于来自注释元素的True
值的情况。 参考:#11091 - [orm] [bug] [regression]
修复了从版本 2.0.28 引起的回归,该回归是由于修复#11085而引起的,其中调整后缓存绑定参数值的新方法会干扰
subqueryload()
加载器选项的实现,该加载器选项在内部使用一些更具传统模式的模式,当使用此加载器选项与此加载器选项一起使用附加加载器条件功能时。 参考:#11173
引擎
- [engine] [bug]
修复了 “插入多个值”行为对 INSERT 语句的行为 功能中的问题,其中使用带有“内联执行”默认生成器的主键列,例如具有显式
Sequence
并具有显式模式名称的生成器,同时使用Connection.execution_options.schema_translate_map
功能将无法正确呈现序列或参数,导致错误。 参考: #11157 - [engine] [bug] 对版本 2.0.10 中对 #9618 所做的调整进行了更改,该调整增加了从批量 INSERT 中协调 RETURNING 行到传递给它的参数的行为。该行为包括已经 DB 转换的绑定参数值与返回的行值之间的比较,并不总是对于 SQL 列类型(如 UUID)是“对称”的,具体取决于不同的 DBAPI 如何接收这些值以及它们如何返回它们,因此需要在这些列类型上添加额外的“标志值解析器”方法。不幸的是,这破坏了第三方列类型,如 SQLModel 中未实现此特殊方法的 UUID/GUID 类型,引发错误“无法将结果集中的标志值与参数集匹配”。与其试图进一步解释和文档化“insertmanyvalues”功能的此实现细节,包括新方法的公共版本,不如将方法调整为不再需要此额外的转换步骤,并且执行比较的逻辑现在在预转换的绑定参数值与后处理结果值之间进行,后者应始终具有匹配的数据类型。在不寻常的情况下,如果自定义 SQL 列类型同时也用作批量 INSERT 的“标志”列不接收和返回相同类型的值,则将引发“无法匹配”错误,但缓解方法很简单,即应传递与返回值相同的 Python 数据类型。 参考: #11160
sql
- [sql] [bug] [regression]
从 1.4 系列的回归中修复了重构
TypeEngine.with_variant()
方法的问题,该问题在“with_variant()”克隆原始 TypeEngine 而不是更改类型中介绍。该问题未考虑到.copy()
方法,该方法会丢失设置的变体映射。对于“schema”类型的非常特定情况而言,这是一个问题,该类型包括Enum
和ARRAY
等类型,当它们在 ORM Declarative 映射与混入一起使用时,类型的复制就会起作用。现在还复制了变体映射。 参考:#11176
typing
- [typing] [错误]
修复了允许 asyncio
run_sync()
方法正确类型化参数的类型问题,该方法根据传递的可调用函数使用了PEP 612ParamSpec
变量。感谢 Francisco R. Del Roio 提供的拉取请求。 参考:#11055
postgresql
- [postgresql] [用例]
PostgreSQL 方言现在在反射具有域作为类型的列时返回
DOMAIN
实例。之前,返回的是域数据类型。作为此更改的一部分,改进了域反射以返回文本类型的校对。感谢 Thomas Stephenson 提供的拉取请求。 参考:#10693
测试
- [测试] [错误]
将对与 asyncio 相关的测试运行方式进行了改进,并将其后移至 SQLAlchemy 2.0,现在使用较新的 Python 3.11
asyncio.Runner
或后移的等效版本,而不是依赖于以前基于asyncio.get_running_loop()
的实现。这样做有望防止在 CPU 负载硬件上进行大型测试套件运行时出现问题,其中事件循环似乎会损坏,从而导致级联失败。 参考:#11187
2.0.28
发布日期:2024 年 3 月 4 日
orm
- [orm] [性能] [错误] [回归]
调整了在#10570中进行的修复,发布在 2.0.23 中,其中添加了新的逻辑来协调可能在
with_expression()
构造中用于缓存键生成的绑定参数值的更改。新的逻辑改变了将新的绑定参数值与语句关联的方法,避免了需要深复制语句的需要,这可能会对非常深/复杂的 SQL 结构造成重大性能损失。新方法不再需要这个深复制步骤。 参考:#11085 - [orm] [错误] [回归]
修复了由#9779引起的回归,其中在关系
and_()
表达式中使用“secondary”表将无法被别名化以匹配“secondary”表在Select.join()
表达式中通常的渲染方式,导致查询无效。 参考:#11010
引擎
- [引擎] [用例]
添加了新的核心执行选项
Connection.execution_options.preserve_rowcount
。设置后,将在语句执行时无条件地将 DBAPI 游标的cursor.rowcount
属性存储,以便无论 DBAPI 为任何类型的语句提供的值都可以使用CursorResult.rowcount
属性从CursorResult
中获取。这允许访问行计数,例如 INSERT 和 SELECT 语句,至少在使用的 DBAPI 支持的程度上。INSERT 语句的“插入多个值”行为也支持此选项,并将在设置时确保为批量插入行时正确设置CursorResult.rowcount
。 参考:#10974
asyncio
- [asyncio] [错误]
如果将
QueuePool
或其他非异步池类传递给create_async_engine()
,则会引发错误。此引擎仅接受与 asyncio 兼容的池类,包括AsyncAdaptedQueuePool
。其他池类(例如NullPool
)与同步和异步引擎都兼容,因为它们不执行任何锁定。 参见 API 文档 - 可用的连接池实现 参考资料:#8771
测试
- [tests] [change] tox.ini 文件中的 pytest 支持已更新,以支持 pytest 8.1。
2.0.27
发布日期:2024 年 2 月 13 日
postgresql
- [postgresql] [bug] [regression] 由于刚发布的修复了#10863的修复导致的回归已经修复,其中将一个无效的异常类添加到了“except”块中,除非实际发生这样的捕获,否则不会被执行。已经添加了一种模拟式测试,以确保在单元测试中执行此捕获。 参考资料:#11005
2.0.26
发布日期:2024 年 2 月 11 日
orm
- [orm] [bug] 已用一个较短的消息替换了“加载器深度过深”的警告,该消息被添加到 SQL 日志中的缓存徽章中,用于 ORM 由于加载器选项的过深链而禁用缓存的语句。此警告突出显示的条件难以解决,并且通常只是 ORM 在应用 SQL 缓存时的限制。未来的功能可能包括调整禁用缓存的阈值的能力,但目前此警告将不再是一个麻烦。 参考资料:#10896
- [orm] [bug]
修复了在类主体内部声明类型(如枚举)时无法在
Mapped
容器类型中使用该类型的问题。现在,用于评估的本地变量范围包括类主体本身。此外,Mapped
内的表达式还可以引用类名本身,如果作为字符串使用或者使用了未来的注释模式。 参考资料:#10899 - [orm] [bug]
修复了使用
Session.delete()
与Mapper.version_id_col
功能时,如果由于对象上使用了relationship.post_update
而导致目标对象上发出了额外的 UPDATE,则会失败使用正确的版本标识符的问题。这个问题类似于#10800,只是对于仅有更新的情况,版本 2.0.25 中刚刚修复了。 参考:#10967 - [orm] [错误]
修复了
with_expression()
实现中的断言,如果使用了不可缓存的 SQL 表达式,则会引发断言错误;这是从 1.4 版本以来的一个 2.0 回归。 参考:#10990
示例
- [示例] [错误]
修复了 history_meta 示例中的回归,其中使用
MetaData.to_metadata()
复制历史表也会复制索引(这是一件好事),但不管用于这些索引的命名方案如何,都会导致命名冲突。现在这些索引都会添加一个“_history”后缀,方式与表名的方式相同。 参考:#10920 - [示例] [错误]
通过将
Identity
构造添加到所有表中,并允许在此后端上进行主键生成,修复了 examples/performance 中性能示例脚本在 Oracle 数据库上基本可用的问题。一些“原始 DBAPI” 情况仍与 Oracle 不兼容。
sql
- [sql] [错误]
修复了
case()
中的问题,即确定表达式类型的逻辑可能导致如果“whens”中的最后一个元素没有类型,或在其他情况下类型可能解析为None
,则会导致NullType
。逻辑已更新为扫描所有给定表达式,以便使用第一个非空类型,并始终确保存在类型。感谢 David Evans 提交的拉取请求。 参考:#10843
typing
- [类型] [错误]
修复了
PoolEvents.checkin()
事件的类型签名,指示给定的DBAPIConnection
参数在连接无效时可能为None
的情况。
postgresql
- [postgresql] [usecase] [reflection]
增加对以“NO INHERIT”标记的 PostgreSQL CHECK 约束的反射支持,将
no_inherit=True
设置为反射数据的键。感谢 Ellis Valentiner 的拉取请求。 引用:#10777 - [postgresql] [usecase]
支持
USING <method>
选项用于 PostgreSQLCREATE TABLE
,以指定用于存储新表内容的访问方法。感谢 Edgar Ramírez-Mondragón 的拉取请求。 另请参阅 PostgreSQL 表选项 引用:#10904 - [postgresql] [usecase]
正确地将 PostgreSQL RANGE 和 MULTIRANGE 类型标记为
Range[T]
和Sequence[Range[T]]
。引入了实用程序序列MultiRange
,以允许更好地支持 MULTIRANGE 类型的互操作性。 引用:#9736 - [postgresql] [usecase]
当从
Range
或MultiRange
实例推断数据库类型时,区分 INT4 和 INT8 范围以及多范围类型,如果值适合 INT4,则优先选择 INT4。 - [postgresql] [bug] [regression]
修复了在 2.0.24 版本中由 #10717 引起的 asyncpg 方言中的回归,该版本中现在尝试在终止之前优雅地关闭 asyncpg 连接的更改将不会对其他可能的与连接相关的异常(除了超时错误之外)回退到
terminate()
,没有考虑到优雅的.close()
尝试因其他原因失败,如连接错误。 引用:#10863 - [postgresql] [bug]
修复了在使用 PostgreSQL 方言时,
Uuid
数据类型与Uuid.as_uuid
参数设置为 False 时的问题。ORM 优化的 INSERT 语句(例如,“insertmanyvalues”功能)将不会正确地对齐主键 UUID 值以进行批量 INSERT 语句,导致错误。类似的问题也针对 pymssql 驱动程序进行了修复。
mysql
- [mysql] [bug] 修复了一个问题,即当一个 MySQL 列同时指定了 VIRTUAL 或 STORED 指令时,NULL/NOT NULL 无法正确反映出来的问题。拉取请求由 Georg Wicke-Arndt 提供。 参考:#10850
- [mysql] [bug]
修复了 asyncio 方言 asyncmy 和 aiomysql 中的问题,其中它们的
.close()
方法显然不是优雅关闭的。用非标准的.ensure_closed()
方法替换,该方法是可等待的,并将.close()
移动到所谓的“终止”情况。 参考:#10893
mssql
- [mssql] [bug]
修复了在使用 pymssql 方言时,
Uuid
数据类型与Uuid.as_uuid
参数设置为 False 时的问题。ORM 优化的 INSERT 语句(例如,“insertmanyvalues”功能)将不会正确地对齐主键 UUID 值以进行批量 INSERT 语句,导致错误。类似的问题也针对 PostgreSQL 驱动程序进行了修复。
Oracle
- [oracle] [performance] [bug] 更改了 Oracle 方言的默认数组大小,以便使用驱动程序设置的值,即写入时的 cx_oracle 和 oracledb 的值为 100。以前默认设置为 50 的值可能会导致在较慢的网络上使用 cx_oracle/oracledb 单独提取许多行时出现显着的性能回归。 参考:#10877
2.0.25
发布日期:2024 年 1 月 2 日
orm
- [orm] [usecase] 添加了对 Python 3.12 pep-695 类型别名结构的初步支持,用于解析 ORM Annotated Declarative 映射的自定义类型映射时。 参考:#10807
- [orm] [bug]
修复了一种情况,即在同时使用
relationship.post_update
功能和使用 mapper version_id_col 时,后者 UPDATE 语句可能会未能正确使用正确的版本标识符,假定在该刷新中已经发出了一个已经增加了版本计数器的 UPDATE。 参考文献:#10800 - [orm] [错误] 修复了 ORM 注解式声明中的问题,如果左侧类型被指定为类而不是字符串,并且没有使用 future 风格的注释,当左侧没有指定任何集合为 uselist=True 时,会误解关系的左侧。 参考文献:#10815
sql
- [sql] [错误]
改进了在布尔比较的否定上下文中编译
any_()
/all_()
的方式,现在将呈现NOT (expr)
而不是将等式操作符反转为不等于,允许对这些非典型运算符进行更精细的否定控制。 参考文献:#10817
类型提示
- [类型提示] [错误]
修复了在版本 2.0.24 中添加到
sqlalchemy.sql.functions
模块的类型提示引起的回归,作为 #6810 的一部分:- 进一步增强了 pep-484 类型提示,以允许从
sqlalchemy.sql.expression.func
派生的元素更有效地与 ORM 映射的属性一起使用 (#10801) - 修复了传递给函数的参数类型,以便像字符串和整数这样的字面表达式再次被正确解释 (#10818)
参考文献:#10801, #10818
- 进一步增强了 pep-484 类型提示,以允许从
asyncio
- [asyncio] [错误]
修复了 asyncio 版本连接池中的关键问题,调用
AsyncEngine.dispose()
会产生一个新的连接池,该连接池没有完全重新建立对 asyncio 兼容互斥锁的使用,导致在使用类似于asyncio.gather()
的并发特性时,在 asyncio 上下文中产生死锁,因为它使用了普通的threading.Lock()
。 这个改变也回溯到了:1.4.51 参考文献:#10813
oracle
- [oracle] [asyncio]
在 asyncio 模式下添加了对 python-oracledb 的支持,使用了新发布的支持 asyncio 的
oracledb
DBAPI 版本。 对于 2.0 系列,这是一个预览版本,当前实现尚未包括对AsyncConnection.stream()
的支持。 SQLAlchemy 计划改进支持以适用于 2.1 版本。 参考文献:#10679
2.0.24
发布日期:2023 年 12 月 28 日
orm
- [orm] [bug] 对在版本 0.9.8 中发布的#3208首次实施的修复进行了改进,其中声明性内部使用的类注册表可能会受到竞争条件的影响,这种情况下在同时清理个别映射类并构造新映射类时可能会发生,如一些测试套件配置或动态类创建环境中可能发生的情况。除了已经添加的弱引用检查外,还首先复制正在迭代的项目列表,以避免“在迭代时更改列表”的错误。感谢 Yilei Yang 提供的拉取请求。 此更改也被回溯到:1.4.51 参考:#10782
- [orm] [bug]
修复了在未对非初始化的
mapped_column()
构造上使用foreign()
注释会产生没有类型的表达式的问题,这样在实际列初始化时不会更新,导致关系无法适当地确定use_get
的问题。 参考:#10597 - [orm] [bug] 改进了工作单元进程将主键列的值设置为 NULL 的错误消息,因为具有对该列的依赖规则的相关对象被删除,包括不仅目标对象和列名,还包括来源列。感谢 Jan Vollmer 提供的拉取请求。 参考:#10668
- [orm] [bug]
修改了
MappedAsDataclass
、DeclarativeBase
和DeclarativeBaseNoMeta
使用的__init_subclass__()
方法,使其接受任意的**kw
并将其传播到super()
调用,从而允许更灵活地安排使用__init_subclass__()
关键字参数的自定义超类和混入。感谢 Michael Oliver 提供的拉取请求。 参考:#10732 - [orm] [bug]
确保了在 ORM 启用的 INSERT、UPDATE 和 DELETE 语句的
returning()
部分中使用Bundle
对象的用例已经得到测试并且完全可用。这在以前从未被明确实现或测试过,并且在 1.4 系列中没有正常工作;在 2.0 系列中,ORM UPDATE/DELETE 缺少了一个实现方法,导致Bundle
对象无法正常工作。 参考:#10776 - [orm] [bug]
修复了 2.0 版本中
MutableList
中的一个回归问题,该问题导致检测序列的例程无法正确地过滤掉字符串或字节实例,从而无法将字符串值分配给特定索引(而非序列值则可以正常工作)。 参考:#10784
engine
- [engine] [bug]
修复了将
URL
对象的用户名和密码部分进行 URL 编码时的问题,在使用URL.render_as_string()
方法将其转换为字符串时,采用了 Python 标准库urllib.parse.quote
,同时允许加号和空格保持不变,以便与 SQLAlchemy 的非标准 URL 解析兼容,而不是多年前的遗留自行编写的例程。感谢 Xavier NUNN 提交的拉取请求。 参考:#10662
sql
- [sql] [bug] 修复了 SQL 元素的字符串化问题,在未传递特定方言的情况下,遇到诸如 PostgreSQL 的“on conflict do update”构造之类的方言特定元素,然后无法提供具有适当状态以呈现构造的字符串化方言,导致内部错误。 参考:#10753
- [sql] [bug]
修复了针对 DML 构造(如
insert()
构造)的CTE
进行字符串化或编译时失败的问题,由于错误地检测到了语句整体是一个 INSERT,导致内部错误。
schema
- [schema] [bug]
修复了创建
Table
等对象时出现意外模式项的错误报告问题,该问题会错误地处理作为元组传递的参数,导致格式错误。错误消息已经使用 f-strings 进行了现代化处理。 参考:#10654
typing
- [typing] [bug]
为
sqlalchemy.sql.functions
模块完成了 pep-484 类型化。对于针对func
元素进行的select()
构造现在应该填充返回类型。 参考:#6810
asyncio
- [asyncio] [change]
async_fallback
方言参数现已弃用,并将在 SQLAlchemy 2.1 中删除。这个标志在一段时间内没有被用于 SQLAlchemy 的测试套件。通过使用greenlet_spawn()
在 greenlet 中运行代码,asyncio 方言仍然可以以同步方式运行。
postgresql
- [postgresql] [bug]
调整了 asyncpg 方言,以便当使用
terminate()
方法丢弃无效的连接时,方言首先会尝试使用带有超时的.close()
优雅地关闭连接,如果操作仅在异步事件循环上下文中进行。这允许 asyncpg 驱动程序处理最终化TimeoutError
,包括能够在程序退出后继续运行的情况下关闭长时间运行的查询服务器端。 参考:#10717
mysql
- [mysql] [bug] 修复了使用旧于 1.0 版本的 PyMySQL 的 pool pre-ping 时,在票证 #10492 中的修复引入的回归。 此更改也被回溯至:1.4.51 参考:#10650
测试
- [tests] [bug]
对测试套件进行了改进,进一步加强了在未安装 Python
greenlet
时运行的能力。现在有一个 tox 目标,其中包含标记“nogreenlet”,该目标将在未安装 greenlet 的情况下运行套件(请注意,它仍然作为 tox 配置的一部分临时安装 greenlet)。 参考:#10747
2.0.23
发布日期:2023 年 11 月 2 日
orm
- [orm] [usecase]
为新式批量 ORM 插入实现了
Session.bulk_insert_mappings.render_nulls
参数,允许render_nulls=True
作为执行选项。这允许使用参数字典中的None
值进行批量 ORM 插入,并使用给定的字典键的单个行批处理,而不是将其拆分为每个 INSERT 中省略 NULL 列的批次。 另请参阅 在 ORM 批量 INSERT 语句中发送 NULL 值](…/orm/queryguide/dml.html#orm-queryguide-insert-null-params) 参考:#10575 - [orm] [bug]
修复了
__allow_unmapped__
指令无法允许具有注释(如Any
或具有特定类型但没有Mapped[]
作为其类型的)的遗留Column
/deferred()
映射,而无需与定位属性名称相关的错误。 参考:#10516 - [orm] [bug]
修复了缓存错误,当与加载器选项
selectinload()
、lazyload()
一起使用with_expression()
构造时,在后续缓存运行中无法正确替换绑定参数值的问题。 参考:#10570 - [orm] [bug]
修复了 ORM 注释声明中的错误,其中使用
ClassVar
,但仍然以某种方式引用 ORM 映射类名会导致无法解释为未映射的ClassVar
。 参考:#10472
sql
- [sql] [usecase]
为 PostgreSQL 和 Oracle 方言的
Interval
数据类型实现了“字面值处理”,允许对间隔值进行字面渲染。感谢 Indivar Mishra 的拉取请求。 参考:#9737 - [sql] [bug]
修复了使用
literal_execute=True
时,与其他字面渲染参数的某些组合中多次使用相同绑定参数会导致值渲染错误的问题,这是由于迭代问题引起的。 此更改也被回溯到:1.4.50 参考:#10142 - [sql] [bug] 为所有包含字面处理的数据类型的“字面处理器”添加了编译器级别的 None/NULL 处理,即在 SQL 语句中内联渲染值而不是作为绑定参数的所有这些类型,对于那些不具有显式“null 值”处理的类型。以前,此行为是未定义且不一致的。 参考:#10535
- [sql]
删除了未使用的占位符方法
TypeEngine.compare_against_backend()
,这个方法是由非常旧版本的 Alembic 使用的。有关详细信息,请参见github.com/sqlalchemy/alembic/issues/1293
。
asyncio
- [asyncio] [bug]
修复了方法
AsyncSession.close_all()
的 bug,该方法之前未能正确工作。还添加了函数close_all_sessions()
,它是close_all_sessions()
的等效函数。拉取请求由 Bryan 不可思议提供。 参考:#10421
postgresql
- [postgresql] [bug] 修复了 2.0 版本中由#7744引起的回归问题,该问题涉及到与其他操作符(如字符串连接)组合使用的 PostgreSQL JSON 运算符的表达式链失去了正确的括号化,这是由于 PostgreSQL 方言特有的实现细节导致的。 参考:#10479
- [postgresql] [bug]
当使用 asyncpg 后端并使用
BIT
数据类型时,修复了“insertmanyvalues”的 SQL 处理。在 asyncpg 上,BIT
显然需要使用一个 asyncpg 特定的BitString
类型,该类型目前在使用此 DBAPI 时被公开,使其与其他所有在此处使用普通位字符串的 PostgreSQL DBAPI 不兼容。在版本 2.1 中的未来修复将会使所有 PG 后端规范化此数据类型。拉取请求由 Sören Oldag 提供。 参考:#10532
mysql
- [mysql] [bug]
修复了 MySQL 的“预先 ping”例程中的新不兼容性问题,其中传递给
connection.ping()
的False
参数,用于禁用不需要的“自动重新连接”功能,在 MySQL 驱动程序和后端中被弃用,并且对于某些版本的 MySQL 原生客户端驱动程序产生警告。它已被 mysqlclient 移除,而对于 PyMySQL 和基于 PyMySQL 的驱动程序,该参数将在某个时间点被弃用并移除,因此使用 API 内省来未来保证这些不同移除阶段的兼容性。 此更改也被回溯到:1.4.50 参考:#10492
mariadb
- [mariadb] [bug]
调整了 MySQL / MariaDB 方言,当使用 MariaDB 时,将生成的列默认为 NULL,如果未使用明确的
True
或False
值指定Column.nullable
,因为 MariaDB 不支持生成列的“NOT NULL”短语。拉取请求由 Indivar 提供。 参考:#10056 - [mariadb] [bug] [regression] 为 MySQL/MariaDB 驱动程序之间似乎存在的一个固有问题建立了一个解决方法,即使用 SQLAlchemy 的“空 IN”条件删除 DML 的 RETURNING 结果返回没有行时,不提供 cursor.description,然后产生返回没有行的结果,导致 ORM 中的回归,在 2.0 系列中使用 RETURNING 用于“同步会话”功能的批量删除语句。为了解决这个问题,当检测到“给出 RETURNING 时没有描述”的特定情况时,将生成一个带有正确游标描述的“空结果”,并用于替代不起作用的游标。 参考:#10505
mssql
- [mssql] [用例]
增加了对为 SQL Server 实现的
aioodbc
驱动程序的支持,该驱动程序建立在 pyodbc 和通用 aio* 方言架构之上。 另请参阅 aioodbc - 在 SQL Server 方言文档中。 参考:#6521 - [mssql] [bug] [反射] 修复了身份列反射失败的问题,对于具有大于 18 位数的大整数起始值的 bigint 列。 此更改也回溯到:1.4.50 参考:#10504
oracle
- [oracle] [bug]
修复了
Interval
数据类型中的问题,在 Oracle 实现未用于 DDL 生成,导致day_precision
和second_precision
参数被忽略,尽管此方言支持。感谢 Indivar 的拉取请求。 参考:#10509 - [oracle] [bug] 修复了 cx_Oracle 方言声称支持比实际上在 SQLAlchemy 的 2.0 系列中支持的更低的 cx_Oracle 版本(7.x)的问题。该方言导入仅在 cx_Oracle 8 或更高版本中才存在的符号,因此运行时方言检查以及 setup.cfg 要求已更新以反映此兼容性。 参考:#10470
2.0.22
发布日期:2023 年 10 月 12 日
orm
- [orm] [用例]
添加了
Session.get_one()
方法,其行为类似于Session.get()
,但如果未找到具有提供的主键的实例,则引发异常。感谢 Carlos Sousa 的拉取请求。 参考:#10202 - [orm] [用例]
添加了一个选项来永久关闭会话。将新参数
Session.close_resets_only
设置为False
将阻止Session
在调用Session.close()
后执行任何其他操作。 添加了新方法Session.reset()
,将会将Session
重置为其初始状态。这是Session.close()
的别名,除非Session.close_resets_only
设置为False
。 参考:#7787 - [orm] [bug]
修复了一系列
mapped_column()
参数,在使用 pep-593Annotated
对象内的mapped_column()
对象时未被传递,包括mapped_column.sort_order
,mapped_column.deferred
,mapped_column.autoincrement
,mapped_column.system
,mapped_column.info
等。 此外,在Annotated
中接收的mapped_column()
中仍不支持有数据类参数,例如mapped_column.kw_only
,mapped_column.default_factory
等。当以这种方式在Annotated
中使用这些参数时,现在会发出警告(并且它们继续被忽略)。 参考:#10046,#10369 - [orm] [bug]
修复了在 ORM 中使用新式
select()
查询调用Result.unique()
时出现的问题,其中一个或多个列产生的值是“未知可哈希性”,通常在使用像func.json_build_object()
这样的 JSON 函数时没有提供类型时会在返回的值实际上不可哈希时内部失败。在这种情况下,修复了对接收到的对象进行哈希性测试,如果不可哈希,则提出了信息性错误消息。请注意,对于“已知不可哈希性”的值,例如直接使用JSON
或ARRAY
类型时,已经提出了信息性错误消息。 此处的“哈希性测试”修复也适用于传统的Query
,但在传统情况下,几乎所有查询都使用Result.unique()
,因此此处不会发出新的警告;在这种情况下,将继续保持回退到在此情况下使用id()
的传统行为,改进是现在将未知类型(结果证明是可哈希的)进行唯一化,而以前不会。 参考:#10459 - [orm] [bug]
修复了最近修订的“insertmanyvalues”功能中的回归问题(可能是问题#9618),在这种情况下,ORM 会误将非 RETURNING 结果解释为具有 RETURNING 结果,如果应用了
implicit_returning=False
参数到映射的Table
,则表示“insertmanyvalues”不能在未提供主键值的情况下使用。 参考:#10453 - [orm] [bug]
修复了 ORM
with_loader_criteria()
不适用于将 ON 子句给定为普通 SQL 比较而不是关系目标或类似的Select.join()
的 bug。 参考:#10365 - [orm] [bug]
修复了
Mapped
等符号在作为子模块元素引用时无法正确解析的问题,假设是基于字符串或“未来注释”样式注释。 参考:#10412 - [orm] [bug]
修复了使用
__allow_unmapped__
声明选项时的类型问题,其中使用集合类型(如list[SomeClass]
)声明的类型与使用 typing 构造List[SomeClass]
声明的类型无法被正确识别的问题。感谢 Pascal Corpet 提供的拉取请求。 参考:#10385
engine
- [engine] [bug] 修复了某些方言中的问题,在这些方言中,对于一个根本不返回任何行的 INSERT 语句,方言可能会错误地返回一个空结果集,这是由于仍然存在来自预取或后取主键的遗留物。受影响的方言包括 asyncpg,所有 mssql 方言。
- [engine] [bug] 修复了在某些垃圾回收/异常场景下,连接池的清理例程会由于意外的状态集而引发错误的问题,这种情况可以在特定条件下重现。 参考:#10414
sql
- [sql] [bug]
修复了在 UPDATE 语句的 SET 子句中引用 FROM 条目时,如果该条目在语句中没有其他地方出现,则不会将其包含在 UPDATE 语句的 FROM 子句中的问题;目前对于通过
Update.add_cte()
添加的 CTE,以在语句顶部提供所需的 CTE,会发生这种情况。 参考:#10408 - [sql] [bug]
修复了 2.0 版本中的回归问题,
DDL
构造不再__repr__()
,因为已删除的on
属性未被容纳。感谢 Iuri de Silvio 提供的拉取请求。 参考:#10443
typing
- [typing] [bug]
修复了传递给
Values
的参数列表过于严格地与List
绑定而不是Sequence
的问题。感谢 Iuri de Silvio 提供的拉取请求。 参考:#10451 - [typing] [bug] 更新了代码库以支持 Mypy 1.6.0。
asyncio
- [asyncio] [bug]
修复了
AsyncSession.get.execution_options
参数未传播到底层Session
并被忽略的问题。
mariadb
- [mariadb] [bug]
修改了 mariadb-connector 驱动程序,预加载了所有查询的
cursor.rowcount
值,以适应像 Pandas 这样硬编码调用Result.rowcount
的工具。SQLAlchemy 通常仅为 UPDATE/DELETE 语句预加载cursor.rowcount
,否则传递给 DBAPI,在那里如果没有值可用,则可以返回 -1。但是,mariadb-connector 不支持在关闭游标本身后调用cursor.rowcount
,而是引发错误。已添加通用测试支持,以确保所有后端支持在结果关闭后允许Result.rowcount
成功(即返回一个整数值,-1 表示“不可用”)。 参考:#10396 - [mariadb] [bug] 为 mariadb-connector 方言添加了额外的修复,以支持 INSERT…RETURNING 语句中结果中的 UUID 数据值。
mssql
- [mssql] [bug]
修复了一个 bug,即在 SQL Server 中阻止 ORDER BY 在子查询中发出的规则没有在使用
select.fetch()
方法限制行数与 WITH TIES 或 PERCENT 结合时被禁用,导致无法使用带有 TOP / ORDER BY 的有效子查询。 参考:#10458
2.0.21
发布日期:2023 年 9 月 18 日
orm
- [orm] [bug]
调整了 ORM 对“target”实体在
Update
和Delete
中的解释,以不干扰传递给语句的目标“from”对象,例如在传递 ORM 映射的aliased
构造时应在“UPDATE FROM”等短语中保留。像使用“SELECT”语句进行 ORM 会话同步的情况,如与 MySQL/MariaDB 一起使用 UPDATE/DELETE 这种形式仍然会有问题,因此最好在使用此类 DML 语句时禁用 synchonize_session。 参考:#10279 - [orm] [bug]
为
selectin_polymorphic()
加入了新的功能,允许其他加载器选项被捆绑为同级,并且引用其子类中的一个,位于父加载器选项的子选项中。以前,只有当selectin_polymorphic()
处于查询选项的顶层时才支持此模式。请参阅新文档部分以获取示例。 作为这个改变的一部分,改进了Load.selectin_polymorphic()
方法/加载策略的行为,因此子类加载不会加载来自父表的大多数已加载列,当选项用于已经进行关系加载的类时。以前,只有在顶级类加载时才有效的加载子类列的逻辑。 也请参阅 当selectin_polymorphic
本身是子选项时应用加载器选项 参考:#10348
引擎
- [引擎] [错误] 修复了一系列反射问题,影响到 PostgreSQL、MySQL/MariaDB 和 SQLite 方言,在反射外键约束时,目标列包含一个或两个表名或列名中的括号时。 参考:#10275
sql
- [sql] [用例]
调整了
Enum
数据类型,接受None
参数作为Enum.length
参数,导致在结果 DDL 中生成没有长度的 VARCHAR 或其他文本类型。这允许在模式中存在后,为该类型添加任何长度的新元素。感谢 Eugene Toder 提交的拉取请求。 参考:#10269 - [sql] [用例]
添加了新的通用 SQL 函数
aggregate_strings
,它接受一个 SQL 表达式和一个分隔符,将多行字符串连接成单个聚合值。该函数根据后端编译成函数,例如group_concat()
、string_agg()
或LISTAGG()
。感谢 Joshua Morris 提交的拉取请求。 参考:#9873 - [sql] [错误]
调整了字符串连接运算符的运算优先级,使其与字符串匹配运算符(如
ColumnElement.like()
,ColumnElement.regexp_match()
,ColumnElement.match()
等)以及纯粹的==
相等,该运算符与字符串比较运算符具有相同的优先级,因此将在跟随字符串匹配运算符的字符串连接表达式中应用括号。这为后端(如 PostgreSQL)提供了便利,其中“regexp match”运算符显然比字符串连接运算符的优先级高。 参考:#9610 - [sql] [bug]
限定了 DDL 编译器中
hashlib.md5()
的使用,该函数用于在 DDL 语句中为长索引和约束名称生成确定性的四个字符后缀,以包含 Python 3.9 中的usedforsecurity=False
参数,以便于 Python 解释器构建用于受限环境(如 FIPS)时,不将此调用视为与安全问题相关联。 参考:#10342 - [sql] [bug]
Values
构造现在将自动为与现有 FROM 子句关联的column
创建代理(即副本)。这使得像values_obj.c.colname
这样的表达式将在colname
作为已与先前的Values
或其他表构造一起使用的column
的情况下生成正确的 FROM 子句。最初认为这可能是一个错误条件的候选项,但很可能这种模式已经被广泛使用,所以现在添加以支持。 参考:#10280
模式
- [schema] [bug]
修改了仅适用于 Oracle 后端的
Identity.order
参数的呈现方式,该参数是Sequence
和Identity
的一部分,并且不适用于其他后端,例如 PostgreSQL 的后端。未来版本将重命名Identity.order
、Sequence.order
和Identity.on_null
参数为 Oracle 特定名称,并弃用旧名称,这些参数仅适用于 Oracle。 此更改也被回溯到:1.4.50 参考:#10207
输入
- [输入] [用例]
使
Mapped
的包含类型协变;这是为了允许更大的灵活性,以适应端用户类型化场景,例如使用协议表示传递给其他函数的特定映射类结构。作为这个改变的一部分,还使依赖和相关类型(如SQLORMOperations
、WriteOnlyMapped
和SQLColumnExpression
)的包含类型也是协变的。感谢 Roméo Després 提交的拉取请求。 参考:#10288 - [输入] [错误]
修复了在 2.0.20 中引入的回归问题,通过 #9600 修复,尝试为
MetaData.naming_convention
添加更正式的类型。这个改变阻止了基本命名约定字典通过类型检查,并且已经进行了调整,以便再次接受字符串键的普通字典以及使用约束类型作为键或两者混合使用的字典。 作为这个改变的一部分,还对命名约定字典的较少使用的形式进行了类型化,包括它目前允许Constraint
类型对象作为键。 参考:#10264,#9284 - [输入] [错误]
修复了应用于表达式构造的基础
Visitable
类的__class_getitem__()
方法的类型注释,以接受Any
作为键,而不是str
,这有助于一些 IDE(例如 PyCharm)在尝试为包含通用选择器的 SQL 构造编写类型注释时。感谢 Jordan Macdonald 的拉取请求。 参考:#9878 - [typing] [bug]
修复了核心“SQL 元素”类
SQLCoreOperations
的类型问题,以支持从类型的角度来看__hash__()
方法,因为对象(如Column
和 ORMInstrumentedAttribute
)是可散列的,并且在Update
和Insert
构造的公共 API 中用作字典键。先前,类型检查器不知道根 SQL 元素是可散列的。 参考:#10353 - [typing] [bug]
修复了
Existing.select_from()
的类型问题,该问题阻止了它与 ORM 类的使用。 参考:#10337 - [typing] [bug] 更新 ORM 加载选项的类型注释,将其限制为仅接受“*”而不是任何字符串作为字符串参数。感谢 Janek Nouvertné的拉取请求。 参考:#10131
postgresql
- [postgresql] [bug]
修复了在 2.0 版本中出现的回归问题,该问题由于#8491而引起,其中当使用
create_engine.pool_pre_ping
参数时,用于 PostgreSQL 方言的修订的“ping”会干扰 asyncpg 与 PGBouncer“transaction”模式的使用,因为 asnycpg 发出的多个 PostgreSQL 命令可能会被分解到多个连接中导致错误,由于这个新修订的“ping”周围没有任何事务。现在在事务内调用 ping,与所有其他基于 pep-249 DBAPI 的其他后端隐式使用的方式相同;这确保了为此命令发送的一系列 PG 命令在同一个后端连接上调用,而不会在命令中途跳转到不同的连接。如果使用 asyncpg 方言处于“AUTOCOMMIT”模式,则不使用事务,这仍然与 pgbouncer 事务模式不兼容。 参考:#10226
杂项
- [bug] [setup]
修复了一个很久以前的问题,在 pytest 运行之外无法导入 SQLAlchemy 模块的全部内容,包括
sqlalchemy.testing.fixtures
。这适用于诸如pkgutil
等尝试导入所有包中所有安装的模块的检查工具。 参考:#10321
2.0.20
发布日期:2023 年 8 月 15 日
orm
- [orm] [usecase] 实现了对启用 ORM 的 DML 语句的“RETURNING ‘*’”用例。这将尽可能地呈现,并返回未经过滤的结果集,但不支持具有特定列渲染要求的多参数“ORM 批量 INSERT”语句。 参考:#10192
- [orm] [bug]
修复了一个基本问题,阻止了某些形式的 ORM “注释” 对使用
Select.join()
进行关系目标的连接的子查询进行。在诸如PropComparator.and_()
和其他 ORM 特定情况下使用这些注释。 此更改也被回溯到:1.4.50 参考:#10223 - [orm] [bug]
修复了一个问题,即 ORM 在具有相同名称列的超类和子类的连接继承模型中生成 SELECT 时,某种方式未能将正确的列名列表发送到
CTE
构造函数,当生成 RECURSIVE 列表时。 参考:#10169 - [orm] [bug]
修复了一个相当重要的问题,即传递给
Session.execute()
的执行选项以及本地于 ORM 执行的语句本身的执行选项不会传播到 eager loaders,如selectinload()
、immediateload()
和sqlalchemy.orm.subqueryload()
,使得不可能禁用单个语句的缓存或使用schema_translate_map
用于单个语句,以及使用用户自定义执行选项。已做出更改,使得所有针对Session.execute()
的面向用户的执行选项都将传播到其他加载器。 作为此更改的一部分,可以通过将execution_options={"compiled_cache": None}
发送到Session.execute()
来在每个语句范围内为“过度深入”的急加载器警告消除缓存被禁用,这将禁用该范围内所有语句的缓存。 参考:#10231 - [orm] [bug]
修复了 ORM 在像
Comparator.any()
这样的表达式中使用的内部克隆,以生成相关 EXISTS 构造会干扰 SQL 编译器的“笛卡尔积警告”功能,导致 SQL 编译器在所有语句元素都正确连接时发出警告。 参考:#10124 - [orm] [bug]
修复了
lazy="immediateload"
加载策略在某些情况下会将内部加载令牌放置到 ORM 映射属性中的问题,例如在递归自引用加载中不应发生加载的情况。作为此更改的一部分,lazy="immediateload"
策略现在以与其他急加载器相同的方式尊重relationship.join_depth
参数进行自引用急加载,其中将其设置为未设置或设置为零将导致自引用的即时加载不会发生,将其设置为一个或更大的值将即时加载直到给定深度。 参考:#10139 - [orm] [bug]
修复了诸如
attribute_keyed_dict()
之类的基于字典的集合在完全正确地 pickle/unpickle 时未能完全 pickle/unpickle 的问题,导致在 unpickling 后尝试变异此类集合时出现问题。 参考:#10175 - [orm] [bug]
修复了从另一个急加载器使用
aliased()
对加入的继承子类进行列局部操作时,链式调用load_only()
或其他通配符使用defer()
会失败的问题。 参考:#10125 - [orm] [bug]
修复了一个问题,即启用 ORM 的
select()
构造不会渲染任何仅通过Select.add_cte()
方法添加的 CTE,这些 CTE 在语句中没有被引用。 参考资料:#10167
例子
- [examples] [bug]
dogpile_caching 例子已更新为 2.0 风格的查询。在“缓存查询”逻辑中,添加了一个条件来区分
Query
和select()
在执行无效操作时的情况。
引擎
- [engine] [bug]
修复了一个关键问题,即将
create_engine.isolation_level
设置为AUTOCOMMIT
(而不是使用Engine.execution_options()
方法),如果临时选择了替代隔离级别,那么会在使用Connection.execution_options.isolation_level
时,无法将“自动提交”恢复到池连接中。 参考资料:#10147
sql
- [sql] [bug]
修复了反序列化
Column
或其他ColumnElement
时无法恢复正确“比较器”对象的问题,该对象用于生成特定于类型对象的 SQL 表达式。 这个更改也被 回溯 到了:1.4.50 参考资料:#10213
类型
- [typing] [usecase]
添加了新的类型仅实用函数
Nullable()
和NotNullable()
以分别将列或 ORM 类型定义为可为空或不可为空。这些函数在运行时无操作,返回未更改的输入。 参考资料:#10173 - [typing] [bug]
类型改进:
- 对一些没有返回的 DML 使用
Session.execute()
时,返回CursorResult
- 修复了
Query.with_for_update.of
参数在Query.with_for_update()
中的类型错误 - 对一些 DML 方法使用的
_DMLColumnArgument
类型进行改进,以传递列表达式 - 添加了对
literal()
的重载,因此推断返回类型为BindParameter[NullType]
,其中literal.type_
参数为 None - 为
ColumnElement.op()
添加重载,以便在未提供ColumnElement.op.return_type
时推断类型为Callable[[Any], BinaryExpression[Any]]
- 添加了对
ColumnElement.__add__()
的丢失重载
拉取请求由 Mehdi Gmira 提供。 参考:#9185
- 对一些没有返回的 DML 使用
- [typing] [错误]
修复了
Session
和AsyncSession
等方法中的问题,例如Session.connection()
在Session.connection.execution_options
参数硬编码为不面向用户的内部类型的情况。 参考:#10182
asyncio
- [asyncio] [用例]
添加了新方法
AsyncConnection.aclose()
作为AsyncConnection.close()
的同义词和AsyncSession.aclose()
作为AsyncSession.close()
的同义词,以提供与 Python 标准库@contextlib.aclosing
构造的兼容性。拉取请求由 Grigoriev Semyon 提供。 参考:#9698
mysql
- [mysql] [用例] 更新了 aiomysql 方言,因为该方言似乎再次得到维护。重新添加到使用版本 0.2.0 进行的 ci 测试。 这个变更也被回溯到:1.4.50
2.0.19
发布日期:2023 年 7 月 15 日
orm
- [orm] [错误]
修复了直接设置关系集合的问题,其中新集合中的对象已经存在时,不会触发该对象的级联事件,导致如果该对象不存在,则不会被添加到
Session
中。这与#6471类似,并且由于在 2.0 系列中删除了cascade_backrefs
,这个问题更加明显。作为#6471的一部分添加的AttributeEvents.append_wo_mutation()
事件现在也会对同一集合的现有成员发出信号,这些成员在该集合的批量设置中存在。 参考:#10089 - [orm] [bug]
修复了通过 backref 与未加载集合关联的对象,但由于在 2.0 系列中删除了
cascade_backrefs
而未合并到Session
中的问题,将不会发出警告,表明这些对象未包含在刷新中,即使它们是集合的待处理成员;在其他情况下,当要刷新的集合包含将被基本丢弃的非附加对象时,会发出警告。对于 backref 待处理集合成员的警告的添加建立了与可能根据不同的关系加载策略在不同时间基于不同时间刷新或不刷新的集合的更大一致性。 参考:#10090 - [orm] [bug] [regression]
修复了由#9805引起的额外回归,其中对语句上“ORM”标志的更积极传播可能导致在 ORM
Query
构造中嵌入一个不包含 ORM 实体的 Core SQL 语句时出现内部属性错误, 在这种情况下,ORM 启用的 UPDATE 和 DELETE 语句。 参考:#10098
engine
- [engine] [bug]
将
Row.t
和Row.tuple()
重命名为Row._t
和Row._tuple()
;这是为了符合所有方法和预定义属性都应采用 Python 标准库namedtuple
风格的策略,其中所有固定名称都有一个前导下划线,以避免与现有列名称冲突。先前的方法/属性现已被弃用,并将发出弃用警告。 参考:#10093 - [engine] [bug]
向
make_url()
函数添加了对非字符串、非URL
对象的检测,允许立即抛出ArgumentError
,而不是稍后引发故障。特殊逻辑确保允许通过模拟URL
的形式。拉取请求由 Grigoriev Semyon 提供。 参考:#10079
postgresql
- [postgresql] [bug]
修复了 PostgreSQL URL 解析改进引起的回归问题 #10004,其中带有冒号的“host”查询字符串参数,以支持各种第三方代理服务器和/或方言,将无法正确解析,因为这些被解析为
host:port
组合。解析已更新,只有当主机名仅包含字母数字字符,并且只包含点或短划线时(例如,没有斜杠),才将冒号视为表示host:port
值的标记,后跟一个零个或多个整数的整数标记。在所有其他情况下,将整个字符串视为主机。 参考:#10069 - [postgresql] [bug]
修复了对
CITEXT
数据类型进行比较时将右侧强制转换为VARCHAR
的问题,导致右侧未被解释为CITEXT
数据类型,对于 asyncpg、psycopg3 和 pg80000 方言。这导致CITEXT
类型在实际使用中基本上无法使用;现已修复此问题,并已更正测试套件以正确断言表达式是否被正确渲染。 参考:#10096
2.0.18
发布日期:2023 年 7 月 5 日
引擎
- [engine] [bug]
调整了
create_engine.schema_translate_map
功能,以便所有语句中的模式名称都现在被标记化,无论指定的名称是否在给定的立即模式翻译映射中,并在执行时回退到原始名称的替换。这两个更改允许在每次运行时使用包含或不包含各种键的模式翻译映射来重复使用已编译的对象,从而允许在每次使用具有不同键集的模式翻译映射时继续运行时缓存 SQL 构造。另外,增加了检测在同一语句的多次调用中获得或失去None
键的 schema_translate_map 字典,这会影响语句的编译,并且与缓存不兼容;针对这些情况引发异常。 References: #10025
sql
- [sql] [bug]
修复了使用“flags”时
ColumnOperators.regexp_match()
不会生成“稳定”缓存键的问题,也就是说,缓存键每次都会改变,导致缓存污染。对于ColumnOperators.regexp_replace()
也存在同样的问题,包括标志和实际替换表达式。现在,标志被表示为固定的修饰符字符串,呈现为安全字符串,而不是绑定参数,并且替换表达式在“binary”元素的主要部分中建立,以便生成适当的缓存键。 请注意,作为此更改的一部分,ColumnOperators.regexp_match.flags
和ColumnOperators.regexp_replace.flags
已修改为仅呈现为文字字符串,而以前它们是呈现为完整的 SQL 表达式,通常是绑定参数。这些参数应始终作为普通的 Python 字符串传递,而不是作为 SQL 表达式构造;不希望在实践中使用 SQL 表达式构造该参数,因此这是一个不向后兼容的更改。 该更改还修改了生成的表达式的内部结构,对于带有或不带有标志的ColumnOperators.regexp_replace()
,以及对于带有标志的ColumnOperators.regexp_match()
。可能已经实现了自己的 regexp 实现的第三方方言(在搜索中找不到此类方言,因此影响预计很低)需要调整结构的遍历以适应。 此更改也 被回溯 至:1.4.49 参考:#10042 - [sql] [错误]
修复了主要内部
CacheKey
构造中__ne__()
运算符未正确实现的问题,导致比较CacheKey
实例时结果荒谬。 此更改也 被回溯 至:1.4.49
扩展
- [扩展] [用例]
为
association_proxy()
association_proxy.create_on_none_assignment
添加了新选项;当一个关联代理引用标量关系被赋值为None
且引用的对象不存在时,通过创建者创建一个新对象。这显然是 1.2 系列中的一个未定义行为,被悄悄移除了。 参考:#10013
键入
- [键入] [用例]
在使用来自
sqlalchemy.sql.operators
的独立运算符函数(如sqlalchemy.sql.operators.eq
)时,改进了类型。 参考:#10054 - [键入] [错误]
修复了在
aliased()
构造中的一些类型问题,以正确接受已用Table.alias()
别名的Table
对象,以及对FromClause
对象作为“selectable”参数的一般支持,因为这是完全支持的。 参考:#10061
postgresql
- [postgresql] [usecase] 为 asyncpg 方言添加了多主机支持。 还对“多主机”用例的 PostgreSQL URL 例程进行了一般改进和错误检查。 感谢 Ilia Dmitriev 提供的拉取请求。 另见 多主机连接 参考:#10004
- [postgresql] [bug]
为所有 PostgreSQL 方言添加了新参数
native_inet_types=False
,表示 DBAPI 使用的转换器将禁用 PostgreSQLINET
和CIDR
列的行转换为 Pythonipaddress
数据类型,而返回字符串。 这允许编写代码以使用这些数据类型的字符串进行迁移,而无需进行代码更改,只需将此参数添加到create_engine()
或create_async_engine()
函数调用中。 另见 网络数据类型 参考:#9945
mariadb
- [mariadb] [usecase] [reflection]
允许从 MariaDB 反射
UUID
列。 这使得 Alembic 能够正确检测现有 MariaDB 数据库中此类列的类型。 参考:#10028
mssql
- [mssql] [usecase]
添加了对 MSSQL 方言中 COLUMNSTORE 索引的创建和反射的支持。 可以在指定
mssql_columnstore=True
的索引上指定。 参考:#7340 - [mssql] [bug] [sql]
修复了将
Cast
执行到具有显式排序规则的字符串类型时,将在 CAST 函数内部渲染 COLLATE 子句的问题,从而导致语法错误。 参考:#9932
2.0.17
发布日期:2023 年 6 月 23 日
orm
- [orm] [bug] [regression]
修复了 2.0 系列中的回归,其中使用
undefer_group()
与selectinload()
或subqueryload()
的查询会引发AttributeError
。 感谢 Matthew Martin 提供的拉取请求。 参考:#9870 - [orm] [bug]
修复了在 ORM Annotated Declarative 中的问题,该问题阻止了在不返回
Mapped
数据类型的混合使用declared_attr
的情况,而是返回了额外的 ORM 数据类型,如AssociationProxy
。声明式运行时错误地尝试将此注释解释为需要Mapped
并引发错误。 参考:#9957 - [orm] [bug] [typing]
修复了使用
declared_attr
函数从AssociationProxy
返回类型的类型问题被禁止的问题。 参考:#9957 - [orm] [bug] [regression]
修复了在 2.0.16 中由#9879引入的回归,其中将可调用对象传递给
mapped_column.default
参数时,同时设置init=False
会将此值解释为 Dataclass 默认值,该值将直接分配给新实例的对象,绕过了作为底层Column.default
值生成器的默认生成器的过程。现在检测到这种情况,以保持先前的行为,但对于这种模棱两可的用法会发出弃用警告;要为Column
填充默认生成器,应使用mapped_column.insert_default
参数,该参数与固定名称的mapped_column.default
参数相区分,其名称根据 pep-681 固定。 参考:#9936 - [orm] [bug]
对 ORM
Session
“状态更改”系统进行了额外的加固和文档,该系统检测到同时使用Session
和AsyncSession
对象的并发使用;在获取来自底层引擎的连接的过程中添加了额外的检查,这是关于内部连接管理的关键部分。 参考:#9973 - [orm] [bug]
在 ORM 加载器策略逻辑中修复了问题,进一步允许在复杂的继承多态/别名/of_type()关系链上的长链中使用
contains_eager()
加载器选项,以便在查询中正确生效。 参考:#10006 - [orm] [bug]
修复了对
Enum
数据类型在registry.type_annotation_map
中的支持,该支持是作为 #8859 的一部分首次添加的,在此过程中,如果在映射中使用了带有固定配置的自定义Enum
,则会失败传递Enum.name
参数,这将导致 PostgreSQL 枚举无法正常工作,如果枚举值被传递为单个值,则会产生其他问题。逻辑已更新,以便传递“名称”,但也使默认Enum
不会设置硬编码名称为"enum"
,该默认枚举是针对纯 Python 枚举 enum.Enum 类或其他“空”枚举的。 参考:#9963
ORM 声明式
- [orm] [declarative] [bug]
当将 ORM
relationship()
和其他MapperProperty
对象同时分配给两个不同的类属性时,会发出警告;只有其中一个属性会被映射。对于此条件,已经为Column
和mapped_column
对象设置了警告。 参考:#3532
扩展
- [extensions] [bug] 修复了与 mypy 1.4 结合使用的 mypy 插件中的问题。 这个更改也被 回溯 到:1.4.49
typing
- [typing] [bug]
修复了类型问题,该问题导致无法完全在 ORM 查询中使用
WriteOnlyMapped
和DynamicMapped
属性。 引用:#9985
postgresql
- [postgresql] [usecase] pg8000 方言现在支持 RANGE 和 MULTIRANGE 数据类型,使用现有的 Range and Multirange Types 中描述的 RANGE API。 Range 和 multirange 类型在 pg8000 驱动程序的版本 1.29.8 中受支持。感谢 Tony Locke 提供的拉取请求。 引用:#9965
2.0.16
发布日期:2023 年 6 月 10 日
平台
- [platform] [usecase] 兼容性改进,使完整的测试套件可以在 Python 3.12.0b1 上通过。
orm
- [orm] [usecase]
改进了
DeferredReflection.prepare()
,使其接受传递给MetaData.reflect()
的任意**kw
参数,允许使用诸如反射视图等用例以及传递给方言特定参数。另外,还现代化了DeferredReflection.prepare.bind
参数,以便将Engine
或Connection
作为“bind”参数接受。 引用:#9828 - [orm] [bug]
修复了
DeclarativeBaseNoMeta
声明基类无法与非映射混合类或抽象类一起使用的问题,而是引发AttributeError
。 引用:#9862 - [orm] [bug] [regression]
修复了 2.0 系列中的一个回归,其中
validates.include_backrefs
的默认值在validates()
函数中更改为False
。现在将该默认值恢复为True
。 引用:#9820 - [orm] [bug] 在版本 2.0.11 中作为#9583的一部分新增的功能中修复了一个 bug,该功能允许在 ORM 按主键批量更新时与 WHERE 子句一起使用,发送不包含每行主键值的字典将通过批量处理,并为行包括“pk=NULL”,但不会引发异常。如果未提供批量更新的主键值,则现在会引发异常。 引用:#9917
- [orm] [bug] [dataclasses]
修复了一个问题,其中生成指定了
default
值并设置init=False
的 dataclasses 字段将无效。在这种情况下,dataclasses 行为是在类上设置默认值,这与 SQLAlchemy 使用的描述符不兼容。为了支持这种情况,在生成 dataclass 时将默认值转换为default_factory
。 引用:#9879 - [orm] [bug]
当向
Mapper
添加属性时已经配置了 ORM 映射属性,或者类上已经存在属性时,将发出弃用警告。先前,对于此情况存在一个非弃用警告,但并非始终一致发出。已改进此警告的逻辑,以便在检测到属性的终端用户替换时发出警告,同时对于内部 Declarative 和其他情况,其中用新的属性替换描述符是预期的情况,不会产生误报。 引用:#9841 - [orm] [bug]
改进了
registry.map_imperatively()
方法的map_imperatively.local_table
参数上的参数检查,确保只传递Table
或其他FromClause
,而不是已存在的映射类,因为该对象将被进一步解释为新的映射时会导致未定义的行为。 引用:#9869 - [orm] [bug]
InstanceState.unloaded_expirable
属性是InstanceState.unloaded
的同义词,现在已弃用;此属性始终是特定于实现的,不应公开。 参考:#9913
asyncio
- [asyncio] [用例]
添加了新的
create_async_engine.async_creator
参数到create_async_engine()
,其完成了与create_engine.creator
参数相同的目的create_engine()
。这是一个不带参数的可调用对象,提供一个新的 asyncio 连接,直接使用 asyncio 数据库驱动程序。create_async_engine()
函数将在适当的结构中封装驱动程序级别的连接。贡献者 Jack Wotherspoon。 参考:#8215
postgresql
- [postgresql] [用例] [反射]
在 PostgreSQL 反射中使用
ARRAY_AGG
时,将NAME
列强制转换为TEXT
。这似乎改善了一些 PostgreSQL 派生产品可能不支持NAME
类型的聚合的兼容性。 参考:#9838 - [postgresql] [用例] 统一了自定义 PostgreSQL 运算符定义,因为它们在多种不同的数据类型之间共享。 参考:#9041
- [postgresql] [用例]
添加了对 PostgreSQL 10
NULLS NOT DISTINCT
唯一索引和唯一约束功能的支持,使用方言选项postgresql_nulls_not_distinct
。更新反射逻辑以正确考虑此选项。贡献者 Pavel Siarchenia。 参考:#8240 - [postgresql] [错误]
在 PostgreSQL 特定运算符上使用适当的优先级,如
@>
。以前优先级错误,导致针对ANY
或ALL
结构呈现时括号错误。 参考:#9836 - [postgresql] [错误]
修复了一个问题,即
ColumnOperators.like.escape
和类似的参数不允许空字符串作为参数,该参数将作为“转义”字符传递;这是 PostgreSQL 支持的语法。贡献者 Martin Caslavsky。 参考:#9907
2.0.15
发布日期:2023 年 5 月 19 日
orm
- [orm] [错误]
随着越来越多的项目使用新式“2.0”ORM 查询,显然,“autoflush”的条件性,即基于给定语句是否引用 ORM 实体,正在变得更加重要。到目前为止,“ORM”标志对于语句是否返回与 ORM 实体或列对应的行已经存在了一定程度的松散关联;“ORM”标志的原始目的是启用应用于 Core 结果集的 ORM 实体获取规则以及应用于语句的 ORM 加载策略的后处理。对于不基于包含 ORM 实体的行构建的语句,认为“ORM”标志基本上是不必要的。
仍然可能存在“autoflush”对于所有使用
Session.execute()
和相关方法的情况更加有效的情况,即使是对纯粹的 Core SQL 构造也是如此。然而,这可能会影响到未预期的旧有情况,并且可能更多地成为 2.1 版本的事情。但是,现在“ORM-标志”的规则已经被放宽,因此包含任何 ORM 实体或属性的语句,包括仅在 WHERE / ORDER BY / GROUP BY 子句中的语句,在标量子查询中等等,都将启用此标志。这将导致这样的语句发生“autoflush”,并且还可以通过ORMExecuteState.is_orm_statement
事件级别属性可见。 引用:#9805
postgresql
- [postgresql] [bug] [regression]
修复了针对 PostgreSQL 方言的基础
Uuid
数据类型,以便在选择“native_uuid”时充分利用 PG 特定的UUID
方言特定的数据类型,以便包含 PG 驱动程序行为。这个问题因为作为#9618的一部分进行的 insertmanyvalues 改进而显现出来,其中类似于#9739,asyncpg 驱动程序对是否存在数据类型转换非常敏感,当使用此通用类型时,必须调用 PostgreSQL 驱动程序特定的本机UUID
数据类型,以便进行这些转换。 引用:#9808
2.0.14
发布日期:2023 年 5 月 18 日
orm
- [orm] [bug]
在一个特定领域修改了
JoinedLoader
的实现,以使用更简单的方法,此前它使用了一个在多个线程之间共享的缓存结构。这样做的理由是为了避免潜在的竞争条件,这被怀疑是导致一个特定崩溃的原因,该崩溃已经被多次报告。所讨论的缓存结构最终仍然通过编译的 SQL 缓存“缓存”,因此不会预期性能下降。 参考:#9777 - [orm] [bug] [回归]
修复了在
CTE
构造中使用update()
或delete()
后,在select()
中使用会引发CompileError
的回归问题,这是由于执行 ORM 级别更新/删除语句的 ORM 相关规则造成的。 参考:#9767 - [orm] [bug]
在新的 ORM 注释式声明中修复了问题,其中通过
pep-593
的Annotated
将ForeignKey
(或其他列级约束)放在mapped_column()
中,然后通过模型复制到模型会将每个约束的副本应用到生成的Table
中的Column
中,导致不正确的 CREATE TABLE DDL 以及在 Alembic 下的迁移指令。 参考:#9766 - [orm] [bug]
使用
joinedload()
加载器选项时,如果使用额外的关系标准,其中额外的标准本身包含引用联接实体的相关子查询,因此也需要对别名实体进行“调整”,则将排除这种适应,从而为joinedload
生成错误的 ON 子句。 参考:#9779
sql
- [sql] [用例]
将 MSSQL 的
try_cast()
函数泛化到sqlalchemy.
导入命名空间中,以便第三方方言也可以实现它。在 SQLAlchemy 中,try_cast()
函数仍然是一个仅适用于 SQL Server 的构造,如果在不支持它的后端使用它,则会引发CompileError
。try_cast()
实现了一个 CAST,其中无法转换的转换返回为 NULL,而不是引发错误。理论上,该构造可以由 Google BigQuery、DuckDB 和 Snowflake 等第三方方言实现,并可能是其他方言。 感谢 Nick Crews 的拉取请求。 引用:#9752 - [sql] [bug]
修复了
values()
构造中的问题,在标量子查询中使用该构造将导致内部编译错误。 引用:#9772
postgresql
- [postgresql] [bug]
修复了一个显然非常久远的问题,即当
ENUM.create_type
参数设置为其非默认值False
时,当复制其所属的Column
时,它将不会被传播,这在使用 ORM 声明性混合时很常见。 引用:#9773
测试
- [tests] [bug] [pypy]
修复了依赖于
sys.getsizeof()
函数不在 pypy 上运行的测试问题,在 pypy 上,该函数似乎具有与 cpython 不同的行为。 引用:#9789
2.0.13
发布日期:2023 年 5 月 10 日
orm
- [orm] [bug]
修复了 ORM 声明式注释在所有情况下无法正确解析前向引用的问题;特别是在与 Pydantic 数据类结合使用
from __future__ import annotations
时。 引用:#9717 - [orm] [bug]
修复了新的使用 RETURNING 与 upsert 语句功能中的问题,其中
populate_existing
执行选项未被传播到加载选项,导致现有属性无法被就地刷新。 引用:#9746 - [orm] [bug]
修复了加载器策略路径问题,例如
joinedload()
/selectinload()
将无法完全遍历多层次深度的加载问题,后跟具有with_polymorphic()
或类似构造的中间成员。 引用:#9715 - [orm] [bug]
修复了
mapped_column()
构造中的问题,当 ORM 映射属性引用相同的Column
时,如果涉及mapped_column()
构造,将不会发出“直接多次命名列 X”的正确警告,而是引发内部断言。 参考:#9630
sql
- [sql] [usecase] 实现了对包含多个未相关的表的 UPDATE 和 DELETE 语句的“笛卡尔积警告”。 参考:#9721
- [sql] [bug]
修复了特定方言浮点/双精度类型的基类;Oracle
BINARY_DOUBLE
现在是Double
的子类,而用于 asyncpg 和 pg8000 的内部类型现在正确地是Float
的子类。 - [sql] [bug]
修复了包含多个表且没有 VALUES 子句的
update()
构造会引发内部错误的问题。当前对于没有值的Update
的行为是生成一个带有空“set”子句的 SQL UPDATE 语句,因此对于这个特定子情况已经保持一致。
schema
- [schema] [performance] 改进了添加表列的方式,避免了不必要的分配,显著加快了创建许多表的速度,比如在反射整个模式时。 参考:#9597
typing
- [typing] [bug]
修复了
Session.get()
和Session.refresh()
(以及AsyncSession
上的相应方法)的Session.get.with_for_update
参数的类型,以接受布尔值True
和运行时参数接受的所有其他形式。 参考:#9762 - [typing] [sql]
添加了类型
ColumnExpressionArgument
作为一个公共类型,指示传递给 SQLAlchemy 构造的面向列的参数,例如Select.where()
、and_()
等。这可以用于为调用这些方法的最终用户函数添加类型。 参考:#9656
asyncio
- [asyncio] [usecase]
添加了一个新的辅助混合类
AsyncAttrs
,旨在改进使用 asyncio 的延迟加载器和其他已过期或延迟的 ORM 属性,提供一个简单的属性访问器,为任何 ORM 属性提供一个await
接口,无论它是否需要发出 SQL。 另请参阅AsyncAttrs
参考:#9731 - [asyncio] [bug]
修复了半私有的
await_only()
和await_fallback()
并发函数中的问题,如果函数抛出GreenletError
,则给定的可等待对象将保持未等待状态,这可能会导致程序后续出现“未等待”警告。在这种情况下,在抛出异常之前,给定的可等待对象现在将被取消。
postgresql
- [postgresql] [bug] [regression]
修复了 2.0.10 中“insertmanyvalues”更改导致的另一个回归问题,类似于回归问题#9701,在使用 asyncpg 驱动程序时,
LargeBinary
数据类型也需要额外的转换以便与新的批量插入格式一起使用。 参考:#9739
oracle
- [oracle] [reflection] 在 Oracle 方言中为基于表达式的索引和索引表达式的排序方向添加了反射支持。 参考:#9597
杂项
- [bug] [ext]
修复了
Mutable
中的问题,其中为 ORM 映射属性注册事件会在映射继承子类中重复调用,导致在继承层次结构中调用重复事件。 参考:#9676
2.0.12
发布日期:2023 年 4 月 30 日
orm
- [orm] [bug]
修复了严重的缓存问题,其中
aliased()
和hybrid_property()
表达式组合的组合会导致缓存键不匹配,导致缓存键持有实际aliased()
对象,同时又不匹配相等结构的缓存键,填充了缓存。 此更改也已回溯到:1.4.48 参考:#9728
mysql
- [mysql] [bug] [mariadb]
修复了关于
Table
和Column
对象的注释反射问题,其中注释包含控制字符,如换行符。对于这些字符以及扩展的 Unicode 字符在表和列注释中的测试支持也已添加到总体测试中。 参考:#9722
2.0.11
发布日期:2023 年 4 月 26 日
orm
- [orm] [用例]
ORM 批量 INSERT 和 UPDATE 现在添加了这些功能:
- 使用“orm” dml_strategy 设置时,不再需要传递额外参数的要求。
- 使用 ORM UPDATE 时,不再需要满足“bulk” dml_strategy 设置时不传递额外的 WHERE 条件的要求。注意,在这种情况下,预期行数的检查被关闭了。
参考:#9583, #9595
- [orm] [bug]
修复了 2.0 中的回归问题,其中在使用 ORM
Session
执行Insert
语句时,在Insert.values()
中使用bindparam()
将无法被正确解释,因为新的 ORM 启用的插入功能 没有实现这种用例。 参考:#9583, #9595
engine
- [engine] [performance]
对
Row
进行了一系列性能增强:-
__getattr__
方法在行的“命名元组”接口的性能得到了提升;在这个变化中,Row
的实现已经简化,移除了在 1.4 版本及以前的 SQLAlchemy 中特有的构造和逻辑。作为这一变化的一部分,Row
的序列化格式已经略微修改,然而使用之前的 SQLAlchemy 2.0 版本进行 pickle 的行将在新格式中被识别。Pull request 由 J. Nick Koston 提供。 - 通过使“bytes”处理程序在每个驱动程序基础上具有条件性,改进了“二进制”数据类型的行处理性能。因此,除了 psycopg2 之外的几乎所有现代形式的驱动程序都已删除了“bytes”结果处理程序,它们都支持直接返回 Python “bytes”。Pull request 由 J. Nick Koston 提供。
- 在
Row
内部进行了进一步的重构,以提高性能。由 Federico Caselli 提供。
引用:#9678、#9680
-
- [engine] [bug] [regression]
修复了阻止
URL.normalized_query
属性正常运行的回归问题。 引用:#9682
sql
- [sql] [usecase]
增加了对
ColumnCollection
的切片访问支持,例如table.c[0:5]
、subquery.c[:-1]
等。切片访问返回一个子ColumnCollection
,方式与传递键元组相同。这是对 #8285 添加的键元组访问的自然延续,其中切片访问用例被省略似乎是一个疏忽。 引用:#8285
typing
- [typing] [bug]
改进了对
RowMapping
的类型标注,以表明它还支持Column
作为索引对象,而不仅仅是字符串名称。Pull request 由 Andy Freeland 提供。 引用:#9644
postgresql
- [postgresql] [bug] [regression] 修复了由#9618引起的严重回归,该回归修改了 2.0.10 的 insertmanyvalues 功能的架构,导致使用 psycopg2 或 psycopg 驱动程序使用 insertmanyvalues 功能插入时,浮点值失去所有小数位。 参考:#9701
mssql
- [mssql] [bug]
为 SQL Server 实现了
Double
类型,在 DDL 时将渲染DOUBLE PRECISION
。这是使用新的 MSSQL 数据类型DOUBLE_PRECISION
实现的,也可以直接使用。
oracle
- [oracle] [bug]
修复了 Oracle 方言中的问题,例如在使用
Insert.returning()
子句返回 INSERT 的值时,Decimal
返回类型(例如Numeric
)会返回浮点值,而不是Decimal
对象的问题。
2.0.10
发布日期:2023 年 4 月 21 日
orm
- [orm] [bug]
修复了各种 ORM 特定的获取器,例如
ORMExecuteState.is_column_load
,ORMExecuteState.is_relationship_load
,ORMExecuteState.loader_strategy_path
等,如果 SQL 语句本身是“复合选择”,如 UNION,则会抛出AttributeError
。 此更改还回溯到:1.4.48 参考:#9634 - [orm] [bug]
修复了当应用于
__mapper_args__
特殊方法名时,declared_attr.directive()
修改器未正确地应用于子类的问题,与直接使用declared_attr
相反。这两种构造在运行时行为应该相同。 参考:#9625 - [orm] [bug]
对
with_loader_criteria()
加载器选项进行了改进,允许在不是 ORM 语句本身的顶级语句的Executable.options()
方法中指示它。示例包括嵌入在诸如union()
的复合语句中的select()
,在Insert.from_select()
构造中,以及在不是 ORM 相关的顶级 CTE 表达式中。 参考:#9635 - [orm] [bug] 修复了 ORM 批量插入功能中的错误,如果请求返回单独列,则在 INSERT 语句中会渲染出额外的不必要列。 参考:#9685
- [orm] [bug]
在 ORM 声明式数据类中修复了一个错误,
query_expression()
和column_property()
构造被记录为只读构造,不能在没有添加init=False
的情况下与MappedAsDataclass
类一起使用,而在query_expression()
中没有可能添加init
参数,因此这个问题不可避免。这些构造已从数据类的角度进行了修改,假定为“只读”,默认设置init=False
,并不再包含在 pep-681 构造函数中。column_property()
的数据类参数init
、default
、default_factory
、kw_only
现已弃用;这些字段不适用于在 Declarative 数据类配置中使用的column_property()
,因为该构造将是只读的。还为query_expression()
添加了一个特定于读取的参数query_expression.compare
;query_expression.repr
已经存在。 参考:#9628 - [orm] [错误]
向
mapped_column()
构造添加了缺失的mapped_column.active_history
参数。
引擎
- [引擎] [用例]
添加了
create_pool_from_url()
和create_async_pool_from_url()
来自字符串或URL
传入的输入 url 创建Pool
实例。 参考:#9613 - [引擎] [错误]
修复了在 2.0 系列首次引入的 “Insert Many Values” Behavior for INSERT statements 性能优化功能中发现的一个主要缺陷。这是对 2.0.9 中的更改的延续,该更改禁用了 SQL Server 版本的功能,因为 ORM 依赖于似乎不保证发生的行排序。该修复为所有“insertmanyvalues”操作应用了新逻辑,当在
Insert.returning()
或UpdateBase.return_defaults()
方法上设置了一个新参数Insert.returning.sort_by_parameter_order
时生效,通过一种交替的 SQL 形式、客户端参数的直接对应以及在某些情况下降级到逐行运行,将对每个返回行批次应用与主键或其他唯一值的对应关系,这些值可以与输入数据相关联。 预计性能影响将是最小的,因为几乎所有常见的主键场景都适合于在除了 SQLite 之外的所有后端实现参数排序批处理,而“逐行”模式与 1.x 系列中使用的非常沉重的方法相比,具有最少的 Python 开销。对于 SQLite,当使用“逐行”模式时,性能没有区别。 预计通过具有高效的“逐行”INSERT 与 RETURNING 批处理功能,后续可以更容易地将“insertmanyvalues”功能推广到包括 RETURNING 支持但不一定易于保证与参数顺序对应的第三方后端。 另请参阅 将返回的行与参数集相关联 参考:#9603, #9618
typing
- [typing] [bug]
为最近添加的运算符
ColumnOperators.icontains()
、ColumnOperators.istartswith()
、ColumnOperators.iendswith()
和位运算符ColumnOperators.bitwise_and()
、ColumnOperators.bitwise_or()
、ColumnOperators.bitwise_xor()
、ColumnOperators.bitwise_not()
、ColumnOperators.bitwise_lshift()
和ColumnOperators.bitwise_rshift()
添加了类型信息。感谢 Martijn Pieters 的拉取请求。 参考:#9650 - [typing] [bug] 对代码库进行更新,以通过 Mypy 1.2.0 的类型检查。
- [typing] [bug]
修复了在加载器选项中(如
selectinload()
)中,PropComparator.and_()
表达式未正确类型化的问题。 参考:#9669
postgresql
- [postgresql] [usecase]
在 asyncpg 方言中添加了
prepared_statement_name_func
连接参数选项。此选项允许传递一个可调用对象,用于自定义执行查询时驱动程序将创建的准备语句的名称。感谢 Pavel Sirotkin 的拉取请求。 另请参阅 使用 PGBouncer 的预准备语句名称 参考:#9608 - [postgresql] [usecase]
添加了缺失的
Range.intersection()
方法。感谢 Yurii Karabas 的拉取请求。 参考:#9509 - [postgresql] [bug]
在
ENUM
的签名中,恢复了ENUM.name
参数作为可选参数,因为这是根据给定的 pep-435Enum
类型自动选择的。 参考:#9611 - [postgresql] [bug]
修复了对普通字符串进行
ENUM
比较时将右侧类型转换为 VARCHAR 的问题,这是由于在诸如 asyncpg 等方言中添加了更明确的转换而导致的 PostgreSQL 类型不匹配错误。 参考:#9621 - [postgresql] [bug] 修复了在 PostgreSQL 中无法反射基于表达式的长表达式索引的问题。表达式错误地被截断为标识符长度(默认为 63 字节)。 参考:#9615
mssql
- [mssql] [bug] 恢复了 Microsoft SQL Server 的 insertmanyvalues 功能。该功能在版本 2.0.9 中被禁用,因为似乎依赖于 RETURNING 的排序,这是不被保证的。“insertmanyvalues” 功能的架构已经重做,以适应 INSERT 语句的特定组织和可以保证返回行与输入记录对应的结果行处理。 参见 将 RETURNING 行与参数集对应 参考:#9603, #9618
oracle
- [oracle] [bug]
修复了在 Oracle 方言的 INSERT…RETURNING 子句中无法使用
Uuid
数据类型的问题。
2.0.9
发布日期:2023 年 4 月 5 日
orm
- [orm] [bug]
修复了当使用“关联到别名类”的特性并且在加载器中指定了一个递归的 eager 加载器(如
lazy="selectinload"
)与另一个相对端的另一个 eager 加载器结合使用时可能发生的无限循环问题。循环检查已修复以包括别名类关系。 这个变更也被 反向移植 到了:1.4.48 参考:#9590
mariadb
- [mariadb] [bug]
在 MariaDb 中将
row_number
添加为保留字。 参考:#9588
mssql
- [mssql] [bug] SQLAlchemy 的“insertmanyvalues”功能允许快速插入许多行,同时还支持 RETURNING,目前已暂时禁用了 SQL Server。由于工作单元当前依赖于此功能,以便将现有 ORM 对象匹配到返回的主键标识,因此此特定使用模式在某些情况下无法与 SQL Server 一起使用,因为“OUTPUT inserted” 返回的行的顺序可能并不总是与发送元组的顺序匹配,导致 ORM 在后续操作中对这些对象做出错误决策。 此功能将在即将发布的版本中重新启用,并且将再次对多行 INSERT 语句产生影响,但是工作单元对此功能的使用将被禁用,可能对所有方言都禁用,除非 ORM 映射的表还包括一个“sentinel”列,以便可以将返回的行引用回传递的原始数据。 参考:#9603
- [mssql] [bug]
当
fast_executemany
设置为True
时,已更改用于 SQL Server 的批量 INSERT 策略“executemany”与 pyodbc,使用fast_executemany
/cursor.executemany()
用于不包含 RETURNING 的批量 INSERT,当此参数设置时,恢复了与 SQLAlchemy 1.4 中使用的相同行为。 最新的终端用户性能细节显示,对于非常大的数据集,fast_executemany
仍然比较快,因为它使用可以在单次往返中接收所有行的 ODBC 命令,允许比“insertmanyvalues”发送的批次更大得多的数据大小,后者已为 SQL Server 实现。 尽管此更改使得“insertmanyvalues”仍然被用于包含 RETURNING 的 INSERT,并且如果未设置fast_executemany
,由于#9603,在任何情况下,“insertmanyvalues” 策略已被完全禁用于 SQL Server。 参考:#9586
2.0.8
发布日期:2023 年 3 月 31 日
orm
- [orm] [usecase]
当使用
MappedAsDataclass
混合类或registry.mapped_as_dataclass()
装饰器时,Python 数据类引发的诸如TypeError
和ValueError
等异常现在将在一个InvalidRequestError
包装器中进行包装,其中包含有关错误消息的信息性上下文,参考 Python 数据类文档作为异常原因的官方来源。 参见 创建<类名>数据类时遇到的 Python 数据类错误 参考:#9563 - [orm] [bug] 修复了 ORM 注释声明中的问题,其中使用递归类型(例如使用嵌套的字典类型)会导致 ORM 的注释解析逻辑中发生递归溢出,即使这种数据类型不是必要的来映射列。 参考:#9553
- [orm] [bug]
修复了在 Declarative mixin 上使用
mapped_column()
构造时,如果包含mapped_column.deferred
参数会引发内部错误的问题。 参考:#9550 - [orm] [bug]
扩展了在声明式映射中存在普通
column()
对象时发出的警告,以包括任何未在适当属性类型内声明的任意 SQL 表达式,例如column_property()
、deferred()
等。这些属性在类字典中保持不变且未映射。由于这种表达式通常不是预期的内容,因此现在对所有这些否则被忽略的表达式发出警告,而不仅仅是column()
的情况。 参考:#9537 - [orm] [bug]
修复了在访问一个混合属性的表达式值时出现的回归问题,该属性位于一个未映射或尚未映射的类上(例如在
declared_attr()
方法中调用它),会引发内部错误,因为对父类映射器的内部获取将失败,并且对于此失败的指令被无意中在 2.0 中删除。 参考:#9519 - [orm] [bug]
在声明式 Mixins 上声明的字段,然后与使用
MappedAsDataclass
的类组合在一起,其中这些 Mixin 字段本身不是数据类的一部分,现在会发出弃用警告,因为这些字段将在将来的版本中被忽略,因为 Python 数据类的行为是忽略这些字段。类型检查器在 pep-681 下不会看到这些字段。 另请参阅 当将转换为数据类时,属性(s)源自不是数据类的超类。 - 关于背景的理由 使用 Mixins 和抽象超类 参考:#9350 - [orm] [bug]
修复了一个问题,其中
BindParameter.render_literal_execute()
方法在调用带有 ORM 注释的参数时会失败。在实践中,当使用一些类似于 Oracle 的使用“FETCH FIRST”的方言以及使用Select
构造的Select.limit()
的组合时,在一些 ORM 上下文中会观察到这种情况,包括如果该语句嵌入在关系 primaryjoin 表达式中时,SQL 编译失败。 参考:#9526 - [orm] [bug]
为了与为 #5984 和 #8862 所做的工作单元一致性保持一致,这两者都禁用了在
Session
进程中的“惰性=‘raise’”处理,这些处理并非由属性访问触发,Session.delete()
方法现在在遍历关系路径以处理“delete”和“delete-orphan”级联规则时,也将禁用“惰性=‘raise’”处理。以前,没有简单的方法可以通用地调用Session.delete()
在设置了“惰性=‘raise’”的对象上,以便只加载必要的关系。由于“惰性=‘raise’”主要用于捕获在属性访问时发出的 SQL 加载,因此Session.delete()
现在被制作成像其他Session
方法一样,包括Session.merge()
以及Session.flush()
以及 autoflush。 参考:#9549 - [orm] [bug]
修复了一个问题,其中仅注释的
Mapped
指令无法在声明性混合类中使用,而不会尝试让该属性对已经映射了该属性的超类的单个或联合继承子类产生影响,从而产生冲突的列错误和/或警告。 参考:#9564 - [orm] [bug] [typing]
适当地对
Insert.from_select.names
进行类型定义,以接受字符串列表或列或映射属性。 参考:#9514
示例
- [examples] [bug]
修复了“版本历史”示例中的问题,使用从
DeclarativeBase
派生的声明性基类会导致映射失败的问题。此外,修复了给定的测试套件,以便通过 Python unittest 运行示例的文档说明现在再次有效。
类型
- [typing] [bug]
修复了
deferred()
和query_expression()
在与 2.0 样式映射正确配合使用时的类型。 参考:#9536
postgresql
- [postgresql] [bug]
修复了 PostgreSQL 方言中的关键回归问题,例如 asyncpg 依赖于 SQL 中的显式转换,以便将数据类型正确传递给驱动程序,其中
String
数据类型将与要比较的确切列长度一起转换,导致在比较较小长度的VARCHAR
与较大长度的字符串时进行隐式截断,而不管使用的操作符是什么(例如 LIKE,MATCH 等)。 PostgreSQL 方言现在在呈现这些转换时省略VARCHAR
的长度。 参考:#9511
mysql
- [mysql] [bug]
修复了字符串数据类型(如
CHAR
、VARCHAR
、TEXT
),以及二进制BLOB
无法使用零长度明确生成的问题,这在 MySQL 中具有特殊含义。感谢 J. Nick Koston 提出的拉取请求。 参考:#9544
杂项
- [bug] [util]
在 OrderedSet 类中实现了缺失的
copy
和pop
方法。 参考:#9487
2.0.7
发布日期:2023 年 3 月 18 日
类型
- [typing] [bug]
修复了
composite()
不允许任意可调用对象作为复合类来源的类型问题。 参考:#9502
postgresql
- [postgresql] [usecase]
添加了新的 PostgreSQL 类型
CITEXT
。拉取请求由 Julian David Rath 提供。 参考:#9416 - [postgresql] [用例] 修改了基本 PostgreSQL 方言,以更好地与 SQLAlchemy 2.0 的第三方方言 sqlalchemy-redshift 进行集成。拉取请求由 matthewgdv 提供。 参考:#9442
2.0.6
发布日期:2023 年 3 月 13 日
orm
- [orm] [错误]
修复了“活动历史记录”功能对复合属性未完全实现的错误,这使得无法接收包含“旧”值的事件成为可能。这似乎也是旧的 SQLAlchemy 版本的情况,其中“active_history”将传播到基础基于列的属性,但是即使设置了 active_history=True 的复合(),监听复合属性本身的事件处理程序也不会收到被替换的“旧”值。
另外,修复了一个局限于 2.0 的回归,该回归禁止了对复合的 active_history 被分配到带有
attr.impl.active_history=True
的实现。 参考:#9460 - [orm] [错误]
修复了在为版本 2.0 重构代码时,涉及 Python 行的 pickling 在 cython 和纯 Python 实现之间发生的回归,这发生在对
Row
进行了带有类型信息的代码重构时。对于纯 Python 版本的Row
,一个特定的常量被转换为基于字符串的Enum
,而 cython 版本继续使用整数常量,导致反序列化失败。 参考:#9418
sql
- [sql] [错误] [回归] 修复了在 1.4 系列中发布的用于 lambda SQL API 的一层并发安全检查的修复引起的回归,该修复针对的是#8098,在补丁中包含了未能应用到主分支的额外修复。这些额外的修复已经应用。 参考:#9461
- [sql] [错误]
修复了在
select()
构造中,如果没有给定列而然后在 EXISTS 的上下文中使用,则无法呈现的回归,而是引发了内部异常。虽然一个空的“SELECT”通常不是有效的 SQL,但在 EXISTS 数据库中(例如 PostgreSQL)允许它,在任何情况下,该条件现在不再引发内部异常。 参考:#9440
打字
- [打字] [错误]
修复了
ColumnElement.cast()
中的类型问题,它不允许独立于ColumnElement
本身的类型引擎参数,而ColumnElement.cast()
的目的就是这样。 参考:#9451 - [typing] [bug] 修复问题以允许在 Mypy 1.1.1 下通过类型测试。
oracle
- [oracle] [bug]
修复了 Oracle “名称标准化”在反射
"PUBLIC"
模式下无法正确工作的反射错误,例如在 Python 端不能将 PUBLIC 名称指定为小写用于Table.schema
参数。使用大写的"PUBLIC"
将起作用,但会导致包括引号的 SQL 查询以及在大写"PUBLIC"
下索引表,这是不一致的。 参考:#9459
2.0.5.post1
发布日期:2023 年 3 月 5 日
orm
- [orm] [bug]
向内置映射集合类型添加构造函数参数,包括
KeyFuncDict
、attribute_keyed_dict()
、column_keyed_dict()
等,以便可以根据提供的数据即时构造这些字典类型;这进一步与诸如 Python 数据类.asdict()
等工具兼容,后者依赖于直接调用这些类作为普通字典类。 参考:#9418 - [orm] [bug] [regression]
由于 #8372 引起的多个退化已修复,涉及
attribute_mapped_collection()
(现在称为attribute_keyed_dict()
)。 首先,收集现在不再可用于具有不是普通映射属性的“键”属性;已修复了与描述符和/或关联代理属性相关的属性。 其次,如果事件或其他操作需要访问“key”以便从未加载的映射属性填充字典,那么这也会不适当地引发错误,而不是像 1.4 版本中那样尝试加载属性。这个问题也已经修复。 对于这两种情况,扩展了#8372的行为。#8372引入了一个错误,当作为映射字典键使用的派生键实际上未被赋值时会引发错误。在此更改中,仅在“.key”属性的有效值为None
时才发出警告,无法明确确定这个None
是否是有意的。None
将不再作为映射集合字典键的支持(因为它通常指的是 NULL,表示“未知”)。设置attribute_keyed_dict.ignore_unpopulated_attribute
现在也将导致忽略这样的None
键。 参考:#9424 - [orm] [bug]
确定了
sqlite
和mssql pyodbc
方言现在与 SQLAlchemy ORM 的“versioned rows”功能兼容,因为 SQLAlchemy 现在通过计算返回的行数来计算 RETURNING 语句的行数,而不是依赖于cursor.rowcount
。特别是,ORM 版本的行用例(在配置版本计数器文档中有描述)现在应该完全支持与 SQL Server pyodbc 方言一起使用。 - [orm] [bug]
添加了对
Mapper.polymorphic_load
参数的支持,该参数应用于继承层次结构中超过一级的每个映射器,允许通过单个语句为层次结构中的所有类加载列,这些列指示使用"selectin"
,而不是忽略那些中间类上的元素,尽管它们也指示它们将参与"selectin"
加载,但它们不是基本的 SELECT 语句的一部分。 参考:#9373 - [orm] [bug]
继续修复 #8853,允许
Mapped
名称完全合格,无论是否存在from __annotations__ import future
。此问题首次在 2.0.0b3 中修复,确认此情况通过测试套件工作,但是测试套件显然没有测试名称Mapped
完全不存在的行为;字符串解析已更新以确保 ORM 如何使用这些函数。 参考:#8853, #9335
orm 声明式
- [bug] [orm declarative]
修复了新
mapped_column.use_existing_column
功能无法工作的问题,如果两个同名列被映射到与列本身的显式名称不同的属性名下。现在,当使用此参数时,属性名称可以不同。 参考:#9332
引擎
- [engine] [performance]
对
Result
的 Cython 实现进行了小优化,使用了一个特定 int 值的 cdef 来避免 Python 开销。拉取请求由 Matus Valo 提供。 参考:#9343 - [engine] [bug]
修复了
Row
对象由于意外依赖不稳定的哈希值而无法在进程间可靠地反序列化的 bug。 参考:#9423
SQL
- [sql] [bug] [regression]
将
nullslast()
和nullsfirst()
旧版本函数恢复到sqlalchemy
导入命名空间中。之前,较新的nulls_last()
和nulls_first()
函数是可用的,但是旧版本函数不小心被移除了。 参考:#9390
模式
- [schema]
验证当提供给
MetaData
的MetaData.schema
参数时,它是一个字符串。
typing
- [typing] [usecase]
导出了由
scoped_session.query_property()
返回的类型,使用了一个新的公共类型QueryPropertyDescriptor
。 参考:#9338 - [typing] [bug]
修复了
Connection.scalars()
方法未被标记为允许多参数列表的错误,现在支持使用insertmanyvalues
操作。 - [typing] [bug]
对传递给
Insert.values()
和Update.values()
的映射的类型进行了改进,使之更加开放,指示只读Mapping
而不是可写Dict
,后者在键类型过于有限时会出错。 参考:#9376 - [typing] [bug]
在
Numeric
类型对象中添加了缺失的初始化重载,以便 pep-484 类型检查器可以正确解析完整的类型,从Numeric.asdecimal
参数派生,确定将表示Decimal
还是float
对象。 参考:#9391 - [typing] [bug]
修复了类型错误,
Select.from_statement()
将不接受text()
或TextualSelect
对象作为有效类型的 bug。此外,修复了columns
方法的返回类型缺失的问题。 参考:#9398 - [typing] [bug]
修复了
with_polymorphic()
未正确记录类类型的类型问题。 参考:#9340
postgresql
- [postgresql] [bug]
修复了在 PostgreSQL
ExcludeConstraint
中的问题,其中文字值被编译为绑定参数而不是直接的内联值,这是 DDL 所必需的。 参考:#9349 - [postgresql] [bug]
修复了 PostgreSQL
ExcludeConstraint
构造中的问题,如果约束包含文本表达式元素,则在Table.to_metadata()
等操作中以及在一些 Alembic 方案中无法复制。 参考:#9401
mysql
- [mysql] [bug] [postgresql]
为了解决在 2.0.0b1 中为 #5648 添加的池 ping 监听器通过
DialectEvents.handle_error()
事件接收异常事件的支持未考虑到诸如 MySQL 和 PostgreSQL 的特定方言的 ping 程序的问题。方言特性已重新设计,使得所有方言都参与事件处理。另外,添加了一个新的布尔元素ExceptionContext.is_pre_ping
,用于标识此操作是否在预 ping 操作中进行。 对于此版本,实现自定义Dialect.do_ping()
方法的第三方方言可以选择通过不再捕获异常或检查异常是否为“is_disconnect”,而是直接将所有异常传播出去来选择新的改进行为。现在由默认方言的一个包围方法来检查异常是否为“is_disconnect”,这确保了在测试异常是否为“断开连接”异常之前调用事件挂钩以处理所有异常情况。如果现有的do_ping()
方法继续捕获异常并检查“is_disconnect”,则它将像以前一样工作,但是如果不将异常传播出去,handle_error
钩子将无法访问异常。 参考:#5648
sqlite
- [sqlite] [bug] [regression]
修复了在 SQLite 连接中的回归,其中在建立数据库函数时使用
deterministic
参数会导致旧版 SQLite 版本(3.8.3 之前的版本)失败。版本检查逻辑已经改进以适应此情况。 参考:#9379
mssql
- [mssql] [bug]
修复了新的
Uuid
数据类型中的问题,该问题导致它无法与 pymssql 驱动程序一起工作。由于 pymssql 似乎又开始维护,因此恢复了对 pymssql 的测试支持。 参考:#9414 - [mssql] [bug] 调整了 pymssql 方言,以更好地利用 RETURNING 来获取 INSERT 语句的最后插入的主键值,与当前的 mssql pyodbc 方言一样。
杂项
- [bug] [ext]
修复了在 automap 中的问题,调用
AutomapBase.prepare()
时,从特定映射类而不是直接从AutomapBase
调用,当 automap 检测到新表时,不会使用正确的基类,而是使用给定的类,导致映射器尝试配置继承关系。虽然通常情况下应该从基类调用AutomapBase.prepare()
,但在从子类调用时不应该出现严重问题。 参考:#9367 - [bug] [ext] [regression]
由于针对 #8667 添加的类型,导致了
sqlalchemy.ext.mutable
的回归错误,其中.pop()
方法的语义发生了变化,使得该方法无法工作。感谢 Nils Philippsen 提交的拉取请求。 参考:#9380
2.0.4
发布日期:2023 年 2 月 17 日
orm
- [orm] [usecase]
为了适应 SQLAlchemy 2.0 中 ORM 声明式使用的列顺序的变化,新增了一个参数
mapped_column.sort_order
,可用于控制 ORM 定义的表中列的顺序,适用于常见用例,如具有应首先出现在表中的主键列的混合类。变更说明在 ORM 声明式以不同方式应用列顺序;使用 sort_order 控制行为 中说明了默认的顺序变更行为(这是所有 SQLAlchemy 2.0 发行版的一部分),以及在使用混合类和多个类时使用mapped_column.sort_order
控制列顺序的用法(2.0.4 中新增)。 另请参阅 ORM 声明式以不同方式应用列顺序;使用 sort_order 控制行为 参考:#9297 - [orm] [usecase]
Session.refresh()
方法现在将立即加载在Session.refresh.attribute_names
集合中明确命名的与关系绑定的属性,即使它当前链接到“select”加载程序,通常是一个不会在刷新期间触发的“lazy”加载程序。 “懒加载器”策略现在将检测到操作明确是用户发起的Session.refresh()
操作,该操作明确命名了此属性,然后将调用“immediateload”策略实际发出 SQL 以加载属性。这对于某些 asyncio 情况特别有帮助,其中必须强制加载未加载的惰性加载属性,而不使用实际不支持 asyncio 的惰性加载属性模式。 参考:#9298 - [orm] [bug] [regression]
由于#9217引入的版本 2.0.2 中的回归错误已修复,其中使用 DML RETURNING 语句以及
Select.from_statement()
构造,如在#9217中“修复”的那样,与使用column_property()
等表达式的 ORM 映射类一起使用,会导致 Core 内部错误,其中它会尝试按名称匹配表达式。修复了 Core 问题,并且还调整了#9217中的修复,以便不会对 DML RETURNING 用例产生影响,其中它增加了不必要的开销。 参考:#9273 - [orm] [bug]
将内部
EvaluatorCompiler
模块标记为 ORM 私有,并将其重命名为_EvaluatorCompiler
。对于可能依赖于此的用户,名称EvaluatorCompiler
仍然存在,但不支持此用法,并将在将来的版本中删除。
orm declarative
- [usecase] [orm declarative]
向
MappedAsDataclass
类和registry.mapped_as_dataclass()
方法添加了新参数dataclasses_callable
,允许使用替代的可调用对象来生成 Pythondataclasses.dataclass
。这里的用例是替换为 Pydantic 的 dataclass 函数。对版本 2.0.1 中为#9179添加的 mixin 支持进行了调整,以便将 mixin 的__annotations__
集合重写,不包括Mapped
容器,与映射类一样,以便 Pydantic dataclasses 构造函数不会暴露给未知类型。 另请参阅 与 Pydantic 等替代 Dataclass 提供者集成 参考:#9266
sql
- [sql] [bug]
修复了元组值的元素类型将被硬编码为从比较的元组中获取类型的问题,当比较使用
ColumnOperators.in_()
运算符时。这与通常确定二进制表达式类型的方式不一致,通常情况下会首先考虑右侧的实际元素类型,然后再应用左侧的类型。 参考:#9313 - [sql]
添加了公共属性
Table.autoincrement_column
,该属性返回在列中标识为自增的列。 参考:#9277
typing
- [typing] [usecase]
改进了 Hybrid Attributes 扩展的类型支持,更新了所有文档以使用 ORM Annotated Declarative mappings,并添加了一个名为
hybrid_property.inplace
的新修改器。此修改器提供了一种改变hybrid_property
的状态的方式,这在 SQLAlchemy 版本 1.2.0 之前的非常早期版本的混合属性中基本上是做的,版本 1.2.0 #3912 改变了这一点,删除了原地突变。现在,在选择加入的基础上恢复了这种原地突变,以允许单个混合具有多个设置的方法,无需命名所有方法相同,也无需仔细“链”不同命名的方法以维护组合。类型工具如 Mypy 和 Pyright 不允许在类上使用同名方法,因此通过此更改恢复了一种简洁的设置混合与类型支持的方法。 另请参阅 使用 inplace 创建符合 pep-484 标准的混合属性 参考:#9321
oracle
- [oracle] [bug]
调整了
thick_mode
参数的行为,以使 python-oracledb 方言正确接受False
作为值。以前,只有None
会表示应禁用 thick mode。 参考:#9295
2.0.3
发布日期:2023 年 2 月 9 日
sql
- [sql] [bug] [regression] 由于 #7744,在 2.0 系列中修复了 SQL 表达式制定的严重回归,改进了对包含许多相同操作符的 SQL 表达式的支持;表达式元素超过前两个元素后,括号分组将丢失。 参考:#9271
typing
- [typing] [bug]
删除了
typing.Self
的临时解决方案,现在使用了 PEP 673 来处理大多数返回Self
的方法。由于这个变化,现在需要mypy>=1.0.0
来对 SQLAlchemy 代码进行类型检查。感谢 Yurii Karabas 提供的拉取请求。 参考:#9254
2.0.2
发布日期:2023 年 2 月 6 日
orm
- [orm] [usecase]
添加了新的事件钩子
MapperEvents.after_mapper_constructed()
,提供了一个事件钩子,可以在Mapper
对象完全构建完成后但在调用registry.configure()
之前发生。这允许根据Mapper
的初始配置创建额外映射和表结构的代码,也与声明性配置集成。以前,在使用声明性时,Mapper
对象是在类创建过程中创建的,此时没有记录的方法来运行代码。这个改变立即使得自定义映射方案受益,比如带有历史表的版本控制示例,该示例根据映射类的创建生成额外的映射和表。 参考:#9220 - [orm] [用例]
很少使用的
Mapper.iterate_properties
属性和Mapper.get_property()
方法,主要用于内部,不再隐式调用registry.configure()
过程。对这些方法的公开访问非常罕见,而拥有registry.configure()
的唯一好处是允许这些集合中存在“backref”属性。为了支持新的MapperEvents.after_mapper_constructed()
事件,现在可以迭代和访问内部的MapperProperty
对象,而不会触发映射器本身的隐式配置。 更公开的迭代所有映射属性的方式,Mapper.attrs
集合等,仍会隐式调用registry.configure()
步骤,从而使得反向引用属性可用。 在所有情况下,registry.configure()
始终可供直接调用。 参考:#9220 - [ORM] [错误] [回归]
修复了由#8705引起的晦涩的 ORM 继承问题,其中一些从本地表和继承表一起指示列组的映射器的情况在
column_property()
下仍然会警告,即使隐式地组合了同名属性。 参考:#9232 - [ORM] [错误] [回归]
修复了在使用具有常规 Python 端递增列的
Mapper.version_id_col
功能时,对于不支持“rowcount”和“RETURNING”的 SQLite 和其他数据库,将“RETURNING”用于这些列,即使实际上并非如此。 参考:#9228 - [ORM] [错误] [回归]
修复了在 ORM 上下文中使用
Select.from_statement()
时的回归,其中仅基于名称匹配列到 SQL 标签的 ORM 语句被禁用,这将阻止具有列名标签的任意 SQL 表达式与要加载的实体匹配,以前在 1.4 和之前的系列中可以工作,因此已恢复了先前的行为。 参考:#9217
ORM 声明式
- [错误] [ORM 声明式]
修复了由于修复#9171引起的回归,该问题本身修复了涉及从
DeclarativeBase
继承的类的__init__()
机制的回归。更改使得如果类上没有直接的__init__()
方法,则__init__()
将应用于用户定义的基类。现在已经调整为只有在用户定义的基类的层次结构中没有其他类具有__init__()
方法时才应用__init__()
。这再次允许基于DeclarativeBase
的用户定义的基类包含包含自定义__init__()
方法的混入。 参考:#9249 - [错误] [ORM 声明式]
修复了与 2.0.1 中新增的对混合类支持相关的 ORM 声明式数据类映射中的问题,该问题通过#9179解决,其中在某些情况下使用混合类加上 ORM 继承会导致字段错误分类,导致字段级数据类参数(如
init=False
)丢失。 参考:#9226 - [错误] [ORM 声明式]
修复了 ORM 声明式映射,允许在使用
mapped_column()
时在__mapper_args__
中指定Mapper.primary_key
参数。尽管这种用法直接在 2.0 文档中,但Mapper
在这种情况下不接受mapped_column()
构造。这个功能已经适用于Mapper.version_id_col
和Mapper.polymorphic_on
参数。 作为这一变化的一部分,可以在非映射混合类上指定__mapper_args__
属性,而无需使用declared_attr()
,包括引用本地存在于混合类上的Column
或mapped_column()
对象的"primary_key"
条目;声明式还将这些列转换为特定映射类的正确列。这在Mapper.version_id_col
和Mapper.polymorphic_on
参数中已经起���用。此外,"primary_key"
中的元素可以指示为现有映射属性的字符串名称。 参考:#9240 - [错误] [ORM 声明式]
如果映射尝试在同一类层次结构中混合使用
MappedAsDataclass
和registry.mapped_as_dataclass()
,则会引发明确的错误,因为这会导致数据类函数在错误的时间应用于映射类,从而在映射过程中导致错误。 参考:#9211
例子
- [examples] [bug]
重新设计了带有历史表的版本控制,以适用于版本 2.0,同时改进了此示例的整体工作,以使用更新的 API,包括新添加的钩子
MapperEvents.after_mapper_constructed()
。 参考:#9220
SQL
- [sql] [usecase] 添加了一套全新的 SQL 位运算符,用于在适当的数据值(如整数、位字符串等)上执行数据库端的位运算表达式。 拉取请求由 Yegor Statkevich 提供。 另请参阅 位运算符 参考:#8780
asyncio
- [asyncio] [bug]
修复了由于修复#8419而引起的回归,这导致了 asyncpg 连接被重置(即事务
rollback()
被调用),并且在连接未被显式返回到连接池并且被 Python 垃圾收集拦截时,正常返回到池中,如果垃圾收集操作在 asyncio 事件循环外被调用,则会失败,导致大量堆栈跟踪活动被转储到日志和标准输出中。 恢复了正确的行为,即所有由于未被显式返回到连接池而被垃圾收集的 asyncio 连接都会从池中分离并且被丢弃,同时伴随着一条警告,而不是被返回到池中,因为它们无法可靠地重置。在 asyncpg 连接的情况下,将使用 asyncpg 特定的terminate()
方法来更优雅地结束该连接,而不仅仅是将其丢弃。 此更改包括了一个小的行为变更,希望对调试 asyncio 应用程序有用,其中在 asyncio 连接意外被垃圾收集时发出的警告已经通过将其移出try/except
块并移到finally:
块中而变得稍微更加激进,无论分离/终止操作是否成功,它都会无条件地发出。这也将使得将 Python 警告提升为异常的应用程序或测试套件会将此视为完整的异常抛出,而以前这个警告是不可能作为异常传播的。在此期间需要容忍此警告的应用程序和测试套件应该调整 Python 警告过滤器,以允许这些警告不会被提升为异常。 传统同步连接的行为保持不变,即垃圾收集的连接继续正常返回到池中,而不会发出警告。在未来的主要发布版本中,这可能会发生变化,至少会像为 asyncio 驱动程序发出的类似警告一样发出警告,因为对于池化连接被垃圾收集拦截而未被正确返回到池中是一种使用错误。 参考:#9237
mysql
- [mysql] [bug] [回归]
修复了由问题#9058引起的回归,调整了 MySQL 方言的
has_table()
,再次使用“DESCRIBE”,当 MySQL 版本 8 在使用不存在的模式名称时引发的特定错误代码是意外的,并且无法解释为布尔结果。 参考:#9251 - [mysql] [bug]
添加了对 MySQL 8 的新
AS <name> ON DUPLICATE KEY
语法的支持,当使用Insert.on_duplicate_key_update()
时,这对于 MySQL 8 的较新版本是必需的,因为先前使用VALUES()
的语法现在在这些版本中会发出弃用警告。服务器版本检测被用来确定是否应该使用传统的 MariaDB / MySQL < 8VALUES()
语法,还是新的 MySQL 8 所需的语法。感谢 Caspar Wylie 的拉取请求。 参考:#8626
sqlite
- [sqlite] [bug]
修复了 SQLite 方言的
has_table()
函数,以便对于包含不存在的模式的非 None 模式名称的查询,正确地报告 False;以前,会引发数据库错误。 参考:#9251
2.0.1
发布日期:2023 年 2 月 1 日
orm
- [orm] [bug] [回归] 修复了使用具有复合外键的连接表继承的 ORM 模型会在映射器内部遇到内部错误的回归。 参考:#9164
- [orm] [bug]
当将基类的链接策略选项链接到子类的另一个属性时,错误报告得到改进,应该使用
of_type()
。以前,当使用Load.options()
时,消息缺乏of_type()
应该使用的信息详细信息,而在直接链接选项时不是这样。即使使用Load.options()
,信息详细信息现在也会发出。 参考:#9182
orm 声明
- [bug] [orm 声明]
添加了对 PEP 484
NewType
的支持,可以在registry.type_annotation_map
中使用,以及在Mapped
构造中使用。这些类型将与当前的自定义类型子类相同;它们必须显式出现在registry.type_annotation_map
中进行映射。 参考资料:#9175 - [bug] [orm declarative]
在使用
MappedAsDataclass
超类时,层次结构中的所有类(不管它们是否实际上已映射)都将通过@dataclasses.dataclass
函数运行,因此在映射的子类被转换为数据类时,层次结构中声明的非 ORM 字段将被使用。该行为既适用于使用__abstract__ = True
映射的中介类,也适用于用户定义的声明基类本身,假设MappedAsDataclass
作为这些类的超类存在。 这允许像InitVar
声明这样的非映射属性在超类上使用,而无需在每个非映射类上显式运行@dataclasses.dataclass
装饰器。新行为被认为是正确的,因为这是当使用超类来指示数据类行为时 PEP 681 实现所期望的。 参考资料:#9179 - [bug] [orm declarative]
添加了对 PEP 586
Literal[]
的支持,可以在registry.type_annotation_map
中使用,以及在Mapped
构造中使用。要使用这样的自定义类型,它们必须显式出现在registry.type_annotation_map
中进行映射。感谢 Frederik Aalund 提交的拉取请求。 作为此更改的一部分,将Enum
在registry.type_annotation_map
中的支持扩展为还包括Literal[]
类型,该类型由字符串值组成,除了enum.Enum
数据类型之外。如果在Mapped[]
中使用了一个未在registry.type_annotation_map
中链接到特定数据类型的Literal[]
数据类型,那么默认将使用一个Enum
。 另请参阅 在类型映射中使用 Python Enum 或 pep-586 Literal 类型 参考:#9187 - [bug] [orm declarative]
在
registry.type_annotation_map
中使用Enum
时,修复了一个问题,即如果根据文档将Enum.native_enum
参数重写为 False,则该参数将不会正确地复制到映射的列数据类型中。 参考:#9200 - [bug] [orm declarative] [regression]
在
DeclarativeBase
类中修复了一个回归,其中注册表的默认构造函数不会应用于基类本身,这与以前的declarative_base()
构造方式不同。这会阻止具有自己的__init__()
方法的映射类调用super().__init__()
以访问注册表的默认构造函数并自动填充属性,而是会命中object.__init__()
,这会导致在任何参数上引发TypeError
。 参考:#9171 - [bug] [orm declarative]
改进了在使用 Annotated Declarative mapping 时解释 PEP 593
Annotated
类型的规则集,内部类型将始终检查“Optional”,并将其添加到确定列是否为“nullable”的条件中;如果Annotated
容器中的类型是可选的(或与None
联合),则如果没有显式的mapped_column.nullable
参数覆盖它,将考虑该列为可空。 参考:#9177
sql
- [sql] [bug]
修正了版本 2.0.0 中发布的对#7664的修复,还包括了
DropSchema
,这在修复中被无意中忽略,允许在没有方言的情况下进行字符串化。这两个构造的修复已经回溯到 1.4.47 版本的 1.4 系列。 参考:#7664 - [sql] [bug] [regression]
修复了与新“insertmanyvalues”功能实现相关的回归,其中在 CTE 中引用另一个
insert()
时会出现内部TypeError
的情况;为此情况进行了额外的修复,适用于像 asyncpg 这样的位置方言在使用“insertmanyvalues”时。 参考:#9173
typing
- [typing] [bug]
打开了对
Select.with_for_update.of
的类型,也接受表和映射类参数,似乎适用于 MySQL 方言。 参考:#9174 - [typing] [bug]
修复了限制/偏移方法的类型,包括
Select.limit()
、Select.offset()
、Query.limit()
、Query.offset()
,允许None
,这是“取消”当前限制/偏移的文档化 API。 参考:#9183 - [typing] [bug]
修复了
mapped_column()
对象被类型化为Mapped
时不会被接受在模式约束中,如ForeignKey
、UniqueConstraint
或Index
。 参考:#9170 - [typing] [bug]
修复了对
ColumnElement.cast()
的类型检查,以接受Type[TypeEngine[T]]
和TypeEngine[T]
;先前只接受TypeEngine[T]
。拉取请求由 Yurii Karabas 提供。 参考资料:#9156
2.0.0
发布日期:2023 年 1 月 26 日
ORM
- [ORM] [错误] 改进了在配置映射器或刷新过程中发出的警告的通知,这些警告通常作为不同操作的一部分调用,以在可能不明显相关的操作中添加附加上下文到警告的消息,指示其中一个这些操作作为警告源在操作中的消息内。 参考资料:#7305
ORM 扩展
- [功能] [ORM 扩展]
向水平分片 API
set_shard_id
添加了新选项,该选项设置了要针对其进行查询的有效分片标识符,包括主查询以及所有次要加载程序,包括关系急加载程序以及关系和列延迟加载程序。 参考资料:#7226 - [用例] [ORM 扩展]
为
AutomapBase
添加了新功能,用于跨多个模式自动加载类,这些类可能具有重叠的名称,方法是提供一个AutomapBase.prepare.modulename_for_table
参数,允许自定义新生成的类的__module__
属性,以及一个新集合AutomapBase.by_module
,它存储了基于__module__
属性的类的点分隔的模块名称空间。 此外,现在可以任意次调用AutomapBase.prepare()
方法,无论是否启用了反射;在每次调用时,只会处理之前未映射的新添加的表。先前,需要显式调用MetaData.reflect()
方法。 另请参阅 从多个模式生成映射 - 同时演示两种技术的使用。 参考资料:#5145
SQL
- [SQL] [错误]
修复了
CreateSchema
DDL 构造的字符串化问题,当没有方言时,会导致AttributeError
。更新:请注意,此修复未考虑到DropSchema
;版本 2.0.1 中的后续修复解决了这个问题。这两个元素的修复已经回溯到 1.4.47。 参考:#7664
输入
- [输入] [错误]
为从
func
命名空间中可用的内置通用函数添加了类型,这些函数接受一组特定的参数并返回特定的类型,例如count
,current_timestamp
等。 参考:#9129 - [输入] [错误]
修正了“lambda 语句”传递的类型,以便 mypy、pyright 等可以接受普通 lambda 而不会出现关于参数类型的任何错误。此外,为更多的 lambda 语句公共 API 实现了类型,并确保
StatementLambdaElement
是Executable
层次结构的一部分,因此它被类型化为被Connection.execute()
接受。 参考:#9120 - [输入] [错误]
ColumnOperators.in_()
和ColumnOperators.not_in()
方法的类型现在包括Iterable[Any]
,而不是Sequence[Any]
,以提供更灵活的参数类型。 参考:#9122 - [输入] [错误]
从类型的角度来看,
or_()
和and_()
需要第一个参数存在,但这些函数仍然接受零个参数,这将在运行时发出弃用警告。还添加了类型支持,以支持将固定字面量False
用于or_()
和True
用于and_()
作为唯一的第一个参数,但文档现在指示在这些情况下发送false()
和true()
构造作为更明确的方法。 参考:#9123 - [打字] [错误]
修复了在对
Query
对象进行迭代时类型不正确的问题。 参考:#9125 - [打字] [错误]
修复了在使用
Result
作为上下文管理器时对象类型未被保留的问题,始终指示所有情况下的Result
而不是特定的Result
子类型。感谢 Martin Baláž 的拉取请求。 参考:#9136 - [打字] [错误]
修复了使用
relationship.remote_side
和类似参数时的问题,传递作为Mapped
类型的注释声明对象将不被类型检查器接受。 参考:#9150 - [打字] [错误]
为诸如
isnot()
、notin_()
等旧操作符添加了类型,这些操作符以前引用了更新的操作符,但它们本身没有被类型化。 参考:#9148
postgresql
- [postgresql] [错误]
添加了对 asyncpg 方言的支持,以在可用时返回
cursor.rowcount
值用于 SELECT 语句。虽然这不是cursor.rowcount
的典型用法,但其他 PostgreSQL 方言通常提供此值。感谢 Michael Gorven 的拉取请求。 此更改也回溯到:1.4.47 参考:#9048
mysql
- [mysql] [用例]
添加了对 MySQL 索引反射的支持,以正确反映先前被忽略的
mysql_length
字典。 此更改也回溯到:1.4.47 参考:#9047
mssql
- [mssql] [bug] [regression]
MSSQL 方言的新添加的注释反射和渲染功能,添加于#7844,如果无法确定是否使用不受支持的后端(如 Azure Synapse),则现在将默认禁用;这个后端不支持表和列注释,也不支持用于生成它们以及反映它们的 SQL Server 例程。方言添加了一个新参数
supports_comments
,默认值为None
,表示应自动检测注释支持。当设置为True
或False
时,注释支持将被无条件启用或禁用。 另请参阅 DDL 注释支持 参考:#9142
2.0.0rc3
发布日期:2023 年 1 月 18 日
orm
- [orm] [feature]
向
Mapper
添加了一个名为Mapper.polymorphic_abstract
的新参数。该指令的目的是让 ORM 不考虑该类被直接实例化或加载,只考虑子类。实际效果是,Mapper
将阻止直接实例化该类的实例,并期望该类没有配置独特的多态标识。 在实践中,使用Mapper.polymorphic_abstract
映射的类可以作为relationship()
的目标,也可以在查询中使用;当然,子类必须在映射中包含多态标识。 新参数会自动应用于继承AbstractConcreteBase
类的类,因为这个类不打算被实例化。 另请参阅 使用多态抽象构建更深层次的层次结构 参考:#9060 - [orm] [bug]
修复了在
registry.type_annotation_map
中使用 pep-593Annotated
类型,其本身包含一个通用的普通容器或collections.abc
类型(例如list
,dict
,collections.abc.Sequence
等)作为目标类型时会在 ORM 尝试解释Annotated
实例时产生内部错误的问题。 参考:#9099 - [orm] [bug]
当
relationship()
映射到抽象容器类型(例如Mapped[Sequence[B]]
)时未提供relationship.container_class
参数时,添加了一个错误消息,此参数在类型为抽象时是必需的。以前,抽象容器会在稍后的步骤中尝试实例化并失败。 参考:#9100
sql
- [sql] [bug]
修复了使用与
Update.values()
方法中的列相同名称的bindparam()
,以及在 2.0 中的Insert.values()
方法中,如果在构造的语句中使用相同名称的参数,则在某些情况下会静默失败,替换为同名的新参数,并丢弃 SQL 表达式的其他元素,例如 SQL 函数等。特定情况将是针对 ORM 实体而不是普通Table
实例构造的语句,但如果使用Session
或Connection
调用语句,则会发生。Update
部分的问题既存在于 2.0 中也存在于 1.4 中,并被回溯到 1.4。 此更改还被回溯到:1.4.47 参考:#9075
typing
- [typing] [bug]
修复了在
sqlalchemy.ext.hybrid
扩展中注释的问题,以更有效地对用户定义的方法进行类型化。现在,typing 使用PEP 612功能,最近的 Mypy 版本也支持,以维护hybrid_method
的参数签名。 混合方法的返回值在Select.where()
等上下文中被接受为 SQL 表达式,同时仍支持 SQL 方法。 参考:#9096
mypy
- [mypy] [bug] 调整了 mypy 插件,以适应 SQLAlchemy 1.4 时可能进行的一些更改,这些更改是针对问题#236 sqlalchemy2-stubs 而进行的。这些更改与 SQLAlchemy 2.0 保持同步。这些更改也向后兼容旧版本的 sqlalchemy2-stubs。 此更改还回溯到:1.4.47
- [mypy] [bug]
修复了 mypy 插件中的崩溃,在 1.4 和 2.0 版本中均可能发生,如果装饰器用于与具有两个以上组件的表达式(例如
@Backend.mapper_registry.mapped
)中引用,则会发生。 现在,此场景被忽略; 使用插件时,装饰器表达式需要是两个组件(即@reg.mapped
)。 此更改还回溯到:1.4.47 参考:#9102
postgresql
- [postgresql] [bug] 修复了 psycopg3 版本 3.1.8 更改了 API 调用的回归,以期望先前未强制执行的特定对象类型,从而破坏了 psycopg3 方言的连接性。 参考:#9106
oracle
- [oracle] [usecase]
添加了对 Oracle SQL 类型
TIMESTAMP WITH LOCAL TIME ZONE
的支持,使用新添加的 Oracle 特定的TIMESTAMP
数据类型。 参考:#9086
2.0.0rc2
Released: January 9, 2023
orm
- [orm] [bug]
修复了在 2.0 中添加的过于严格的 ORM 映射规则,该规则阻止了对
TableClause
对象的映射,例如在 wiki 上使用的视图配方中使用的那些。 参考:#9071
typing
- [typing] [bug]
数据类转换参数
field_descriptors
在 PEP 681 的已接受版本中更名为field_specifiers
。 参考:#9067
postgresql
- [postgresql] [json]
Implemented missing
JSONB
operations:-
@@
使用Comparator.path_match()
-
@?
使用Comparator.path_exists()
-
#-
使用Comparator.delete_path()
感谢 Guilherme Martins Crocetti 提供的拉取请求。 参考文献:#7147
-
mysql
- [mysql] [bug]
恢复了
Inspector.has_table()
的行为,以报告 MySQL / MariaDB 的临时表。这是所有其他包含的方言当前的行为,但是在 1.4 中由于不再使用 DESCRIBE 命令而删除了 MySQL 的该行为;在此版本或任何以前的版本上都没有记录支持通过Inspector.has_table()
方法报告临时表的文件,因此以前的行为未定义。 由于 SQLAlchemy 2.0 已经为临时表状态添加了正式支持通过Inspector.has_table()
,因此 MySQL / MariaDB 方言已恢复为使用“DESCRIBE”语句,就像 SQLAlchemy 1.3 系列和以前一样,并且添加了测试支持以包含 MySQL / MariaDB 的此行为。由于 SQLAlchemy 2.0 中Connection
如何处理事务的简化,1.4 试图改进的 ROLLBACK 引发的先前问题不适用。 DESCRIBE 是必需的,因为 MariaDB 特别是没有任何一致可用的公共信息模式以报告临时表,除了依赖于抛出错误以报告无结果的 DESCRIBE/SHOW COLUMNS。 参考文献:#9058
oracle
- [oracle] [bug]
支持外键约束的用例,其中本地列标记为“不可见”。当反射创建检查目标列的
ForeignKeyConstraint
时,通常生成的错误被禁用,并且与已存在的具有类似问题的Index
一样,跳过该约束并发出警告。 参考:#9059
2.0.0rc1
发布日期:2022 年 12 月 28 日
通用
- [通用] [错误]
修复了基础兼容模块调用
platform.architecture()
以检测某些系统属性的回归错误,结果是对系统级别的file
调用进行了过于广泛的系统调用,在某些情况下不可用,包括某些安全环境配置中。 此更改也已被回溯到:1.4.46 参考:#8995
ORM
- [orm] [功能]
添加了一个新的默认值为
Mapper.eager_defaults
参数“auto”的值,这将在工作单元刷新期间自动获取表默认值,如果方言支持 INSERT 的 RETURNING,以及可用的 insertmanyvalues。对于服务器端 UPDATE 默认值的及时获取,这是非常罕见的,只有当Mapper.eager_defaults
设置为True
时才会发生,因为对于 UPDATE 语句没有批量 RETURNING 形式。 参考:#8889 - [orm] [用例]
关于
Session
的可扩展性调整,以及ShardedSession
扩展的更新:-
Session.get()
现在接受Session.get.bind_arguments
,特别是在使用水平分片扩展时可能会有用。 -
Session.get_bind()
接受任意关键字参数,这有助于开发使用覆盖此方法的Session
类的代码,该方法具有附加参数。 - 添加了一个新的 ORM 执行选项
identity_token
,它可用于直接影响与新加载的 ORM 对象关联的“身份令牌”。这个令牌是分片方法(主要是ShardedSession
,但也可以在其他情况下使用)在不同“分片”之间分离对象标识的方式。 另见 身份令牌 -
SessionEvents.do_orm_execute()
事件钩子现在可以用于影响所有与 ORM 相关的选项,包括autoflush
、populate_existing
和yield_per
;这些选项在事件钩子被调用后重新消耗,然后才被执行。以前,像autoflush
这样的选项在这一点上已经被评估过了。新的identity_token
选项也在这种模式下受支持,并且现在被水平分片扩展使用。 -
ShardedSession
类用新的钩子ShardedSession.identity_chooser
替换了ShardedSession.id_chooser
钩子,不再依赖于传统的Query
对象。在替代ShardedSession.identity_chooser
时,会发出弃用警告,仍然接受ShardedSession.id_chooser
。
参考:#7837
-
- [orm] [usecase]
“将外部事务加入到会话中”的行为已经进行了修订和改进,允许显式控制
Session
如何适应已经建立事务和可能已经建立保存点的传入Connection
。新参数Session.join_transaction_mode
包括一系列选项值,可以以多种方式适应现有事务,最重要的是允许Session
以完全事务方式操作,仅使用保存点,同时在任何情况下保持外部启动的事务未提交且活动,允许测试套件回滚测试中发生的所有更改。 此外,对Session.close()
方法进行了修订,以完全关闭可能仍存在的保存点,这也允许“外部事务”配方在Session
未明确结束其自身 SAVEPOINT 事务时继续进行而不产生警告。 另请参阅 会话的新事务加入模式 参考:#9015 - [orm] [usecase]
移除了在检测到非
Mapped[]
注释时必须使用__allow_unmapped__
属性的要求;以前,如果检测到旨在支持遗留 ORM 类型映射的错误消息将被引发,此外还未提及与 Dataclasses 特别相关的正确模式。如果使用了registry.mapped_as_dataclass()
或MappedAsDataclass
,则不再引发此错误消息。 另请参阅 使用非映射数据类字段 参考:#8973 - [orm] [bug]
修复了内部 SQL 遍历中的问题,例如对
Update
和Delete
等 DML 语句,这将导致除其他潜在问题之外,使用 ORM 更新/删除功能的 lambda 语句的特定问题。 此更改也被回溯到:1.4.46 参考:#9033 - [orm] [bug]
修复了一个 bug,即
Session.merge()
无法保留使用relationship.viewonly
参数指示的关系属性的当前加载内容,从而破坏了使用Session.merge()
从缓存和其他类似技术中拉取完全加载的对象的策略。在相关更改中,修复了一个问题,即包含已配置为在映射上lazy='raise'
的已加载关系的对象在传递给Session.merge()
时会失败;假设Session.merge.load
参数保持其默认值True
,则合并过程中的“raise”检查现在被暂停了。 总体而言,这是对 1.4 系列中引入的更改的行为调整,截至#4994,该更改将“merge”从“viewonly”关系的默认级联集中移除。由于“viewonly”关系在任何情况下都不会被持久化,因此在“merge”期间允许其内容传输不会影响目标对象的持久化行为。这使得Session.merge()
能够正确地适用于其用例之一,即将在其他地方加载的对象添加到Session
中,通常是为了从缓存中恢复。 此更改也被回溯到:1.4.45 参考:#8862 - [orm] [bug]
修复了
with_expression()
中的问题,在某些情况下,由于表达式由从外部 SELECT 中引用的列组成,因此不会正确地在某些上下文中呈现 SQL,在表达式具有与使用query_expression()
的属性匹配的标签名称的情况下,即使query_expression()
没有默认表达式。暂时,如果query_expression()
确实具有默认表达式,则仍将使用该标签名称作为该默认表达式,并且将继续忽略具有相同名称的其他标签。总体而言,这种情况相当棘手,因此可能需要进一步调整。 此更改还回溯到:1.4.45 参考:#8881 - [orm] [bug]
如果在
relationship()
中使用的反向引用名称在目标类上命名了已经有方法或属性分配给该名称的属性,则会发出警告,因为反向引用声明将替换该属性。 参考:#4629 - [orm] [bug]
一系列关于
Session.refresh()
的变更和改进。总体变更是,当要刷新与关系绑定的属性时,对象的主键属性现在无条件地包含在刷新操作中,即使未过期,即使未在刷新中指定。- 改进了
Session.refresh()
,以便如果启用了自动刷新(如Session
的默认值),则自动刷新将在刷新过程的较早部分发生,以便应用待处理的主键更改而不会引发错误。以前,此自动刷新发生得太晚,并且 SELECT 语句不会使用正确的键来定位行,并且会引发InvalidRequestError
。 - 当存在上述条件时,即对象上存在未刷新的主键更改,但未启用自动刷新时,refresh()方法现在明确禁止操作继续进行,并引发一个信息性的
InvalidRequestError
,要求首先刷新待处理的主键更改。以前,这种用例简单地被破坏,无论如何都会引发InvalidRequestError
。这个限制是为了安全起见,以便刷新主键属性,这对于能够刷新具有 relationship 绑定的次要急切加载器的对象是必要的。无论是否实际上需要刷新 PK 列,这个规则都适用于保持 API 行为一致,因为在任何情况下,刷新对象的某些属性而保留其他属性“待处理”是不寻常的。 -
Session.refresh()
方法已经得到增强,以便刷新那些在映射时或通过最近使用的加载器选项与relationship()
绑定并链接到急切加载器的属性,在所有情况下都会被刷新,即使传递了一个不包括父行上任何列的属性列表。这是在 1.4 中作为#1763的一部分首次实现的功能,允许急切加载的与 relationship 绑定的属性参与Session.refresh()
操作。如果刷新操作没有指示要刷新父行上的任何列,则主键列仍将包括在刷新操作中,这允许加载继续到正常情况下指示的次要关系加载器。以前,对于这种情况会引发一个InvalidRequestError
错误(#8703) - 修复了一个问题,即在
Session.refresh()
与一组过期属性以及像selectinload()
这样发出“secondary”查询的急加载器一起调用时,会发出不必要的额外 SELECT 的情况,如果主键属性也处于过期状态。由于主键属性现在自动包含在刷新中,因此当关系加载器开始为它们选择时,这些属性不会有额外的加载(#8997)。 - 修复了由 2.0.0b1 中的#8126引起的回归,其中
Session.refresh()
方法将在传递过期的列名以及链接到“secondary” eagerloader(如selectinload()
)的关系绑定属性的名称时失败,并引发AttributeError
(#8996)。
参考:#8703, #8996, #8997
- 改进了
- [orm] [bug]
改进了版本 1.4 中首次修复的问题,用于#8456,该问题减少了内部“多态适配器”的使用,用于在使用
Mapper.with_polymorphic
参数时渲染 ORM 查询。这些适配器非常复杂且容易出错,现在仅在使用用户提供的显式子查询用于Mapper.with_polymorphic
的情况下使用,其中包括仅使用polymorphic_union()
辅助程序的具体继承映射的用例,以及在不需要的现代用例中使用别名子查询的联合继承映射的传统用例。 对于使用内置多态加载方案的联合继承映射的最常见情况,其中包括使用Mapper.polymorphic_load
参数设置为inline
的情况,现在不再使用多态适配器。这对查询构造的性能有积极影响,同时也极大简化了内部查询渲染过程。 目标特定问题是允许column_property()
引用标量子查询中的联合继承类,现在其工作方式尽可能直观。 参考:#8168
engine
- [engine] [bug]
修复了连接池中的长期竞争条件,该条件可能在 eventlet/gevent monkeypatching 方案与使用 eventlet/gevent
Timeout
条件相结合时发生,其中由于超时而中断的连接池检出将无法清理失败的状态,导致底层连接记录以及有时是数据库连接本身“泄漏”,将池留在无效状态中,无法访问条目。这个问题首次在 SQLAlchemy 1.2 中被识别和修复,用于 #4225,然而在该修复中检测到的故障模式未能适应BaseException
,而不是Exception
,这导致无法捕获 eventlet/geventTimeout
。此外,在初始池连接中还确定了一个块,并通过BaseException
-> “清除失败的连接”块来加固,以适应在此位置的相同条件。非常感谢 Github 用户 @niklaus 在识别和描述这个复杂问题方面的顽强努力。 此更改也被回溯到:1.4.46 参考:#8974 - [engine] [bug]
修复了
Result.freeze()
方法在使用text()
或Connection.exec_driver_sql()
时无法工作的问题。 此更改也被回溯到:1.4.45 参考:#8963
sql
- [sql] [usecase] 在“字面绑定参数”渲染操作失败的情况下,现在会抛出一个信息性的重新引发,指示值本身和正在使用的数据类型,以帮助调试在语句中渲染字面参数时的情况。 此更改也被回溯到:1.4.45 参考:#8800
- [sql] [bug]
修复了 Lambda SQL 功能中的问题,其中字面值的计算类型不会考虑“与类型比较”的类型强制转换规则,导致 SQL 表达式(例如与
JSON
元素的比较等)缺乏类型信息。 此更改也被回溯到:1.4.46 参考:#9029 - [sql] [bug]
修复了一系列关于渲染绑定参数的位置以及有时身份的问题,例如用于 SQLite、asyncpg、MySQL、Oracle 等的参数。一些编译形式不会正确维护参数的顺序,例如 PostgreSQL
regexp_replace()
函数、首次在#4123中引入的CTE
构造的“嵌套”特性,以及使用 Oracle 的FunctionElement.column_valued()
方法形成的可选择表。 此更改也被回溯到:1.4.45 参考:#8827 - [sql] [bug]
添加了测试支持,以确保 SQLAlchemy 中所有
Compiler
实现中的所有编译器visit_xyz()
方法都接受**kw
参数,以便所有编译器在所有情况下都接受额外的关键字参数。 参考:#8988 - [sql] [bug]
SQLCompiler.construct_params()
方法以及SQLCompiler.params
访问器现在将返回与使用render_postcompile
参数编译的编译语句对应的确切参数。之前,该方法返回的参数结构本身既不对应原始参数也不对应扩展参数。 不再允许将新参数字典传递给使用render_postcompile
构造的SQLCompiler
的SQLCompiler.construct_params()
;相反,为了为另一组参数制作新的 SQL 字符串和参数集,添加了一个新方法SQLCompiler.construct_expanded_state()
,该方法将使用包含新的 SQL 语句和新的参数字典的ExpandedState
容器产生给定参数集的新扩展形式,以及一个位置参数元组。 参考:#6114 - [sql] [bug]
为了适应对绑定参数有不同字符转义需求的第三方方言,SQLAlchemy 中用于“转义”(即在其位置替换为另一个字符)绑定参数名称的系统已被扩展,使用
SQLCompiler.bindname_escape_chars
字典,可以在任何SQLCompiler
子类的类声明级别进行覆盖。作为此更改的一部分,还将点号"."
添加为默认的 “转义” 字符。 引用:#8994
typing
- [typing] [bug]
pep-484 typing 已完成对
sqlalchemy.ext.horizontal_shard
扩展以及sqlalchemy.orm.events
模块的类型标注。感谢 Gleb Kisenkov 的努力。 引用:#6810, #9025
asyncio
- [asyncio] [bug]
从
AsyncResult
中删除了不起作用的merge()
方法。这个方法从未起作用,是错误地包含在AsyncResult
中的。 此更改还 反向移植 至:1.4.45 引用:#8952
postgresql
- [postgresql] [bug]
修复了一个 PostgreSQL 的 bug,其中
Insert.on_conflict_do_update.constraint
参数会接受一个Index
对象,但是不会将此索引展开为其各个索引表达式,而是在 ON CONFLICT ON CONSTRAINT 子句中呈现其名称,这在 PostgreSQL 中不被接受;“约束名”形式仅接受唯一或排除约束名。该参数继续接受索引,但现在会将其展开为其组件表达式以进行呈现。 此更改还 反向移植 至:1.4.46 引用:#9023 - [postgresql] [bug]
对 PostgreSQL 方言在从表中反射列时考虑列类型的方式进行了调整,以适应可能从 PG 的
format_type()
函数返回 NULL 的替代后端。 此更改还 反向移植 至:1.4.45 引用:#8748 - [postgresql] [bug]
增加了对使用
asyncpg
和psycopg
(仅限于 SQLAlchemy 2.0)的 PG 全文函数的显式支持,关于第一个参数的REGCONFIG
类型转换,之前会错误地转换为 VARCHAR,导致这些方言上的失败,这些方言依赖于显式类型转换。这包括对to_tsvector
,to_tsquery
,plainto_tsquery
,phraseto_tsquery
,websearch_to_tsquery
,ts_headline
的支持,每个函数根据传递的参数数量来确定第一个字符串参数是否应解释为 PostgreSQL 的REGCONFIG
值;如果是,则使用新添加的类型对象REGCONFIG
进行类型转换,然后在 SQL 表达式中显式地转换。 参考:#8977 - [postgresql] [错误]
修复了新修订的 PostgreSQL 范围类型(例如
INT4RANGE
自定义类型的实现,而是引发TypeError
的回归问题。 参考:#9020 - [postgresql] [错误]
当与不同类的实例进行比较时,
Range.__eq___()
现在会返回NotImplemented
,而不是引发AttributeError
异常。 参考:#8984
sqlite
- [sqlite] [用例] 为 SQLite 后端增加了反映可能存在于外键结构上的“DEFERRABLE”和“INITIALLY”关键字的支持。感谢 Michael Gorven 提交的拉取请求。 这个变化也被回溯到:1.4.45 参考:#8903
- [sqlite] [用例] 增加了对 SQLite 方言中索引中包含的表达式导向的 WHERE 条件的反射支持,类似于 PostgreSQL 方言的方式。感谢 Tobias Pfeiffer 提交的拉取请求。 这个变化也被回溯到:1.4.45 参考:#8804
oracle
- [oracle] [错误]
修复了 Oracle 编译器中
FunctionElement.column_valued()
语法不正确的问题,导致COLUMN_VALUE
名称没有正确限定源表。 此更改还被反向移植至:1.4.45 参考:#8945
测试
- [测试] [错误] 修复了 tox.ini 文件中的问题,其中在 tox 4.0 系列对“passenv”的格式进行更改导致 tox 无法正常工作,特别是在 tox 4.0.6 中引发错误。 此更改还被反向移植至:1.4.46
- [测试] [错误]
添加了针对第三方方言的新排除规则
unusual_column_name_characters
,可以将其关闭,以防第三方方言不支持具有不寻常字符的列名,例如点、斜杠或百分号,即使名称已正确引用。 此更改还被反向移植至:1.4.46 参考:#9002
2.0.0b4
发布日期:2022 年 12 月 5 日
orm
- [orm] [功能]
添加了一个新参数
mapped_column.use_existing_column
以适应单表继承映射的用例,该映射使用一个以上的子类指示相同的列位于超类上。以前可以通过在超类的.__table__
中使用declared_attr()
与定位现有列的方法来实现此模式,但现在已更新为使用mapped_column()
以及 pep-484 类型提示,以一种简单而简洁的方式。 另请参阅 使用 use_existing_column 解决列冲突 参考:#8822 - [orm] [用例]
添加了对自定义用户定义类型的支持,这些类型扩展了 Python
enum.Enum
基类,以便在使用注释式声明表功能时自动解析为 SQLAlchemy 的Enum
SQL 类型。该功能通过向 ORM 类型映射功能添加的新查找功能实现,并包括对默认生成的Enum
的参数进行更改的支持,以及设置映射中特定的enum.Enum
类型及其特定参数的支持。 另请参阅 在类型映射中使用 Python Enum 或 pep-586 字面类型 参考:#8859 - [orm] [用例]
为相关的 ORM 属性构造(包括
mapped_column()
,relationship()
等)添加了mapped_column.compare
参数,以提供 Python 数据类field()
的compare
参数,当使用声明性数据类映射功能时。感谢 Simon Schiele 的拉取请求。 参考:#8905 - [orm] [性能] [bug]
在 ORM 启用的 SQL 语句中进一步增强了性能,特别针对在构造 ORM 语句时的调用计数,使用
aliased()
与union()
和类似“复合”结构的组合,以及对 ORM 频繁使用的corresponding_column()
内部方法的直接性能改进,例如aliased()
和类似构造。 参考:#8796 - [orm] [bug]
修复了在列基础属性的
Mapped
注释中使用未知数据类型时静默失败而不是报告异常的问题;现在会引发一个信息性异常消息。 参考:#8888 - [orm] [bug]
修复了一系列问题,涉及与字典类型一起使用
Mapped
的情况,例如Mapped[Dict[str, str] | None]
,在声明性 ORM 映射中将不会被正确解释。已修复以正确“去可选化”此类型的支持,包括用于在type_annotation_map
中查找的支持。 参考:#8777 - [orm] [bug]
在声明性数据类映射功能中修复了一个 bug,该 bug 导致在映射中使用带有
__allow_unmapped__
指令的普通数据类字段时,不会为这些字段创建具有正确类级状态的数据类,不适当地在数据类自身已经用类级默认值替换Field
对象后将原始Field
对象复制到类中。 参考:#8880 - [orm] [bug] [回归]
修复了一个回归问题,即刷新映射到子查询的映射类时(例如直接映射或某些形式的具体表继承),如果使用了
Mapper.eager_defaults
参数,将会失败。 参考:#8812 - [ORM] [错误]
修复了 2.0.0b3 中的一个回归问题,由 #8759 导致,其中使用限定名称(如
sqlalchemy.orm.Mapped
)指示Mapped
名称将无法被 Declarative 认为指示Mapped
结构。 参考:#8853
ORM 扩展
- [用例] [ORM 扩展]
增加了对
association_proxy()
扩展函数的支持,以在 Pythondataclasses
配置中参与,使用了声明性数据类映射中描述的原生数据类功能。包括属性级参数,包括association_proxy.init
和association_proxy.default_factory
。 关联代理的文档也已更新,以在示例中使用 “带注解的声明性表格” 表单,包括用于AssocationProxy
本身的类型注解。 参考:#8878
SQL
- [SQL] [用例]
添加了
ScalarValues
,可用作列元素,允许在IN
子句中使用Values
,或与ANY
或ALL
集合聚合一起使用。此新类是使用方法Values.scalar_values()
生成的。当在IN
或NOT IN
操作中使用时,现在会将Values
实例强制转换为ScalarValues
。 参考:#6289 - [SQL] [错误] 修复了在缓存密钥生成中识别的关键内存问题,其中对于使用大量 ORM 别名和子查询的非常大且复杂的 ORM 语句,缓存密钥生成可能会产生比语句本身大几个数量级的大密钥。非常感谢 Rollo Konig Brock 在最终确定此问题方面的非常耐心和长期的帮助。 此更改也回溯到:1.4.44 参考:#8790
- [sql] [bug]
numeric
pep-249 paramstyle 的方法已被重写,并且现在得到了完全支持,包括“扩展 IN”和“insertmanyvalues”等功能。参数名称也可以在源 SQL 构造中重复,这将在数值格式内正确表示为单个参数。引入了一个名为numeric_dollar
的附加数值 paramstyle,它是由 asyncpg 方言使用的; 该 paramstyle 等效于numeric
,只是数字指示器使用美元符号而不是冒号。asyncpg 方言现在直接使用numeric_dollar
paramstyle,而不是首先编译为format
样式。numeric
和numeric_dollar
paramstyles 假设目标后端能够以任何顺序接收数字参数,并将给定的参数值与语句匹配,基于将它们的位置(从 1 开始)与数字指示器进行匹配。这是numeric
paramstyles 的正常行为,尽管观察到 SQLite DBAPI 实现了一个不使用的numeric
样式,它不遵守参数排序。 参考:#8849 - [sql] [bug]
调整了
RETURNING
的渲染,特别是在使用Insert
时,现在会像Select
构造一样渲染列,以生成标签,其中将包括消除歧义的标签,以及将命名列周围的 SQL 函数标记为列名本身。这在从Select
构造或使用UpdateBase.returning()
的 DML 语句中选择行时建立了更好的跨兼容性。1.4 系列还做了一项较窄的范围更改,仅调整了函数标签问题。 参考:#8770
架构
- [schema] [bug]
对于将
Column
对象附加到Table
对象,现在有更严格的规则,将一些先前的弃用警告转移到异常,并阻止一些先前可能导致表中出现重复列的情况,当设置Table.extend_existing
为True
时,无论是在编程式Table
构建还是在反射操作期间。 请参阅相同名称、键的表对象中列替换规则更严格以了解这些更改的概述。 另请参阅 相同名称、键的表对象中列替换规则更严格 参考:#8925
类型
- [类型] [用例]
添加了一个新类型
SQLColumnExpression
,可以在用户代码中表示任何 SQL 列导向表达式,包括基于ColumnElement
和 ORMQueryableAttribute
的表达式。这个类型是一个真正的类,而不是别名,因此也可以用作其他对象的基础。另外还包括了一个额外的 ORM 特定子类SQLORMExpression
。 参考:#8847 - [类型] [错误]
调整了内部对 Python
enum.IntFlag
类的使用,该类在 Python 3.11 中改变了其行为契约。这并没有导致运行时失败,但导致了在 Python 3.11 下的类型运行失败。 参考:#8783 - [类型] [错误]
sqlalchemy.ext.mutable
扩展和sqlalchemy.ext.automap
扩展现在完全符合 pep-484 类型标准。非常感谢 Gleb Kisenkov 在这方面的努力。 参考:#6810, #8667 - [类型] [错误]
修正了对
relationship.secondary
参数的类型支持,该参数也可以接受返回FromClause
的可调用对象(lambda)。 - [类型] [错误]
改进了
sessionmaker
和async_sessionmaker
的类型,使得它们的返回值的默认类型将会是Session
或AsyncSession
,而无需明确指定此类型。以前,Mypy 无法从其泛型基类自动推断出这些返回类型。 这次更改的一部分是,对于Session
、AsyncSession
、sessionmaker
和async_sessionmaker
的参数除了初始的“bind”参数之外,已经被设置为关键字参数,其中包括一直以来都被记录为关键字参数的参数,比如Session.autoflush
、Session.class_
等。 感谢 Sam Bull 提交的拉取请求。 参考:#8842 - [typing] [bug]
修复了将返回列元素可迭代对象的可调用函数传递给
relationship.order_by
时在类型检查器中标记为错误的问题。 参考:#8776
postgresql
- [postgresql] [usecase]
作为 #8690 的补充,新增了诸如
Range.adjacent_to()
、Range.difference()
、Range.union()
等方法到 PG 特定的范围对象中,使其与底层AbstractRange.comparator_factory
实现的标准操作保持一致。 此外,类的__bool__()
方法已校正,以与常见的 Python 容器行为以及其他流行的 PostgreSQL 驱动程序相一致:现在它告诉范围实例是否不为空,而不是相反。 拉取请求由 Lele Gaifax 提供。 参考:#8765 - [postgresql] [change] [asyncpg]
将 asyncpg 使用的 paramstyle 从
format
更改为numeric_dollar
。这有两个主要好处,因为它不需要对语句进行额外处理,并且允许语句中存在重复的参数。 参考:#8926 - [postgresql] [bug] [mssql] 仅针对 PostgreSQL 和 SQL Server 方言,调整了编译器,以便在渲染 RETURNING 子句中的列表达式时,建议使用 SELECT 语句中使用的“非匿名”标签作为 SQL 表达式元素的标签;主要示例是可能作为列类型的一部分发出的 SQL 函数,其中标签名称默认应与列名称匹配。这恢复了一个在 1.4.21 版本中由于#6718,#6710而改变的不好定义的行为。Oracle 方言具有不同的 RETURNING 实现,不受此问题的影响。版本 2.0 对其他后端广泛扩展的 RETURNING 支持进行了全面变更。 此更改还反向移植到:1.4.44 参考:#8770
- [postgresql] [bug]
对新的 PostgreSQL
Range
类型进行了额外的类型检测,以前允许直接通过 DBAPI 接收 psycopg2 原生范围对象的情况已停止工作,因为现在我们有了自己的值对象。Range
对象已得到增强,以便 SQLAlchemy 核心在其他模糊情况下检测到它(例如与日期的比较),并应用适当的绑定处理程序。拉取请求由 Lele Gaifax 提供。 参考:#8884
mssql
- [mssql] [bug] 由#8177的组合引起的回归,重新启用了 setinputsizes 用于 SQL 服务器,除非使用 fast_executemany DBAPI executemany 用于语句,以及#6047,实现了“insertmanyvalues”,该值绕过了 DBAPI executemany,而是使用 INSERT 语句的自定义 DBAPI execute。如果打开 fast_executemany,setinputsizes 将不会用于使用“insertmanyvalues”的多个参数集 INSERT 语句,因为检查将错误地假设这是一个 DBAPI executemany 调用。然后,“回归”的问题就是,“insertmanyvalues”语句格式显然对于不使用相同类型的多行特别敏感,因此在这种情况下,尤其需要 setinputsizes。 修复了 fast_executemany 检查,使其仅在使用 true DBAPI executemany 时禁用 setinputsizes。 参考:#8917
oracle
- [oracle] [bug] 对 Oracle 修复#8708的持续修复,在 1.4.43 中发布,其中以下划线开头的绑定参数名称(Oracle 不允许的)仍然未在所有情况下正确转义。 此更改也反向移植到:1.4.45 参考:#8708
测试
- [tests] [bug]
修复了测试套件中
--disable-asyncio
参数的问题,该参数实际上无法禁止运行 greenlet 测试,并且也无法阻止套件在整个运行过程中使用“wrapping” greenlet。此参数现在确保在设置时不会在整个运行期间发生 greenlet 或 asyncio 使用。 此更改也反向移植到:1.4.44 参考:#8793
2.0.0b3
发布日期:2022 年 11 月 4 日
orm
- [orm] [bug] 修复了在连接式预加载中出现断言失败的问题,在使用特定外/内连接式预加载组合时会出现断言失败,在跨三个映射器进行预加载时,中间映射器是一个继承的子类映射器。 此更改也反向移植到:1.4.43 参考:#8738
- [orm] [bug]
修复了涉及
Select
构造的错误,其中Select.select_from()
与Select.join()
的组合,以及在使用Select.join_from()
时,会导致with_loader_criteria()
功能以及单表继承查询所需的 IN 条件在查询的列子句没有明确包含 JOIN 左侧实体时不会呈现。现在,正确的实体已传递给内部生成的Join
对象,以便正确添加对左侧实体的条件。 此更改也回溯到:1.4.43 参考:#8721 - [orm] [bug]
当
with_loader_criteria()
选项作为特定“加载器路径”添加的加载器选项时,现在会引发一个信息性异常,例如在Load.options()
中使用它时。这种用法不受支持,因为with_loader_criteria()
只打算用作顶级加载器选项。以前会生成内部错误。 此更改也回溯到:1.4.43 参考:#8711 - [orm] [bug]
为
Session.get()
改进了“字典模式”,以便可以在命名字典中指示引用主键属性名称的同义词名称。 此更改也回溯到:1.4.43 参考:#8753 - [orm] [bug]
修复了继承映射器的“selectin_polymorphic”加载不会正确工作的问题,如果
Mapper.polymorphic_on
参数引用的 SQL 表达式不直接映射到类上。 此更改也回溯到:1.4.43 参考:#8704 - [orm] [bug]
修复了当使用
Query
对象作为迭代器时,如果在迭代过程中出现用户定义的异常情况,则底层的 DBAPI 游标不会被关闭的问题。当使用Query.yield_per()
来创建服务器端游标时,这会导致通常与 MySQL 相关的服务器端游标不同步的问题,并且由于无法直接访问Result
对象,最终用户的代码无法访问游标以关闭它。 为了解决这个问题,在迭代器方法中应用了对GeneratorExit
的捕获,这样当迭代器被中断时将关闭结果对象,并且按定义将被 Python 解释器关闭。 作为针对 1.4 系列实现的这一变化的一部分,确保了在所有Result
实现上都提供了.close()
方法,包括ScalarResult
、MappingResult
。这一变化的 2.0 版本还包括了用于与Result
类一起使用的新上下文管理器模式。 这一变化也被回溯到了:1.4.43 参考:#8710
orm 声明式
- [orm] [declarative] [bug]
在 ORM 声明式注释中为
relationship()
指定的类名添加了支持,以及为Mapped
符号本身的名称,使其与直接的类名不同,以支持诸如将Mapped
导入为from sqlalchemy.orm import Mapped as M
,或者相关类名以类似方式导入为替代名称的情况。此外,作为relationship()
的主参数给定的目标类名将始终优先于左手注释中给定的名称,以便仍然可以在注释中使用否则无法导入的名称,而且这些名称也不与类名匹配。 参考:#8759 - [orm] [declarative] [bug]
改进对使用注释的遗留 1.4 映射的支持,这些注释不包括
Mapped[]
,通过确保__allow_unmapped__
属性可以用于允许这些遗留注释通过 Annotated Declarative 而不引发错误,并且不在 ORM 运行时上下文中被解释。此外,当检测到这种情况时改进了生成的错误消息,并为应该如何处理这种情况添加了更多文档。不幸的是,1.4 WARN_SQLALCHEMY_20 迁移警告不能在运行时使用当前架构检测到这个特定的配置问题。 参考:#8692 - [orm] [declarative] [bug]
改变了
Mapper
的一个基本配置行为,其中在Mapper.properties
字典中显式存在的Column
对象,无论是直接还是包含在映射器属性对象内部,现在都将在映射的Table
(或其他可选择的)本身中以它们出现的顺序进行映射(假设它们实际上是该表的列列表的一部分),从而保持在映射的可选择上的列的顺序与在映射类中操纵的顺序相同,以及在 ORM SELECT 语句中为该映射器渲染的内容相同。以前(“以前”意味着自版本 0.0.1 以来),在Mapper.properties
字典中的Column
对象总是会首先映射,超过了在映射的Table
中其他列的映射,导致在映射器分配属性给映射类时的顺序以及它们在语句中呈现的顺序之间存在差异。 此更改最显著地发生在声明式将声明的列分配给Mapper
的方式上,特别是在处理具有 DDL 名称明确不同于映射属性名称的Column
(或mapped_column()
)对象以及使用deferred()
等构造时。新行为将使映射的Table
中的列顺序与属性映射到类中的顺序相同,由Mapper
本身分配,并在 ORM 语句(如 SELECT 语句)中呈现,独立于Column
针对Mapper
的配置方式。 参考:#8705 - [orm] [declarative] [bug] 修复了新数据类映射功能中的问题,其中在某些情况下,在继承子类的构造函数中,声明在声明基类/抽象基类/混合类上的列会泄漏。 参考:#8718
- [bug] [orm declarative]
修复了声明式类型解析器(即解析
ForwardRef
对象的解析器)中的问题,其中在一个特定的源文件中为列声明的类型在最终映射的类位于另一个源文件时会引发NameError
。现在,这些类型是根据每个类所在的模块来解析的。 参考:#8742
引擎
- [engine] [feature]
为了更好地支持用户定义的异常可能会中断迭代的
Result
和AsyncResult
对象的使用情况,现在这两个对象以及诸如ScalarResult
、MappingResult
、AsyncScalarResult
、AsyncMappingResult
等变体都支持上下文管理器的使用,结果将在上下文管理器块的末尾关闭。 另外,确保所有上述提到的Result
对象都包括Result.close()
方法以及Result.closed
访问器,包括以前没有.close()
方法的ScalarResult
和MappingResult
。 另请参阅 结果、AsyncResult 的上下文管理器支持 引用:#8710 - [engine] [用例]
添加了新参数
PoolEvents.reset.reset_state
到PoolEvents.reset()
事件中,同时放置了一个将继续接受使用先前一组参数的事件钩子的弃用逻辑。这指示了关于重置正在进行的方式的各种状态信息,并且被用于允许在给定完整上下文的情况下进行自定义重置方案。 在这个改变中,也包括了一个在 1.4 中回溯的修复,该修复重新启用了PoolEvents.reset()
事件,以便在所有情况下继续进行,包括当Connection
已经“重置”连接时。 这两个更改共同允许使用PoolEvents.reset()
事件来实现自定义重置方案,而不是使用PoolEvents.checkin()
事件(其功能与以往一样)。 参考资料:#8717 - [engine] [bug] [regression]
修复了一个问题,即当
Connection
关闭并且正在将其 DBAPI 连接返回到连接池时,在某些情况下不会调用PoolEvents.reset()
事件钩子。 当Connection
已经在将连接返回到池的过程中在其 DBAPI 连接上发出.rollback()
时,场景是它随后会指示连接池放弃执行自己的“重置”以节省额外的方法调用。但是,这会阻止在此钩子中使用自定义池重置方案,因为此类钩子根据定义正在执行的不仅仅是调用.rollback()
,而且需要在所有情况下调用。这是在版本 1.4 中出现的一种退化。 对于版本 1.4,PoolEvents.checkin()
仍然可作为用于自定义“重置”实现的备用事件钩子。版本 2.0 将提供一个改进版本的PoolEvents.reset()
,它将被调用用于额外的场景,例如终止 asyncio 连接,并且还传递有关重置的上下文信息,以允许对不同的重置方案作出响应以不同的方式处理不同的重置场景。 此更改也被回溯到:1.4.43 参考资料:#8717
sql
- [sql] [bug]
修复了一个问题,它阻止
literal_column()
构造在Select
构造的上下文中正常工作,以及其他可能生成“匿名标签”的地方,如果文字表达式包含可能干扰格式字符串的字符,例如括号,由于“匿名标签”的实现细节。 此更改也被回溯到:1.4.43 参考资料:#8724
typing
- [typing] [bug] 更正了引擎和异步引擎包中的各种类型问题。
postgresql
- [postgresql] [feature]
添加了新方法
Range.contains()
和Range.contained_by()
到新的Range
数据对象中,这些方法与 PostgreSQL 的@>
和<@
操作符的行为相同,以及comparator_factory.contains()
和comparator_factory.contained_by()
SQL 操作符方法。感谢 Lele Gaifax 提供的拉取请求。 参考:#8706 - [postgresql] [usecase] 优化了对 PostgreSQL 后端的新 RANGE / MULTIRANGE 支持和更改 中描述的范围对象的新方法,以适应驱动程序特定的范围和多范围对象,更好地适应传统代码以及将结果从原始 SQL 结果集传递回新范围或多范围表达式时。 参考:#8690
mssql
- [mssql] [bug]
修复了与使用 SQL Server 方言的临时表时使用
Inspector.has_table()
相关的问题,这会导致某些 Azure 变体上失败,因为不支持那些服务器版本上的一个不必要的信息模式查询。感谢 Mike Barry 提供的拉取请求。 此更改还回溯到:1.4.43 参考:#8714 - [mssql] [bug] [reflection]
修复了与
Inspector.has_table()
相关的问题,当对使用 SQL Server 方言的视图使用时,错误地返回False
,这是由于 1.4 系列中的一个回归导致的,该系列在 SQL Server 上删除了对此的支持。这个问题在使用不同反射架构的 2.0 系列中不存在。添加了测试支持,以确保has_table()
符合视图的规范。 此更改还回溯到:1.4.43 参考:#8700
oracle
- [oracle] [bug] 修复了一个问题,其中包含需要在 Oracle 中用引号引起的字符的绑定参数名称,包括那些从同名数据库列自动生成的名称,在使用 Oracle 方言的“扩展参数”时不会被转义,导致执行错误。 Oracle 方言使用的绑定参数的通常“引用”不与“扩展参数”架构一起使用,因此使用了大范围字符的转义,现在使用了一个针对 Oracle 的字符/转义列表。 此更改也回溯到:1.4.43 参考:#8708
- [oracle] [bug]
修复了一个问题,在新的 ORM 类型声明映射中,没有实现在关系配置中使用
Optional[MyClass]
或类似形式(例如MyClass | None
)的类型注释的能力,导致错误。 文档还为这种用例添加了关于关系配置的文档。 此更改也回溯到:1.4.43 参考:#8744
2.0.0b2
发布日期:2022 年 10 月 20 日
orm
- [orm] [bug] 移除了在使用 ORM 启用的更新/删除时发出的警告,该警告首次出现在#4073中;这个警告实际上掩盖了一个场景,否则可能会根据实际列而为 ORM 映射的属性填充错误的 Python 值,因此移除了这个不建议使用的情况。在 2.0 中,ORM 启用的更新/删除使用“auto”作为“synchronize_session”,这应该会自动为任何给定的 UPDATE 表达式执行正确的操作。 参考:#8656
orm 声明
- [orm] [declarative] [usecase]
添加了对映射类也是
Generic
子类的支持,可以在语句和调用inspect()
时指定为GenericAlias
对象(例如MyClass[str]
)。 参考:#8665 - [orm] [declarative] [bug]
改进了
DeclarativeBase
类,以便与其他混入类(如MappedAsDataclass
)结合使用时,类的顺序可以是任意顺序。 参考:#8665 - [orm] [declarative] [bug]
修复了一个问题,在新的 ORM 类型声明映射中,没有实现在关系配置中使用
Optional[MyClass]
或类似形式(例如MyClass | None
)的类型注释的能力,导致错误。 文档还为这种用例添加了关于关系配置的文档。 参考:#8668 - [orm] [declarative] [bug]
修复了新的 dataclass 映射功能中的问题,当处理覆盖
mapped_column()
声明的混入时,传递给 dataclasses API 的参数有时可能被错误排序,导致初始化问题。 参考:#8688
sql
- [sql] [bug] [regression]
修复了新的“insertmanyvalues”功能中的 bug,其中包含使用
bindparam()
的子查询的 INSERT 在“insertmanyvalues”格式中无法正确呈现的问题。这直接影响了 psycopg2,因为“insertmanyvalues”在此驱动程序中无条件使用。 参考:#8639
类型
- [typing] [bug]
修复了 pylance 严格模式下报告“实例变量覆盖类变量”的类型问题,当使用方法定义
__tablename__
、__mapper_args__
或__table_args__
时。 参考:#8645 - [typing] [bug]
修复了 pylance 严格模式下报告“部分未知”数据类型的
mapped_column()
构造的类型问题。 参考:#8644
mssql
- [mssql] [bug]
由于 SQL Server pyodbc 更改 #8177 引起的回归问题已修复,现在默认使用
setinputsizes()
;对于 VARCHAR,如果字符大小大于 4000(或 2000,取决于数据),则会失败,因为传入的数据类型是 NVARCHAR,其限制为 4000 个字符,尽管 VARCHAR 可以处理无限字符。 当数据类型的大小> 2000 个字符时,现在还将传递额外的 pyodbc 特定的类型信息给setinputsizes()
。 这个更改也适用于受此问题影响的JSON
类型,用于大型 JSON 序列化。 参考:#8661 - [mssql] [bug]
Sequence
构造恢复到了 1.4 系列之前的 DDL 行为,即创建一个没有额外参数的Sequence
将会发出一个简单的CREATE SEQUENCE
指令,没有任何额外的“起始值”参数。对于大多数后端来说,无论如何,这都是之前的工作方式;然而,对于 MS SQL Server,此数据库上的默认值是-2**63
;为了防止这个通常不实用的默认值在 SQL Server 上生效,应该提供Sequence.start
参数。由于对于多年以来一直在IDENTITY
上标准化的 SQL Server 来说,对Sequence
的使用是不寻常的,希望这个变化影响最小。 另请参阅 Sequence 构造不再具有任何显式默认的 “start” 值;影响 MS SQL Server 参考:#7211
2.0.0b1
发布日期:2022 年 10 月 13 日
常规
- [常规] [更改]
迁移代码库以删除所有之前标记为在 2.0 中移除的预先 2.0 版本行为和架构,包括但不限于:
- 删除所有 Python 2 代码,最低版本现在为 Python 3.7
-
Engine
和Connection
现在使用新的 2.0 工作风格,其中包括 “autobegin”,库级别的自动提交已删除,子事务和 “branched” 连接已删除。 - 结果对象使用 2.0 风格的行为;
Row
完全是一个具有命名元组而没有 “映射” 行为,使用RowMapping
来进行 “映射” 行为 - 所有 Unicode 编码/解码架构已从 SQLAlchemy 中删除。所有现代的 DBAPI 实现都通过 Python 3 透明地支持 Unicode,因此已经删除了
convert_unicode
功能以及相关的在 DBAPIcursor.description
等中查找字节字符串的机制。 - 从
MetaData
,Table
和从以前可以引用 “绑定引擎”的所有 DDL/DML/DQL 元素中的.bind
属性和参数 - 独立的
sqlalchemy.orm.mapper()
函数已移除;所有经典映射应通过registry.map_imperatively()
方法的registry
进行。 -
Query.join()
方法不再接受字符串作为关系名称;使用Class.attrname
作为连接目标的长期记录方法现在是标准的。 -
Query.join()
不再接受“aliased”和“from_joinpoint”参数。 -
Query.join()
不再在一个方法调用中接受多个连接目标链。 -
Query.from_self()
,Query.select_entity_from()
和Query.with_polymorphic()
已移除。 -
relationship.cascade_backrefs
参数现在必须保持其新默认值False
;save-update
级联不再沿着反向引用级联。 -
Session.future
参数必须始终设置为True
。Session
的 2.0 风格事务模式现在始终生效。 - 加载器选项不再接受属性名称的字符串。使用
Class.attrname
作为加载器选项目标的长期记录方法现在是标准的。 - 遗留形式的
select()
已移除,包括select([cols])
,some_table.select()
的“whereclause”和关键参数。 -
Select
上的遗留“就地变异器”方法,如append_whereclause()
,append_order_by()
等已移除。 - 移除了非常古老的“dbapi_proxy”模块,早期 SQLAlchemy 版本中用于在原始 DBAPI 连接上提供透明连接池。
参考:#7257
- [通用] [更改]
Query.instances()
方法已弃用。该方法的行为约定,即可以通过任意结果集迭代对象,早已过时且不再测试。可以使用类似:meth.Select.from_statement
或aliased()
的构造来返回对象。
平台
- [平台] [特性]
SQLAlchemy 的 C 扩展已被全部使用 Cython 编写的新实现所取代。与以前的 C 扩展一样,针对许多常见平台的预构建轮文件可在 pypi 上获得,因此构建不是问题。对于自定义构建,
python setup.py build_ext
与以前一样工作,只需额外的 Cython 安装即可。pyproject.toml
现在也是源代码的一部分,当使用 pip 时将建立正确的构建依赖关系。 参见 C 扩展现已移植到 Cython 参考:#7256 - [platform] [change]
SQLAlchemy 的源代码构建和安装现在包括一个
pyproject.toml
文件,以完全支持 PEP 517。 参见 安装现在完全支持 pep-517 参考:#7311
orm
- [orm] [feature] [sql] 添加了对所有支持 RETURNING 的包含方言的新功能,称为“insertmanyvalues”。这是“fast executemany”功能的一般化,该功能首先在 psycopg2 驱动程序中的 1.4 版本中引入,详情请参阅 ORM Batch inserts with psycopg2 now batch statements with RETURNING in most cases,它允许 ORM 将 INSERT 语句批处理到一个更高效的 SQL 结构中,同时仍能够使用 RETURNING 检索新生成的主键和 SQL 默认值。 此功能现在适用于支持 RETURNING 以及多个 VALUES 构造用于 INSERT 的许多方言,包括所有 PostgreSQL 驱动程序,SQLite,MariaDB,MS SQL Server。另外,Oracle 方言还使用本机 cx_Oracle 或 OracleDB 功能获得相同的能力。 参考:#6047
- [orm] [feature]
添加了新参数
AttributeEvents.include_key
,它将包含诸如__setitem__()
(例如obj[key] = value
)和__delitem__()
(例如del obj[key]
)等操作的字典或列表键,使用一个新的关键字参数“key”或“keys”,取决于事件,例如AttributeEvents.append.key
,AttributeEvents.bulk_replace.keys
。这允许事件处理程序考虑传递给操作的键,对于与MappedCollection
一起工作的字典操作尤其重要。 参考:#8375 - [orm] [feature]
添加了新参数
Operators.op.python_impl
,可从Operators.op()
以及直接使用custom_op
构造函数时使用,允许提供一个在 Python 中进行评估的函数,以及自定义 SQL 运算符。当操作符对象在两侧使用普通 Python 对象作为操作数时,此评估函数将成为使用的实现,并且特别兼容与 ORM 启用的 INSERT、UPDATE 和 DELETE 语句一起使用的synchronize_session='evaluate'
选项。 参考:#3162 - [orm] [feature]
Session
(以及间接AsyncSession
)现在具有新的状态跟踪功能,将主动捕获在特定事务方法进行时发生的任何意外状态更改。这是为了允许在线程不安全的方式中使用Session
的情况,其中事件钩子或类似的可能在操作中调用意外方法,以及在其他并发情况下(如 asyncio 或 gevent)在首次发生非法访问时引发信息性消息,而不是默默传递导致由于Session
处于无效状态而导致的次要故障。 另请参阅 当检测到非法并发或重入访问时,会主动引发会话 参考:#7433 - [orm] [feature]
当与 Python
dataclass
一起使用时,composite()
映射构造现在支持值的自动解析;不再需要实现__composite_values__()
方法,因为此方法是从数据类的检查中派生的。 此外,由composite
映射的类现在支持排序比较操作,例如<
、>=
等。 请参阅复合列类型中的新文档以获取示例。 - [orm] [feature]
添加了对
selectinload()
和immediateload()
加载器选项的非常实验性功能,名为selectinload.recursion_depth
/immediateload.recursion_depth
,它允许单个加载器选项自动递归到自引用关系中。设置为指示深度的整数,并且也可以设置为-1,以指示继续加载直到找不到更多层级为止。对selectinload()
和immediateload()
进行了主要的内部更改,以便使此功能在继续正确使用编译缓存的同时工作,并且不使用任意递归,因此支持任何深度级别(尽管会发出相同数量的查询)。这对于必须完全急切加载的自引用结构可能会有用,例如在使用 asyncio 时。 当检测到相关对象加载中的过度递归深度时,还会发出警告,该警告也会在加载器选项以任意长度连接在一起时(即,不使用新的recursion_depth
选项)发出。此操作继续使用大量内存,并且性能极差;当检测到此条件时,缓存会被禁用,以防止缓存被任意语句淹没。 参考:#8126 - [orm] [feature]
添加了新参数
Session.autobegin
,当设置为False
时,将阻止Session
隐式地开始事务。必须首先显式调用Session.begin()
方法,以便继续进行操作,否则在任何操作本应自动开始时都会引发错误。此选项可用于创建一个“安全”的Session
,该会话不会隐式启动新事务。 作为这一变化的一部分,还添加了一个新的状态变量origin
,可能对事件处理代码有用,以了解特定SessionTransaction
的来源。 参考:#6928 - [orm] [特性]
使用包含
ForeignKey
引用的Column
对象的声明性混合物不再需要使用declared_attr()
来实现此映射;当列应用于声明的映射时,ForeignKey
对象与Column
本身一起复制。 - [orm] [用例]
在
load_only()
加载器选项中添加了load_only.raiseload
参数,以便未加载的属性可能具有“raise”行为而不是延迟加载。以前没有真正直接使用load_only()
选项来实现这一点。 - [orm] [更改]
为了更好地适应显式类型,一些通常在内部构造但有时也可见于消息传递和类型化的 ORM 构造的名称已更改为更简洁的名称,这些名称也与构造函数的名称(大小写不同)匹配,在所有情况下都保留了旧名称的别名以备将来使用:
-
RelationshipProperty
成为主要名称Relationship
的别名,始终由relationship()
函数构建 -
SynonymProperty
成为主要名称Synonym
的别名,始终由synonym()
函数构建 -
CompositeProperty
现在成为主要名称Composite
的别名,始终由composite()
函数构建。
-
- [orm] [change]
为了与突出的 ORM 概念
Mapped
保持一致,基于字典的集合attribute_mapped_collection()
、column_mapped_collection()
和MappedCollection
的名称已更改为attribute_keyed_dict()
、column_keyed_dict()
和KeyFuncDict
,使用“dict”短语以减少与术语“mapped”的混淆。旧名称将无限期保留,没有删除计划。 参考:#8608 - [orm] [bug]
所有
Result
对象现在在硬关闭后使用时都会一致地引发ResourceClosedError
,包括在调用类似Result.first()
和Result.scalar()
这样的“单行或值”方法后发生的“硬关闭”。这已经是基于CursorResult
的最常见的 Core 语句执行返回的结果对象的行为,因此这种行为并不新鲜。然而,这一变化已经扩展到正确地适应使用 2.0 风格 ORM 查询时返回的 ORM“过滤”结果对象,以前这些对象会以“软关闭”方式返回空结果,或者根本不会真正“软关闭”并会继续从底层游标中产生结果。 作为这一变更的一部分,还将Result.close()
添加到基础Result
类中,并为 ORM 使用的过滤结果实现了它,这样就可以在使用yield_per
执行选项时调用底层CursorResult
上的CursorResult.close()
方法,在获取剩余的 ORM 结果之前关闭服务器端游标。这对于核心结果集已经可用,但此变更也使其适用于 2.0 风格的 ORM 结果。 此更改也回溯到:1.4.27 参考:#7274 - [orm] [bug]
修复了
registry.map_declaratively()
方法返回内部“映射器配置”对象而不是 API 文档中所述的Mapper
对象的问题。 - [orm] [bug]
修复了至少在 1.3 版本中出现的性能回归,如果不是更早(在 1.0 之后的某个时候),那么从连接的继承子类加载延迟列(那些明确映射为
defer()
的列,而不是已过期的未延迟列),将不会使用“优化”查询,该查询仅查询包含未加载列的直接表,而是运行完整的 ORM 查询,该查询会为所有基本表发出 JOIN,当仅从子类加载列时,这是不必要的。 参考:#7463 - [orm] [bug]
Load
对象及相关加载策略模式的内部大部分已经重写,以利用现在仅支持属性绑定路径而不是字符串的事实。重写希望能更直接地解决加载策略系统中的新用例和微妙问题。 参考:#6986 - [orm] [bug] 对“延迟加载”/“仅加载”一组策略选项进行了改进,其中如果一个对象从一个查询中的两个不同逻辑路径加载,那么至少有一个选项配置为填充的属性将在所有情况下被填充,即使该对象的其他加载路径没有设置此选项。以前,基于随机性来确定哪个“路径”首先处理对象。 参考:#8166
- [orm] [bug] 修复了在针对联合继承子类创建语句时启用 ORM 的 UPDATE 时出现的问题,仅更新本地表列,其中“fetch”同步策略不会为使用 RETURNING 进行获取同步的数据库呈现正确的 RETURNING 子句。还调整了在 UPDATE FROM 和 DELETE FROM 语句中使用的 RETURNING 策略。 参考:#8344
- [orm] [bug] [asyncio]
从
begin
和begin_nested
中删除了未使用的**kw
参数。这些 kw 没有被使用,似乎是错误地添加到 API 中的。 参考:#7703 - [orm] [bug]
更改了
attribute_mapped_collection()
和column_mapped_collection()
(现在称为attribute_keyed_dict()
和column_keyed_dict()
)在填充字典时使用的属性访问方法,断言对象上用作字典键的数据值实际上存在,并且不是因为属性从未被分配而使用“None”。这用于防止在通过反向引用进行分配时错误地为键分配 None,其中对象上的“键”属性尚未被分配。 由于此处的失败模式是一种通常不会持续到数据库的瞬态条件,并且很容易通过类的构造函数根据分配参数的顺序产生,因此很有可能许多应用程序已经包含了这种行为,而这种行为被悄悄地忽略了。为了适应现在引发此错误的应用程序,还添加了一个新参数attribute_keyed_dict.ignore_unpopulated_attribute
到attribute_keyed_dict()
和column_keyed_dict()
,这个参数将导致错误的反向引用赋值被跳过。 参考:#8372 - [orm] [bug]
添加了新参数
AbstractConcreteBase.strict_attrs
到AbstractConcreteBase
声明混合类。这个参数的效果是,子类上的属性范围正确地限制在声明每个属性的子类中,而不是之前的行为,其中整个层次结构的所有属性都应用到基本的“抽象”类上。这样会产生更清晰、更正确的映射,子类不再具有仅对同级类有用的属性。此参数的默认值为 False,这保留了先前的行为不变;这是为了支持在查询中明确使用这些属性的现有代码。要迁移到更新的方法,根据需要将显式属性应用到抽象基类中。 参考:#8403 - [orm] [bug]
defer()
在处理主键和“多态鉴别器”列时的行为已经修订,以使这些列不再是可延迟的,无论是明确指定还是使用诸如defer('*')
这样的通配符。先前,通配符延迟不会加载主键/多态列,这导致在所有情况下都出现错误,因为 ORM 依赖于这些列来生成对象标识。对主键列的显式延迟行为不变,因为这些延迟已经被隐式忽略。 参考:#7495 - [orm] [bug]
修复了
Mapper.eager_defaults
参数行为中的错误,使得仅在表定义中存在客户端 SQL 默认值或 onupdate 表达式时,ORM 为行执行 INSERT 或 UPDATE 时触发 RETURNING 或 SELECT 的操作。之前,仅服务器端默认值作为表 DDL 的一部分或服务器端 onupdate 表达式会触发此次提取,尽管客户端 SQL 表达式在渲染提取时也会被包含在内。 参考:#7438
引擎
- [引擎] [特性]
DialectEvents.handle_error()
事件现已从EngineEvents
套件移至DialectEvents
套件,并且现在参与连接池的“预 ping”事件,对于那些使用断开代码来检测数据库是否存活的方言。这使得最终用户代码能够更改“预 ping”的状态。请注意,这不包括包含本地“ping”方法的方言,如 psycopg2 或大多数 MySQL 方言。 参考:#5648 - [引擎] [特性]
ConnectionEvents.set_connection_execution_options()
和ConnectionEvents.set_engine_execution_options()
事件钩子现在允许对给定的选项字典进行就地修改,新内容将作为最终执行选项接收。以前,不支持对字典进行就地修改。 - [引擎] [用例]
将
create_engine.isolation_level
参数泛化到基本方言,因此不再依赖于单独的方言。该参数为所有新数据库连接的“隔离级别”设置提供了设置,一旦连接池创建它们,该值就会保持设置而不是在每次 checkin 时重置。create_engine.isolation_level
参数在功能上与通过Engine.execution_options.isolation_level
参数使用Engine.execution_options()
设置相当。区别在于前者设置隔离级别只会在创建连接时执行一次,后者在每次连接检出时设置和重置给定级别。 参考:#6342 - [engine] [change]
关于引擎和方言的一些小的 API 更改:
-
Dialect.set_isolation_level()
、Dialect.get_isolation_level()
、:meth: 方言方法将始终传递原始的 DBAPI 连接 -
Connection
和Engine
类不再共享基础的Connectable
超类,该超类已被移除。 - 添加了一个新的接口类
PoolProxiedConnection
- 这是熟悉的_ConnectionFairy
类的公共接口,尽管它是一个私有类。
参考:#7122
-
- [engine] [bug] [regression]
修复了当结果完全耗尽时,
CursorResult.fetchmany()
方法未能自动关闭服务器端游标(即在使用stream_results
或yield_per
时,无论是核心还是 ORM 导向的结果)的回归问题。 此更改也被回溯至:1.4.27 参考:#7274 - [engine] [bug]
修复了未来
Engine
中的问题,当调用Engine.begin()
并进入上下文管理器时,如果实际的 BEGIN 操作由于某种原因失败,例如事件处理程序引发异常,则连接不会关闭;未来版本的引擎未测试此用例。请注意,“未来”上下文管理器在实际输入上下文管理器之前不会运行 “BEGIN” 操作。这与立即运行 “BEGIN” 操作的传统版本不同。 此更改也被回溯至:1.4.27 参考:#7272 - [engine] [bug]
当
pool_size=0
时,QueuePool
现在会忽略max_overflow
,从而正确地使池在所有情况下都是无限的。 参考:#8523 - [engine] [bug]
为了提高安全性,当调用
str(url)
时,URL
对象现在默认使用密码混淆。要将 URL 字符串化为明文密码,可以使用URL.render_as_string()
,将URL.render_as_string.hide_password
参数传递为False
。感谢我们的贡献者提供了此拉取请求。 另请参阅 str(engine.url) 现在默认混淆密码 参考:#8567 - [engine] [bug]
Inspector.has_table()
方法现在将一致地检查给定名称的视图和表格。先前,此行为取决于方言,其中 PostgreSQL、MySQL/MariaDB 和 SQLite 支持它,而 Oracle 和 SQL Server 不支持它。第三方方言也应确保它们的Inspector.has_table()
方法搜索给定名称的视图和表格。 参考:#7161 - [engine] [bug]
在
Result.columns()
方法中修复了一个问题,在某些情况下,特别是 ORM 结果对象的情况下,调用带有单个索引的Result.columns()
可能导致Result
生成标量对象而不是Row
对象,就像调用了Result.scalars()
方法一样。在 SQLAlchemy 1.4 中,此场景会发出警告,指出行为将在 SQLAlchemy 2.0 中更改。 引用:#7953 - [engine] [错误]
将
DefaultGenerator
对象(例如Sequence
)传递给Connection.execute()
方法已弃用,因为此方法被类型化为返回一个CursorResult
对象,而不是纯标量值。应改用Connection.scalar()
方法,该方法已经重写了新的内部代码路径以适用于调用 SELECT 以获取默认生成对象而不经过Connection.execute()
方法。 - [engine] [已移除]
从
create_engine()
中移除了之前弃用的case_sensitive
参数,这只会影响 Core-only 结果集行中字符串列名称的查找;它不会影响 ORM 的行为。case_sensitive
指向的有效行为保持其默认值True
,意味着在row._mapping
中查找的字符串名称将与大小写敏感地匹配,就像任何其他 Python 映射一样。 请注意,case_sensitive
参数与控制大小写敏感性、引用和“名称规范化”(即转换为将所有大写字母视为大小写不敏感的数据库)DDL 标识符名称的一般主题没有任何关系,这仍然是 SQLAlchemy 的一个常规核心功能。 - [engine] [已移除]
移除了已弃用的旧版包
sqlalchemy.databases
。请改用sqlalchemy.dialects
。 引用:#7258 - [engine] [已弃用]
create_engine.implicit_returning
参数已经在create_engine()
函数中弃用;该参数仅在Table
对象上保留。该参数最初旨在在 SQLAlchemy 首次开发时启用“implicit returning”功能,但默认情况下未启用。在现代用法下,没有理由禁用该参数,并且观察到它会引起混乱,因为它会降低性能,使 ORM 更难以检索最近插入的服务器默认值。该参数仅在Table
上保留,以特别适应使 RETURNING 不可行的数据库级边缘情况,目前唯一的示例是 SQL Server 的限制,即不得在具有 INSERT 触发器的表上使用 INSERT RETURNING。 参考:#6962
sql
- [sql] [feature]
添加了长期要求的不区分大小写的字符串操作符
ColumnOperators.icontains()
,ColumnOperators.istartswith()
,ColumnOperators.iendswith()
。这些操作符生成不区分大小写的 LIKE 组合(在 PostgreSQL 上使用 ILIKE,在所有其他后端上使用 LOWER()函数),以补充现有的 LIKE 组合操作符ColumnOperators.contains()
,ColumnOperators.startswith()
等。对于实现这些新方法的 Matias Martinez Rebori 的细致和完整的工作表示巨大的感谢。 参考:#3482 - [sql] [feature]
在所有
FromClause
对象的FromClause.c
集合中添加了新的语法,允许传递键的元组给__getitem__()
,以及支持select()
构造处理直接处理结果类似元组的集合,允许select(table.c['a', 'b', 'c'])
语法成为可能。返回的子集合本身也是一个ColumnCollection
,现在也可以直接被select()
和类似方法消耗。 参见 设置 COLUMNS 和 FROM 子句 参考:#8285 - [sql] [功能]
添加了新的与后端无关的
Uuid
数据类型,从 PostgreSQL 方言泛化到核心类型,以及将UUID
从 PostgreSQL 方言迁移到核心类型。SQL Server 的UNIQUEIDENTIFIER
数据类型也变成了一个 UUID 处理数据类型。感谢 Trevor Gross 的帮助。 参考:#7212 - [sql] [功能]
向
sqlalchemy.
模块命名空间添加了Double
、DOUBLE
、DOUBLE_PRECISION
数据类型,用于显式使用 double/double precision 以及通用的“double”数据类型。使用Double
来提供通用支持,根据不同后端需要解析为 DOUBLE/DOUBLE PRECISION/FLOAT。 参考:#5465 - [sql] [用例]
更改了
Insert
构造的编译机制,使得“自动递增主键”列值将通过cursor.lastrowid
或 RETURNING 获取,即使它存在于参数集中或在Insert.values()
方法中作为普通绑定值,用于特定后端上已知在明确传递 NULL 时仍生成自动递增值的单行 INSERT 语句。这恢复了 1.3 系列中的行为,用于分离的参数集以及Insert.values()
方法。在 1.4 中,参数集行为无意中更改为不再执行此操作,但Insert.values()
方法仍会获取自动递增值,直到 1.4.21,其中 #6770 再次无意中更改了行为,因为此用例从未得到覆盖。 现在已定义行为为“工作”,以适应数据库(如 SQLite、MySQL 和 MariaDB 等)忽略显式 NULL 主键值并仍调用自动递增生成器的情况。 引用: #7998 - [sql] [usecase]
当使用 PostgreSQL、MySQL、MariaDB、MSSQL、Oracle 方言提供的 SQL 编译器与
literal_binds
一起使用时,添加了修改后的 ISO-8601 渲染(即将 T 转换为空格的 ISO-8601),对于 Oracle,ISO 格式被包装在适当的 TO_DATE() 函数调用内。先前,此渲染未针对方言特定编译实现。 另请参阅 DATE、TIME、DATETIME 数据类型现在在所有后端上支持文本渲染 引用: #5052 - [sql] [usecase]
添加了新的参数
HasCTE.add_cte.nest_here
到HasCTE.add_cte()
,该参数将在父语句级别“嵌套”给定的CTE
。该参数等同于使用HasCTE.cte.nesting
参数,但在某些情况下可能更直观,因为它允许同时设置嵌套属性和 CTE 的显式级别。HasCTE.add_cte()
方法还接受多个 CTE 对象。 参考:#7759 - [sql] [bug]
当使用
Select.select_from()
方法在select()
构造上建立 FROM 子句时,这些子句现在将首先在渲染的 SELECT 的 FROM 子句中呈现,这有助于保持子句的顺序,就像它们传递给Select.select_from()
方法本身时一样,而不受这些子句也在查询的其他部分提及的影响。如果Select
的其他元素也生成 FROM 子句,例如列子句或 WHERE 子句,这些将在由Select.select_from()
提供的子句之后呈现,假设它们未明确传递给Select.select_from()
。这一改进在某些情况下非常有用,其中特定数据库基于 FROM 子句的特定顺序生成理想的查询计划,并允许完全控制 FROM 子句的顺序。 参考:#7888 - [sql] [bug]
Enum.length
参数,用于为非本地枚举类型的VARCHAR
列设置长度,在为VARCHAR
数据类型发出 DDL 时现在无条件使用,包括当为目标后端设置了Enum.native_enum
参数为True
时继续使用VARCHAR
的情况。在这种情况下,先前该参数将被错误地忽略。先前为此情况发出的警告现已移除。 参考:#7791 - [sql] [bug]
Python 整数的原地类型检测,如表达式
literal(25)
,现在也将应用基于值的适配,以适应 Python 大整数,其中确定的数据类型将是BigInteger
而不是Integer
。这适用于诸如 asyncpg 之类的方言,其既将隐式类型信息发送给驱动程序,又对数值刻度敏感。 参考:#7909 - [sql] [bug]
为所有“创建”/“删除”结构(包括
CreateSequence
、DropSequence
、CreateIndex
、DropIndex
等)添加了if_exists
和if_not_exists
参数,允许在 DDL 中呈现通用的“IF EXISTS”/“IF NOT EXISTS”短语。感谢 Jesse Bakker 提供的拉取请求。 参考:#7354 - [sql] [bug]
改进了 SQL 二进制表达式的构造,以允许针对相同的关联操作符进行非常长的表达式,而无需特殊步骤以避免高内存使用和过度递归深度。现在,一个特定的二元操作
A op B
可以与另一个元素op C
连接,结果结构将被“平铺”,以使表示以及 SQL 编译不需要递归。 此更改的一个影响是使用 SQL 函数的字符串连接表达式现在变得“平坦”,例如,MySQL 现在将呈现concat('x', 'y', 'z', ...)
而不是将两个元素函数嵌套在一起的concat(concat('x', 'y'), 'z')
。重写字符串连接运算符的第三方方言将需要实现一个新方法def visit_concat_op_expression_clauselist()
,以配合现有的def visit_concat_op_binary()
方法。 参考:#7744 - [sql] [bug]
使用“/”和“//”运算符实现了对“truediv”和“floordiv”的完全支持。
Integer
类型的两个表达式之间的“truediv”操作现在被视为Numeric
类型,并且方言级别的编译将根据方言特定的基础将右操作数转换为数字类型,以确保实现 truediv。对于 floordiv,还添加了转换,对于那些默认情况下不执行 floordiv 的数据库(如 MySQL、Oracle),在这种情况下还会渲染FLOOR()
函数,以及右操作数不是整数的情况(对于 PostgreSQL 等其他数据库也是需要的)。 此更改解决了不同后端上除法运算符行为不一致的问题,并修复了 Oracle 上整数除法无法获取结果的问题,因为输出类型处理程序不合适的问题。 另见 Python 除法运算符对所有后端执行真除法;添加了地板除法 参考:#4926 - [sql] [bug] 在编译器中增加了额外的查找步骤,用于跟踪所有的 FROM 子句,这些子句是表,可能在多个模式中共享具有相同名称的情况,其中一个模式是隐式的“默认”模式;在这种情况下,当在没有模式限定符的情况下引用该名称时,编译器级别将为表名称生成一个匿名别名,以消除两个(或更多)名称的歧义。还考虑了使用服务器检测到的“默认模式名称”值对通常未限定名称进行模式限定的方法,但是这种方法不适用于 Oracle,SQL Server 也不接受,而且不适用于 PostgreSQL 搜索路径中的多个条目。在此解决的名称冲突问题已被确认至少影响到 Oracle、PostgreSQL、SQL Server、MySQL 和 MariaDB。 参考:#7471
- [sql] [bug]
从值的类型确定 SQL 类型的 Python 字符串值,主要是当使用
literal()
时,现在将应用String
类型,而不是Unicode
数据类型,对于使用 Pythonstr.isascii()
测试为“ascii only”的 Python 字符串值。如果字符串不是isascii()
,则将绑定Unicode
数据类型,这在以前所有字符串检测中都使用了。这种行为仅适用于使用literal()
或其他没有现有数据类型的上下文的数据类型的就地检测,通常不适用于正常的Column
比较操作,其中正在比较的Column
的类型始终优先。 在诸如 SQL Server 等后端中,使用Unicode
数据类型可以确定文字字符串的格式化方式,其中文字值(即使用literal_binds
)将呈现为N'<value>'
而不是'value'
。对于常规绑定值处理,Unicode
数据类型还可能对传递值到 DBAPI 产生影响,再次以 SQL Server 为例,pyodbc 驱动程序支持使用 setinputsizes 模式,它将以不同方式处理String
与Unicode
。 参考:#7551 - [sql] [bug]
array_agg
现在将数组维度设置为 1。改进了对ARRAY
的处理,以接受None
值作为多维数组的值。 参考:#7083
架构
- [schema] [feature]
在
ExecutableDDLElement
类(从DDLElement
重命名)实现的“条件 DDL”系统上进行了扩展,直接可用于SchemaItem
构造,如Index
、ForeignKeyConstraint
等,使得用于生成这些元素的条件逻辑包含在默认的 DDL 发射过程中。这个系统也可以被 Alembic 的未来版本支持,以支持所有模式管理系统中的条件 DDL 元素。 另请参阅 新的条件 DDL 用于约束和索引 参考:#7631 - [模式] [用例]
在
DropConstraint
构造中添加了参数DropConstraint.if_exists
,这将导致“IF EXISTS” DDL 被添加到 DROP 语句中。这个短语不被所有数据库接受,如果数据库不支持它,该操作将在一个单独的 DDL 语句的范围内失败,因为在这个范围内没有类似的兼容回退。感谢 Mike Fiedler 的拉取请求。 参考:#8141 - [模式] [用例]
为所有包含不同的 CREATE 或 DROP 步骤的
SchemaItem
对象实现了 DDL 事件钩子DDLEvents.before_create()
、DDLEvents.after_create()
、DDLEvents.before_drop()
、DDLEvents.after_drop()
,当该步骤被调用为一个独立的 SQL 语句时,包括ForeignKeyConstraint
、Sequence
、Index
和 PostgreSQL 的ENUM
。 参考:#8394 - [schema] [performance]
重构了模式反射 API,以允许参与的方言利用高性能的批量查询来一次反射多个表的模式,使用数量级较少的查询。新的性能特性首先针对 PostgreSQL 和 Oracle 后端,可以应用于使用 SELECT 查询反映表的系统目录表的任何方言。该变化还包括对
Inspector
对象的新 API 特性和行为改进,包括像Inspector.has_table()
、Inspector.get_table_names()
等方法的一致、缓存行为,以及新方法Inspector.has_schema()
和Inspector.has_index()
。 另见 数据库反射的主要架构、性能和 API 增强 - 完整背景 参考:#4379 - [schema] [bug]
当使用
Table.include_columns
参数排除后发现仍然是这些约束的一部分的列时,关于索引或唯一约束的反射发出的警告已被移除。当使用Table.include_columns
参数时,应该预期生成的Table
构造将不包括依赖于被省略列的约束。这个变化是对#8100作出的回应,该问题修复了Table.include_columns
与依赖于被省略列的外键约束的一起使用的情况,其中使用案例表明省略此类约束是可以预期的。 参考:#8102 - [schema] [postgresql]
对
Constraint
对象添加了对评论的支持,包括 DDL 和反射;该字段已添加到基本的Constraint
类和相应的构造函数中,但目前只有 PostgreSQL 是支持该功能的后端。请参阅参数,如ForeignKeyConstraint.comment
,UniqueConstraint.comment
或CheckConstraint.comment
。 参考:#5677 - [schema] [mariadb] [mysql]
添加对 MySQL 和 MariaDB 分区和示例页面的支持反映选项。这些选项存储在表方言选项字典中,因此以下关键字需要根据后端添加
mysql_
或mariadb_
前缀。支持的选项包括:-
stats_sample_pages
-
partition_by
-
partitions
-
subpartition_by
当从数据库加载表时,这些选项也会反映出来,并将填充表
Table.dialect_options
。感谢 Ramon Will 的拉取请求。 参考:#4038 -
typing
- [typing] [improvement]
TypeEngine.with_variant()
方法现在返回原始TypeEngine
对象的副本,而不是将其包装在Variant
类中,该类实际上已被移除(导入符号仍保留以向后兼容可能测试此符号的代码)。虽然以前的方法保持了 Python 中的行为,但保持原始类型允许更清晰的类型检查和调试。TypeEngine.with_variant()
还可以在每次调用时接受多个方言名称,特别是对于相关的后端名称,如"mysql", "mariadb"
。 另请参阅 “with_variant()”克隆原始 TypeEngine 而不是更改类型 参考:#6980
postgresql
- [postgresql] [feature]
添加了新的 PostgreSQL
DOMAIN
数据类型,其遵循与 PostgreSQLENUM
相同的 CREATE TYPE / DROP TYPE 行为。非常感谢 David Baumgold 的努力。 另见DOMAIN
参考:#7316 - [postgresql] [usecase] [asyncpg]
添加了可重写方法
PGDialect_asyncpg.setup_asyncpg_json_codec
和PGDialect_asyncpg.setup_asyncpg_jsonb_codec
,用于在使用 asyncpg 时注册这些数据类型所需的 JSON/JSONB 编解码器。变更之处在于将方法拆分为单独的可重写方法,以支持需要修改或禁用这些特定编解码器设置的第三方方言。 此变更还被 回溯 到:1.4.27 参考:#7284 - [postgresql] [usecase]
为
ARRAY
和ARRAY
数据类型添加了文字类型渲染。通用的字符串化将使用方括号进行渲染,例如[1, 2, 3]
,而 PostgreSQL 特定的将使用 ARRAY 文字,例如ARRAY[1, 2, 3]
。还考虑了多维和引号。 参考:#8138 - [postgresql] [usecase]
添加了对 PostgreSQL 多范围类型的支持,该类型引入于 PostgreSQL 14 中。现在已将对 PostgreSQL 范围和多范围的支持概括为 psycopg3、psycopg2 和 asyncpg 后端,并提供了进一步方言支持的空间,使用与以前使用的 psycopg2 对象兼容的后端无关
Range
数据对象。请参阅新文档以了解使用模式。 此外,增强了范围类型处理,以便自动渲染类型转换,因此对于不提供任何上下文的语句的就地往返,不需要为数据库明确指定所需的类型(在 #8540 中讨论)。 非常感谢 @zeeeeeb 提交并测试新数据类型和 psycopg 支持的拉取请求。 另见 PostgreSQL 后端的新 RANGE / MULTIRANGE 支持和变更 范围和多范围类型 参考:#7156, #8540 - [postgresql] [usecase]
配置
create_engine.pool_pre_ping
时发出的“ping”查询,对于 psycopg、asyncpg 和 pg8000,但不适用于 psycopg2,已更改为一个空查询(;
),而不是SELECT 1
;此外,对于 asyncpg 驱动程序,已修复了此查询不必要使用准备语句的问题。其理由是消除 PostgreSQL 在发出 ping 时产生查询计划的需要。当前不支持由psycopg2
驱动程序执行此操作,它继续使用SELECT 1
。 参考:#8491 - [postgresql] [change] SQLAlchemy 现在要求 PostgreSQL 版本为 9 或更高。在某些有限的用例中,旧版本可能仍然可以工作。
- [postgresql] [change] [mssql]
UUID
的参数UUID.as_uuid
,以前专门针对 PostgreSQL 方言,现在已经泛化为 Core(连同一个新的与后端无关的Uuid
数据类型),现在默认为True
,表示此数据类型默认接受 PythonUUID
对象。此外,SQL Server 的UNIQUEIDENTIFIER
数据类型已转换为接收 UUID 的类型;对于使用字符串值的遗留代码,设置UNIQUEIDENTIFIER.as_uuid
参数为False
。 参考:#7225 - [postgresql] [change]
PostgreSQL 特定的
ENUM
数据类型的ENUM.name
参数现在是一个必需的关键字参数。在任何情况下,“name”都是必要的,否则在 SQL/DDL 渲染时会引发错误。 - [postgresql] [change]
支持新的 PostgreSQL 功能,包括 psycopg3 方言以及扩展的“快速插入多个”支持,用于将绑定参数的类型信息传递给 PostgreSQL 数据库的系统已经重新设计,现在使用 SQL 编译器发出的内联转换,并且现在适用于所有 PostgreSQL 方言。这与以前的方法相反,以前的方法依赖于正在使用的 DBAPI 来自行呈现这些转换,例如 pg8000 和适应的 asyncpg 驱动程序的情况下,将使用 pep-249
setinputsizes()
方法,或者对于 psycopg2 驱动程序,在大多数情况下将依赖于驱动程序本身,对于 ARRAY 则会做一些特殊的例外。 现在,所有 PostgreSQL 方言都使用 PostgreSQL 双冒号样式在编译器内呈现这些转换所需的转换,并且对于 PostgreSQL 方言,已删除了使用setinputsizes()
,因为这在任何情况���通常不是这些 DBAPI 的一部分(pg8000 是唯一的例外,它在 SQLAlchemy 开发人员的请求下添加了该方法)。 这种方法的优势包括每个语句的性能,因为在执行时不需要对编译后的语句进行第二次遍历,对所有 DBAPI 的更好支持,因为现在有一个一致的应用类型信息系统,以及改进的透明度,因为 SQL 日志输出以及编译语句的字符串输出将直接显示这些转换存在于语句中,而以前这些转换在日志输出中是不可见的,因为它们会在语句记录后发生。 - [postgresql] [错误]
Operators.match()
运算符现在在 PostgreSQL 全文搜索中使用plainto_tsquery()
,而不是to_tsquery()
。这种更改的理由是为了提供更好的与其他数据库后端上的 match 的跨兼容性。通过与Operators.bool_op()
(布尔运算符的改进版本Operators.op()
)结合使用func
,仍然可以通过使用所有 PostgreSQL 全文函数来获得完全支持。 另请参阅 PostgreSQL 上的 match()运算符使用 plainto_tsquery()而不是 to_tsquery() 参考:#7086 - [postgresql] [已移除]
移除对多个已弃用驱动程序的支持:
- 用于 PostgreSQL 的 pypostgresql。这作为外部驱动程序可在
github.com/PyGreSQL
获得。 - 用于 PostgreSQL 的 pygresql。
请切换到受支持的驱动程序之一或同一驱动程序的外部版本。 参考:#7258
- 用于 PostgreSQL 的 pypostgresql。这作为外部驱动程序可在
- [postgresql] [方言]
添加了对
psycopg
方言的支持,支持同步和异步执行。此方言在create_engine()
和create_async_engine()
引擎创建函数下可用。 另请参阅 对 psycopg 3(又名“psycopg”)的方言支持 psycopg 参考:#6842 - [postgresql] [psycopg2] 更新了 psycopg2 方言,使用 DBAPI 接口执行两阶段事务。以前使用 SQL 命令处理这种类型的事务。 参考:#7238
- [postgresql] [schema]
引入了类型
JSONPATH
,可在转换表达式中使用。在使用诸如jsonb_path_exists
或jsonb_path_match
这样接受jsonpath
作为输入的函数时,某些 PostgreSQL 方言需要这个类型。 另请参阅 JSON 类型 - PostgreSQL JSON 类型。 参考:#8216 - [postgresql] [reflection]
PostgreSQL 方言现在支持基于表达式的索引的反射。在使用
Inspector.get_indexes()
时以及使用Table.autoload_with
反射Table
时都支持反射。感谢 immerrr 和 Aidan Kane 在这个问题上的帮助。 参考:#7442
mysql
- [mysql] [usecase] [mariadb]
ROLLUP
函数现在会在 MySql 和 MariaDB 上正确呈现WITH ROLLUP
,允许在这些后端使用 group by rollup。 参考:#8503 - [mysql] [bug]
修复了 MySQL
Insert.on_duplicate_key_update()
中的问题,当在 VALUES 表达式中使用表达式时,会呈现错误的列名。感谢 Cristian Sabaila 提供的拉取请求。 此更改也 被后移 到:1.4.27 参考:#7281 - [mysql] [removed] 移除了对 OurSQL 驱动程序的支持,该驱动程序不再维护。 参考:#7258
mariadb
- [mariadb] [usecase]
添加了一个新的执行选项
is_delete_using=True
,当使用 ORM 启用的 DELETE 语句与“fetch”同步策略一起使用时,该选项将被消耗;此选项表示预计 DELETE 语句将使用多个表,在 MariaDB 上是 DELETE…USING 语法。然后,该选项指示对于已知不支持“DELETE…USING…RETURNING”语法的数据库,不应使用在 MariaDB 中新实现的 SQLAlchemy 2.0 的 RETURNING(对于#7011)。尽管它们支持“DELETE…USING”,但它们不支持“DELETE…USING…RETURNING”语法,这是 MariaDB 的当前能力。 这个选项的原因是,ORM 启用的 DELETE 当前不知道 DELETE 语句是否针对多个表,直到编译发生,无论如何,编译都会被缓存,但需要知道这一点,以便事先发出用于待删除行的 SELECT。与为了预先检查所有 DELETE 语句以获取这种相对不寻常的 SQL 模式而对所有 DELETE 语句应用全面性能惩罚相比,通过在编译步骤中引发一个新的异常消息来请求is_delete_using=True
执行选项。此异常消息仅在以下情况下特定(且仅)引发:语句是启用了 ORM 的 DELETE,已请求“fetch”同步策略;后端是 MariaDB 或具有此特定限制的其他后端;已检测到初始编译中的语句,否则会发出“DELETE…USING…RETURNING”。通过应用执行选项,ORM 知道要首先运行一个 SELECT。ORM 启用的 UPDATE 也实现了类似的选项,但目前还没有需要它的后端。 参考:#8344 - [mariadb] [用例] 为 MariaDB 方言添加了 INSERT…RETURNING 和 DELETE…RETURNING 支持。UPDATE…RETURNING 尚未得到 MariaDB 的支持。从 10.5.0 开始,MariaDB 支持 INSERT…RETURNING,从 10.0.5 开始,支持 DELETE…RETURNING。 参考:#7011
sqlite
- [sqlite] [用例]
为 SQLite 的反射方法添加了一个名为
sqlite_include_internal=True
的新参数;当省略时,以sqlite_
为前缀的本地表(根据 SQLite 文档,这些表被称为“内部模式”表,例如生成以支持“AUTOINCREMENT”列的sqlite_sequence
表),不会包含在返回本地对象列表的反射方法中。这样可以避免在使用 Alembic 自动生成时出现问题,以前会将这些由 SQLite 生成的表视为从模型中移除。 另请参阅 反射内部模式表 参考:#8234 - [sqlite] [用例] 为 SQLite 方言添加了 RETURNING 支持。自 SQLite 版本 3.35 起,SQLite 支持 RETURNING。 参考:#6195
- [sqlite] [用例]
SQLite 方言现在支持 UPDATE…FROM 语法,用于 UPDATE 语句可能在语句的 WHERE 条件中引用其他表而无需使用子查询。当使用
Update
构造时,当使用多个表或其他实体或可选择时,此语法会自动调用。 参考:#7185 - [sqlite] [性能] [bug]
当使用基于文件的数据库时,SQLite 方言现在默认使用
QueuePool
。这是与将check_same_thread
参数设置为False
一起设置的。已经观察到,默认使用NullPool
的先前方法,在释放数据库连接后不会保留连接,实际上会对性能产生可衡量的负面影响。如常,通过create_engine.poolclass
参数可以自定义池类。 参见 SQLite 方言为基于文件的数据库使用 QueuePool 参考:#7490 - [sqlite] [性能] [用例]
SQLite 的 datetime、date 和 time 数据类型现在使用 Python 标准库的
fromisoformat()
方法来解析传入的 datetime、date 和 time 字符串值。这比以前基于正则表达式的方法提高了性能,还自动适应包含六位“微秒”格式或三位“毫秒”格式的 datetime 和 time 格式。 参考:#7029 - [sqlite] [bug]
移除了关于
Numeric
类型发出的关于 DBAPI 不原生支持 Decimal 值的警告。这个警告是针对 SQLite 的,因为 SQLite 没有任何真正的方法(除非使用额外的扩展或解决方法)来处理超过 15 个有效数字的精度数值,因为它只使用浮点数来表示数字。由于这是 SQLite 本身已知且有文档记录的限制,而不是 pysqlite 驱动程序的怪癖,因此 SQLAlchemy 不需要为此发出警告。这个更改不会修改精度数值的处理方式。值可以继续按照Numeric
、Float
和相关数据类型配置为Decimal()
或float()
,只是在使用 SQLite 时无法保持超过 15 个有效数字的精度,除非使用字符串等替代表示方法。 参考:#7299
mssql
- [mssql] [用例]
实现了 SQL Server 方言的“clustered index” 标志
mssql_clustered
的反射。感谢 John Lennox 提供的拉取请求。 参考:#8288 - [mssql] [用例] 在创建表时,为 MSSQL 添加了对表和列注释的支持。添加了反射表注释的支持。感谢 Daniel Hall 在此拉取请求中的帮助。 参考:#7844
- [mssql] [错误]
mssql pyodbc
方言的use_setinputsizes
参数现在默认为True
;这样非 Unicode 字符串比较将由 pyodbc 绑定到 pyodbc.SQL_VARCHAR 而不是 pyodbc.SQL_WVARCHAR,从而使得对 VARCHAR 列的索引生效。为了让fast_executemany=True
参数继续正常工作,use_setinputsizes
模式现在在fast_executemany
为 True 且使用的具体方法是cursor.executemany()
时会跳过cursor.setinputsizes()
调用,因为该方法不支持 setinputsizes。此更改还为被标记为Unicode
或UnicodeText
的值添加了适当的 pyodbc DBAPI 类型,并将基础的JSON
数据类型修改为将 JSON 字符串值视为Unicode
而不是String
。 参考:#8177 - [mssql] [已移除] 由于缺乏测试支持,已移除对 mxodbc 驱动程序的支持。ODBC 用户可以使用完全受支持的 pyodbc 方言。 参考:#7258
oracle
- [oracle] [feature]
添加对新的 Oracle 驱动程序
oracledb
的支持。 另请参阅 对 oracledb 的方言支持 python-oracledb 参考:#8054 - [oracle] [feature]
实现了
FLOAT
数据类型的 DDL 和反射支持,其中包括显式的“binary_precision”值。使用特定于 Oracle 的FLOAT
数据类型,可以指定新参数FLOAT.binary_precision
,这将直接呈现 Oracle 的浮点类型精度。此值在反射期间解释。在反射回FLOAT
数据类型时,返回的数据类型是DOUBLE_PRECISION
(对于精度为 126 的FLOAT
,这也是 Oracle 的默认精度)、REAL
(对于精度为 63)、以及FLOAT
(对于自定义精度,按照 Oracle 文档)。 作为这一变更的一部分,当为 Oracle 生成 DDL 时,明确拒绝了通用的Float.precision
值,因为此精度无法准确转换为“二进制精度”;相反,错误消息鼓励使用TypeEngine.with_variant()
,以便精确选择 Oracle 的特定精度形式。这是一种与以往行为不兼容的更改,因为以前的“精度”值对于 Oracle 被静默地忽略。 另请参阅 新的 Oracle FLOAT 类型,具有二进制精度;不直接接受十进制精度 参考:#5465 - [oracle] [feature]
对于 cx_Oracle 方言,完全实现了“RETURNING”支持,涵盖了两种个别功能:
- 实现了多行 RETURNING,意味着对于产生多于一个 RETURNING 行的 DML 语句,现在将收到多个 RETURNING 行。
- “executemany RETURNING” 也已实现 - 这允许当使用
cursor.executemany()
时,RETURNING 每个语句产生一行。这一特性的实现为 ORM 插入提供了显著的性能改进,就像 SQLAlchemy 1.4 变更 ORM Batch inserts with psycopg2 now batch statements with RETURNING in most cases 中为 psycopg2 添加的一样。
参考:#6245
- [oracle] [用例]
Oracle 现在将在 Oracle 12c 及以上版本中默认使用 FETCH FIRST N ROWS / OFFSET 语法来支持 limit/offset。当直接使用
Select.fetch()
时,该语法已经可用,现在对Select.limit()
和Select.offset()
也适用。 参考:#8221 - [oracle] [更改]
在 Oracle 上,物化视图现在被反映为视图。在之前的 SQLAlchemy 版本中,视图会在表名中返回,而不在视图名中返回。由于此更改的副作用,默认情况下它们不会被
MetaData.reflect()
反映,除非设置了views=True
。要获取物化视图列表,请使用新的检查方法Inspector.get_materialized_view_names()
。 - [oracle] [错误] 对 cx_Oracle 和 oracledb 方言中的 BLOB / CLOB / NCLOB 数据类型进行了调整,以根据 Oracle 开发人员的建议改善性能。 参考:#7494
- [oracle] [错误]
关于
create_engine.implicit_returning
弃用的相关内容,现在 “implicit_returning” 特性在所有情况下都为 Oracle 方言启用;以前,当检测到 Oracle 8/8i 版本时,该特性会被关闭,然而在线文档显示这两个版本都支持与现代版本相同的 RETURNING 语法。 参考:#6962 - [oracle] cx_Oracle 7 现在是 cx_Oracle 的最低版本。
杂项
- [已移除] [sybase] 删除了在之前的 SQLAlchemy 版本中已弃用的 “sybase” 内部方言。第三方方言支持可用。 另请参阅 外部方言 参考:#7258
- [已移除] [firebird] 移除了在以前的 SQLAlchemy 版本中已弃用的“firebird”内部方言。第三方方言支持可用。 另请参阅 外部方言 参考:#7258
2.0.30
无发布日期
orm
- [orm] [bug]
添加了新属性
ORMExecuteState.is_from_statement
,用于检测形式为select().from_statement()
的语句,并增强了FromStatement
以根据发送到Select.from_statement()
方法本身的元素设置ORMExecuteState.is_select
、ORMExecuteState.is_insert
、ORMExecuteState.is_update
和ORMExecuteState.is_delete
。 参考:#11220
引擎
- [engine] [bug]
修复了
Connection.execution_options.logging_token
选项中的问题,其中更改已经记录了消息的连接的logging_token
值不会更新以反映新的记录令牌。特别是这阻止了使用Session.connection()
在连接上更改选项,因为 BEGIN 记录消息已经被发出。 参考:#11210
typing
- [typing] [bug] [regression]
修复了在版本 2.0.29 中由 PR #11055引起的输入退化,该版本尝试将
ParamSpec
添加到 asynciorun_sync()
方法中,其中使用AsyncConnection.run_sync()
与MetaData.reflect()
将由于 bug 在 mypy 上失败。有关详细信息,请参见github.com/python/mypy/issues/17093
。Pull request 由 Francisco R. Del Roio 提供。 参考:#11200
杂项
- [bug] [test]
在测试中使用
subprocess.run
时,请确保PYTHONPATH
变量正确初始化。 参考:#11268
orm
- [orm] [bug]
添加了新属性
ORMExecuteState.is_from_statement
,用于检测形式为select().from_statement()
的语句,并增强了FromStatement
以根据发送到Select.from_statement()
方法本身的元素设置ORMExecuteState.is_select
、ORMExecuteState.is_insert
、ORMExecuteState.is_update
和ORMExecuteState.is_delete
。 参考:#11220
engine
- [engine] [bug]
修复了
Connection.execution_options.logging_token
选项中的问题,其中在已经记录了消息的连接上更改logging_token
的值不会更新以反映新的日志令牌。特别是这阻止了使用Session.connection()
在连接上更改选项,因为 BEGIN 日志消息已经被发出。 参考:#11210
typing
- [typing] [bug] [regression]
修复了由版本 2.0.29 中 PR #11055引起的类型回归,该 PR 试图将
ParamSpec
添加到 asynciorun_sync()
方法中,其中在 mypy 上使用AsyncConnection.run_sync()
与MetaData.reflect()
会由于错误而在 mypy 上失败。有关详细信息,请参见github.com/python/mypy/issues/17093
。感谢 Francisco R. Del Roio 提供的拉取请求。 参考:#11200
misc
- [bug] [test]
在测试中使用
subprocess.run
时,请确保PYTHONPATH
变量正确初始化。 参考:#11268
2.0.29
发布日期:2024 年 3 月 23 日
orm
- [orm] [usecase]
添加了对PEP 695
TypeAliasType
构造的支持,以及与 python 3.12 本地type
关键字配合使用 ORM 注释声明形式时,当使用这些构造将链接到 PEP 593Annotated
容器时,允许解析Annotated
的过程。 参考文献:#11130 - [orm] [bug]
修复了声明性问题,其中使用
Relationship
而不是Mapped
来对关系进行类型化,会无意中为该属性引入“动态”关系加载器策略。 参考文献:#10611 - [orm] [bug]
修复了在 ORM 注释声明中使用
mapped_column()
时出现的问题,其中使用mapped_column.index
或mapped_column.unique
设置为False
的情况将被一个具有该参数设置为True
的传入Annotated
元素覆盖,即使直接mapped_column()
元素更具体且应该优先。增强了协调布尔值的逻辑,以适应本地值为False
仍优先于来自注释元素的传入True
值的情况。 参考文献:#11091 - [orm] [bug] [regression]
修复了从版本 2.0.28 引入的回归,该回归是由于修复了#11085中新方法调整后缓存的参数值,该方法会干扰到
subqueryload()
加载器选项的实现,当使用此加载器选项与此加载器选项一起使用时,会使用一些更多的旧模式。 参考文献:#11173
engine
- [engine] [bug]
修复了“INSERT 语句的“Insert Many Values”行为功能中的问题,其中使用具有“内联执行”默认生成器的主键列,例如显式
Sequence
和显式架构名称,同时使用Connection.execution_options.schema_translate_map
功能将无法正确呈现序列或参数,导致错误。 参考:#11157 - [engine] [错误] 在版本 2.0.10 中对#9618所做的调整进行了更改,该版本添加了批量 INSERT 的 RETURNING 行协调到传递给它的参数的行为。此行为包括已转换为 DB 的绑定参数值与返回的行值的比较,并不总是对于 SQL 列类型(例如 UUID)“对称”,具体取决于不同 DBAPI 接收此类值的方式与它们返回的方式,因此需要在这些列类型上增加额外的“哨兵值解析器”方法。不幸的是,这破坏了第三方列类型,如 SQLModel 中未实现此特殊方法的 UUID/GUID 类型,引发了错误“无法将结果集中的哨兵值与参数集匹配”。与其尝试进一步解释和文档化此“insertmanyvalues”特性的实现细节,包括新方法的公共版本,不如修改方法以不再需要此额外的转换步骤,并且进行比较的逻辑现在作用于预转换的绑定参数值与后处理值相比,后者应始终是匹配的数据类型。在罕见情况下,如果自定义 SQL 列类型也恰好用于批量 INSERT 的“哨兵”列,并且未接收和返回相同的值类型,则将引发“无法匹配”错误,但是缓解方法很简单,即传递与返回的相同 Python 数据类型。 参考:#11160
sql
- [sql] [错误] [回归]
修复了 1.4 系列中的回归问题,在
TypeEngine.with_variant()
方法的重构中引入的问题,该方法在 “with_variant()” 克隆原始 TypeEngine 而不是更改类型 中未能考虑到.copy()
方法,这将丢失设置的变体映射。对于“schema”类型的非常特定情况,这会成为一个问题,其中包括Enum
和ARRAY
等类型,当它们在 ORM Declarative 映射中与 mixin 一起使用时,类型的复制就会发挥作用。现在也复制了变体映射。 参考:#11176
typing
- [typing] [bug]
修复了允许 asyncio 的
run_sync()
方法正确对参数进行类型标记的问题,根据传递的可调用对象使用 PEP 612ParamSpec
变量。感谢 Francisco R. Del Roio 提供的拉取请求。 参考:#11055
postgresql
- [postgresql] [usecase]
PostgreSQL 方言现在在反射具有域作为类型的列时返回
DOMAIN
实例。之前,返回的是域数据类型。作为此更改的一部分,改进了域反射以同时返回文本类型的排序规则。感谢 Thomas Stephenson 提供的拉取请求。 参考:#10693
测试
- [tests] [bug]
已将改进后的测试套件应用于 SQLAlchemy 2.0,改进了与 asyncio 相关的测试运行方式,现在使用更新的 Python 3.11
asyncio.Runner
或其等价物,而不是依赖于先前基于asyncio.get_running_loop()
的实现。这应该能够在 CPU 负载硬件上运行大量套件时防止事件循环出现故障,导致级联失败。 参考:#11187
orm
- [orm] [usecase]
增加了对 PEP 695
TypeAliasType
构造的支持,以及与 Python 3.12 本地type
关键字一起使用 ORM Annotated Declarative 形式时的支持,当使用这些构造链接到 PEP 593Annotated
容器时,允许解析Annotated
时继续进行。 参考:#11130 - [orm] [bug]
修复了声明式中的问题,其中使用
Relationship
而不是Mapped
来定义关系会无意中引入该属性的“动态”关系加载器策略。 引用:#10611 - [orm] [bug]
修复了使用 ORM 注释的声明式时,使用带有
mapped_column.index
或mapped_column.unique
设置为 False 的mapped_column()
会被传入的Annotated
元素覆盖,即使直接的mapped_column()
元素更具体且应该优先。调解布尔值的逻辑已经得到增强,以适应本地值为False
的情况,仍然优先于注释元素传入的True
值。 引用:#11091 - [orm] [bug] [regression]
修复了从版本 2.0.28 开始由于对#11085的修复而引起的回归,新的方法调整后缓存的参数值会干扰
subqueryload()
加载器选项的实现,当使用额外的加载器条件特性与此加载器选项一起使用时,内部使用了一些更传统的模式。 引用:#11173
engine
- [engine] [bug]
修复了在 “Insert Many Values” Behavior for INSERT statements 功能中的问题,其中使用主键列与“内联执行”默认生成器(如显式的
Sequence
并带有显式模式名称),同时使用Connection.execution_options.schema_translate_map
功能将无法正确渲染序列或参数,导致错误。 引用:#11157 - [engine] [bug] 对版本 2.0.10 中对 #9618 进行的调整进行了更改,该版本增加了从批量插入中协调 RETURNING 行到传递给它的参数的行为。此行为包括将已经转换为数据库绑定参数值与返回的行值进行比较,对于 SQL 列类型如 UUID,不同的 DBAPI 接收这些值的方式与它们返回的方式具体取决于细节,因此需要对这些列类型进行额外的“哨兵值解析器”方法。不幸的是,这破坏了第三方列类型,如 SQLModel 中没有实现此特殊方法的 UUID/GUID 类型,引发错误“无法将结果集中的哨兵值与参数集匹配”。与其尝试进一步解释和文档化“insertmanyvalues”功能的这一实现细节,包括新方法的公共版本,不如将方法改进为不再需要这个额外的转换步骤,现在进行比较的逻辑是对预先转换的绑定参数值与后处理的值进行比较,后者应始终是匹配的数据类型。在不寻常的情况下,如果一个自定义的 SQL 列类型也碰巧用作批量插入的“哨兵”列,并且不接收和返回相同的值类型,将引发“无法匹配”错误,但是减轻措施很简单,应传递与返回相同的 Python 数据类型。 参考:#11160
sql
- [sql] [错误] [回归]
修复了 1.4 系列中的回归,该系列中对
TypeEngine.with_variant()
方法的重构,引入了“with_variant()”克隆原始 TypeEngine 而不是更改类型,未能适应.copy()
方法,这将丢失设置的变体映射。对于非常特定的“模式”类型,这成为问题,该类型包括在 ORM Declarative 映射中与混合使用时的类型,其中类型的复制变得重要。现在也复制了变体映射。 参考:#11176
输入
- [输入] [错误]
修复了允许 asyncio
run_sync()
方法正确对参数进行类型标记的输入问题,根据传递的可调用对象,使用了PEP 612ParamSpec
变量。感谢 Francisco R. Del Roio 提交的拉取请求。 参考:#11055
postgresql
- [postgresql] [用例]
当反射一个具有域类型的列时,PostgreSQL 方言现在返回
DOMAIN
实例。以前,会返回域数据类型。作为这一改变的一部分,域反射还改进了以返回文本类型的排序规则。感谢 Thomas Stephenson 提交的拉取请求。 参考:#10693
测试
- [tests] [bug]
对于与 asyncio 相关的测试,对 SQLAlchemy 2.0 进行了改进,现在使用了更新的 Python 3.11
asyncio.Runner
或等价的后移版,而不是依赖于基于asyncio.get_running_loop()
的先前实现。这样做希望能够防止在 CPU 负载硬件上运行大量测试时出现问题,其中事件循环似乎会变得损坏,导致级联故障。 参考:#11187
2.0.28
发布日期:2024 年 3 月 4 日
orm
- [orm] [performance] [bug] [regression]
调整了在 2.0.23 版中发布的 #10570 中进行的修复,其中添加了新逻辑来协调可能在
with_expression()
构造中使用的缓存键生成过程中可能变化的绑定参数值。新逻辑改变了将新绑定参数值与语句关联的方法,避免了需要深度复制语句的情况,这可能会对非常深/复杂的 SQL 构造造成显著的性能损耗。新方法不再需要这个深复制步骤。 参考:#11085 - [orm] [bug] [regression]
修复了由 #9779 引起的回归,其中在关系的
and_()
表达式中使用“secondary”表会失败,无法将其别名为与Select.join()
表达式中“secondary”表的正常渲染相匹配,导致查询无效。 参考:#11010
引擎
- [engine] [usecase]
添加了新的核心执行选项
Connection.execution_options.preserve_rowcount
。设置后,DBAPI 游标的cursor.rowcount
属性将在语句执行时无条件地被记忆化,因此无论 DBAPI 为任何类型的语句提供的值是什么,都可以使用CursorResult.rowcount
属性从CursorResult
中获取。这允许访问像 INSERT 和 SELECT 这样的语句的 rowcount,程度取决于所使用的 DBAPI 的支持。INSERT
语句的“插入多个值”行为也支持此选项,并在设置时将确保为批量插入行时正确设置CursorResult.rowcount
。 参考:#10974
asyncio
- [asyncio] [错误]
如果将
QueuePool
或其他非异步池类传递给create_async_engine()
,则会引发错误。此引擎仅接受包括AsyncAdaptedQueuePool
在内的符合 asyncio 的池类。其他池类,如NullPool
,与同步和异步引擎兼容,因为它们不执行任何锁定。 另请参阅 API 文档 - 可用的池实现 参考:#8771
测试
- [测试] [更改] tox.ini 文件中的 pytest 支持已更新以支持 pytest 8.1。
orm
- [orm] [性能] [错误] [回归]
调整了在#10570中进行的修复,发布于 2.0.23,其中添加了新逻辑,用于协调可能在
with_expression()
构造中使用的缓存键生成过程中可能更改的绑定参数值。新逻辑改变了将新绑定参数值与语句关联的方法,避免了需要深度复制语句的需求,这可能会对非常深/复杂的 SQL 结构造成显著的性能损耗。新方法不再需要这个深度复制步骤。 参考:#11085 - [orm] [bug] [regression]
修复了由 #9779 引起的回归问题,其中在关系
and_()
表达式中使用 “secondary” 表会无法被别名化,以匹配 “secondary” 表在Select.join()
表达式中通常的呈现方式,导致查询无效。 参考:#11010
engine
- [engine] [usecase]
添加了新的核心执行选项
Connection.execution_options.preserve_rowcount
。当设置时,DBAPI 游标的cursor.rowcount
属性将在语句执行时无条件地被存储,以便无论语句的任何种类,都可以使用CursorResult.rowcount
属性从CursorResult
获取 DBAPI 提供的任何值。这允许访问像 INSERT 和 SELECT 这样的语句的 rowcount,以 DBAPI 使用的程度支持。“INSERT 语句的插入多个值”行为 也支持此选项,并将确保在设置时对行进行批量插入时正确设置CursorResult.rowcount
。 参考:#10974
asyncio
- [asyncio] [bug]
如果将
QueuePool
或其他非 asyncio 连接池类传递给create_async_engine()
,则会引发错误。此引擎仅接受与 asyncio 兼容的连接池类,包括AsyncAdaptedQueuePool
。其他连接池类,如NullPool
,与同步和异步引擎均兼容,因为它们不执行任何锁定。 另请参见 API 文档 - 可用的连接池实现 参考:#8771
测试
- [tests] [change] tox.ini 文件中的 pytest 支持已更新以支持 pytest 8.1。
2.0.27
发布日期:2024 年 2 月 13 日
postgresql
- [postgresql] [bug] [regression] 由于刚发布的修复导致的回归,修复了#10863中一个无效的异常类被添加到“except”块的问题,除非确实发生了这样的捕获,否则不会被执行。已添加了一个模拟式测试以确保这种捕获在单元测试中被执行。 参考:#11005
postgresql
- [postgresql] [bug] [regression] 由于刚发布的修复导致的回归,修复了#10863中一个无效的异常类被添加到“except”块的问题,除非确实发生了这样的捕获,否则不会被执行。已添加了一个模拟式测试以确保这种捕获在单元测试中被执行。 参考:#11005
2.0.26
发布日期:2024 年 2 月 11 日
orm
- [orm] [bug] 使用缓存徽章替换了“加载器深度过深”的警告,对于 ORM 由于加载器选项链过于深而禁用缓存的那些语句,向 SQL 日志中添加了一个较短的消息。此警告突出显示的条件难以解决,并且通常只是 ORM 在应用 SQL 缓存时的限制。未来的功能可能包括调整禁用缓存的阈值的能力,但目前这个警告将不再是一个麻烦。 参考:#10896
- [orm] [bug]
修复了一个问题,即如果该类型在类体内部局部声明,则无法在
Mapped
容器类型中使用类型(例如枚举)。现在,用于评估的本地变量范围包括类体本身的范围。此外,如果以字符串形式或使用将来的注释模式,Mapped
中的表达式也可以引用类名本身。 参考:#10899 - [orm] [bug]
修复了一个问题,即在使用
Session.delete()
与Mapper.version_id_col
功能时,如果由于对象上的relationship.post_update
的使用导致针对目标对象的附加 UPDATE,则使用正确的版本标识符将失败。这个问题类似于版本 2.0.25 中刚刚修复的 #10800 的情况,仅对更新情况进行了修复。 参考:#10967 - [orm] [bug]
修复了在实现
with_expression()
时,如果使用不可缓存的 SQL 表达式,则会引发断言错误的问题;这是自 1.4 以来的 2.0 回归。 参考:#10990
examples
- [examples] [bug]
修复了历史元示例中的回归,使用
MetaData.to_metadata()
复制历史表时也会复制索引(这是一件好事),但无论用于这些索引的命名方案如何,都会导致索引命名冲突。现在这些索引都添加了“_history”后缀,方式与表名相同。 参考:#10920 - [examples] [bug]
通过在所有表中添加
Identity
构造,并允许在此后端上进行主键生成,修复了 examples/performance 中性能示例脚本在 Oracle 数据库中大部分情况下的运行问题。仍有一些“原始 DBAPI”情况与 Oracle 不兼容。
sql
- [sql] [bug]
修复了
case()
中确定表达式类型的逻辑问题,可能导致如果“whens”中的最后一个元素没有类型,则结果为NullType
,或者在其他情况下,类型可能解析为None
。逻辑已更新为扫描所有给定表达式,以便使用第一个非空类型,并始终确保存在类型。拉取请求由 David Evans 提供。 参考:#10843
typing
- [typing] [bug]
修复了
PoolEvents.checkin()
事件的类型签名,指示给定的DBAPIConnection
参数在连接被无效化的情况下可能为None
。
postgresql
- [postgresql] [usecase] [reflection]
添加了对带有“NO INHERIT”标记的 PostgreSQL CHECK 约束的反射支持,设置反射数据中的关键字
no_inherit=True
。拉取请求由 Ellis Valentiner 提供。 参考:#10777 - [postgresql] [usecase]
支持 PostgreSQL
CREATE TABLE
的USING <method>
选项,以指定用于存储新表内容的访问方法。拉取请求由 Edgar Ramírez-Mondragón 提供。 另请参阅 PostgreSQL 表选项 参考:#10904 - [postgresql] [usecase]
正确地将 PostgreSQL 的 RANGE 和 MULTIRANGE 类型类型化为
Range[T]
和Sequence[Range[T]]
。引入了实用序列MultiRange
,以便更好地支持 MULTIRANGE 类型的互操作性。 参考:#9736 - [postgresql] [usecase]
在从
Range
或MultiRange
实例推断数据库类型时,区分 INT4 和 INT8 范围和多范围类型,如果值适合 INT4,则优先选择 INT4。 - [postgresql] [bug] [regression]
在发布 2.0.24 版本中由于 #10717 导致 asyncpg 方言中的回归问题,现在尝试在终止之前优雅地关闭 asyncpg 连接的更改不会对除超时错误之外的其他潜在连接相关异常回退到
terminate()
,没有考虑到优雅的.close()
尝试由于其他原因(如连接错误)失败的情况。 参考:#10863 - [postgresql] [bug]
修复了在使用 PostgreSQL 方言时,使用
Uuid
数据类型且将Uuid.as_uuid
参数设置为 False 时出现的问题,ORM 优化的 INSERT 语句(例如“insertmanyvalues”功能)将无法正确对齐批量 INSERT 语句的主键 UUID 值,导致错误。类似的问题也已经为 pymssql 驱动程序修复。
mysql
- [mysql] [bug] 修复了在 MySQL 列中未正确反映 NULL/NOT NULL 的问题,该列还指定了 VIRTUAL 或 STORED 指令。感谢 Georg Wicke-Arndt 的拉取请求。 参考:#10850
- [mysql] [bug]
修复了 asyncio 方言 asyncmy 和 aiomysql 中的问题,其中它们的
.close()
方法显然不是一个优雅的关闭。替换为非标准的.ensure_closed()
方法,该方法是可等待的,并将.close()
移动到所谓的“终止”情况。 参考:#10893
mssql
- [mssql] [bug]
修复了在使用 pymssql 方言时,当使用
Uuid
数据类型且Uuid.as_uuid
参数设置为 False 时的问题。ORM 优化的 INSERT 语句(例如“insertmanyvalues”功能)将无法正确对齐用于批量 INSERT 语句的主键 UUID 值,导致错误。类似的问题也已针对 PostgreSQL 驱动程序进行了修复。
oracle
- [oracle] [performance] [bug] 更改了 Oracle 方言的默认 arraysize,以使用驱动程序设置的值,即在撰写本文时,cx_oracle 和 oracledb 均为 100。以前默认值为 50。将值设置为 50 可能会导致与仅使用 cx_oracle/oracledb 在较慢的网络上获取许多行时相比,性能显着下降。 参考:#10877
orm
- [orm] [bug] 用更短的消息替换了“加载器深度过深”的警告,该消息添加到 SQL 日志中的缓存徽章中,对于那些由于 ORM 禁用缓存而导致的加载器选项链过深的语句。此警告突出显示的条件很难解决,通常只是 ORM 在应用 SQL 缓存时的一个限制。未来的功能可能包括调整禁用缓存的阈值的能力,但目前该警告将不再成为一个麻烦。 参考:#10896
- [orm] [bug]
修复了在类体内部声明本地类型(例如枚举)时无法在
Mapped
容器类型中使用该类型的问题。现在,用于 eval 的本地变量范围包括类体本身。此外,Mapped
中的表达式也可以引用类名本身,如果作为字符串或使用未来注释模式。 参考:#10899 - [orm] [bug]
修复了使用
Session.delete()
与Mapper.version_id_col
功能一起时,如果由于对象上的relationship.post_update
的使用导致针对目标对象发出额外的 UPDATE,则会失败使用正确的版本标识符的问题。该问题类似于#10800,只是在仅有更新的情况下在版本 2.0.25 中修复了。 参考:#10967 - [orm] [错误]
修复了在
with_expression()
实现中,如果使用的 SQL 表达式不可缓存,则会引发断言错误的问题;这是自 1.4 版以来的 2.0 版本的退化。 参考:#10990
示例
- [示例] [错误]
修复了 history_meta 示例中的退化问题,其中使用
MetaData.to_metadata()
来复制历史表也会复制索引(这是好事),但无论使用的索引命名方案如何,都会导致索引命名冲突。现在为这些索引添加了“_history”后缀,方式与为表名添加后缀相同。 参考:#10920 - [示例] [错误]
通过向所有表添加
Identity
结构并允许主键在此后端上生成,修复了 examples/performance 中性能示例脚本在 Oracle 数据库中的大部分兼容性问题。一些“原始 DBAPI” 情况仍不兼容 Oracle。
sql
- [sql] [错误]
修正了
case()
中确定表达式类型的逻辑问题,如果“whens”中的最后一个元素没有类型或在其他情况下类型可能解析为None
,则可能导致NullType
。逻辑已更新以扫描所有给定表达式,以使用第一个非空类型,并始终确保存在类型。感谢 David Evans 提交的拉取请求。 参考:#10843
类型
- [类型] [错误]
修正了
PoolEvents.checkin()
事件的类型签名,指示给定的DBAPIConnection
参数在连接被失效的情况下可能为None
。
postgresql
- [postgresql] [用例] [反射]
增加了对 PostgreSQL CHECK 约束的反射支持,标记为“NO INHERIT”,在反射数据中设置键
no_inherit=True
。感谢 Ellis Valentiner 提交的拉取请求。 参考:#10777 - [postgresql] [用例]
为了支持 PostgreSQL 的
CREATE TABLE
中的USING <method>
选项,以指定用于存储新表内容的访问方法。感谢 Edgar Ramírez-Mondragón 提交的拉取请求。 另请参阅 PostgreSQL 表选项 参考:#10904 - [postgresql] [usecase]
正确地将 PostgreSQL RANGE 和 MULTIRANGE 类型类型化为
Range[T]
和Sequence[Range[T]]
。引入了实用程序序列MultiRange
,以更好地支持 MULTIRANGE 类型的互操作性。 参考:#9736 - [postgresql] [usecase]
当从
Range
或MultiRange
实例推断数据库类型时,区分 INT4 和 INT8 范围和多范围类型,如果值适合 INT4,则优先使用 INT4。 - [postgresql] [bug] [regression]
在 2.0.24 版本中由于#10717导致的 asyncpg 方言中的回归问题修复,该变更现在在终止之前尝试优雅地关闭 asyncpg 连接,不会为除超时错误之外的其他潜在连接相关异常回退到
terminate()
,没有考虑到当优雅的.close()
尝试由于其他原因(如连接错误)失败时的情况。 参考:#10863 - [postgresql] [bug]
修复了在使用 PostgreSQL 方言时,当使用
Uuid
数据类型且Uuid.as_uuid
参数设置为 False 时的问题。ORM 优化的 INSERT 语句(例如“insertmanyvalues”功能)不会正确对齐批量 INSERT 语句的主键 UUID 值,导致错误。pymssql 驱动程序也修复了类似的问题。
mysql
- [mysql] [bug] 修复了一个问题,即当 MySQL 列还指定了 VIRTUAL 或 STORED 指令时,NULL/NOT NULL 未能正确反映。感谢 Georg Wicke-Arndt 的拉取请求。 参考:#10850
- [mysql] [bug]
修复了 asyncio 方言 asyncmy 和 aiomysql 中的一个问题,即它们的
.close()
方法显然不是一个优雅的关闭。将其替换为非标准的.ensure_closed()
方法,该方法可等待,并将.close()
移到所谓的“终止”情况。 参考:#10893
mssql
- [mssql] [bug]
修复了使用
Uuid
数据类型以及设置Uuid.as_uuid
参数为 False 时的问题,当使用 pymssql 方言时,ORM 优化的 INSERT 语句(例如“insertmanyvalues”功能)将不正确地对齐批量 INSERT 语句的主键 UUID 值,导致错误。类似的问题也已在 PostgreSQL 驱动程序中修复。
oracle
- [oracle] [performance] [bug] 更改了 Oracle 方言的默认 arraysize,以使用驱动程序设置的值,在撰写本文时,cx_oracle 和 oracledb 的值均为 100。先前,默认值设置为 50。默认值为 50 可能导致与仅使用 cx_oracle/oracledb 在较慢的网络上获取数百行时相比出现显着的性能回退。 参考:#10877
2.0.25
发布日期:2024 年 1 月 2 日
orm
- [orm] [usecase] 添加了对 Python 3.12 pep-695 类型别名结构的初步支持,用于解析 ORM 注释声明映射的自定义类型映射。 参考:#10807
- [orm] [bug]
修复了在同时使用
relationship.post_update
特性和使用映射器 version_id_col 时可能导致第二个 UPDATE 语句未能使用正确的版本标识符的问题,假设在该 flush 中已经发出了一个已经增加了版本计数器的 UPDATE。 参考:#10800 - [orm] [bug] 修复了 ORM 注释声明会错误解释没有指定集合为 uselist=True 的关系左侧的问题,如果左侧类型被给定为类而不是字符串,并且没有使用 future-style 注释。 参考:#10815
sql
- [sql] [bug]
在布尔比较的否定情况下改进了
any_()
/all_()
的编译,现在将呈现NOT (expr)
而不是将等式操作符反转为不等号,允许对这些非典型操作符进行更精细的否定控制。 参考:#10817
typing
- [typing] [bug]
修复了在版本 2.0.24 中向
sqlalchemy.sql.functions
模块添加了类型后引起的回归问题,作为#6810的一部分:- 进一步增强了 pep-484 类型提示,以便从
sqlalchemy.sql.expression.func
派生的元素更有效地与 ORM 映射属性一起使用(#10801) - 修复了传递给函数的参数类型,以便再次正确解释文本表达式,如字符串和整数(#10818)
引用:#10801,#10818
- 进一步增强了 pep-484 类型提示,以便从
asyncio
- [asyncio] [错误]
修复了 asyncio 版本的连接池中的关键问题,调用
AsyncEngine.dispose()
会生成一个新的连接池,该连接池未完全重新建立对 asyncio 兼容互斥锁的使用,导致在使用像asyncio.gather()
这样的并发特性时,在 asyncio 上下文中发生死锁时使用了普通的threading.Lock()
。 此更改也 回溯 到:1.4.51 引用:#10813
oracle
- [oracle] [asyncio]
在 asyncio 模式下添加了对 python-oracledb 的支持,使用了新发布的支持 asyncio 的
oracledb
DBAPI 版本。 对于 2.0 系列,这是一个预览版本,当前实现尚未包括对AsyncConnection.stream()
的支持。 改进的支持计划在 SQLAlchemy 的 2.1 发布中实现。 引用:#10679
orm
- [orm] [使用情况] 在为 ORM 注释性声明映射解析自定义类型映射时,添加了对 Python 3.12 pep-695 类型别名结构的初步支持。 引用:#10807
- [orm] [错误]
修复了同时使用
relationship.post_update
功能和使用 mapper version_id_col 时可能导致的问题,在这种情况下,后续更新功能发出的第二个 UPDATE 语句可能无法使用正确的版本标识符,假设在该刷新中已经发出了一个已经增加了版本计数器的 UPDATE。 引用:#10800 - [orm] [错误] 修复了 ORM 注释性声明在没有指定任何集合的情况下误解释关系左侧的问题,如果左侧类型是作为类而不是字符串给出的,并且没有使用未来样式注释。 引用:#10815
sql
- [sql] [错误]
改进了在布尔比较的否定上下文中
any_()
/all_()
的编译,现在将呈现NOT (expr)
而不是将等式运算符反转为不等于,允许更精细地控制这些非典型运算符的否定。 参考:#10817
输入
- [输入] [错误]
修复了在版本 2.0.24 中添加到
sqlalchemy.sql.functions
模块的类型提示引起的回归,作为#6810的一部分:- 进一步增强了 pep-484 类型提示,以允许从
sqlalchemy.sql.expression.func
派生的元素更有效地与 ORM 映射的属性一起使用(#10801) - 修复了传递给函数的参数类型,以便像字符串和整数这样的文字表达式再次被正确解释(#10818)
参考:#10801, #10818
- 进一步增强了 pep-484 类型提示,以允许从
asyncio
- [asyncio] [错误]
修复了在连接池的 asyncio 版本中的关键问题,调用
AsyncEngine.dispose()
会产生一个未完全重新建立使用 asyncio 兼容互斥锁的新连接池,导致在使用并发功能时(如asyncio.gather()
)在 asyncio 上下文中使用普通的threading.Lock()
会导致死锁。 此更改也回溯到:1.4.51 参考:#10813
oracle
- [oracle] [asyncio]
在 asyncio 模式下添加了对 python-oracledb 的支持,使用包含 asyncio 支持的新发布版本的
oracledb
DBAPI。对于 2.0 系列,这是一个预览版本,当前实现尚未包括对AsyncConnection.stream()
的支持。改进的支持计划在 SQLAlchemy 的 2.1 版本中实现。 参考:#10679
2.0.24
发布日期:2023 年 12 月 28 日
orm
- [orm] [错误] 改进了首次在版本 0.9.8 中发布的用于#3208的修复,其中声明内部使用的类注册表可能会受到竞争条件的影响,即在个别映射类同时被垃圾回收时,同时正在构建新的映射类,这可能发生在某些测试套件配置或动态类创建环境中。除了已添加的弱引用检查外,还首先复制正在迭代的项目列表,以避免“在迭代时更改列表”错误。拉取请求由 Yilei Yang 提供。 此更改也回溯到:1.4.51 参考:#10782
- [orm] [bug]
修复了在未对非初始化的
mapped_column()
构造上使用foreign()
注释会产生一个没有类型的表达式的问题,然后在实际列初始化时未更新,导致关系未适当确定use_get
的问题。 参考:#10597 - [orm] [bug] 改进了当工作单元过程将主键列的值设置为 NULL 时产生的错误消息,原因是具有对该列的依赖规则的相关对象被删除,包括不仅目标对象和列名,还包括源列,从中 NULL 值起源。拉取请求由 Jan Vollmer 提供。 参考:#10668
- [orm] [bug]
修改了
MappedAsDataclass
、DeclarativeBase
和DeclarativeBaseNoMeta
使用的__init_subclass__()
方法,以接受任意的**kw
并将其传播到super()
调用,允许更大的灵活性安排使用__init_subclass__()
关键字参数的自定义超类和混入。拉取请求由 Michael Oliver 提供。 参考:#10732 - [orm] [bug]
确保在 ORM 启用的 INSERT、UPDATE 和 DELETE 语句的
returning()
部分中使用的Bundle
对象的用例经过测试并完全可用。这在以前从未明确实现或测试过,并且在 1.4 系列中无法正常工作;在 2.0 系列中,带有 WHERE 条件的 ORM UPDATE/DELETE 缺少实现方法,导致无法使用Bundle
对象。 参考:#10776 - [orm] [bug]
修复了 2.0 版本中
MutableList
的回归问题,其中检测序列的例程未能正确过滤字符串或字节实例,导致无法将字符串值分配给特定索引(而非序列值将正常工作)。 参考:#10784
engine
- [engine] [bug]
修复了在将
URL
对象转换为字符串时,使用URL.render_as_string()
方法对用户名和密码组件进行 URL 编码的问题,通过使用 Python 标准库urllib.parse.quote
,同时允许加号和空格保持不变,以支持 SQLAlchemy 的非标准 URL 解析,而不是多年前的传统自制例程。感谢 Xavier NUNN 的拉取请求。 参考:#10662
sql
- [sql] [bug] 修复了 SQL 元素的字符串化问题,在没有传递特定方言的情况下,遇到特定方言元素(如 PostgreSQL 的“on conflict do update”构造)时,未能提供适当状态以渲染构造,导致内部错误。 参考:#10753
- [sql] [bug]
修复了针对 DML 构造(如
insert()
构造)的CTE
的字符串化或编译失败的问题,由于错误地检���到语句整体为 INSERT,导致内部错误。
schema
- [schema] [bug]
修复了在创建像
Table
这样的对象时,当参数本身作为元组传递时,错误报告对意外模式项的处理不正确,导致格式错误。错误消息已经更新为使用 f-strings。 参考:#10654
typing
- [typing] [bug]
为
sqlalchemy.sql.functions
模块完成了 pep-484 类型注解。针对func
元素进行的select()
构造现在应该具有填充的返回类型。 参考:#6810
asyncio
- [asyncio] [change]
async_fallback
方言参数现已弃用,并将在 SQLAlchemy 2.1 中移除。这个标志在 SQLAlchemy 的测试套件中已经有一段时间没有使用了。通过使用greenlet_spawn()
在 greenlet 中运行代码,asyncio 方言仍然可以以同步方式运行。
postgresql
- [postgresql] [bug]
调整了 asyncpg 方言,使得当使用
terminate()
方法丢弃一个无效的连接时,方言将首先尝试使用带有超时的.close()
优雅地关闭连接,如果操作仅在异步事件循环上下文中进行。这允许 asyncpg 驱动程序处理最终化TimeoutError
,包括能够关闭长时间运行的查询服务器端,否则该查询可能会在程序退出后继续运行。 参考:#10717
mysql
- [mysql] [bug] 修复了使用旧于 1.0 版本的 PyMySQL 进行池预先检查时由修复票号 #10492 引入的回归。 此更改也已回溯至:1.4.51 参考:#10650
tests
- [tests] [bug]
对测试套件进行了改进,进一步加固了在未安装 Python
greenlet
时运行的能力。现在有一个 tox 目标,其中包含标记“nogreenlet”,将在未安装 greenlet 的情况下运行测试套件(请注意,它仍然会在 tox 配置中临时安装 greenlet)。 参考:#10747
orm
- [orm] [bug] 改进了首次在版本 0.9.8 中发布的针对 #3208 实施的修复,其中 declarative 内部使用的类注册表可能会在同时进行垃圾回收的个别映射类与新映射类构造时发生竞争条件,这可能会在某些测试套件配置或动态类创建环境中发生。除了已添加的 weakref 检查外,还首先复制正在迭代的项目列表,以避免“在迭代时更改列表”错误。感谢 Yilei Yang 提交的拉取请求。 此更改也已回溯至:1.4.51 参考:#10782
- [orm] [bug]
修复了在非初始化的
mapped_column()
构造上使用foreign()
注释会产生没有类型的表达式的问题,然后在实际列的初始化时不会更新,导致关系无法适当地确定use_get
等问题的问题。 参考:#10597 - [orm] [bug] 改进了工作单元过程生成的错误消息,当由于相关对象对该列具有依赖规则并且被删除时,工作单元过程将主键列的值设置为 NULL 时,不仅包括目标对象和列名,还包括源列的列名,从而使 NULL 值起源于哪里。拉取请求由 Jan Vollmer 提供。 参考:#10668
- [orm] [bug]
修改了
MappedAsDataclass
、DeclarativeBase
和DeclarativeBaseNoMeta
使用的__init_subclass__()
方法,接受任意的**kw
并将它们传播到super()
调用,允许更灵活地安排使用__init_subclass__()
关键字参数的自定义超类和混入。拉取请求由 Michael Oliver 提供。 参考:#10732 - [orm] [bug]
确保在 ORM 启用的 INSERT、UPDATE 和 DELETE 语句的
returning()
部分中使用的Bundle
对象的用例经过测试并且完全可用。这在之前从未明确实现或测试过,在 1.4 系列中没有正常工作;在 2.0 系列中,具有 WHERE 条件的 ORM UPDATE/DELETE 缺少实现方法,阻止了Bundle
对象的正常工作。 参考:#10776 - [orm] [bug]
修复了在 2.0 中的
MutableList
中的回归,其中检测序列的例程不会正确地过滤出字符串或字节实例,使得无法将字符串值分配给特定索引(而非序列值则正常工作)。 参考:#10784
引擎
- [engine] [bug]
修复了在使用
URL.render_as_string()
方法将用户名和密码组件进行 URL 编码时的问题,通过使用 Python 标准库urllib.parse.quote
,同时允许加号和空格保持不变,以支持 SQLAlchemy 的非标准 URL 解析,而不是多年前的传统自制程序。感谢 Xavier NUNN 的拉取请求。 参考:#10662
sql
- [sql] [bug] 修复了 SQL 元素的字符串化问题,其中未传递特定方言时,遇到特定方言元素(如 PostgreSQL 的“on conflict do update”构造),然后未提供适当状态以呈现构造的字符串化方言,导致内部错误。 参考:#10753
- [sql] [bug]
修复了针对 DML 构造(如
insert()
)的CTE
进行字符串化或编译时失败的问题,由于错误地检测到语句整体是一个 INSERT,导致内部错误。
模式
- [schema] [bug]
修复了在创建对象(如
Table
)时,对于意外模式项的错误报告处理不正确的问题,该参数本身被传递为元组,导致格式化错误。错误消息已经更新为使用 f-strings。 参考:#10654
类型注释
- [typing] [bug]
完成了
sqlalchemy.sql.functions
模块的 pep-484 类型注释。针对func
元素进行的select()
构造现在应该具有填充的返回类型。 参考:#6810
asyncio
- [asyncio] [change]
async_fallback
方言参数现已弃用,并将在 SQLAlchemy 2.1 中删除。这个标志已经有一段时间没有在 SQLAlchemy 的测试套件中使用了。通过使用greenlet_spawn()
在 greenlet 中运行代码,asyncio 方言仍然可以以同步方式运行。
postgresql
- [postgresql] [bug]
调整了 asyncpg 方言,使得当使用
terminate()
方法丢弃一个无效的连接时,方言将首先尝试使用带有超时的.close()
优雅地关闭连接,仅在异步事件循环上下文中进行该操作时。这允许 asyncpg 驱动程序处理最终化TimeoutError
,包括能够在程序退出后继续运行的长时间运行的查询服务器端。 参考:#10717
mysql
- [mysql] [bug] 修复了使用旧于 1.0 版本的 PyMySQL 与池预先 PING 时由修复票证 #10492 引入的回归问题。 此更改还回溯到:1.4.51 参考:#10650
测试
- [tests] [bug]
对测试套件进行改进,以进一步加强在未安装 Python
greenlet
时运行的能力。现在有一个 tox 目标包含标记“nogreenlet”,将以未安装 greenlet 的方式运行测试套件(注意,它仍然在 tox 配置中临时安装 greenlet)。 参考:#10747
2.0.23
发布日期:2023 年 11 月 2 日
orm
- [orm] [usecase]
对于新样式批量 ORM 插入,实现了
Session.bulk_insert_mappings.render_nulls
参数,允许render_nulls=True
作为执行选项。这允许参数字典中含有混合的None
值的批量 ORM 插入使用给定的字典键的单个行批次,而不是将每个 INSERT 中的 NULL 列分开成批次。 另请参阅 在 ORM 批量 INSERT 语句中发送 NULL 值 参考:#10575 - [orm] [bug]
修复了
__allow_unmapped__
指令无法允许旧式Column
/deferred()
映射的问题,这些映射尽管没有Mapped[]
作为它们的类型,但仍然具有诸如Any
或特定类型的注释,并且不会出现有关定位属性名称的错误。 参考:#10516 - [orm] [bug]
修复了使用
with_expression()
结构与加载器选项selectinload()
、lazyload()
结合使用时,在后续缓存运行中无法正确替换绑定参数值的缓存错误。 参考:#10570 - [orm] [bug]
修复了 ORM 注释的声明式中的错误,其中使用
ClassVar
,但仍然以某种方式引用了 ORM 映射类名,将无法解释为未映射的ClassVar
。 参考:#10472
sql
- [sql] [usecase]
为 PostgreSQL 和 Oracle 方言的
Interval
数据类型实现了“文字值处理”,允许文字渲染间隔值。Pull request 由 Indivar Mishra 提供。 参考:#9737 - [sql] [bug]
修复了在某些与其他文字渲染参数的组合中,使用相同的绑定参数超过一次并且
literal_execute=True
会导致错误值渲染的问题,这是由于迭代问题造成的。 此更改也已被回溯至:1.4.50 参考:#10142 - [sql] [bug] 为所有包含文字处理的数据类型的“文字处理器”添加了编译器级的 None/NULL 处理,即在 SQL 语句中将值内联呈现而不是作为绑定参数,适用于所有那些不具有显式“null 值”处理的类型。之前,这种行为是未定义且不一致的。 参考:#10535
- [sql]
移除了未使用的占位符方法
TypeEngine.compare_against_backend()
。该方法被 Alembic 的非常旧的版本使用。有关详细信息,请参见github.com/sqlalchemy/alembic/issues/1293
。
asyncio
- [asyncio] [bug]
修复了
AsyncSession.close_all()
方法的错误。还添加了函数close_all_sessions()
,它是close_all_sessions()
的等效项。Pull request 由 Bryan 不可思议 提供。 参考:#10421
postgresql
- [postgresql] [bug] 修复了 2.0 中由 #7744 引起的回归,其中涉及 PostgreSQL JSON 操作符与其他操作符(如字符串连接)组合的表达式链会由于特定于 PostgreSQL 方言的实现细节而失去正确的括号,。 参考:#10479
- [postgresql] [bug]
当使用 asyncpg 后端和
BIT
数据类型时,修复了“insertmanyvalues”的 SQL 处理。 asyncpg 上的BIT
显然需要使用 asyncpg 特定的BitString
类型,该类型当前在使用此 DBAPI 时公开,使其与其他所有在此处使用普通位串的 PostgreSQL DBAPI 不兼容。 在版本 2.1 中的未来修复将会使这种数据类型在所有 PG 后端上正规化。 感谢 Sören Oldag 提交的拉取请求。 参考:#10532
mysql
- [mysql] [bug]
修复了 MySQL “预 Ping”例程中的新不兼容性,其中传递给
connection.ping()
的False
参数,该参数旨在禁用不需要的“自动重新连接”功能,在 MySQL 驱动程序和后端中被弃用,并且对于某些版本的 MySQL 本机客户端驱动程序正在产生警告。 对于 mysqlclient,它已被删除,而对于 PyMySQL 和基于 PyMySQL 的驱动程序,该参数将在某个时候被弃用并删除,因此使用 API 内省来对抗这些不同阶段的移除。 此更改也已回溯到:1.4.50 参考:#10492
mariadb
- [mariadb] [bug]
当使用 MariaDB 时,调整了 MySQL / MariaDB 方言,如果未使用显式的
True
或False
值指定Column.nullable
,则将生成的列默认设置为 NULL,因为 MariaDB 不支持具有生成列的“NOT NULL”短语。 感谢 Indivar 提交的拉取请求。 参考:#10056 - [mariadb] [bug] [regression] 为似乎是 MySQL/MariaDB 驱动程序之间的固有问题建立了一个解决方法,该问题在使用 SQLAlchemy 的“空 IN”条件返回不包含行的 DELETE DML 的 RETURNING 结果时失败,该 DELETE DML 在 2.0 系列中用于“同步会话”功能的批量 DELETE 语句。 为了解决这个问题,当检测到“给定 RETURNING 时没有描述”的特定情况时,将生成一个带有正确游标描述的“空结果”,并将其用于替代不起作用的游标。 参考:#10505
mssql
- [mssql] [usecase]
已添加对基于 pyodbc 和通用 aio*方言架构构建的 SQL Server 的
aioodbc
驱动程序的支持。 另请参阅 aioodbc - 在 SQL Server 方言文档中。 参考:#6521 - [mssql] [bug] [reflection] 修复了在具有大于 18 位数的大型标识起始值的 bigint 列的情况下,标识列反射将失败的问题。 此更改也反向移植到:1.4.50 参考:#10504
oracle
- [oracle] [bug]
在
Interval
数据类型中修复了问题,其中 Oracle 实现未用于 DDL 生成,导致day_precision
和second_precision
参数被忽略,尽管该方言支持。感谢 Indivar 的 Pull 请求。 参考:#10509 - [oracle] [bug] 修复了 cx_Oracle 方言声称支持比实际上在 SQLAlchemy 2.0 系列中实际支持的更低的 cx_Oracle 版本(7.x)的问题。方言导入了仅在 cx_Oracle 8 或更高版本中才有的符号,因此运行时方言检查以及 setup.cfg 要求已更新以反映此兼容性。 参考:#10470
orm
- [orm] [usecase]
实现了
Session.bulk_insert_mappings.render_nulls
参数,用于新样式的批量 ORM 插入,允许render_nulls=True
作为执行选项。这允许在参数字典中使用None
值的批量 ORM 插入使用给定的一组字典键的单个行批次,而不是将其拆分为省略每个 INSERT 中的 NULL 列的批次。 另请参阅 在 ORM 批量 INSERT 语句中发送 NULL 值 参考:#10575 - [orm] [bug]
修复了
__allow_unmapped__
指令无法允许具有Any
或没有Mapped[]
作为其类型的特定类型的注释的遗留Column
/deferred()
映射的问题,而无需与定位属性名称相关的错误。 参考:#10516 - [orm] [bug]
修复了使用
with_expression()
结构与加载器选项selectinload()
,lazyload()
结合使用时,与后续缓存运行中正确替换绑定参数值失败的缓存错误。 引用:#10570 - [orm] [bug]
修复了 ORM 注释声明中的错误,其中使用了一个
ClassVar
,尽管以某种方式引用了 ORM 映射的类名,但未能被解释为未映射的ClassVar
。 引用:#10472
sql
- [sql] [usecase]
实现了对于
Interval
数据类型的“字面值处理”,适用于 PostgreSQL 和 Oracle 方言,允许直接渲染间隔值。感谢 Indivar Mishra 提供的拉取请求。 引用:#9737 - [sql] [bug]
修复了一个问题,即在某些与其他字面渲染参数组合使用
literal_execute=True
时,多次使用相同的绑定参数会由于迭代问题导致错误的值渲染。 此更改还回溯到:1.4.50 引用:#10142 - [sql] [bug] 为所有包含字面处理的数据类型的“字面处理器”添加了编译器级 None/NULL 处理,即在 SQL 语句中将值内联呈现而不是作为绑定参数,对于所有不具有显式“空值”处理的类型。以前,此行为是未定义的且不一致的。 引用:#10535
- [sql]
移除了未使用的占位符方法
TypeEngine.compare_against_backend()
,此方法仅用于非常旧版本的 Alembic。有关详细信息,请参见github.com/sqlalchemy/alembic/issues/1293
。
asyncio
- [asyncio] [bug]
修复了
AsyncSession.close_all()
方法无法正常工作的错误。还添加了函数close_all_sessions()
,它等同于close_all_sessions()
。拉取请求由 Bryan 不可思议 提供。 引用:#10421
postgresql
- [postgresql] [bug] 修复了由 #7744 引起的 2.0 版本回归,其中涉及 PostgreSQL JSON 运算符的表达式链与其他运算符(如字符串连接)组合会丢失正确的括号化,这是由于特定于 PostgreSQL 方言的实现细节造成的。 参考:#10479
- [postgresql] [bug]
修复了在使用 asyncpg 后端时使用
BIT
数据类型的 “insertmanyvalues” 的 SQL 处理问题。在 asyncpg 上,BIT
显然需要使用 asyncpg 特定的BitString
类型,目前在使用此 DBAPI 时暴露,这使其与其他 PostgreSQL DBAPI 不兼容,所有这些 DBAPI 都在这里使用普通的位字符串。在版本 2.1 中,将通过将此数据类型在所有 PG 后端上归一化来解决此问题。拉取请求由 Sören Oldag 提供。 参考:#10532
mysql
- [mysql] [bug]
修复了 MySQL 的 “pre-ping” 例程中的一个新的不兼容性,其中传递给
connection.ping()
的False
参数,用于禁用不想要的 “自动重新连接” 功能,正在被 MySQL 驱动程序和后端弃用,并且对某些版本的 MySQL 的本机客户端驱动程序产生警告。对于 mysqlclient,它已被移除,而对于 PyMySQL 和基于 PyMySQL 的驱动程序,该参数将在某个时候被弃用并移除,因此使用 API 内省来未来证明对这些移除的各个阶段进行了保护。 这个更改也被回溯到了:1.4.50 参考:#10492
mariadb
- [mariadb] [bug]
调整了 MySQL / MariaDB 方言,当使用 MariaDB 时,默认将生成的列设置为 NULL,如果
Column.nullable
没有使用显式的True
或False
值进行指定,因为 MariaDB 不支持带有生成列的“NOT NULL”短语。拉取请求由 Indivar 提供。 参考:#10056 - [mariadb] [bug] [regression] 建立了一个解决 MySQL/MariaDB 驱动程序中似乎存在的一个固有问题的方法,即对于使用 SQLAlchemy 的 “空 IN” 条件返回不返回任何行的 DELETE DML 的 RETURNING 结果,失败提供 cursor.description,然后返回没有行的结果,导致在 2.0 系列中为 ORM 使用 RETURNING 用于“同步会话”功能的批量 DELETE 语句时出现回归。为了解决这个问题,当检测到 “给出 RETURNING 时没有描述” 的特定情况时,会生成一个带有正确游标描述的“空结果”,并在非工作游标的位置使用它。 参考:#10505
mssql
- [mssql] [usecase]
为 SQL Server 实现的
aioodbc
驱动添加了支持,该驱动建立在 pyodbc 和通用 aio* 方言架构之上。 另请参阅 aioodbc - 在 SQL Server 方言文档中。 参考:#6521 - [mssql] [bug] [reflection] 修复了对于具有大于 18 位数的大整数起始值的 bigint 列的身份列反射失败的问题。 此更改也被 回溯 至:1.4.50 参考:#10504
oracle
- [oracle] [bug]
修复了
Interval
数据类型中的问题,在 Oracle 实现未用于 DDL 生成,导致day_precision
和second_precision
参数被忽略,尽管该方言支持这些参数。Indivar 提供的拉取请求。 参考:#10509 - [oracle] [bug] 修复了 cx_Oracle 方言声称支持比实际在 SQLAlchemy 2.0 系列中支持的更低的 cx_Oracle 版本(7.x)的问题。方言导入了仅在 cx_Oracle 8 或更高版本中才存在的符号,因此运行时方言检查以及 setup.cfg 要求已更新以反映此兼容性。 参考:#10470
2.0.22
发布日期:2023 年 10 月 12 日
orm
- [orm] [usecase]
添加了
Session.get_one()
方法,其行为类似于Session.get()
,但是如果未找到具有提供的主键的实例,则引发异常而不是返回None
。由 Carlos Sousa 提供的拉取请求。 参考:#10202 - [orm] [usecase]
添加了一个选项以永久关闭会话。将新参数
Session.close_resets_only
设置为False
将阻止在调用Session.close()
后执行任何其他操作。 添加了新方法Session.reset()
,它将一个Session
重置为其初始状态。这是Session.close()
的别名,除非Session.close_resets_only
设置为False
。 参考:#7787 - [orm] [bug]
修复了一系列
mapped_column()
参数,在 pep-593Annotated
对象中使用mapped_column()
对象时未被传递,包括mapped_column.sort_order
,mapped_column.deferred
,mapped_column.autoincrement
,mapped_column.system
,mapped_column.info
等。 另外,仍然不支持使用mapped_column.kw_only
等数据类参数,这些参数在通过Annotated
接收的mapped_column()
中指定,因为这在 pep-681 数据类转换中不受支持。当以这种方式在Annotated
中使用这些参数时,将发出警告(并且它们继续被忽略)。 参考:#10046, #10369 - [orm] [bug]
修复了使用 ORM 中的新式
select()
查询调用Result.unique()
方法时的问题,在此查询中,一个或多个列产生的值是“未知可哈希性”,通常是在使用func.json_build_object()
等 JSON 函数时没有提供类型时会导致内部失败。在这种情况下,修复了将对象作为接收到的对象测试其可哈希性的行为,并在不可哈希时引发一个信息性错误消息。请注意,对于“已知不可哈希性”的值,例如直接使用JSON
或ARRAY
类型时,已经会引发一个信息性错误消息。 这里的“可哈希性测试”修复也适用于传统的Query
,然而在传统情况下,几乎所有的查询都使用Result.unique()
,因此这里不会发出新的警告;在这种情况下,保持了使用id()
的传统行为,改进是一个未知类型如果被证明是可哈希的,那么现在将被独特化,而以前是不会的。 参考:#10459 - [orm] [bug]
修复了最近修订的“insertmanyvalues”功能中的回归(可能是问题 #9618),在这种情况下,ORM 会不经意地将一个非 RETURNING 结果误解为具有 RETURNING 结果,这是因为将
implicit_returning=False
参数应用于映射的Table
时指示“insertmanyvalues”不能在不提供主键值的情况下使用。 参考:#10453 - [orm] [bug]
修复了 ORM
with_loader_criteria()
不会应用于Select.join()
的 bug,其中 ON 子句被给定为一个普通的 SQL 比较,而不是作为一个关系目标或类似的东西。 参考:#10365 - [orm] [bug]
修复了当作为给定注释的子模块的元素引用时,无法正确解析
Mapped
符号(如WriteOnlyMapped
和DynamicMapped
)的问题,假设注释是基于字符串或“未来注释”样式的。 参考:#10412 - [orm] [bug]
修复了使用
__allow_unmapped__
声明选项时的问题,其中使用集合类型(例如list[SomeClass]
)声明的类型与使用 typing 构造List[SomeClass]
的类型无法正确识别。由 Pascal Corpet 提供的拉取请求。 参考:#10385
engine
- [engine] [bug] 修复了一些方言中可能出现的问题,即方言可能会对根本不返回行的 INSERT 语句错误地返回空结果集,这是由于仍然存在来自行的主键的预获取或后获取的影响所致。受影响的方言包括 asyncpg 和所有的 mssql 方言。
- [engine] [bug] 修复了在某些垃圾回收/异常场景下,连接池的清理例程会由于意外的状态集而引发错误的问题,在特定条件下可以重现该问题。 参考:#10414
sql
- [sql] [bug]
修复了一个问题,即在 UPDATE 语句的 SET 子句中引用 FROM 条目时,如果该条目在语句中没有其他地方,则不会将其包括在 UPDATE 语句的 FROM 子句中;目前,对于使用
Update.add_cte()
添加的 CTE(通用表达式),以提供所需的 CTE 的情况,会出现这种情况。 参考:#10408 - [sql] [bug]
修复了 2.0 版本的回归问题,即由于移除了未被考虑到的
on
属性而导致DDL
结构不再执行__repr__()
。由 Iuri de Silvio 提供的拉取请求。 参考:#10443
typing
- [typing] [bug]
修复了传递给
Values
的参数列表过于严格地与List
而不是Sequence
绑定的类型问题。由 Iuri de Silvio 提供的拉取请求。 参考:#10451 - [typing] [bug] 更新了代码库以支持 Mypy 1.6.0。
asyncio
- [asyncio] [bug]
修复了未将
AsyncSession.get.execution_options
参数传播到底层Session
并且被忽略的问题。
mariadb
- [mariadb] [bug]
修改了 mariadb-connector 驱动程序,预加载所有查询的
cursor.rowcount
值,以适应像 Pandas 这样硬编码调用Result.rowcount
的工具。SQLAlchemy 通常仅为 UPDATE/DELETE 语句预加载cursor.rowcount
,否则会传递给 DBAPI,在那里如果没有值可用,则可以返回-1。然而,mariadb-connector 在关闭光标本身后不支持调用cursor.rowcount
,而是引发错误。已添加通用测试支持,以确保所有后端支持在结果关闭后允许Result.rowcount
成功(即返回一个整数值,-1 表示“不可用”)。 参考:#10396 - [mariadb] [bug] 为 mariadb-connector 方言添加了额外的修复,以支持 INSERT…RETURNING 语句中结果中的 UUID 数据值。
mssql
- [mssql] [bug]
修复了一个 bug,在这个 bug 中,阻止 ORDER BY 在 SQL Server 的子查询中发出的规则在使用
select.fetch()
方法限制行数与 WITH TIES 或 PERCENT 结合使用时未被禁用,从而阻止了可以使用带有 TOP / ORDER BY 的有效子查询。 参考:#10458
orm
- [orm] [usecase]
添加了类似于
Session.get()
但在未找到具有提供的主键的实例时引发异常而不是返回None
的方法Session.get_one()
。感谢 Carlos Sousa 的拉取请求。 参考:#10202 - [orm] [usecase]
添加了一个选项来永久关闭会话。将新参数
Session.close_resets_only
设置为False
将阻止Session
在调用Session.close()
后执行任何其他操作。 添加了新方法Session.reset()
,将Session
重置为初始状态。这是Session.close()
的别名,除非设置Session.close_resets_only
为False
。 参考:#7787 - [orm] [bug]
修复了一系列
mapped_column()
参数,在使用Annotated
对象内部的mapped_column()
对象时未被传递,包括mapped_column.sort_order
,mapped_column.deferred
,mapped_column.autoincrement
,mapped_column.system
,mapped_column.info
等。 此外,在Annotated
中接收到 参考:#10046,#10369 - [orm] [bug]
修复了在 ORM 中使用新风格的
select()
查询调用Result.unique()
时的问题,在此情况下,如果一个或多个列产生的值是“未知的可哈希性”,通常是在使用像func.json_build_object()
这样的 JSON 函数时没有提供类型时,会在返回的值实际上不可哈希时内部失败。此行为已修复,此时会对接收到的对象进行哈希性测试,如果不可哈希,则会引发一个信息性错误消息。请注意,对于“已知的不可哈希性”值,例如直接使用JSON
或ARRAY
类型时,已经会引发信息性错误消息。 此处的“哈希性测试”修复也适用于传统的Query
,但在传统情况下,几乎所有查询都使用Result.unique()
,因此此处不会发出新的警告;在这种情况下,保留了使用id()
的传统行为,改进是现在将被证明是可哈希的未知类型现在会被唯一化,而以前则不会。 参考:#10459 - [orm] [bug]
修复了最近修订的“insertmanyvalues”功能中的回归(可能是问题 #9618),在这种情况下,如果将
implicit_returning=False
参数应用于映射的Table
,表示如果未提供主键值,则 ORM 会意外地尝试将非 RETURNING 结果解释为带有 RETURNING 结果,表明“insertmanyvalues”不能在不提供主键值的情况下使用。 参考:#10453 - [orm] [bug]
修复了 ORM
with_loader_criteria()
在 ON 子句被给定为普通 SQL 比较而不是作为关系目标或类似的情况下不应用于Select.join()
的 bug。 参考:#10365 - [orm] [bug]
修复了
Mapped
符号,例如WriteOnlyMapped
和DynamicMapped
在引用为给定注释的子模块的元素时无法正确解析的问题,假定使用基于字符串或“未来注释”样式注释。 参考:#10412 - [ORM] [错误]
修复了
__allow_unmapped__
声明选项中的问题,其中使用集合类型(如list[SomeClass]
)声明的类型与使用 typing 构造List[SomeClass]
相比将无法被正确识别。 感谢 Pascal Corpet 提供的拉取请求。 参考:#10385
引擎
- [引擎] [错误] 修复了某些方言中的问题,其中方言可能会对根本不返回行的 INSERT 语句错误地返回空结果集,原因是仍然存在来自预先或后期获取行的主键的痕迹。受影响的方言包括 asyncpg,所有 mssql 方言。
- [引擎] [错误] 修复了在某些垃圾收集 / 异常情况下,连接池的清理例程会由于意外的状态集而引发错误的问题,该问题可以在特定条件下重现。 参考:#10414
SQL
- [SQL] [错误]
修复了在 UPDATE 语句的 SET 子句中引用 FROM 条目不会将其包括在 UPDATE 语句的 FROM 子句中的问题,如果该条目在语句中没有其他地方出现;这目前适用于通过
Update.add_cte()
添加的 CTE,以在语句顶部提供所需的 CTE。 参考:#10408 - [SQL] [错误]
修复了 2.0 版中的回归,其中
DDL
构造由于已移除的on
属性未被容纳而不再__repr__()
。 感谢 Iuri de Silvio 提供的拉取请求。 参考:#10443
类型
- [类型] [错误]
修复了类型问题,其中传递给
Values
的参数列表过于严格地绑定到List
而不是Sequence
。 感谢 Iuri de Silvio 提供的拉取请求。 参考:#10451 - [类型] [错误] 更新了代码库以支持 Mypy 1.6.0。
异步 IO
- [异步 IO] [错误]
修复了未将
AsyncSession.get.execution_options
参数传播到底层Session
并且被忽略的问题。
mariadb
- [mariadb] [bug]
修改了 mariadb-connector 驱动程序,以预加载所有查询的
cursor.rowcount
值,以适应像 Pandas 这样硬编码调用Result.rowcount
的工具。SQLAlchemy 通常仅为 UPDATE/DELETE 语句预加载cursor.rowcount
,否则传递给 DBAPI,在那里如果没有值可用则可以返回 -1。但是,mariadb-connector 不支持在关闭游标本身后调用cursor.rowcount
,而是引发错误。已添加通用测试支持,以确保所有后端支持在结果关闭后允许Result.rowcount
成功(即返回一个整数值,-1 表示“不可用”)。 参考:#10396 - [mariadb] [bug] 为 mariadb-connector 方言添加了额外的修复,以支持 INSERT…RETURNING 语句中结果中的 UUID 数据值。
mssql
- [mssql] [bug]
修复了一个错误,即在 SQL Server 上阻止 ORDER BY 在子查询中发出的规则未在使用
select.fetch()
方法限制行数与 WITH TIES 或 PERCENT 结合时被禁用,导致无法使用带有 TOP / ORDER BY 的有效子查询。 参考:#10458
2.0.21
发布日期:2023 年 9 月 18 日
orm
- [orm] [bug]
调整了 ORM 对“target”实体的解释,用于
Update
和Delete
中,以不干扰传递给语句的目标“from”对象,例如在传递 ORM 映射的aliased
构造时应在“UPDATE FROM”等短语中保留。像使用“SELECT”语句进行 ORM 会话同步的情况,如与 MySQL/MariaDB 一起使用此类形式的 UPDATE/DELETE 仍然会有问题,因此最好在使用此类 DML 语句时禁用 synchonize_session。 参考:#10279 - [orm] [bug]
为
selectin_polymorphic()
加载器选项添加了新的功能,允许其他加载器选项作为兄弟节点捆绑在其中,引用其子类之一,在父加载器选项的子选项中。以前,只有在查询的选项的顶层才支持此模式。参见新的文档部分示例。 作为此更改的一部分,改进了Load.selectin_polymorphic()
方法/加载策略的行为,因此在对已经关系加载的类使用该选项时,子类加载不会加载父表中已加载的大多数列。先前,仅对顶级类加载的逻辑才能仅加载子类列。 另请参阅 在 selectin_polymorphic 本身作为子选项时应用加载器选项 参考:#10348
引擎
- [engine] [bug] 修复了一系列反射问题,影响到 PostgreSQL、MySQL/MariaDB 和 SQLite 方言,在反映外键约束时,目标列的表名或列名中包含括号的情况下。 参考:#10275
sql
- [sql] [用例]
调整了
Enum
数据类型,接受Enum.length
参数的值为None
,在生成的 DDL 中,结果为 VARCHAR 或其他文本类型而没有长度。这允许在模式中存在类型后向类型添加任意长度的新元素。感谢 Eugene Toder 的拉取请求。 参考:#10269 - [sql] [用例]
添加了新的通用 SQL 函数
aggregate_strings
,接受一个 SQL 表达式和一个分隔符,将多行字符串连接为单个聚合值。该函数根据每个后端编译为诸如group_concat()
、string_agg()
或LISTAGG()
等函数。感谢 Joshua Morris 的拉取请求。 参考:#9873 - [sql] [bug]
调整了字符串连接运算符的操作符优先级,使其等于字符串匹配运算符的优先级,例如
ColumnElement.like()
、ColumnElement.regexp_match()
、ColumnElement.match()
等,以及与字符串比较运算符相同优先级的纯==
,这样括号将应用于跟在字符串匹配运算符后面的字符串连接表达式。这为后端,例如 PostgreSQL 提供了可能比字符串连接运算符优先级更高的 “regexp match” 运算符的情况。 参考:#9610 - [sql] [bug]
在 DDL 编译器中对
hashlib.md5()
的使用进行了限定,该函数用于在 DDL 语句中为长索引和约束名称生成确定性的四字符后缀,以包括 Python 3.9 中的usedforsecurity=False
参数,以便 Python 解释器构建为诸如 FIPS 之类的受限环境时不认为此调用与安全问题有关。 参考:#10342 - [sql] [bug]
Values
构造现在将自动创建column
的代理(即复制),如果该列已经与现有的 FROM 子句相关联。这允许像values_obj.c.colname
这样的表达式即使在colname
被传递为已经与以前的Values
或其他表构造一起使用的column
的情况下,也能产生正确的 FROM 子句。最初认为这可能是一个错误条件的候选项,但是很可能这种模式已经被广泛使用,所以现在添加了支持。 参考:#10280
schema
- [schema] [bug]
修改了仅适用于 Oracle 的
Identity.order
参数的渲染,该参数是Sequence
和Identity
的一部分,仅适用于 Oracle 后端,而不适用于其他后端,如 PostgreSQL。未来的版本将重命名Identity.order
、Sequence.order
和Identity.on_null
参数为 Oracle 特定名称,弃用旧名称,这些参数仅适用于 Oracle。 此更改也回溯到:1.4.50 参考:#10207
typing
- [typing] [usecase]
使
Mapped
的包含类型协变;这是为了允许更大的灵活性,以满足最终用户的类型化场景,例如使用协议来表示传递给其他函数的特定映射类结构。作为此更改的一部分,还使依赖和相关类型的包含类型协变,如SQLORMOperations
、WriteOnlyMapped
和SQLColumnExpression
。拉取请求由 Roméo Després 提供。 参考:#10288 - [typing] [bug]
修复了在 2.0.20 中引入的回归问题,通过 #9600 修复尝试为
MetaData.naming_convention
添加更正式的类型化。此更改阻止了基本命名约定字典通过类型化,并已调整为再次接受键为字符串的普通字典以及使用约束类型作为键或两者混合使用的字典。 作为此更改的一部分,还对命名约定字典的较少使用形式进行了类型化,包括当前允许将Constraint
类型对象用作键。 参考:#10264, #9284 - [typing] [bug]
修复了应用于表达式构造基类
Visitable
的__class_getitem__()
的类型注释,使其接受Any
作为键,而不是str
,这有助于一些 IDE(如 PyCharm)在尝试为包含泛型选择器的 SQL 构造编写类型注释时。感谢 Jordan Macdonald 的拉取请求。 参考资料:#9878 - [打字] [错误]
修复了核心“SQL 元素”类
SQLCoreOperations
以支持从类型角度来看的__hash__()
方法,因为像Column
和 ORMInstrumentedAttribute
这样的对象是可散列的,并且在Update
和Insert
构造的公共 API 中用作字典键。先前,类型检查器不知道根 SQL 元素是可散列的。 参考资料:#10353 - [打字] [错误]
修复了使用 ORM 类时,
Existing.select_from()
的类型注释问题。 参考资料:#10337 - [打字] [错误] 更新 ORM 加载选项的类型注解,限制其只接受“*”而不是任何字符串作为字符串参数。感谢 Janek Nouvertné 的拉取请求。 参考资料:#10131
postgresql
- [postgresql] [错误]
修复了由于 #8491 在 2.0 中出现的回归问题,当使用
create_engine.pool_pre_ping
参数时,PostgreSQL 方言的修订“ping”会干扰 asyncpg 与 PGBouncer 的“transaction”模式的使用,因为 asnycpg 发出的多个 PostgreSQL 命令可能被分成多个连接导致错误,因为这种新修订的“ping”周围没有任何事务。现在,在事务内调用 ping,与所有其他基于 pep-249 DBAPI 的后端一样;这保证了由此命令发送的一系列 PG 命令在同一后端连接上被调用,而不是在命令执行中跳转到另一个连接。如果 asyncpg 方言以“AUTOCOMMIT”模式使用,则不使用事务,这与 pgbouncer 事务模式不兼容。 参考资料:#10226
杂项
- [错误] [设置]
修复了一个很久以前的问题,即无法在 pytest 运行之外导入 SQLAlchemy 模块的全部范围,包括
sqlalchemy.testing.fixtures
。这适用于诸如pkgutil
等尝试在所有包中导入所有已安装模块的检查实用程序。 参考:#10321
orm
- [orm] [错误]
调整了 ORM 对于
Update
和Delete
中使用的“target”实体的解释,以避免干扰语句中传递的目标“from”对象,比如传递 ORM 映射的aliased
结构,在像“UPDATE FROM”这样的短语中应保持不变。像 ORM 会话同步使用“SELECT”语句的情况,比如 MySQL/MariaDB,仍然会出现这种形式的 UPDATE/DELETE 的问题,因此最好在使用此类 DML 语句时禁用 synchonize_session。 参考:#10279 - [orm] [错误]
为
selectin_polymorphic()
加载器选项添加了新的功能,允许将其他加载器选项作为同级项捆绑在其中,引用其中一个子类,在父加载器选项的子选项中。以前,只有在查询的选项的顶级中才支持这种模式。请参阅新的文档部分以获取示例。 作为这一变化的一部分,改进了Load.selectin_polymorphic()
方法/加载器策略的行为,以便在已经对父表进行关系加载时,子类加载不会加载大部分已加载列。以前,仅加载子类列的逻辑仅适用于顶层类加载。 参见 在 selectin_polymorphic 本身是子选项时应用加载器选项 参考:#10348
engine
- [engine] [错误] 修复了一系列反射问题,影响到 PostgreSQL、MySQL/MariaDB 和 SQLite 方言,在反射外键约束时,目标列中包含括号的情况下,其中一个或两个表名或列名中都包含括号。 参考:#10275
sql
- [sql] [用例]
调整了
Enum
数据类型,使其接受None
参数作为Enum.length
参数,从而在生成的 DDL 中得到一个没有长度限制的 VARCHAR 或其他文本类型。这允许在模式中存在该类型后添加任意长度的新元素。感谢 Eugene Toder 的拉取请求。 参考:#10269 - [sql] [usecase]
添加了新的通用 SQL 函数
aggregate_strings
,接受一个 SQL 表达式和一个分隔符,将多行字符串连接成单个聚合值。该函数根据每个后端编译成函数,如group_concat()
、string_agg()
或LISTAGG()
。感谢 Joshua Morris 的拉取请求。 参考:#9873 - [sql] [bug]
调整了字符串连接运算符的运算优先级,使其与字符串匹配运算符(如
ColumnElement.like()
、ColumnElement.regexp_match()
、ColumnElement.match()
等)以及普通的==
运算符相等,这样括号将应用于跟在字符串匹配运算符后的字符串连接表达式。这为后端(如 PostgreSQL)提供了支持,其中“regexp match”运算符显然比字符串连接运算符的优先级高。 参考:#9610 - [sql] [bug]
限定了 DDL 编译器中
hashlib.md5()
的使用,用于为 DDL 语句中的长索引和约束名称生成确定性的四字符后缀,以包括 Python 3.9 的usedforsecurity=False
参数,以便 Python 解释器构建用于受限环境(如 FIPS)时不将此调用视为与安全问题相关。 参考:#10342 - [sql] [bug]
Values
构造现在将自动创建一个代理(即复制),如果列已经与现有的 FROM 子句相关联。这样一来,即使colname
已经作为一个column
被传递给了先前的Values
或其他表构造,表达式values_obj.c.colname
也会产生正确的 FROM 子句。最初认为这可能会导致错误,但很可能这种模式已经被广泛使用,所以现在添加以支持。 参考:#10280
模式
- [模式] [错误]
修改了仅适用于 Oracle 的
Identity.order
参数的呈现方式,该参数既属于Sequence
又属于Identity
,现在只在 Oracle 后端生效,而不是像 PostgreSQL 那样适用于其他后端。将来的版本将会将Identity.order
、Sequence.order
和Identity.on_null
参数重命名为 Oracle 特定的名称,并弃用旧名称,这些参数仅适用于 Oracle。 此更改也回溯到:1.4.50 参考:#10207
typing
- [类型] [用例]
对于
Mapped
中包含的类型进行了协变处理;这样做是为了在端用户的类型场景中提供更大的灵活性,比如使用协议来表示特定映射类结构,这些结构会传递给其他函数。作为这一变更的一部分,对于依赖和相关类型,如SQLORMOperations
、WriteOnlyMapped
和SQLColumnExpression
,也对其中包含的类型进行了协变处理。感谢 Roméo Després 提交的拉取请求。 参考:#10288 - [类型] [错误]
修复了在 2.0.20 中引入的回归问题,通过 #9600 修复,该修复尝试为
MetaData.naming_convention
添加更正式的类型注解。这一变更阻止了基本的命名约定字典通过类型检查,并已调整为再次接受纯字符串键的普通字典以及使用约束类型作为键或两者混合使用的字典。 作为这一变更的一部分,还对命名约定字典的较少使用形式进行了类型化,其中目前允许Constraint
类型对象作为键。 参考:#10264, #9284 - [typing] [bug]
修复了应用于表达式构造基础的
Visitable
类的__class_getitem__()
的类型注解,以接受Any
作为键,而不是str
,这有助于一些 IDE,如 PyCharm,在尝试为包含通用选择器的 SQL 构造编写类型注解时。感谢 Jordan Macdonald 的拉取请求。 参考:#9878 - [typing] [bug]
修复了核心“SQL 元素”类
SQLCoreOperations
,以支持从类型的角度看待__hash__()
方法,因为像Column
和 ORMInstrumentedAttribute
这样的对象是可哈希的,并且在公共 API 中用作字典键,用于Update
和Insert
构造。以前,类型检查器不知道根 SQL 元素是可哈希的。 参考:#10353 - [typing] [bug]
修复了与
Existing.select_from()
的类型问题,这阻止了它与 ORM 类的使用。 参考:#10337 - [typing] [bug] 更新了 ORM 加载选项的类型注解,将其限制为仅接受“*”而不是任何字符串作为字符串参数。感谢 Janek Nouvertné 的拉取请求。 参考:#10131
postgresql
- [postgresql] [bug]
修复了 2.0 版本中出现的回归问题,这是由于#8491导致的,其中当使用
create_engine.pool_pre_ping
参数时,用于 PostgreSQL 方言的修订“ping”会干扰 asyncpg 与 PGBouncer“事务”模式的使用,因为 asnycpg 发出的多个 PostgreSQL 命令可能会被分配到多个连接中,导致错误,由于对此新修订的“ping”周围没有任何事务。现在,在事务中调用 ping,就像所有其他基于 pep-249 DBAPI 的后端隐式使用的一样;这保证了由于此命令发送的 PG 命令系列会在同一后端连接上调用,而不是在命令中间跳到不同的连接。如果使用 asyncpg 方言处于“AUTOCOMMIT”模式下,则不使用事务,这仍然与 pgbouncer 事务模式不兼容。 参考资料:#10226
杂项
- [错误] [设置]
修复了很旧的问题,即无法在 pytest 运行外导入 SQLAlchemy 模块的全部内容,包括
sqlalchemy.testing.fixtures
。这适用于诸如pkgutil
等试图导入所有包中所有已安装模块的检查工具。 参考资料:#10321
2.0.20
发布日期:2023 年 8 月 15 日
orm
- [orm] [用例] 实现了 ORM 启用的 DML 语句的“RETURNING '*”用例。这将在尽可能多的情况下呈现,并返回未过滤的结果集,但不支持具有特定列呈现要求的多参数“ORM 批量 INSERT”语句。 参考资料:#10192
- [orm] [错误]
修复了阻止某些形式的 ORM“注释”对使用
Select.join()
对关系目标进行连接的子查询进行的问题。在特殊情况下使用这些注释,例如在PropComparator.and_()
和其他 ORM 特定场景中使用子查询时。 此更改也被回溯到:1.4.50 参考资料:#10223 - [orm] [错误]
修复了 ORM 从具有同名列的超类和子类的连接继承模型中生成 SELECT 时出现问题的问题,当生成 RECURSIVE 列列表时,不会发送正确的列名列表到
CTE
构造。。 参考资料:#10169 - [orm] [错误]
修复了一个相当严重的问题,即传递给
Session.execute()
的执行选项以及本身 ORM 执行的语句的执行选项将不会传递给 eager loaders,例如selectinload()
、immediateload()
和sqlalchemy.orm.subqueryload()
,从而使得禁用单个语句的缓存或者为单个语句使用schema_translate_map
等操作变得不可能,以及使用用户自定义执行选项。已经做出了更改,即现在所有对于Session.execute()
的用户界面执行选项都将传递到附加的 loaders 中。 作为这一更改的一部分,对于导致禁用缓存的“过度深层” eager loaders 的警告现在可以通过向Session.execute()
发送execution_options={"compiled_cache": None}
来在每个语句的基础上消除,这将禁用该范围内所有语句的缓存。 参考文献:#10231 - 【orm】【错误】
修复了 ORM 内部克隆的问题,该克隆用于像
Comparator.any()
这样的表达式,以生成相关 EXISTS 构造,会干扰 SQL 编译器的“笛卡尔积警告”特性,导致 SQL 编译器在语句的所有元素都正确连接时发出警告。 参考文献:#10124 - 【orm】【错误】
修复了
lazy="immediateload"
加载策略在某些情况下会将内部加载令牌放入 ORM 映射属性中的问题,例如在递归自引用加载时不应发生加载。作为这一更改的一部分,lazy="immediateload"
策略现在与其他 eager loaders 一样尊重relationship.join_depth
参数,对于自引用 eager 加载,如果将其设置为未设置或设置为零,将不会发生自引用 immediateload,如果将其设置为大于零的值,将会立即加载直到给定的深度。 参考文献:#10139 - 【orm】【错误】
修复了一个问题,即基于字典的集合(如
attribute_keyed_dict()
)未正确地完全序列化/反序列化,导致在反序列化后尝试突变此类集合时出现问题。 参考文献:#10175 - [orm] [bug]
修复了一个问题,即从另一个急切加载器使用
aliased()
对于连接的继承子类链的超类的本地列失败时,链接load_only()
或其他通配符使用defer()
。 参考文献:#10125 - [orm] [bug]
修复了一个问题,其中启用 ORM 的
select()
结构不会呈现仅通过Select.add_cte()
方法添加的任何 CTEs,而这些 CTEs 在语句中没有被引用。 参考文献:#10167
示例
- [examples] [bug]
dogpile_caching 示例已更新为 2.0 样式的查询。在“缓存查询”逻辑内部,添加了一个条件来区分
Query
和select()
在执行无效操作时。
引擎
- [engine] [bug]
修复了一个严重问题,即将
create_engine.isolation_level
设置为AUTOCOMMIT
(而不是使用Engine.execution_options()
方法),如果临时选择了替代隔离级别,则会导致无法将“autocommit”恢复到池化连接中,使用Connection.execution_options.isolation_level
。 参考文献:#10147
sql
- [sql] [bug]
修复了一个问题,即对
Column
或其他ColumnElement
进行反序列化会失败恢复正确的“比较器”对象,该对象用于生成特定于类型对象的 SQL 表达式。 此更改也已回溯至:1.4.50 参考文献:#10213
类型
- [typing] [usecase]
添加了新的仅用于类型的实用函数
Nullable()
和NotNullable()
,用于分别将列或 ORM 类的类型定义为可空或不可空。这些函数在运行时不起作用,返回不变的输入。 参考:#10173 - [typing] [bug]
类型改进:
- 当使用无返回的 DML 时,对于某些形式的
Session.execute()
,将返回CursorResult
- 修正了
Query.with_for_update.of
参数的类型,该参数在Query.with_for_update()
中被修复为正确的类型。 - 改进了某些 DML 方法中使用的
_DMLColumnArgument
类型,用于传递列表达式 - 给
literal()
添加了重载,以便在未提供literal.type_
参数时推断出返回类型为BindParameter[NullType]
- 给
ColumnElement.op()
添加了重载,以便在未提供ColumnElement.op.return_type
时推断出的类型为Callable[[Any], BinaryExpression[Any]]
- 给
ColumnElement.__add__()
添加了缺失的重载
Pull request 由 Mehdi Gmira 提供。 参考:#9185
- 当使用无返回的 DML 时,对于某些形式的
- [typing] [bug]
修复了
Session
和AsyncSession
方法中的问题,例如Session.connection()
,其中Session.connection.execution_options
参数被硬编码为不面向用户的内部类型。 参考:#10182
asyncio
- [asyncio] [usecase]
添加了新方法
AsyncConnection.aclose()
作为AsyncConnection.close()
的同义词,以及AsyncSession.aclose()
作为AsyncSession.close()
的同义词,添加到AsyncConnection
和AsyncSession
对象中,以提供与 Python 标准库@contextlib.aclosing
构造的兼容性。拉取请求由 Grigoriev Semyon 提供。 参考:#9698
mysql
- [mysql] [usecase] 由于 aiomysql 方言再次得到维护,已更新 aiomysql 方言。重新添加到 ci 测试中,使用版本 0.2.0。 此更改也 回溯 到:1.4.50
orm
- [orm] [usecase] 实现了 ORM 启用的 DML 语句的 “RETURNING ‘*’” 用例。这将尽可能地呈现,并返回未经过滤的结果集,但不支持具有特定列呈现要求的多参数 “ORM 批量插入” 语句。 参考:#10192
- [orm] [bug]
修复了一些形式的 ORM “注释” 无法对使用
Select.join()
进行的子查询进行注释的根本问题,这些子查询在特殊情况下使用,比如在PropComparator.and_()
和其他 ORM 特定场景中使用。 此更改也 回溯 到:1.4.50 参考:#10223 - [orm] [bug]
修复了 ORM 从具有同名列的超类和子类的联合继承模型生成 SELECT 时,当生成递归列列表时,某种方式未正确发送列名列表到
CTE
构造的问题,当递归列列表被生成时。 参考:#10169 - [orm] [bug]
修复了将执行选项传递给
Session.execute()
以及 ORM 执行语句本身的执行选项不会传播到selectinload()
、immediateload()
和sqlalchemy.orm.subqueryload()
等急切加载器的问题,使得无法禁用单个语句的缓存或对单个语句使用schema_translate_map
,以及使用用户自定义执行选项。已经进行了更改,所有针对Session.execute()
的用户可见执行选项都将传播到其他加载器。 作为这一变化的一部分,可以通过向Session.execute()
发送execution_options={"compiled_cache": None}
来在每个语句的基础上消除“过度深入”急切加载器导致缓存被禁用的警告,这将禁用该范围内所有语句的缓存。 参考:#10231 - [orm] [bug]
修复了内部克隆在 ORM 中用于生成类似
Comparator.any()
的表达式以产生相关的 EXISTS 结构时会干扰 SQL 编译器的“笛卡尔积警告”功能的问题,导致 SQL 编译器在所有语句元素正确连接时发出警告。 参考:#10124 - [orm] [bug]
修复了
lazy="immediateload"
加载策略在某些情况下会将内部加载标记放入 ORM 映射属性中的问题,例如在递归自引用加载中不应发生加载的情况。作为这一变化的一部分,lazy="immediateload"
策略现在以与其他急切加载器相同的方式尊重relationship.join_depth
参数用于自引用急切加载,其中将其未设置或设置为零将导致自引用的 immediateload 不会发生,将其设置为一个或更大的值将会 immediateload 直到给定深度。 参考:#10139 - [orm] [bug]
修复了诸如
attribute_keyed_dict()
之类基于字典的集合在反序列化时未能完全正确地 pickle/unpickle 的问题,导致在反序列化后尝试修改此类集合时出现问题。 参考:#10175 - [orm] [bug]
修复了从另一个急切加载器使用
aliased()
针对连接继承子类的情况下,链式调用load_only()
或其他通配符使用defer()
会导致对于超类本地列无法生效的问题。 参考:#10125 - [orm] [bug]
修复了 ORM 启用的
select()
构造不会呈现仅通过Select.add_cte()
方法添加的任何 CTE,而这些 CTE 在语句中没有被引用。 参考:#10167
examples
- [examples] [bug]
dogpile_caching 示例已更新为 2.0 风格的查询。在“缓存查询”逻辑中,添���了一个条件来区分在执行无效操作时
Query
和select()
之间的区别。
engine
- [engine] [bug]
修复了将
create_engine.isolation_level
设置为AUTOCOMMIT
(而不是使用Engine.execution_options()
方法)会导致如果使用Connection.execution_options.isolation_level
临时选择了替代隔离级别,则无法将“autocommit”恢复到池化连接的关键问题。 参考:#10147
sql
- [sql] [bug]
修复了反序列化
Column
或其他ColumnElement
时无法恢复正确的“比较器”对象的问题,该对象用于生成特定于类型对象的 SQL 表达式。 此更改也回溯到:1.4.50 参考:#10213
typing
- [typing] [usecase]
添加了新的仅用于类型的实用函数
Nullable()
和NotNullable()
,用于分别将列或 ORM 类类型化为可空或不可空。这些函数在运行时不起作用,返回不变的输入。 参考:#10173 - [typing] [bug]
类型改进:
- 一些形式的
Session.execute()
中返回了CursorResult
,其中使用了没有返回的 DML - 修正了
Query.with_for_update.of
参数的类型,在Query.with_for_update()
内部。 - 对一些 DML 方法使用的
_DMLColumnArgument
类型进行了改进,以传递列表达式。 - 添加了对
literal()
的重载,以便推断返回类型为BindParameter[NullType]
,其中literal.type_
参数为 None - 添加了对
ColumnElement.op()
的重载,以便在未提供ColumnElement.op.return_type
时推断类型为Callable[[Any], BinaryExpression[Any]]
。 - 添加了对
ColumnElement.__add__()
的缺失重载
拉取请求由 Mehdi Gmira 提供。 参考:#9185
- 一些形式的
- [typing] [bug]
修复了
Session
和AsyncSession
方法中的问题,例如Session.connection()
,其中Session.connection.execution_options
参数被硬编码为不是面向用户的内部类型。 参考:#10182
asyncio
- [asyncio] [usecase]
新增了
AsyncConnection.aclose()
作为AsyncConnection.close()
的同义词,以及AsyncSession.aclose()
作为AsyncSession.close()
的同义词,用于AsyncConnection
和AsyncSession
对象,以与 Python 标准库@contextlib.aclosing
构造兼容。感谢 Grigoriev Semyon 提交的拉取请求。 参考:#9698
mysql
- [mysql] [usecase] 更新了 aiomysql 方言,因为该方言似乎再次得到维护。重新使用版本 0.2.0 进行 ci 测试。 此更改也已回溯至:1.4.50
2.0.19
发布日期:2023 年 7 月 15 日
orm
- [orm] [bug]
修复了直接设置关系集合的问题,其中新集合中的对象已经存在时,不会触发该对象的级联事件,导致如果该对象尚未存在,则不会添加到
Session
中。这与#6471类似,并且由于在 2.0 系列中删除了cascade_backrefs
,这个问题更加明显。作为#6471的一部分,现在还为已存在于相同集合的批量设置中的现有成员触发AttributeEvents.append_wo_mutation()
事件。 参考:#10089 - [orm] [bug]
修复了通过 backref 与未合并到
Session
中的加载集合相关联的对象的问题,由于在 2.0 系列中删除了cascade_backrefs
,这些对象不会发出警告,即使它们是集合的待定成员;在其他类似情况下,当要刷新的集合包含将被实质性丢弃的未附加对象时,会发出警告。为 backref-待定集合成员添加警告增加了与可能存在或不存在的集合以及基于不同关系加载策略在不同时间可能刷新或不刷新的集合的一致性。 引用:#10090 - [orm] [bug] [regression]
通过 #9805 引起的额外回归被修复,其中对语句上的“ORM”标志更积极的传播可能导致在包含没有 ORM 实体的 ORM
Query
构造中引发内部属性错误,即使在这种情况下 ORM 启用的 UPDATE 和 DELETE 语句中也不包含 ORM 实体。 引用:#10098
engine
- [engine] [bug]
将
Row.t
和Row.tuple()
重命名为Row._t
和Row._tuple()
;这是为了遵循所有在Row
上的方法和预定义属性应该以 Python 标准库namedtuple
的风格命名的政策,所有固定名称都有一个前导下划线,以避免与现有列名称发生冲突。以前的方法/属性现在已被弃用,并将发出弃用警告。 引用:#10093 - [engine] [bug]
对
make_url()
函数添加了对非字符串、非URL
对象的检测,允许立即抛出ArgumentError
,而不是在后来导致失败。特殊逻辑确保模拟形式的URL
可以通过。感谢 Grigoriev Semyon 的拉取请求。 引用:#10079
postgresql
- [postgresql] [bug]
由于在#10004中对 PostgreSQL URL 解析进行了改进,导致的回归问题已修复,其中“host”查询字符串参数中包含冒号,以支持各种第三方代理服务器和/或方言,将无法正确解析,因为这些被视为
host:port
组合。解析已更新,只有当主机名仅包含字母数字字符,点或破折号(例如没有斜杠),后跟一个冒号,然后跟着一个零个或多个整数的令牌时,才将冒号视为指示host:port
值。在所有其他情况下,整个字符串被视为主机。 参考:#10069 - [postgresql] [bug]
修复了与
CITEXT
数据类型的比较会将右侧转换为VARCHAR
的问题,导致右侧不被解释为CITEXT
数据类型,适用于 asyncpg、psycopg3 和 pg80000 方言。这导致CITEXT
类型在实际使用中基本上无法使用;现在已修复此问题,并且测试套件已经更正,以正确断言表达式是否被正确渲染。 参考:#10096
orm
- [orm] [bug]
修复了直接设置关系集合的问题,其中新集合中的对象已经存在时,不会触发该对象的级联事件,导致如果该对象不存在,则不会被添加到
Session
中。这与#6471类似,并且由于在 2.0 系列中删除了cascade_backrefs
,这个问题更加明显。作为#6471的一部分添加的AttributeEvents.append_wo_mutation()
事件现在也会对已存在于同一集合的批量设置中的现有成员发出。 参考:#10089 - [orm] [bug]
修复了一个问题,即通过反向引用与未合并到
Session
的未加载集合相关联的对象,因为在 2.0 系列中删除了cascade_backrefs
,所以不会发出警告,即这些对象未被包含在刷新中,即使它们是集合的待处理成员;在其他类似情况下,当正在刷新的集合包含将被基本丢弃的非附加对象时,将发出警告。对于反向引用挂起的集合成员添加警告,可以建立更大一致性,这些集合可能存在或不存在,并可能根据不同的关系加载策略在不同的时间进行刷新或不刷新。 参考:#10090 - [orm] [bug] [regression]
修复了由#9805导致的额外回归,其中对语句上的“ORM”标志的更积极传播可能导致在嵌入了 ORM
Query
构造的核心 SQL 语句中包含没有 ORM 实体的情况下导致内部属性错误,即使在这种情况下,ORM 启用的 UPDATE 和 DELETE 语句也不包含 ORM 实体。 参考:#10098
引擎
- [engine] [bug]
将
Row.t
和Row.tuple()
重命名为Row._t
和Row._tuple()
;这是为了符合所有方法和预定义属性在Row
上应采用 Python 标准库namedtuple
风格的政策,其中所有固定名称都带有前导下划线,以避免与现有列名称发生冲突。以前的方法/属性现已弃用,并将发出弃用警告。 参考:#10093 - [engine] [bug]
添加了对非字符串、非
URL
对象的检测到make_url()
函数,允许立即抛出ArgumentError
,而不是后来导致失败。特殊逻辑确保允许通过URL
的模拟形式。感谢 Grigoriev Semyon 的拉取请求。 参考:#10079
postgresql
- [postgresql] [bug]
修复了在#10004中改进 PostgreSQL URL 解析时引起的回归,其中在主机查询字符串参数中含有冒号的情况下,以支持各种第三方代理服务器和/或方言,将无法正确解析,因为这些被评估为
host:port
组合。 解析已更新为仅在主机名仅包含字母数字字符以及仅包含点或破折号(例如没有斜杠)的情况下,考虑冒号表示host:port
值,后跟零个或多个整数的全整数标记的情况下,才表示主机。 在所有其他情况下,将完整字符串视为主机。 引用:#10069 - [postgresql] [bug]
修复了与
CITEXT
数据类型的比较问题,导致右侧被转换为VARCHAR
,导致右侧未被解释为CITEXT
数据类型,适用于 asyncpg、psycopg3 和 pg80000 方言。 这导致CITEXT
类型在实际使用中基本不可用;现已修复此问题,并已更正测试套件以正确断言表达式是否被正确呈现。 引用:#10096
2.0.18
发布日期:2023 年 7 月 5 日
引擎
- [引擎] [bug]
调整了
create_engine.schema_translate_map
功能,使得语句中的所有模式名称现在都被标记化,而不管特定名称是否在给定的立即模式翻译映射中,并且在执行时当键不在实际模式翻译映射中时回退到替换原始名称。 这两个更改允许在每次运行时使用包含或不包含各种键的模式翻译映射来重复使用已编译的对象,从而使得当每次使用时都使用具有不同键集的模式翻译映射时,缓存的 SQL 结构可以继续在运行时正常工作。 另外,还添加了在相同语句的调用间获得或失去None
键的 schema_translate_map 字典的检测,这会影响语句的编译,并且与缓存不兼容; 这些情况下会引发异常。 引用:#10025
sql
- [sql] [bug]
修复了当使用“标志”时
ColumnOperators.regexp_match()
不会产生“稳定”的缓存密钥的问题,即,缓存密钥每次都会更改,导致缓存污染。对于带有标志和实际替换表达式的ColumnOperators.regexp_replace()
也存在相同的问题。现在,标志被表示为固定的修饰符字符串,呈现为 safestring,而不是绑定参数,替换表达式在“二进制”元素的主要部分中确定,因此它生成适当的缓存密钥。 请注意,作为此更改的一部分,ColumnOperators.regexp_match.flags
和ColumnOperators.regexp_replace.flags
已修改为仅渲染为文字字符串,而以前它们被渲染为完整的 SQL 表达式,通常是绑定参数。这些参数应始终作为普通的 Python 字符串传递,而不是作为 SQL 表达式构造;不希望在实践中使用 SQL 表达式构造此参数,因此这是一个不兼容的更改。 此更改还修改了生成的表达式的内部结构,对于带有或不带有标志的ColumnOperators.regexp_replace()
和带有标志的ColumnOperators.regexp_match()
。可能已经实现了自己的正则表达式实现的第三方方言(在搜索中找不到此类方言,因此预期影响很小)需要调整结构的遍历以适应。 此更改还 回溯到:1.4.49 参考:#10042 - [sql] [错误]
修复了在主要内部
CacheKey
构造中的问题,其中__ne__()
运算符未正确实现,导致当比较CacheKey
实例时产生荒谬的结果。 此更改还 回溯到:1.4.49
扩展
- [扩展] [用例]
向
association_proxy()
association_proxy.create_on_none_assignment
添加了新选项;当一个关联代理引用一个标量关系并被赋予值None
,并且引用的对象不存在时,通过创建者创建一个新对象。这显然是 1.2 系列中的一个未定义行为,已经被悄悄移除了。 参考资料:#10013
类型提示
- [类型提示] [用例]
当使用
sqlalchemy.sql.operators
中的独立运算符函数(例如sqlalchemy.sql.operators.eq
)时,改进了类型提示。 参考资料:#10054 - [类型提示] [错误]
修正了
aliased()
结构内部的一些类型提示,以正确接受已使用Table.alias()
别名的Table
对象,以及对传递为“可选择”参数的FromClause
对象的一般支持,因为这都得到了支持。 参考资料:#10061
postgresql
- [postgresql] [用例] 为 asyncpg 方言添加了多主机支持。还添加了对“多主机”用例的 PostgreSQL URL 例程的一般改进和错误检查。拉取请求由 Ilia Dmitriev 提供。 请参阅 多主机连接 参考资料:#10004
- [postgresql] [错误]
向所有 PostgreSQL 方言添加了新参数
native_inet_types=False
,该参数指示 DBAPI 使用的转换器将 PostgreSQL 的INET
和CIDR
列中的行转换为 Pythonipaddress
数据类型时应禁用,返回字符串。这样,编写用于这些数据类型的字符串的代码可以在无需代码更改的情况下添加此参数到create_engine()
或create_async_engine()
函数调用中而迁移到 asyncpg、psycopg 或 pg8000。 请参阅 网络数据类型 参考:#9945
mariadb
- [mariadb] [用例] [反射]
允许从 MariaDB 反射
UUID
列。这使得 Alembic 能够正确地检测现有 MariaDB 数据库中这些列的类型。 参考:#10028
mssql
- [mssql] [用例]
在 MSSQL 方言中添加了对 COLUMNSTORE 索引的创建和反射支持。可以在指定了
mssql_columnstore=True
的索引上指定。 参考:#7340 - [mssql] [错误] [sql]
修复了在对具有显式排序规则的字符串类型执行
Cast
时会在 CAST 函数内部呈现 COLLATE 子句的问题,从而导致语法错误。 参考:#9932
引擎
- [引擎] [错误]
调整了
create_engine.schema_translate_map
功能,使得语句中的所有模式名称现在都被标记化,无论指定了具体名称是否在立即模式翻译映射中,都会在执行时回退到原始名称。这两个变化允许对具有包含或不包含不同键集的模式翻译映射的编译对象进行重复使用,每次运行时使用不同的模式翻译映射,从而使得缓存的 SQL 构造在运行时继续工作。此外,增加了在同一语句的不同调用中增加或减少None
键的 schema_translate_map 字典的检测,这会影响语句的编译,并且不兼容缓存;对于这些情况,会引发异常。 参考:#10025
SQL
- [sql] [错误]
修复了使用“flags”时
ColumnOperators.regexp_match()
未生成“稳定”缓存键的问题,即每次缓存键都会发生变化,导致缓存污染。相同的问题也存在于带有 flags 和实际替换表达式的ColumnOperators.regexp_replace()
中。现在,flags 被表示为固定的修改器字符串,呈现为安全字符串,而不是绑定参数,并且替换表达式在“binary”元素的主要部分内建立,以生成适当的缓存键。 注意,作为这一变更的一部分,ColumnOperators.regexp_match.flags
和ColumnOperators.regexp_replace.flags
已经修改为仅呈现为字面字符串,而以前它们呈现为完整的 SQL 表达式,通常是绑定参数。这些参数应始终作为普通的 Python 字符串传递,而不是作为 SQL 表达式构造;预计实践中不会使用 SQL 表达式构造来传递此参数,因此这是一个不兼容的变更。 此变更还修改了生成的表达式的内部结构,用于带有或不带有 flags 的ColumnOperators.regexp_replace()
,以及带有 flags 的ColumnOperators.regexp_match()
。可能已经实现了自己的正则表达式的第三方方言(在搜索中找不到这样的方言,因此预期影响很小)需要调整结构的遍历以适应。 此变更还 回溯 到:1.4.49 参考文献:#10042 - [SQL] [错误]
修复了大部分内部
CacheKey
构造中__ne__()
运算符未正确实现的问题,导致在将CacheKey
实例相互比较时产生荒谬的结果。 此变更还 回溯 到:1.4.49
扩展
- [扩展] [用例]
为
association_proxy()
添加了新选项association_proxy.create_on_none_assignment
; 当将引用标量关系的关联代理分配为None
值时,并且引用的对象不存在时,通过创建器创建一个新对象。在 1.2 系列中,这显然是一种未定义的行为,被默默删除了。 参考:#10013
输入
- [输入] [用例]
当使用来自
sqlalchemy.sql.operators
的独立运算符函数(如sqlalchemy.sql.operators.eq
)时,改进了类型提示。 参考:#10054 - [输入] [错误]
修复了
aliased()
构造中的一些类型提示,以正确接受已使用Table.alias()
别名的Table
对象,以及一般性对于FromClause
对象作为“selectable”参数的支持,因为这都是受支持的。 参考:#10061
postgresql
- [postgresql] [用例] 为 asyncpg 方言添加了多主机支持。还为“多主机”用例的 PostgreSQL URL 例程添加了一般性改进和错误检查。感谢 Ilia Dmitriev 的拉取请求。 参见 多主机连接 参考:#10004
- [postgresql] [错误]
对所有 PostgreSQL 方言添加了新参数
native_inet_types=False
,指示 DBAPI 使用的转换器将 PostgreSQLINET
和CIDR
列的行转换为 Pythonipaddress
数据类型时应禁用,而是返回字符串。这允许为这些数据类型编写使用字符串的代码迁移到 asyncpg、psycopg 或 pg8000 而无需其他代码更改,只需将此参数添加到create_engine()
或create_async_engine()
函数调用中。 参见 网络数据类型 参考:#9945
mariadb
- [mariadb] [usecase] [reflection]
允许从 MariaDB 反射
UUID
列。 这使得 Alembic 能够正确地检测到现有 MariaDB 数据库中此类列的类型。 参考:#10028
mssql
- [mssql] [usecase]
添加了对 MSSQL 方言中 COLUMNSTORE 索引的创建和反射支持。 可以在指定
mssql_columnstore=True
的索引上指定。 参考:#7340 - [mssql] [bug] [sql]
修复了将具有显式排序规则的字符串类型执行
Cast
时会在 CAST 函数内部呈现 COLLATE 子句的问题,这导致语法错误。 参考:#9932
2.0.17
发布日期:2023 年 6 月 23 日
orm
- [orm] [bug] [regression]
修复了 2.0 系列中的回归问题,其中使用
undefer_group()
与selectinload()
或subqueryload()
的查询会引发AttributeError
。 拉取请求由 Matthew Martin 提供。 参考:#9870 - [orm] [bug]
修复了在 ORM 注释声明中的问题,该问题阻止了
declared_attr
在未返回Mapped
数据类型的混合类型上使用,而是返回了诸如AssociationProxy
之类的补充 ORM 数据类型。 声明式运行时会错误地尝试解释此注释为需要Mapped
并引发错误。 参考:#9957 - [orm] [bug] [typing]
修复了使用
declared_attr
函数的AssociationProxy
返回类型被禁止的类型问题。 参考:#9957 - [orm] [bug] [regression]
修复了 2.0.16 中由#9879引入的回归,其中将可调用对象传递给
mapped_column.default
参数时,同时设置init=False
会将此值解释为 Dataclass 默认值,该值将直接分配给对象的新实例,绕过了作为底层Column.default
值生成器的默认生成器所发生的情况。现在检测到此条件以保持先前的行为,但发出了对此模棱两可用法的弃用警告;为了为Column
填充默认生成器,应使用mapped_column.insert_default
参数,该参数使其与固定名称的mapped_column.default
参数相区分,根据 pep-681。 参考:#9936 - [orm] [bug]
对 ORM
Session
“状态更改”系统进行了额外的强化和文档编写,该系统检测到Session
和AsyncSession
对象的并发使用;在从底层引擎获取连接的过程中添加了额外的检查,在内部连接管理方面是一个关键部分。 参考:#9973 - [orm] [bug]
修复了 ORM 加载器策略逻辑中的问题,进一步允许在复杂的继承多态/别名/
of_type()
关系链中横跨长链的contains_eager()
加载器选项以正确生效于查询中。 参考:#10006 - [orm] [bug]
修复了在
registry.type_annotation_map
中首次添加的Enum
数据类型支持中的问题,其中使用映射中的自定义Enum
并且在映射中使用固定配置会导致传输Enum.name
参数失败,其中一个问题是如果枚举值作为单独的值传递,则会阻止 PostgreSQL 枚举正常工作。逻辑已更新,使“name”被传输,但也使默认的Enum
不会设置一个硬编码的名称为"enum"
。 参考:#9963
ORM 声明性
- [ORM] [声明性] [错误]
当将 ORM
relationship()
和其他MapperProperty
对象同时分配给两个不同的类属性时,会发出警告;只会映射其中一个属性。对于此情况的警告已经适用于Column
和mapped_column
对象。 参考:#3532
扩展
- [扩展] [错误] 修复了与 mypy 1.4 结合使用的 mypy 插件中的问题。 此更改还被 回溯 至:1.4.49
typing
- [类型] [错误]
修复了阻止
WriteOnlyMapped
和DynamicMapped
属性在 ORM 查询中完全使用的类型问题。 参考:#9985
postgresql
- [postgresql] [用例] pg8000 方言现在支持 RANGE 和 MULTIRANGE 数据类型,使用现有的 RANGE API 描述在 Range and Multirange Types。pg8000 驱动程序从版本 1.29.8 开始支持范围和多范围类型。感谢 Tony Locke 提交的拉取请求。 参考:#9965
ORM
- [ORM] [错误] [回归]
修复了 2.0 系列中的回归问题,即使用
undefer_group()
与selectinload()
或subqueryload()
的查询会引发AttributeError
。感谢 Matthew Martin 提交的拉取请求。 参考:#9870 - [orm] [bug]
修复了 ORM 注释声明中的问题,该问题导致无法在未返回
Mapped
数据类型的混合使用declared_attr
,而是返回了诸如AssociationProxy
等补充的 ORM 数据类型。声明式运行时错误地尝试将此注释解释为需要Mapped
并引发错误。 参考:#9957 - [orm] [bug] [typing]
修复了使用
declared_attr
函数中的AssociationProxy
返回类型被禁止的类型问题。 参考:#9957 - [orm] [bug] [regression]
修复了 2.0.16 中由 #9879 引入的回归问题,当将可调用对象传递给
mapped_column.default
参数时,同时设置init=False
会将此值解释为 Dataclass 的默认值,该值将直接分配给对象的新实例,绕过了基础Column.default
值生成器在Column
上发生的默认生成器。现在检测到这种情况以保持先前的行为,但是对于这种模棱两可的使用会发出弃用警告;要为Column
填充默认生成器,应使用mapped_column.insert_default
参数,该参数与mapped_column.default
参数相区分,其名称固定为 pep-681。 参考:#9936 - [orm] [bug]
对于 ORM
Session
的“状态更改”系统进行了额外的加固和文档编制,该系统检测到同时使用Session
和AsyncSession
对象;在获取来自底层引擎的连接过程中添加了额外的检查,这是关于内部连接管理的关键部分。 参考:#9973 - [orm] [bug]
修复了 ORM 加载程序策略逻辑中的问题,进一步允许在复杂的继承多态/别名/ of_type() 关系链上跨长链的
contains_eager()
加载选项,以在查询中产生正确的效果。 参考:#10006 - [orm] [bug]
修复了在
registry.type_annotation_map
中首次添加的Enum
数据类型支持中出现的问题,该问题涉及使用映射中的固定配置的自定义Enum
时会失败传输Enum.name
参数,其中,如果将枚举值作为单独的值传递,则会导致阻止 PostgreSQL 枚举起作用的问题。逻辑已更新,使“name”被传递,但同时也确保了默认Enum
不会设置硬编码的名称为"enum"
。 引用:#9963
ORM 声明
- [orm] [声明] [错误]
当 ORM
relationship()
和其他MapperProperty
对象同时分配给两个不同的类属性时,会发出警告;只有其中一个属性会被映射。对于这种情况的警告已经存在于Column
和mapped_column
对象中。 引用:#3532
扩展
- [扩展] [错误] 修复了与 mypy 1.4 一起使用时的 mypy 插件中的问题。 此更改也被回溯到:1.4.49
打字
- [打字] [错误]
修复了一个打字错误问题,该问题导致
WriteOnlyMapped
和DynamicMapped
属性在 ORM 查询中无法完全使用。 引用:#9985
postgresql
- [postgresql] [用例] pg8000 方言现在支持 RANGE 和 MULTIRANGE 数据类型,使用现有的 RANGE 和 Multirange 类型中描述的 RANGE API。Range 和 multirange 类型在 pg8000 驱动程序的版本 1.29.8 中受支持。感谢 Tony Locke 提供的拉取请求。 引用:#9965
2.0.16
发布日期:2023 年 6 月 10 日
平台
- [平台] [用例] 兼容性改进,允许完整测试套件在 Python 3.12.0b1 上通过。
ORM
- [orm] [用例]
改进
DeferredReflection.prepare()
,接受任意的**kw
参数,这些参数将传递给MetaData.reflect()
,允许用例,例如反射视图以及传递特定于方言的参数。此外,现代化了DeferredReflection.prepare.bind
参数,使得一个Engine
或Connection
都可作为“bind”参数。 参考:#9828 - [orm] [bug]
修复了
DeclarativeBaseNoMeta
声明基类无法与非映射的混入或抽象类一起使用的问题,而是引发AttributeError
。 参考:#9862 - [orm] [bug] [regression]
修复了 2.0 系列中的回归问题,其中
validates.include_backrefs
的默认值在validates()
函数中更改为False
。现在将此默认值恢复为True
。 参考:#9820 - [orm] [bug] 修复了一个新功能中的错误,该功能允许在 ORM 通过主键进行批量更新 时与 WHERE 子句一起使用,该功能是在版本 2.0.11 中作为 #9583 的一部分添加的,如果发送的字典不包括每行的主键值,则会通过批量处理过程并为行包含“pk=NULL”,这将导致静默失败。如果未提供批量更新的主键值,则现在会引发异常。 参考:#9917
- [orm] [bug] [dataclasses]
修复了一个问题,即生成指定了
default
值并设置init=False
的数据类字段不起作用。在这种情况下,数据类的行为是在类上设置默认值,这与 SQLAlchemy 使用的描述符不兼容。为了支持这种情况,生成数据类时将默认值转换为default_factory
。 参考:#9879 - [orm] [bug]
每当在
Mapper
上添加属性时,如果已经配置了 ORM 映射属性,或者类上已经存在属性,则会发出弃用警告。以前,对于这种情况有一个不一致地发出的非弃用警告。对于这个警告的逻辑已经改进,以便检测到终端用户替换属性,同时不会误报内部声明式和其他情况,其中替换描述符为新描述符是预期的。 参考:#9841 - [orm] [bug]
改进了
registry.map_imperatively()
方法的map_imperatively.local_table
参数上的参数检查,确保仅传递Table
或其他FromClause
,而不是现有的映射类,这会导致未定义的行为,因为对象将进一步解释为新的映射。 参考:#9869 - [orm] [bug]
InstanceState.unloaded_expirable
属性是InstanceState.unloaded
的同义词,现已弃用;此属性始终是特定于实现的,并且不应该是公共的。 参考:#9913
asyncio
- [asyncio] [usecase]
在
create_async_engine()
中添加了新的create_async_engine.async_creator
参数,其作用与create_engine()
的create_engine.creator
参数相同。这是一个无参数可调用对象,使用 asyncio 数据库驱动程序直接提供新的 asyncio 连接。create_async_engine()
函数将在适当的结构中包装驱动程序级连接。拉取请求由杰克·沃瑟斯普恩提供。 参考:#8215
postgresql
- [postgresql] [usecase] [reflection]
在 PostgreSQL 反射中,将
NAME
列转换为TEXT
当使用ARRAY_AGG
时。这似乎提高了与一些不支持NAME
类型聚合的 PostgreSQL 派生产品的兼容性。 参考:#9838 - [postgresql] [usecase] 统一了自定义的 PostgreSQL 运算符定义,因为它们在多个不同的数据类型之间共享。 参考:#9041
- [postgresql] [usecase]
增加了对 PostgreSQL 10
NULLS NOT DISTINCT
特性的支持,使用方言选项postgresql_nulls_not_distinct
。更新了反射逻辑,以正确考虑此选项。感谢 Pavel Siarchenia 的拉取请求。 参考:#8240 - [postgresql] [bug]
在 PostgreSQL 特定运算符上使用正确的优先级,比如
@>
。之前的优先级错误,导致在与ANY
或ALL
结构渲染时括号错误。 参考:#9836 - [postgresql] [bug]
修复了
ColumnOperators.like.escape
和类似参数不允许空字符串作为传递的“转义”字符的问题;这是 PostgreSQL 支持的语法。感谢 Martin Caslavsky 的拉取请求。 参考:#9907
platform
- [platform] [usecase] 兼容性改进,使完整的测试套件能够在 Python 3.12.0b1 上通过。
orm
- [orm] [usecase]
改进了
DeferredReflection.prepare()
,接受传递给MetaData.reflect()
的任意**kw
参数,允许用例如反射视图以及传递方言特定参数。此外,现代化了DeferredReflection.prepare.bind
参数,以便接受Engine
或Connection
作为“bind”参数。 参考:#9828 - [orm] [bug]
修复了
DeclarativeBaseNoMeta
声明基类无法与非映射混入类或抽象类一起使用的问题,而是引发AttributeError
。 参考:#9862 - [orm] [bug] [regression]
修复了 2.0 系列中的回归问题,其中
validates.include_backrefs
的默认值在validates()
函数中被更改为False
。现在将此默认值恢复为True
。 参考:#9820 - [orm] [bug] 修复了新功能中的 bug,该功能允许在 ORM 按主键批量更新 中使用 WHERE 子句,该功能在版本 2.0.11 中作为 #9583 的一部分添加,其中发送的字典未包含每行的主键值时,将通过批量处理并为行包括“pk=NULL”,默默失败。如果未提供批量更新的主键值,则现在会引发异常。 参考:#9917
- [orm] [bug] [dataclasses]
修复了生成指定
default
值并设置init=False
的 dataclasses 字段不起作用的问题。在这种情况下,dataclasses 的行为是在类上设置默认值,这与 SQLAlchemy 使用的描述符不兼容。为了支持这种情况,在生成 dataclass 时将默认值转换为default_factory
。 参考:#9879 - [orm] [bug]
当向
Mapper
添加属性时,如果已经配置了 ORM 映射属性,或者类上已经存在属性,则会发出弃用警告。以前,对于这种情况,存在一个不一致发出的非弃用警告。现在已经改进了此警告的逻辑,以便在检测到用户替换属性时发出警告,同时不会对内部 Declarative 和其他情况产生误报,其中预期使用新描述符替换旧描述符。 参考:#9841 - [orm] [bug]
改进了
registry.map_imperatively()
方法的map_imperatively.local_table
参数的参数检查,确保只传递了Table
或其他FromClause
,而不是已存在的映射类,因为这将导致对象在进一步解释时出现未定义的行为。 参考:#9869 - [orm] [错误]
InstanceState.unloaded_expirable
属性是InstanceState.unloaded
的同义词,并已弃用;此属性始终是特定于实现的,不应公开。 参考:#9913
asyncio
- [asyncio] [用例]
向
create_async_engine()
添加了新的create_async_engine.async_creator
参数,它实现了与create_engine()
的create_engine.creator
参数相同的目的。这是一个无参数的可调用对象,提供一个新的 asyncio 连接,直接使用 asyncio 数据库驱动程序。create_async_engine()
函数将以适当的结构包装驱动程序级别的连接。感谢 Jack Wotherspoon 提交的拉取请求。 参考:#8215
postgresql
- [postgresql] [用例] [反射]
在使用 PostgreSQL 反射时,将
NAME
列转换为TEXT
。这似乎提高了与一些 PostgreSQL 派生产品的兼容性,这些产品可能不支持在NAME
类型上进行聚合。 参考:#9838 - [postgresql] [用例] 统一了自定义 PostgreSQL 操作符的定义,因为它们在多个不同的数据类型之间共享。 参考:#9041
- [postgresql] [用例]
增加了对 PostgreSQL 10
NULLS NOT DISTINCT
特性的支持,该特性使用方言选项postgresql_nulls_not_distinct
。 更新了反射逻辑以正确考虑此选项。 Pavel Siarchenia 的 Pull request 提供支持。 参考:#8240 - [postgresql] [bug]
在 PostgreSQL 特定运算符上使用正确的优先级,例如
@>
。 之前优先级错误,导致在与ANY
或ALL
结构进行渲染时出现错误的括号。 参考:#9836 - [postgresql] [bug]
修复了一个问题,
ColumnOperators.like.escape
和类似参数不允许空字符串作为参数,该参数将作为“转义”字符传递;这是 PostgreSQL 支持的语法。 感谢 Martin Caslavsky 的 Pull requset。 参考:#9907
2.0.15
发布日期:2023 年 5 月 19 日
orm
- [orm] [bug]
随着越来越多的项目开始使用新型“2.0” ORM 查询,显然“自动刷新”的条件性质,基于给定语句是否涉及 ORM 实体,正在变得更加关键。直到现在,“ORM”标志对于语句是否返回与 ORM 实体或列对应的行一直是松散的;“ORM”标志的原始目的是启用 ORM 实体获取规则,该规则将后处理应用于核心结果集以及将 ORM 加载器策略应用于语句。 对于不建立在包含 ORM 实体的行上的语句,认为“ORM”标志基本上是不必要的。
仍然可能是“自动刷新”对于 所有 使用
Session.execute()
和相关方法更好,即使对于纯粹的 Core SQL 构造也是如此。 但是,这可能仍然会影响不期望的遗留情况,并且可能更多地成为 2.1 版本的事情。 然而,目前“ORM 标志”的规则已经放宽,因此任何语句,包括在 WHERE / ORDER BY / GROUP BY 子句中的 ORM 实体或属性,在标量子查询中等都将启用此标志。 这将导致对这些语句进行“自动刷新”,并且还可以通过ORMExecuteState.is_orm_statement
事件级属性可见。 参考:#9805
postgresql
- [postgresql] [bug] [regression]
修复了 PostgreSQL 方言的基本
Uuid
数据类型,以充分利用 PG 特定的UUID
方言特定数据类型,当选择“native_uuid”时,以便包含 PG 驱动程序的行为。由于作为#9618的一部分进行的 insertmanyvalues 改进,这个问题变得明显,类似于#9739,asyncpg 驱动程序对数据类型转换的存在与否非常敏感,当使用这种通用类型时,必须调用 PostgreSQL 驱动程序特定的本地UUID
数据类型,以便进行这些转换。 参考:#9808
orm
- [orm] [bug]
随着越来越多的项目使用新式“2.0” ORM 查询,显而易见的是,“autoflush”的条件性,基于给定语句是否涉及 ORM 实体,正在变得更加关键。直到现在,对于语句是否返回与 ORM 实体或列对应的行,一直是围绕“ORM”标志的松散基础;“ORM”标志的最初目的是启用 ORM 实体获取规则,这些规则将后处理应用于 Core 结果集以及 ORM 加载器策略到语句。对于不建立在包含 ORM 实体的行上的语句,认为“ORM”标志基本上是不必要的。
仍然可能是“autoflush”对于所有使用
Session.execute()
和相关方法更好,即使是纯粹的 Core SQL 构造。然而,这可能会影响到不期望的遗留情况,可能更多是 2.1 的事情。但是,目前,“ORM-flag”的规则已经放宽,以便包含 ORM 实体或属性的语句中的任何地方,包括仅在 WHERE / ORDER BY / GROUP BY 子句中,在标量子查询中等,将启用此标志。这将导致这些语句发生“autoflush”,并且还可以通过ORMExecuteState.is_orm_statement
事件级属性可见。 参考:#9805
postgresql
- [postgresql] [bug] [regression]
修复了基本的
Uuid
数据类型,使其在选择“native_uuid”时充分利用了 PostgreSQL 方言的 PG 特定UUID
方言特定数据类型,以便包含 PG 驱动程序的行为。这个问题由于作为#9618的一部分所做的 insertmanyvalues 改进而变得显而易见,其中与#9739类似,asyncpg 驱动程序对是否存在数据类型转换非常敏感,当使用此通用类型时,必须调用 PostgreSQL 驱动程序特定的本地UUID
数据类型,以便进行这些转换。 参考:#9808
2.0.14
发布日期:2023 年 5 月 18 日
orm
- [orm] [bug]
修改了
JoinedLoader
的实现,在一个特定的区域使用了更简单的方法,之前它使用了一个缓存结构,该结构将在线程之间共享。这样做的原因是避免潜在的竞争条件,这被怀疑是导致特定崩溃的原因。所涉及的缓存结构最终仍然通过编译后的 SQL 缓存“缓存”,因此不预期出现性能下降。 参考:#9777 - [orm] [bug] [regression]
修复了在
CTE
构造中使用update()
或delete()
,然后在select()
中使用会引发CompileError
的回归,原因是 ORM 相关规则执行 ORM 级别的更新/删除语句。 参考:#9767 - [orm] [bug]
在新的 ORM Annotated Declarative 中修复了使用
ForeignKey
(或其他列级约束)位于mapped_column()
中,然后通过 pep-593Annotated
复制到模型中时,将每个约束的副本应用到目标Table
中的Column
,从而导致不正确的 CREATE TABLE DDL 以及 Alembic 下的迁移指令。 参考:#9766 - [orm] [bug]
修复了使用
joinedload()
加载器选项时,使用附加的关系条件的问题,其中附加的条件本身包含引用加入实体的相关子查询,因此还需要对别名实体进行“调整”,否则会排除这种调整,导致 joinedload 的 ON 子句错误。 References: #9779
sql
- [sql] [usecase]
将 MSSQL 的
try_cast()
函数泛化为`sqlalc