The :class:`.TypeDecorator` class will now emit a warning when used in SQL
compilation with caching unless the ``.cache_ok`` flag is set to ``True``
or ``False``. ``.cache_ok`` indicates that all the parameters passed to the
object are safe to be used as a cache key, ``False`` means they are not.
Fixes: #6436
Change-Id: Ib1bb7dc4b124e38521d615c2e2e691e4915594fb
Fixed regression caused by the "empty in" change just made in
🎫`6397` 1.4.12 where the expression needs to be parenthesized for
the "not in" use case, otherwise the condition will interfere with the
other filtering criteria.
also amends StrSQLCompiler to use the newer "empty IN" style for
its compilation process.
Fixes: #6428
Change-Id: I182a552fc0d3065a9e38c0f4ece2deb143735c36
Established a deprecation path for calling upon the
:meth:`_cursor.CursorResult.keys` method for a statement that returns no
rows to provide support for legacy patterns used by the "records" package
as well as any other non-migrated applications. Previously, this would
raise :class:`.ResourceClosedException` unconditionally in the same way as
it does when attempting to fetch rows. While this is the correct behavior
going forward, the :class:`_cursor.LegacyCursorResult` object will now in
this case return an empty list for ``.keys()`` as it did in 1.3, while also
emitting a 2.0 deprecation warning. The :class:`_cursor.CursorResult`, used
when using a 2.0-style "future" engine, will continue to raise as it does
now.
Fixes: #6427
Change-Id: I4148f28c88039e4141deeab28b1a5994e6d6e098
Fixed regression where :meth:`_orm.Query.filter_by` would not work if the
lead entity were a SQL function or other expression derived from the
primary entity in question, rather than a simple entity or column of that
entity. Additionally, improved the behavior of
:meth:`_sql.Select.filter_by` overall to work with column expressions even
in a non-ORM context.
Fixes: #6414
Change-Id: I316b5bf98293bec1ede08787f6181dd14be85419
Fixed regression in ``selectinload`` loader strategy that would cause it to
cache its internal state incorrectly when handling relationships that join
across more than one column, such as when using a composite foreign key.
The invalid caching would then cause other loader operations to fail.
Fixes: #6410
Change-Id: I9f95ccca3553e7fd5794c619be4cf85c02b04626
Fixed regression caused by 🎫`5395` where tuning back the check for
sequences in :func:`_sql.select` now caused failures when doing 2.0-style
querying with a mapped class that also happens to have an ``__iter__()``
method. Tuned the check some more to accommodate this as well as some other
interesting ``__iter__()`` scenarios.
Fixes: #6300
Change-Id: Idf1983fd764b91a7d5fa8117aee8a3def3cfe5ff
Fixed an issue with the (deprecated in 1.4)
:meth:`_schema.ForeignKeyConstraint.copy` method that caused an error when
invoked with the ``schema`` argument.
Fixes: #6353
Change-Id: I03330d9ec254d64377f2b2e86af69a4eaff43ac6
Revised the "EMPTY IN" expression to no longer rely upon using a subquery,
as this was causing some compatibility and performance problems. The new
approach for selected databases takes advantage of using a NULL-returning
IN expression combined with the usual "1 != 1" or "1 = 1" expression
appended by AND or OR. The expression is now the default for all backends
other than SQLite, which still had some compatibility issues regarding
tuple "IN" for older SQLite versions.
Third party dialects can still override how the "empty set" expression
renders by implementing a new compiler method
``def visit_empty_set_op_expr(self, type_, expand_op)``, which takes
precedence over the existing
``def visit_empty_set_expr(self, element_types)`` which remains in place.
Fixes: #6258Fixes: #6397
Change-Id: I2df09eb00d2ad3b57039ae48128fdf94641b5e59
Ensure that the MySQL and MariaDB dialect ignore the
:class:`_sql.Identity` construct while rendering the
``AUTO_INCREMENT`` keyword in a create table.
The Oracle and PostgreSQL compiler was updated to not render
:class:`_sql.Identity` if the database version does not support it
(Oracle < 12 and PostgreSQL < 10). Previously it was rendered regardless
of the database version.
Fixes: #6338
Change-Id: I2ca0902fdd7b4be4fc1a563cf5585504cbea9360
Fixed critical regression where bound parameter tracking as used in the SQL
caching system could fail to track all parameters for the case where the
same SQL expression containing a parameter were used in an ORM-related
query using a feature such as class inheritance, which was then embedded in
an enclosing expression which would make use of that same expression
multiple times, such as a UNION. The ORM would individually copy the
individual SELECT statements as part of compilation with class inheritance,
which then embedded in the enclosing statement would fail to accommodate
for all parameters. The logic that tracks this condition has been adjusted
to work for multiple copies of a parameter.
Fixes: #6391
Change-Id: I6db5dee0d361a3bb58d753a2d27ef2eee2b369c5
Fixed very old issue where the :class:`_types.Enum` datatype would not
inherit the :paramref:`_schema.MetaData.schema` parameter of a
:class:`_schema.MetaData` object when that object were passed to the
:class:`_types.Enum` using :paramref:`_types.Enum.metadata`.
Fixes: #6373
Change-Id: Ie77d5e8cbc0bd7bfd0039fb60a4a0bde2df58ca9
Fixed issue where usage of an explicit :class:`.Sequence` would produce
inconsistent "inline" behavior for an :class:`.Insert` construct that
includes multiple values phrases; the first seq would be inline but
subsequent ones would be "pre-execute", leading to inconsistent sequence
ordering. The sequence expressions are now fully inline.
Fixes: #6361
Change-Id: Ie16794ec0e19979a7e6c8d1bef5716a9fc199889
Fixed two distinct issues, each of which would come into play under certain
circumstances, most likely however one which is a common mis-configuration
in :class:`_hybrid.hybrid_property`, where the "expression" implementation
would return a non :class:`_sql.ClauseElement` such as a boolean value.
For both issues, 1.3's behavior was to silently ignore the
mis-configuration and ultimately attempt to interpret the value as a
SQL expression, which would lead to an incorrect query.
* Fixed issue regarding interaction of the attribute system with
hybrid_property, where if the ``__clause_element__()`` method of the
attribute returned a non-:class:`_sql.ClauseElement` object, an internal
``AttributeError`` would lead the attribute to return the ``expression``
function on the hybrid_property itself, as the attribute error was
against the name ``.expression`` which would invoke the ``__getattr__()``
method as a fallback. This now raises explicitly. In 1.3 the
non-:class:`_sql.ClauseElement` was returned directly.
* Fixed issue in SQL argument coercions system where passing the wrong
kind of object to methods that expect column expressions would fail if
the object were altogether not a SQLAlchemy object, such as a Python
function, in cases where the object were not just coerced into a bound
value. Again 1.3 did not have a comprehensive argument coercion system
so this case would also pass silently.
Fixes: #6350
Change-Id: I5bba0a6b27f45e5f8ebadfd6d511fa773388ef7c
Fixed regression where usage of the :func:`_sql.text` construct inside the
columns clause of a :class:`_sql.Select` construct, which is better handled
by using a :func:`_sql.literal_column` construct, would nonetheless prevent
constructs like :func:`_sql.union` from working correctly. Other use cases,
such as constructing subuqeries, continue to work the same as in prior
versions where the :func:`_sql.text` construct is silently omitted from the
collection of exported columns. Also repairs similar use within the
ORM.
This adds a new internal method _all_selected_columns. The existing
"selected_columns" collection can't store a TextClause and this never
worked, so they are omitted. The TextClause is also not "exported",
i.e. available for SELECT from a subquery, as was already the case
in 1.3, so the "exported_columns" and "exported_columns_iterator"
accessors are where we now omit TextClause.
Fixed regression involving legacy methods such as
:meth:`_sql.Select.append_column` where internal assertions would fail.
Fixes: #6343Fixes: #6261
Change-Id: I7c2e5b9ae5d94131c77599a020f4310dcf812bcf
Fixed issue in SQL compiler where the bound parameters set up for a
:class:`.Values` construct wouldn't be positionally tracked correctly if
inside of a :class:`_sql.CTE`, affecting database drivers that support
VALUES + ctes and use positional parameters such as SQL Server in
particular as well as asyncpg. The fix also repairs support for
compiler flags such as ``literal_binds``.
Fixes: #6327
Change-Id: I2d549228691d0bfc10dadd0955b1549d7584db51
Repaired and solidified issues regarding custom functions and other
arbitrary expression constructs which within SQLAlchemy's column labeling
mechanics would seek to use ``str(obj)`` to get a string representation to
use as an anonymous column name in the ``.c`` collection of a subquery.
This is a very legacy behavior that performs poorly and leads to lots of
issues, so has been revised to no longer perform any compilation by
establishing specific methods on :class:`.FunctionElement` to handle this
case, as SQL functions are the only use case that it came into play. An
effect of this behavior is that an unlabeled column expression with no
derivable name will be given an arbitrary label starting with the prefix
``"_no_label"`` in the ``.c`` collection of a subquery; these were
previously being represented either as the generic stringification of that
expression, or as an internal symbol.
This change seeks to make the concept of "anon name" more private
and renames anon_label and anon_key_label to _anon_name_label
and _anon_key_label. There's no end-user utility to these accessors
and we need to be able to reorganize these as well.
Fixes: #6256
Change-Id: Ie63c86b20ca45873affea78500388da94cf8bf94
Fixed an argument error in the default and PostgreSQL compilers that
would interfere with an UPDATE..FROM or DELETE..FROM..USING statement
that was then SELECTed from as a CTE.
The incorrect pattern was also fixed in the mysql and sybase dialects.
MySQL supports CTEs but not "returning".
Fixes: #6303
Change-Id: Ic94805611a5ec443749fb6b1fd8a1326b0d83ef7
Fixed a critical performance issue where the traversal of a
:func:`_sql.select` construct would traverse a repetitive product of the
represented FROM clauses as they were each referred towards by columns in
the columns clause; for a series of nested subqueries with lots of columns
this could cause a large delay and significant memory growth. This
traversal is used by a wide variety of SQL and ORM functions, including by
the ORM :class:`_orm.Session` when it's configured to have
"table-per-bind", which while this is not a common use case, it seems to be
what Flask-SQLAlchemy is hardcoded as using, so the issue impacts
Flask-SQLAlchemy users. The traversal has been repaired to uniqify on FROM
clauses which was effectively what would happen implicitly with the pre-1.4
architecture.
Fixes: #6304
Change-Id: I43497e943db4065deab0bfc830fbb68c17b80a53
Fixed regression where an empty in statement on a tuple would result
in an error when compiled with the option ``literal_binds=True``.
Fixes: #6290
Change-Id: Ic0dff8f4a874cccdb201b6d9dcd3c2e7b7884cbb
Fixed a cache leak involving the :func:`_orm.with_expression` loader
option, where the given SQL expression would not be correctly considered as
part of the cache key.
Additionally, fixed regression involving the corresponding
:func:`_orm.query_expression` feature. While the bug technically exists in
1.3 as well, it was not exposed until 1.4. The "default expr" value of
``null()`` would be rendered when not needed, and additionally was also not
adapted correctly when the ORM rewrites statements such as when using
joined eager loading. The fix ensures "singleton" expressions like ``NULL``
and ``true`` aren't "adapted" to refer to columns in ORM statements, and
additionally ensures that a :func:`_orm.query_expression` with no default
expression doesn't render in the statement if a
:func:`_orm.with_expression` isn't used.
Fixes: #6259
Change-Id: I5a70bc12dadad125bbc4324b64048c8d4a18916c
Fixed regression where the introduction of the INSERT syntax "INSERT...
VALUES (DEFAULT)" was not supported on some backends that do however
support "INSERT..DEFAULT VALUES", including SQLite. The two syntaxes are
now each individually supported or non-supported for each dialect, for
example MySQL supports "VALUES (DEFAULT)" but not "DEFAULT VALUES".
Support for Oracle is still not enabled as there are unresolved issues
in using RETURNING at the same time.
Fixes: #6254
Change-Id: I47959bc826e3d9d2396ccfa290eb084841b02e77
Fixed regression where the :class:`_sql.BindParameter` object would not
properly render for an IN expression (i.e. using the "post compile" feature
in 1.4) if the object were copied from either an internal cloning
operation, or from a pickle operation, and the parameter name contained
spaces or other special characters.
Fixes: #6249
Change-Id: Icd0d4096c8fa4eb1a1d4c20f8a96d8b1ae439f0a
The tuple returned by :attr:`.CursorResult.inserted_primary_key` is now a
:class:`_result.Row` object with a named tuple interface on top of the
existing tuple interface.
Fixes: #3314
Change-Id: I85677ef60d8329648f368bf497f634758f4e087b
Fixed up the behavior of the :class:`_result.Row` object when dictionary
access is used upon it, meaning converting to a dict via ``dict(row)`` or
accessing members using strings or other objects i.e. ``row["some_key"]``
works as it would with a dictionary, rather than raising ``TypeError`` as
would be the case with a tuple, whether or not the C extensions are in
place. This was originally supposed to emit a 2.0 deprecation warning for
the "non-future" case using :class:`_result.LegacyRow`, and was to raise
``TypeError`` for the "future" :class:`_result.Row` class. However, the C
version of :class:`_result.Row` was failing to raise this ``TypeError``,
and to complicate matters, the :meth:`_orm.Session.execute` method now
returns :class:`_result.Row` in all cases to maintain consistency with the
ORM result case, so users who didn't have C extensions installed would
see different behavior in this one case for existing pre-1.4 style
code.
Therefore, in order to soften the overall upgrade scheme as most users have
not been exposed to the more strict behavior of :class:`_result.Row` up
through 1.4.6, :class:`_result.LegacyRow` and :class:`_result.Row` both
provide for string-key access as well as support for ``dict(row)``, in all
cases emitting the 2.0 deprecation warning when ``SQLALCHEMY_WARN_20`` is
enabled. The :class:`_result.Row` object still uses tuple-like behavior for
``__contains__``, which is probably the only noticeable behavioral change
compared to :class:`_result.LegacyRow`, other than the removal of
dictionary-style methods ``values()`` and ``items()``.
Also remove filters for result set warnings.
callcounts updated for 2.7/ 3.9, am pushing jenkins to use python 3.9
now
Fixes: #6218
Change-Id: Ia69b974f3dbc46943c57423f57ec82323c8ae63b
Enhanced the "expanding" feature used for :meth:`_sql.ColumnOperators.in_`
operations to infer the type of expression from the right hand list of
elements, if the left hand side does not have any explicit type set up.
This allows the expression to support stringification among other things.
In 1.3, "expanding" was not automatically used for
:meth:`_sql.ColumnOperators.in_` expressions, so in that sense this change
fixes a behavioral regression.
Fixes: #6222
Change-Id: Icdfda1e2c226a21896cafd6d8f251547794451c2
Fixed the "stringify" compiler to support a basic stringification
of a "multirow" INSERT statement, i.e. one with multiple tuples
following the VALUES keyword.
Change-Id: I1fe38d204d9965275d3a72157d5a72a53bec4b11
Fixed regression where usage of a token in the
:paramref:`_engine.Connection.execution_options.schema_translate_map`
dictionary which contained special characters such as braces would fail to
be substituted properly. Use of square bracket characters ``[]`` is now
explicitly disallowed as these are used as a delimiter character in the
current implementation.
Fixes: #6216
Change-Id: I7ccfc2292b17340054cedf485ed1adf3119b96c8
The :class:`_sql.Table` object now raises an informative error message if
it is instantiated without passing at least the :paramref:`_sql.Table.name`
and :paramref:`_sql.Table.metadata` arguments positionally. Previously, if
these were passed as keyword arguments, the object would silently fail to
initialize correctly.
Fixes: #6135
Change-Id: I54d0c89fd549fc504289a87ea0bb37369f982b06
Executing a :class:`_sql.Subquery` using :meth:`_engine.Connection.execute`
is deprecated and will emit a deprecation warning; this use case was an
oversight that should have been removed from 1.4. The operation will now
execute the underlying :class:`_sql.Select` object directly for backwards
compatibility. Similarly, the :class:`_sql.CTE` class is also not
appropriate for execution. In 1.3, attempting to execute a CTE would result
in an invalid "blank" SQL statement being executed; since this use case was
not working it now raises :class:`_exc.ObjectNotExecutableError`.
Previously, 1.4 was attempting to execute the CTE as a statement however it
was working only erratically.
The change also breaks out StatementRole from ReturnsRowsRole, as these
roles should not be in the same lineage (some statements don't return
rows, the whole class of ReturnsRows that are from clauses are
not statements). Consolidate StatementRole and
CoerceTextStatementRole as there's no usage difference between
these. Simplify some old tests that were trying to make
sure that "execution options" didn't transmit from a cte/subquery
out to a select; as cte/subuqery() aren't executable in any case
the options are removed.
Fixes: #6204
Change-Id: I62613b7ab418afdd22c409eae75659e3f52fb65f
Fixed further issues in the same area as that of 🎫`6173` released in
1.4.5, where a "postcompile" parameter, again most typically those used for
LIMIT/OFFSET rendering in Oracle and SQL Server, would fail to be processed
correctly if the same parameter rendered in multiple places in the
statement.
Fixes: #6202
Change-Id: I95c355aa52a7546fe579ad67f9a8402a213cb79d
Fixed regression where use of the :meth:`.Operators.in_` method with a
:class:`_sql.Select` object against a non-table-bound column would produce
an ``AttributeError``, or more generally using a :class:`_sql.ScalarSelect`
that has no datatype in a binary expression would produce invalid state.
Fixes: #6181
Change-Id: I1ddea433b3603fdab8f489bff571b512a6ffc66b