Compare commits

...
1897 Commits
Author SHA1 Message Date
rayluandMike Bayer 8acbc2624f Expand joins when calculating PostgreSQL "WITH FOR UPDATE OF"
Modified the :paramref:`.Select.with_for_update.of` parameter so that if a
join or other composed selectable is passed, the individual :class:`.Table`
objects will be filtered from it, allowing one to pass a join() object to
the parameter, as occurs normally when using joined table inheritance with
the ORM.  Pull request courtesy Raymond Lu.

Fixes: #4550
Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Closes: #4551
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4551
Pull-request-sha: 452da77d154a4087d530456db1c9af207d65cef4

Change-Id: If4b7c231f7b71190d7245543959fb5c3351125a1
2019-03-21 10:25:29 -04:00
ericdeansanchez 8eaccf16ac Changed urllib.quote_plus to urllib.parse.quote_plus (Python 3 versio…
Fixes: #4542

Closes: #4546
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4546
Pull-request-sha: 95d905cdcc33f44ff21d13e411e4a17843e6b54a

Change-Id: Ibaf0852822e281e79770763e7e3550270d26cf66
2019-03-18 10:51:53 -04:00
Antony GelbergandMike Bayer e209df356a Clarify that declarative string resolution does not imply imports are implicit
Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Closes: #4545
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4545
Pull-request-sha: c25221838d726f316dc04102b6b2002cec6b3a6c

Change-Id: Ic38621f7deb3cb25e250aab61c5b2b02d633b187
2019-03-16 17:42:59 -04:00
mike bayer 4aadcca993 Merge "Clone internals for Select._correlate_except collection as well as _correlate" 2019-03-11 14:49:23 +00:00
Mike Bayer 25fc9562f0 Clone internals for Select._correlate_except collection as well as _correlate
Fixed bug where use of :func:`.with_polymorphic` or other aliased construct
would not properly adapt when the aliased target were used as the
:meth:`.Select.correlate_except` target of a subquery used inside of a
:func:`.column_property`.  This required a fix to the clause adaption
mechanics to properly handle a selectable that shows up in the "correlate
except" list, in a similar manner as which occurs for selectables that show
up in the "correlate" list.  This is ultimately a fairly fundamental bug
that has lasted for a long time but it is hard to come across it.

Fixes: #4537
Change-Id: Ibb97d4eea18b3c452aad519dd14919bfb84d422f
2019-03-10 23:44:08 -04:00
Mike Bayer 16411cd8d6 Version 1.3.2 placeholder 2019-03-09 14:38:14 -05:00
Mike Bayer f7d2556cd3 - 1.3.1 2019-03-09 14:32:32 -05:00
Mike Bayer cbc31716c2 Commit transaction after SNAPSHOT isolation change
A commit() is emitted after an isolation level change to SNAPSHOT, as both
pyodbc and pymssql open an implicit transaction which blocks subsequent SQL
from being emitted in the current transaction.

Fixes: #4536
Change-Id: If3ba70f495bce2a35a873a3a72d1b30406e678c8
2019-03-08 23:45:25 -05:00
Mike Bayer d514c032cd black reformatting
Change-Id: Idc48f1c80867cd953f9d611719d1d5b5d244ae38
2019-03-08 23:45:02 -05:00
Mike Bayer 7b0dfe3c46 Remove convert_unicode nodes and add version for deprecation
Fixes: #4535
Change-Id: Ic5b1991ecef3b258573e1c59f5106a534f92a813
2019-03-08 14:42:24 -05:00
Mike Bayer 312d529dbb Update the mysql-connector-python docs for now
mysql-connector-python still seems to have issues with binary datatypes
but the other issues here, with the possible exception of the deadlock
still being investigated, seem to have been resolved in the recent
8.x series of mysql-connector-python.   The driver is still not
recommended due to these issues however we don't need a special
class of warnings at this point.

Change-Id: I2d59e76df5e84b34e318a24b468626900c39da46
References: #4531
2019-03-08 09:54:58 -05:00
Mike Bayer e6d0963040 Add documentation section for cascade_scalar_deletes
Change-Id: I56825652e0608862472bc594fc6c2b12ed5cc16f
References: #4534
2019-03-07 09:54:45 -05:00
mike bayer 2160b7e652 Merge "Ensure association proxy works over synonym" 2019-03-06 16:38:49 +00:00
mike bayer db212bcf49 Merge "Fix large_resultsets performance example field name" 2019-03-06 16:11:36 +00:00
mike bayer 0137b75136 Merge "Ensure scale param not sent to float types" 2019-03-06 15:47:01 +00:00
Matt Schuchhardt 203de6946e Fix large_resultsets performance example field name
Fixed bug in large_resultsets example case where a re-named "id" variable
due to code reformatting caused the test to fail.  Pull request courtesy
Matt Schuchhardt.

Fixes: #4528
Closes: #4529
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4529
Pull-request-sha: 8f52f10422114c397254db9e6f940d042708e0bd

Change-Id: Iaca6fd06ec0ede8ff1745d627708ba492a2114c8
2019-03-06 10:34:17 -05:00
Mike Bayer b78f460465 Ensure association proxy works over synonym
Fixed regression where an association proxy linked to a synonym would no
longer work, both at instance level and at class level.

Fixes: #4522
Change-Id: I949079229ef87c12736c362df35444f6e30c8038
2019-03-06 10:16:49 -05:00
Mike Bayer cb968b6dcd Loosen SingletonThreadPoolTest
This test is non-critical as the SingletonThreadPool is
not production-level robust under multithreaded scenarios in
any case.

Fixes: #4527
Change-Id: Ie19ebd69438c97b2d8adb571f8f1b2c56894f7fb
2019-03-06 09:09:38 -05:00
Mike Bayer 2a2011389a Ensure scale param not sent to float types
Fixed regression in SQL Server reflection due to 🎫`4393` where the
removal of open-ended ``**kw`` from the :class:`.Float` datatype caused
reflection of this type to fail due to a "scale" argument being passed.

Fixes: #4525
Change-Id: Ief8bb535778055eff2ab0d71660f81e3676390a1
2019-03-06 09:06:04 -05:00
Mike Bayer 201c4a60e4 run a black run
fix some pep8s that snuck in

Change-Id: Ied282007df30a52d232b1ba88659f2a123ff380f
2019-03-05 20:29:05 -05:00
Mike Bayer 66373c5811 Fix pooling typo
eng -> engine

Fixes: #4526
Change-Id: If117099b8521e15887ae916a5dbfcfa0b7cd594b
2019-03-05 19:42:41 -05:00
Mike Bayer 62bc03c51b Merge remote-tracking branch 'origin/pr/4520'
Change-Id: I3ca8e33c361ea088323e83437d6817ba02737de7
2019-03-05 12:39:07 -05:00
Mike Bayer 5c4b556c7a Add a note that the truncation logic also raises an exception for
too-long names.

Change-Id: I8291a56235171827f5c41361b74118ba9c28c4c5
2019-03-05 12:13:08 -05:00
Mike Bayer 837d964004 - repair param inject to work around code examples to some degree
- link to correct text() construct for CheckConstraint

Change-Id: Ic46d1f79670a532f33bd9feb7f568dc3d1d6e38a
2019-03-05 11:35:15 -05:00
Mike Bayer cfaf830a6f Version 1.3.1 placeholder 2019-03-04 16:50:17 -05:00
Daniel Demmel 4f62c23cf3 Add missing attribute in hybrid.py docs 2019-03-04 18:10:22 +00:00
Mike Bayer 740bb50c22 - 1.3.0 2019-03-04 13:05:44 -05:00
mike bayer 8eda38e2aa Merge "Use basepython 3.7 for flake8 tests" 2019-03-04 17:40:31 +00:00
Mike Bayer b9d9d41691 Use basepython 3.7 for flake8 tests
this to prevent flake8 from running with python 2 as we have
py3k-specific checks

Change-Id: I456c4b64c5bc04a81cd43de7dac1e803346f1245
2019-03-04 12:22:07 -05:00
mike bayer f24659b72b Merge "Add port comparison in __eq__() and __ne__() method to URL" 2019-03-04 15:45:53 +00:00
Sanjana 9268c320bf Add port comparison in __eq__() and __ne__() method to URL
Comparing two objects of :class:`.URL` using ``__eq__()`` did not take port
number into consideration, two objects differing only by port number were
considered equal. Port comparison is now added in ``__eq__()`` method of
:class:`.URL`, objects differing by port number are now not equal.
Additionally, ``__ne__()`` was not implemented for :class:`.URL` which
caused unexpected result when ``!=`` was used in Python2, since there are no
implied relationships among the comparison operators in Python2.

Fixes: #4406
Closes: #4515
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4515
Pull-request-sha: 0f15b805f07e7fca1f82ca6c3aad98d50ea705b8

Change-Id: Iba7d224f1282dc3f4b884d1a746f2d46669f551e
2019-02-28 14:34:52 -05:00
Mike Bayer a690ec0824 Add resolve_fks=False option for reflection
Added new parameters :paramref:`.Table.resolve_fks` and
:paramref:`.MetaData.reflect.resolve_fks` which when set to False will
disable the automatic reflection of related tables encountered in
:class:`.ForeignKey` objects, which can both reduce SQL overhead for omitted
tables as well as avoid tables that can't be reflected for database-specific
reasons.  Two :class:`.Table` objects present in the same :class:`.MetaData`
collection can still refer to each other even if the reflection of the two
tables occurred separately.

Fixes: #4517
Change-Id: I623baed42042a16c5109e4c8af6b2f64d2d00f95
2019-02-28 13:49:09 -05:00
Aidan Feldman 358a0dcf10 link to PyHive as a dialect 2019-02-27 16:01:04 -05:00
Ville Brofeldt dc48ac5489 Ignore Pipenv* and .idea 2019-02-23 18:02:42 +02:00
mike bayer 53c7fc4690 Merge "Add test to as_interface when no cls or methods" 2019-02-22 00:33:55 +00:00
mike bayer 0cdc89c276 Merge "Prevent __init__ from being called for Alias, subclasses" 2019-02-22 00:33:31 +00:00
Toni Karppi 40401d7933 Add test to as_interface when no cls or methods
Fixes #4511

### Description
The `as_interface` function requires that an argument be provided for at least one of the parameters `cls` or `methods`. There was no test that tested the case when neither of these arguments were provided.

### Checklist
<!-- go over following points. check them with an `x` if they do apply, (they turn into clickable checkboxes once the PR is submitted, so no need to do everything at once)

-->

This pull request is:

- [ ] A documentation / typographical error fix
	- Good to go, no issue or tests are needed
- [x] A short code fix
	- please include the issue number, and create an issue if none exists, which
	  must include a complete example of the issue.  one line code fixes without an
	  issue and demonstration will not be accepted.
	- Please include: `Fixes: #<issue number>` in the commit message
	- please include tests.   one line code fixes without tests will not be accepted.
- [ ] A new feature implementation
	- please include the issue number, and create an issue if none exists, which must
	  include a complete example of how the feature would look.
	- Please include: `Fixes: #<issue number>` in the commit message
	- please include tests.

**Have a nice day!**

Closes: #4512
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4512
Pull-request-sha: 156f6af95ede730d2e1a9d2c935c830cf3cfc96e

Change-Id: Ifa23dbe1dbe9a824fe680e4947b81c96a50c133f
2019-02-21 14:22:48 -05:00
mike bayer eed102f465 Merge "Add support for key-word based get()" 2019-02-21 19:19:49 +00:00
Mike Bayer 4ca3092c0a Prevent __init__ from being called for Alias, subclasses
The :class:`.Alias` class and related subclasses :class:`.CTE`,
:class:`.Lateral` and :class:`.TableSample` have been reworked so that it is
not possible for a user to construct the objects directly.  These constructs
require that the standalone construction function or selectable-bound method
be used to instantiate new objects.

Fixes: #4509
Change-Id: I74ae4786cb3ae625dab33b00bfd6bdc4e1219139
2019-02-21 11:18:19 -05:00
mike bayer 0a1c640531 Merge "Include newlines in StatementError formatting" 2019-02-21 15:52:29 +00:00
Nate Clark 8f318692d4 Include newlines in StatementError formatting
Revised the formatting for :class:`.StatementError` when stringified. Each
error detail is broken up over multiple newlines instead of spaced out on a
single line.  Additionally, the SQL representation now stringifies the SQL
statement rather than using ``repr()``, so that newlines are rendered as is.
Pull request courtesy Nate Clark.

Fixes: #4500

Closes: #4501
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4501
Pull-request-sha: 60cc0ee68dc96b8f483a60d37bcb26b6c6d53efe

Change-Id: I79d8418b7495e5691c9a56f41e79495c26a967ff
2019-02-20 18:56:47 -05:00
sanjana c89a93e953 Add support for key-word based get()
The :meth:`.Query.get` method can now accept a dictionary of attribute keys
and values as a means of indicating the primary key value to load; is
particularly useful for composite primary keys.  Pull request courtesy
Sanjana S.

Fixes: #4316

Closes: #4505
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4505
Pull-request-sha: cfa8297ad2490be9eae24ec8b1a691e43cd75868

Change-Id: Ib19e7d51599a36f4878119c2f801c5c694793422
2019-02-20 17:08:34 -05:00
Mike Bayer 7a4c40ff6b Remove inadvertent test_schema.db commit
also revise .gitignore

Change-Id: I93d900287fe35441db827203b9fdf63eb681ca69
2019-02-20 13:06:20 -05:00
mike bayer d879bed878 Merge "Add NCHAR to Oracle dialect" 2019-02-20 17:54:07 +00:00
Mike Bayer a3135c494e revise timestamp correction scheme
For very slow CI this test still fails so establish the date
as being between the range of what the operation took

Change-Id: I9204cd1915777ebc58bd598065b9015befb93345
2019-02-20 12:52:40 -05:00
Mike Bayer d71f34cb2a Ensure _simple_lazy_clause bind names are fixed before cloning
Fixed a regression in 1.2 due to the introduction of baked queries for
relationship lazy loaders, where a race condition is created during the
generation of the "lazy clause" which occurs within a memoized attribute. If
two threads initialize the memoized attribute concurrently, the baked query
could be generated with bind parameter keys that are then replaced with new
keys by the next run, leading to a lazy load query that specifies the
related criteria as ``None``. The fix establishes that the parameter names
are fixed before the new clause and parameter objects are generated, so that
the names are the same every time.

Fixes: #4507
Change-Id: I605b824e028c87bc20ca8c2577227cdf6a591064
2019-02-19 19:46:17 -05:00
Mike Bayer 5fe9da55c7 Add NCHAR to Oracle dialect
Added support for reflection of the :class:`.NCHAR` datatype to the Oracle
dialect, and added :class:`.NCHAR` to the list of types exported by the
Oracle dialect.

Fixes: #4506
Change-Id: I3a120b9ad714cbd0ebd8064519f43cf57e99d920
2019-02-19 12:13:04 -05:00
Mike Bayer c0bd36873b cherry-pick changelog update for 1.2.19 2019-02-15 13:08:58 -05:00
Mike Bayer 11f5ea1f7f cherry-pick changelog from 1.2.18 2019-02-15 13:08:57 -05:00
Mike Bayer c1b87bc95d - formatting fix
Change-Id: I93126865ffb5cc6486464402ed7ef17027441886
2019-02-15 12:38:49 -05:00
mike bayer 4d7ac4be6c Merge "Adding setter to should_evaluate_none property" 2019-02-14 15:40:06 +00:00
sanjana 12dad561a7 Adding setter to should_evaluate_none property
Fixed issue where the :class:`.JSON` type had a read-only
:attr:`.JSON.should_evaluate_none` attribute, which would cause failures
when making use of the :meth:`.TypeEngine.evaluates_none` method in
conjunction with this type.  Pull request courtesy Sanjana S.

Fixes: #4485

Closes: #4496
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4496
Pull-request-sha: 044beb23982d411be6fe640716b1b693df0f7189

Change-Id: I1f3e1d7dec9d2ceb6ccaaa8cac158a062cf02710
2019-02-13 17:29:13 -05:00
Mike Bayer 71d642711d Set IDENTITY_INSERT for insert.values({column: expr})
Fixed bug where the SQL Server "IDENTITY_INSERT" logic that allows an INSERT
to proceed with an explicit value on an IDENTITY column was not detecting
the case where :meth:`.Insert.values` were used with a dictionary that
contained a :class:`.Column` as key and a SQL expression as a value.

Fixes: #4499
Change-Id: Ia61cd6524b030b40a665db9c20771f0c5aa5fcd7
2019-02-13 11:26:54 -05:00
mike bayer 5cc5234e0b Merge "Allow SQL expression for ORM primary keys" 2019-02-13 01:35:15 +00:00
Mike Bayer c1f310df44 Allow SQL expression for ORM primary keys
A SQL expression can now be assigned to a primary key attribute for an ORM
flush in the same manner as ordinary attributes as described in
:ref:`flush_embedded_sql_expressions` where the expression will be evaulated
and then returned to the ORM using RETURNING, or in the case of pysqlite,
works using the cursor.lastrowid attribute.Requires either a database that
supports RETURNING (e.g. Postgresql, Oracle, SQL Server) or pysqlite.

Fixes: #3133
Fixes: #4494
Change-Id: I83da8357354de002cb04fa4a553f2a2f90c5157d
2019-02-12 16:55:48 -05:00
mike bayer 104625941d Merge "Add complete coverage and fix lower() for MySQL 88718 workaround" 2019-02-11 20:22:27 +00:00
Mike Bayer 49197c7b36 Add complete coverage and fix lower() for MySQL 88718 workaround
Fixed a second regression caused by 🎫`4344` (the first was
🎫`4361`), which works around MySQL issue 88718, where the lower
casing function used was not correct for Python 2 with OSX/Windows casing
conventions, which would then raise ``TypeError``.  Full coverage has been
added to this logic so that every codepath is exercised in a mock style for
all three casing conventions on all versions of Python. MySQL 8.0 has
meanwhile fixed issue 88718 so the workaround is only applies to a
particular span of MySQL 8.0 versions.

Fixes: #4492
Change-Id: I14e7237e0be4a9c21c58c921066304ae99ac4dc6
2019-02-11 09:11:37 -05:00
mike bayer bb7b353d6f Merge "Don't run pending_to_persistent for non-new objects" 2019-02-10 03:57:10 +00:00
Mike Bayer b2afef966d Don't run pending_to_persistent for non-new objects
Fixed fairly simple but critical issue where the
:meth:`.SessionEvents.pending_to_persistent` event would be invoked for
objects not just when they move from pending to persistent, but when they
were also already persistent and just being updated, thus causing the event
to be invoked for all objects on every update.

Fixes: #4489
Change-Id: Ibe147020aa62f7d605cb1029b7f3b776f42e6b43
2019-02-09 14:38:43 -05:00
Mike Bayer 833583458c Note for history methods that history is reset per-flush.
Change-Id: I9bc4d0ddfa93f13e6717b89fa9934f1b8052147f
2019-02-09 12:22:39 -05:00
Mike Bayer fcb5dbf395 mention no_autoflush in the flush section of the docs
also remove link to wiki which is obsolete

Change-Id: I9ebd578923c3eba6e35f3b6203c01ba003dd4115
2019-02-08 17:48:51 -05:00
Mike Bayer 6c177df67c Version 1.3.0 placeholder 2019-02-08 15:19:40 -05:00
Mike Bayer 38d34ca4da - 1.3.0b3 2019-02-08 15:12:18 -05:00
Ivan LevkivskyiandMike Bayer b51f045ee5 Add type stubs link to the docs
Moved by Mike to be a sidebar in the Declarative docs, as
the plugin appears to be specific to Declarative.  These docs will
eventually be moved out of the "extension" section and merged
into the primary narrative documentation.

Co-authored-by:  Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Idba4c13ffc920b1140b5e51d206ab02f19015e8e
2019-02-08 14:47:02 -05:00
Mike Bayer 6c30a06aef Use declarative mapping for the embedded SQL expressions example
Change-Id: I1e778409f2d6e50dfba40bafc58e56f3625e7a27
(cherry picked from commit 7816476cdd0a6c83cdd0eeab8698c2469aa0197b)
2019-02-07 10:20:51 -05:00
mike bayer f572cdf785 Merge "Remove all remaining text() coercions and ensure identifiers are safe" 2019-02-07 03:54:44 +00:00
Mike Bayer 30307c4616 Remove all remaining text() coercions and ensure identifiers are safe
Fully removed the behavior of strings passed directly as components of a
:func:`.select` or :class:`.Query` object being coerced to :func:`.text`
constructs automatically; the warning that has been emitted is now an
ArgumentError or in the case of order_by() / group_by() a CompileError.
This has emitted a warning since version 1.0 however its presence continues
to create concerns for the potential of mis-use of this behavior.

Note that public CVEs have been posted for order_by() / group_by() which
are resolved by this commit:  CVE-2019-7164  CVE-2019-7548

Added "SQL phrase validation" to key DDL phrases that are accepted as plain
strings, including :paramref:`.ForeignKeyConstraint.on_delete`,
:paramref:`.ForeignKeyConstraint.on_update`,
:paramref:`.ExcludeConstraint.using`,
:paramref:`.ForeignKeyConstraint.initially`, for areas where a series of SQL
keywords only are expected.Any non-space characters that suggest the phrase
would need to be quoted will raise a :class:`.CompileError`.   This change
is related to the series of changes committed as part of 🎫`4481`.

Fixed issue where using an uppercase name for an index type (e.g. GIST,
BTREE, etc. ) or an EXCLUDE constraint would treat it as an identifier to
be quoted, rather than rendering it as is. The new behavior converts these
types to lowercase and ensures they contain only valid SQL characters.

Quoting is applied to :class:`.Function` names, those which are usually but
not necessarily generated from the :attr:`.sql.func` construct,  at compile
time if they contain illegal characters, such as spaces or punctuation. The
names are as before treated as case insensitive however, meaning if the
names contain uppercase or mixed case characters, that alone does not
trigger quoting. The case insensitivity is currently maintained for
backwards compatibility.

Fixes: #4481
Fixes: #4473
Fixes: #4467
Change-Id: Ib22a27d62930e24702e2f0f7c74a0473385a08eb
2019-02-06 22:53:16 -05:00
Mike Bayer b956a323cd Remove all occurrences of the word "password" from all examples and tutorials
Fixes: #4484
Change-Id: I97e8cbd9f4906332ac0a4fe9c8496a0147fc9a9b
2019-02-05 18:24:29 -05:00
mike bayer e93e61b4a6 Merge "Improve support for with_polymorphic in mapper options" 2019-02-04 19:27:31 +00:00
Mike Bayer 95c371f1d3 Improve support for with_polymorphic in mapper options
Improved the behavior of :func:`.orm.with_polymorphic` in conjunction with
loader options, in particular wildcard operations as well as
:func:`.orm.load_only`.  The polymorphic object will be more accurately
targeted so that column-level options on the entity will correctly take
effect.The issue is a continuation of the same kinds of things fixed in
🎫`4468`.

The path logic when using chained mapper options is improved
to be more accurate in terms of the entities being linked
in the path; when using :func:`.with_polymorphic`, mapper
options against this entity need to specify attributes
in terms of the with_polymorphic() object and not against the
base mappings.  New error conditions are raised which were previously
more than likely silenty failures.

Fixes: #4469
Change-Id: Ie8d802879663b4ff6f6ac1438c885c06d78ae2a0
2019-02-04 10:37:45 -05:00
Mike Bayer 11845453d7 Add bulk_replace to AssociationSet, AssociationDict
Implemented a more comprehensive assignment operation (e.g. "bulk replace")
when using association proxy with sets or dictionaries.  Fixes the problem
of redundant proxy objects being created to replace the old ones, which
leads to excessive events and SQL and in the case of unique constraints
will cause the flush to fail.

Fixes: #2642
Change-Id: I57ab27dd9feba057e539267722cce92254fca777
2019-02-04 10:34:25 -05:00
Mike Bayer 025cf86441 Repair incorrect issue number
This reopens #4406 inadvertently closed and fixes #4464, already
released in 1.3.0b2.

Fixes: #4464
Change-Id: I82f3dbdff01fe24ea51a4dda0608c0a284320a57
2019-02-03 12:51:19 -05:00
mike bayer 2a2f7fe88c Merge "Remove Nose support" 2019-02-03 17:45:28 +00:00
Parth Shandilya d427d0643b Remove Nose support
The test system has removed support for Nose, which is unmaintained for
several years and is producing warnings under Python 3. The test suite is
currently standardized on Pytest.  Pull request courtesy Parth Shandilya.

Fixes: #4460

Closes: #4476
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4476
Pull-request-sha: e857af9c7d07355e52841149ee2e5d4448409e1e

Change-Id: I76516fae1cf0eb58f2e9fc9f692e591e0fcf39a4
2019-02-02 11:25:44 -05:00
Bartlomiej Biernacki 620bfde695 Render parenthesis around sqlite expression defaults
Fixed bug in SQLite DDL where using an expression as a server side default
required that it be contained within parenthesis to be accepted by the
sqlite parser.  Pull request courtesy Bartlomiej Biernacki.

Fixes: #4474
Closes: #4475
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4475
Pull-request-sha: 0af3238c69c2610333cf62082c12047d45c31ce0

Change-Id: I888c69bfba5a5ab8ffa420f512557ac311a36b31
(cherry picked from commit f7ce37e9dd493d4b60b3156f08ef4c98fd63904d)
2019-02-01 22:04:22 -05:00
Mike Bayer 5ae8a54ed3 repair F632 issue
in b8f9517cdd we disabled this new error
coming up, but it's just this one line in a test that is in fact wrong.

Change-Id: I4e3612596e9735c7db066832d13ccb454c93808f
2019-02-01 21:34:53 -05:00
mike bayer 7e48d8b2a7 Merge "Add informative failure modes to _DeferredMapperConfig" 2019-01-31 16:09:41 +00:00
Ben Brumm 06d9529509 Added a link for Candidate Keys
(cherry picked from commit 4421688162302af2c90ed7d1daf17161daded1e6)

Change-Id: Ifb74aec34c4db27cd496f081c8fd6d872b9addd4
2019-01-31 10:05:30 -06:00
Mike Bayer 147f6d382c Add informative failure modes to _DeferredMapperConfig
Added some helper exceptions that invoke when a mapping based on
:class:`.AbstractConcreteBase`, :class:`.DeferredReflection`, or
:class:`.AutoMap` is used before the mapping is ready to be used, which
contain descriptive information on the class, rather than falling through
into other failure modes that are less informative.

Fixes: #4470
Change-Id: I9bc51697f63cedaa7809a0adb17b2398c209e289
2019-01-30 21:06:27 -06:00
Mike Bayer b8f9517cdd Add F632 another issue that just popped up
Change-Id: I4658615f450ed670bbde39e085e1b1f913e3736f
2019-01-30 21:04:47 -06:00
Mike Bayer 1e29997dcc add F821 which for some reason is some new thing flake8 wants to complain about
Change-Id: I27df129ae883d75217ec07ff6d0139447444cc60
2019-01-30 21:00:36 -06:00
Ville Brofeldt ce481b3f60 Fix typo: issue is #4442, not #4222 2019-01-29 12:50:43 +02:00
Mike Bayer 17412c64d7 remove py36 from test profiles
Since we aren't regenerating for py36 we need to take the
obsolete numbers out also.

Change-Id: I67c4268bcec63d7d3a03ab757674780ee8693677
2019-01-27 00:55:54 -05:00
mike bayer a4e01bad93 Merge "Ensure of_type subclass taken into account with wildcards" 2019-01-26 22:21:46 +00:00
Mike Bayer 29e033f496 Ensure of_type subclass taken into account with wildcards
Fixed a regression in 1.2 where a wildcard/load_only loader option would
not work correctly against a loader path where of_type() were used to limit
to a particular subclass.  The fix only works for of_type() of a simple
subclass so far, not a with_polymorphic entity which will be addressed in a
separate issue; it is unlikely this latter case was working previously.

Since we ensure that the entity is broken out into its superclasses
when a wilcard is encountered, we can limit the entity path to the
specific entity given in this case.

Within this issue some additional issues with with_polymorphic()
loaders were found which will be addressed in #4469.

Fixes: #4468
Change-Id: Ie91ec27b49104e019636f870776e294321586a9e
2019-01-26 15:04:07 -05:00
Mike Bayer d3227c09f1 Version 1.3.0b3 placeholder 2019-01-25 21:51:35 -05:00
Mike Bayer f814da2f4c - 1.3.0b2 2019-01-25 21:40:01 -05:00
Mike Bayer cb615dcd83 Version 1.2.18 placeholder
(cherry picked from commit d196c49918)
2019-01-25 21:37:25 -05:00
Mike Bayer c85385ca98 - 1.2.17
(cherry picked from commit 47c245b90c)
2019-01-25 21:36:55 -05:00
Mike Bayer ecbaa44582 Fix timeout method doc to be for QueuePool
Change-Id: I14d4e623a5761963e10bb8f5d99a8ca3684db61b
2019-01-25 21:30:55 -05:00
Mike Bayer 2eb3f211da Improve error messages in the area of loader options
Improved error messages emitted by the ORM in the area of loader option
traversal.  This includes early detection of mis-matched loader strategies
along with a clearer explanation why these strategies don't match.

Fixes: #4433
Change-Id: I3351b64241f7f62ca141a0be95085e6ef8ca6d32
2019-01-25 20:59:08 -05:00
Mike Bayer f0b344ee9d Fix some long lines that sneaked in with the spelling fixes change
Change-Id: Icc6d8e564c9d31da2adc39d060e077c3d4811186
2019-01-25 15:13:48 -05:00
Lele Gaifax 66e88d30a8 Fix many spell glitches
This affects mostly docstrings, except in orm/events.py::dispose_collection()
where one parameter gets renamed: given that the method is
empty, it seemed reasonable to me to fix that too.

Closes: #4440
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4440
Pull-request-sha: 779ed75acb6142e1f1daac467b5b14134529bb4b

Change-Id: Ic0553fe97853054b09c2453af76d96363de6eb0e
2019-01-25 14:56:50 -05:00
mike bayer c9a31767e0 Merge "Add getters for all execution_options" 2019-01-25 19:55:25 +00:00
mike bayer 2f32a1c8e0 Merge "Fix mssql quote schema warning" 2019-01-25 19:54:14 +00:00
mike bayer 537dd06e57 Merge "Implement relationship to AliasedClass; deprecate non primary mappers" 2019-01-25 16:58:08 +00:00
Mike Bayer 5e48f8445c Fix mssql quote schema warning
The deprecations review didn't include tests of identifier_preparer.quote.force
for backends, so MSSQL slipped through.  We have to fully reimplement
the deprecation warning here so that it passes tests which are now
enabled for all backends.

Change-Id: I9d07e6766e16b5a35b7f7566f1daf94b04346270
2019-01-25 11:36:54 -05:00
Daniel Lister 2bbd3ac1fb Add getters for all execution_options
Added accessors for execution options to Core and ORM, via
:meth:`.Query.get_execution_options`,
:meth:`.Connection.get_execution_options`,
:meth:`.Engine.get_execution_options`, and
:meth:`.Executable.get_execution_options`.  PR courtesy Daniel Lister.

Fixes: #4406
Closes: #4465
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4465
Pull-request-sha: 9674688bb5e80471a6a421bac06f995c2e64f8f7

Change-Id: I93ba51d7a2d687e255edd6938db15615e56dd237
2019-01-25 11:19:03 -05:00
mike bayer 9331613fc8 Merge "Use pg_get_constraintdef for CHECK constraint reflection" 2019-01-25 14:30:54 +00:00
Mike Bayer 93855ed623 Implement relationship to AliasedClass; deprecate non primary mappers
Implemented a new feature whereby the :class:`.AliasedClass` construct can
now be used as the target of a :func:`.relationship`.  This allows the
concept of "non primary mappers" to no longer be necessary, as the
:class:`.AliasedClass` is much easier to configure and automatically inherits
all the relationships of the mapped class, as well as preserves the
ability for loader options to work normally.

- introduce new name for mapped_table, "persist_selectable".  this is
the selectable that selects against the local mapper and its superclasses,
but does not include columns local only to subclasses.

- relationship gains "entity" which is the mapper or aliasedinsp.

- clarfiy name "entity" vs. "query_entity" in loader strategies.

Fixes: #4423
Fixes: #4422
Fixes: #4421
Fixes: #3348

Change-Id: Ic3609b43dc4ed115006da9ad9189e574dc0c72d9
2019-01-25 09:28:28 -05:00
Mike Bayer 1a70a27d89 - this is a meth, not a ref
Change-Id: I6761732fe0a93673dff27fdf15287b189f31784b
2019-01-24 19:38:42 -05:00
Mike Bayer 377f12696b Use pg_get_constraintdef for CHECK constraint reflection
Revised the query used when reflecting CHECK constraints to make use of the
``pg_get_constraintdef`` function, as the ``consrc`` column is being
deprecated in PG 12.  Thanks to John A Stevenson for the tip.

Fixes: #4463
Change-Id: Ie0ee9bdfddb0635db72b35c2e2e4b27f154162fd
2019-01-24 19:25:59 -05:00
mike bayer 99b7dd4512 Merge "Provide public accessor for Pool.timeout()." 2019-01-24 21:35:55 +00:00
Irina Delamare f9c9f6453a Provide public accessor for Pool.timeout().
Added public accessor :meth:`.Pool.timeout` that returns the configured
timeout for a :class:`.Pool` object.  Pull request courtesy Irina Delamare.

Fixes: #3689

Closes: #4447
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4447
Pull-request-sha: 0179b0a829e9609429dc698992670d2e6749c10c

Change-Id: I402b065cf9183160f71d9de73e308268356b7deb
2019-01-24 12:45:06 -05:00
Mike Bayer a11a5f5af6 - all the checkboxes are just embarassing, just do something simple
Change-Id: Icb689ffbc780016ec59c549c65e6add20c96951e
2019-01-24 12:41:51 -05:00
mike bayer 78e598e3a5 Merge "Add deprecation warnings to all deprecated APIs" 2019-01-24 08:08:22 +00:00
Mike Bayer 4c2c2c40fd Add deprecation warnings to all deprecated APIs
A large change throughout the library has ensured that all objects, parameters,
and behaviors which have been noted as deprecated or legacy now emit
``DeprecationWarning`` warnings when invoked.   As the Python 3 interpreter now
defaults to displaying deprecation warnings, as well as that modern test suites
based on tools like tox and pytest tend to display deprecation warnings,
this change should make it easier to note what API features are obsolete.

See the notes added to the changelog and migration notes for further
details.

Fixes: #4393
Change-Id: If0ea11a1fc24f9a8029352eeadfc49a7a54c0a1b
2019-01-23 18:10:06 -05:00
Mike Bayer bd735eba63 Add QueryEvents before_compile_update / before_compile_delete
Added new event hooks :meth:`.QueryEvents.before_compile_update` and
:meth:`.QueryEvents.before_compile_delete` which complement
:meth:`.QueryEvents.before_compile` in the case of the :meth:`.Query.update`
and :meth:`.Query.delete` methods.

Fixes: #4461
Change-Id: I47884f0e1f07d7e62870c2a918b15f917f9245ab
2019-01-22 22:24:08 -05:00
Mike Bayer 5832f71729 Don't use cx_Oracle.NATIVE_INT in output type handlers
Fixed regression in integer precision logic due to the refactor of the
cx_Oracle dialect in 1.2.  We now no longer apply the cx_Oracle.NATIVE_INT
type to result columns sending integer values (detected as positive
precision with scale ==0) which encounters integer overflow issues with
values that go beyond the 32 bit boundary.  Instead, the output variable
is left untyped so that cx_Oracle can choose the best option.

Fixes: #4457
Change-Id: I1e3114c2f37bf028fb1f521a3e9789a77e3a7491
2019-01-19 10:34:47 -05:00
Mike Bayer 1c56b6049a Cleanup with query aliasing
Try to simplify some of the "adapter" stuff in query:

1. identify that join(.., aliased=True) doesn't work if the
right side has no mapper.   The adaption of the right side is
done via the mapper with aliased(), so that doesn't effect
a selectable only.  raise an error, so we can simplify
the code.

2. build fewer adapter objects.   these are confusing to follow
and we should try to figure out exactly what purpose which
one serves where and make that clear.

Change-Id: I18dfcd01e6ad533aa0b8d557fc637ee2766ed050
2019-01-18 21:48:20 -05:00
Mike Bayer 265644072e Regenerate callcounts for mysqlclient 1.4.0
Fixes: #4455
Change-Id: I396230f649f6bb5e396798e63339fcecb3b85eaf
2019-01-18 18:52:40 -05:00
mike bayer 76d3be1433 Merge "Adapt single inh criteria more specifically" 2019-01-18 16:31:14 +00:00
Mike Bayer 894acf7b8e Feature mysqlclient
MySQL-Python hasn't been released in about five years and there
is no reason that it should be listed as a viable DBAPI;
all MySQL / MariaDB users should be using mysqlclient or PyMySQL today.

Change-Id: I2f12babe6e60bc7393398400a125d0592e86dbb8
2019-01-18 01:02:07 -05:00
Mike Bayer 77a932e321 Add example of password URL encoding
Fixes: #4452
Change-Id: I6d6ef36c4a0aa1e7c064b8aed289a1ce79b5120f
2019-01-18 00:53:55 -05:00
Mike Bayer 5ea803494a link the psycopg2 fast execution document to the Core tutorial executemany section
Fixes: #4109

Change-Id: I62fcb703b552db842be335c8f9257cc0e8c5cdd5
2019-01-18 00:35:30 -05:00
Mike Bayer c8d7141c79 Adapt single inh criteria more specifically
Fixed issue where when using single-table inheritance in conjunction with a
joined inheritance hierarchy that uses "with polymorphic" loading, the
"single table criteria" for that single-table entity could get confused for
that of other entities from the same hierarchy used in the same query.The
adaption of the "single table criteria" is made more specific to the target
entity to avoid it accidentally getting adapted to other tables in the
query.

Change-Id: Ia9f915a4b01e8bb9cee365c4c70e00c626f103c4
Fixes: #4454
2019-01-17 23:14:24 -05:00
Mike Bayer d038f66b2a Repair use of deprecated text() typemap, bindparams parameters
These will emit a deprecation warning once
If0ea11a1fc24f9a8029352eeadfc49a7a54c0a1b is merged, modernize these
ahead of time as this should likely be backported to 1.2 as well.

Change-Id: Iae4426a856d5617e8a325b14d8b6fc22333f2cda
2019-01-17 13:16:04 -05:00
Vraj Mohan 0717ce9d1d Reinstate elementtree example
Partially fixes sqlalchemy/sqlalchemy#4426.

Closes: #4441
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4441
Pull-request-sha: ed90f3b77c2d0f4cc2cd54f40f5af29b489977d2

Change-Id: Ic32e5d8020073da055b12a6aeb61e698a97dc504
2019-01-16 20:21:48 -05:00
Mike Bayer 313be7c78d - pep8 fix
Change-Id: I5e2e013c3460c035ad80dae7fd08efe5d1676a5d
2019-01-16 20:20:45 -05:00
Mike Bayer 26a8e46527 Convert most "See also" phrases into .. seealso::
Change-Id: Ie32598b895c1c5f5bce7c8e1573abbcfe9d434a8
(cherry picked from commit e81d3815abb36c52b0019dee6e4f67990e3d1c7d)
2019-01-15 16:14:01 -05:00
mike bayer e1b299df81 Merge "Render N'' for SQL Server unicode literals" 2019-01-15 17:47:14 +00:00
Mike Bayer 885f15a306 Remove version directives for 0.6, 0.7, 0.8
- fix a few "seealso"s
- ComparableProprerty's "superseded in 0.7" becomes deprecated in 0.7

Backport to currently maintained doc versions 1.2, 1.1

Change-Id: Ib1fcb2df8673dbe5c4ffc47f3896a60d1dfcb4b2
2019-01-15 10:49:36 -05:00
Mike Bayer a7d6cb13ac PR template tweaks
Change-Id: I49557362057fef3ea151bc2f4bd8c3c96cdf5935
2019-01-15 10:10:56 -05:00
mike bayer c1a53669c8 Merge "Relax "ambiguous" association proxy restrictions, support Proxy" 2019-01-15 15:06:05 +00:00
Mike Bayer c0e6ebd70b Render N'' for SQL Server unicode literals
The ``literal_processor`` for the :class:`.Unicode` and
:class:`.UnicodeText` datatypes now render an ``N`` character in front of
the literal string expression as required by SQL Server for Unicode string
values rendered in SQL expressions.

Note that this adds full unicode characters to the standard test suite,
which means we also need to bump MySQL provisioning up to utf8mb4.
Modern installs do not seem to be reproducing the 1271 issue locally,
if it reproduces in CI it would be better for us to skip those ORM-centric
tests for MySQL.

Also remove unused _StringType from SQL Server dialect

Fixes: #4442
Change-Id: Id55817b3e8a2d81ddc8b7b27f85e3f1dcc1cea7e
2019-01-15 10:04:09 -05:00
mike bayer e288092848 Merge "move to inspect_getfullargspec" 2019-01-15 15:02:17 +00:00
Mike Bayer 150ccf1716 move to inspect_getfullargspec
Replace inspect_getargspec with inspect_getfullargspec
including a compatibility fallback for Py2k and use
getfullargspec fully.

Change-Id: I92bce0aafc37ce1a360b4f61b75f5892d0911c7e
2019-01-15 10:01:53 -05:00
Mike Bayer 836178d426 Relax "ambiguous" association proxy restrictions, support Proxy
Fixed issue in association proxy due to 🎫`3423` which caused the use
of custom :class:`.PropComparator` objects with hybrid attribites, such as
the one demonstrated in  the ``dictlike-polymorphic`` example to not
function within an association proxy.  The strictness that was added in
🎫`3423` has been relaxed, and additional logic to accomodate for
an association proxy that links to a custom hybrid have been added.

Fixes: #4446
Change-Id: I8addc80f51094769915ac2dce1a301bd72ee7433
2019-01-14 21:26:35 -05:00
Mike Bayer 5f697cb672 Pull request template final
Change-Id: Id94b90a58753e044ec3495601fea4c12e79d6e3d
2019-01-14 16:51:04 -05:00
Mike Bayer e8cddcf723 another change to the PR template
Change-Id: I29b0f60d3ec32249333edaeb6550147bd740d893
2019-01-14 16:38:14 -05:00
Mike Bayer 4db74e2a88 Try a new pull request template
Change-Id: I4c2c176c30eb99157bd037035501f876cb344823
2019-01-14 16:32:16 -05:00
Mike Bayer b229a50c77 correct paramref to property links to refer to creation function
Change-Id: I2c528bd4639863aa7b8a592beed776d53bab3e5c
2019-01-13 12:36:57 -05:00
mike bayer b2cf930893 Merge "Add standalone orm.close_all method and deprecate SessionMaker.close_all" 2019-01-13 02:46:08 +00:00
mike bayer 8138e70d63 Merge "use ..deprecated directive w/ version in all cases" 2019-01-12 23:22:47 +00:00
Augustin Trancart 8fac612ec0 Add standalone orm.close_all method and deprecate SessionMaker.close_all
Added a new function :func:`.close_all_sessions` which takes
over the task of the :meth:`.Session.close_all` method, which
is now deprecated as this is confusing as a classmethod.
Pull request courtesy Augustin Trancart.

Fixes: #4412

Closes: #4438
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4438
Pull-request-sha: 7833d12a9898c82d50716427144bf3276c22ab3f

Change-Id: Ib35eaa520ae886f3f8f550f9712fc3b139e00b60
2019-01-12 17:19:37 -05:00
Mike Bayer a6094d6682 use ..deprecated directive w/ version in all cases
These changes should be ported from 1.3 back to 1.0 or
possibly 0.9 to the extent they are relevant in each
version. In 1.3 we hope to turn all deprecation documentation
into warnings.

Change-Id: I205186cde161af9389af513a425c62ce90dd54d8
2019-01-11 22:09:53 -05:00
Mike Bayer 55f930ef3d cherry-pick changelog update for 1.2.17 2019-01-11 10:15:39 -05:00
Mike Bayer b4a8c1fbcf cherry-pick changelog from 1.2.16 2019-01-11 10:15:38 -05:00
Mike Bayer 6f270fb0e3 happy new year
Change-Id: I6a71f4924d046cf306961c58dffccf21e9c03911
2019-01-11 10:06:10 -05:00
Mike Bayer 2db54ee92e Leave bytestring exception messages as bytestrings
Fixed a regression introduced in version 1.2 where a refactor
of the :class:`.SQLAlchemyError` base exception class introduced an
inappropriate coercion of a plain string message into Unicode under
python 2k, which is not handled by the Python interpreter for characters
outside of the platform's encoding (typically ascii).  The
:class:`.SQLAlchemyError` class now passes a bytestring through under
Py2K for ``__str__()`` as is the behavior of exception objects in general
under Py2K, does a safe coercion to unicode utf-8 with
backslash fallback for ``__unicode__()``.  For Py3K the message is
typically unicode already, but if not is again safe-coerced with utf-8
with backslash fallback for the ``__str__()`` method.

Fixes: #4429
Change-Id: I2289da3f2c45c7d0041fa43d838958f7614defc3
2019-01-10 18:02:00 -05:00
mike bayer f1706ae317 Merge "Skip expression-based index reflection for SQLite" 2019-01-10 02:07:24 +00:00
Mike Bayer 08994cb97c Skip expression-based index reflection for SQLite
Reflection of an index based on SQL expressions are now skipped with a
warning, in the same way as that of the Postgresql dialect, where we currently
do not support reflecting indexes that have SQL expressions within them.
Previously, an index with columns of None were produced which would break
tools like Alembic.

Fixes: #4431
Change-Id: I1363ade912d206b42669331e2be2bb6f444b65a2
2019-01-09 21:06:57 -05:00
Mike Bayer 2a840c147e Render correct DDL for unsetting table comments
Fixed issue where the DDL emitted for :class:`.DropTableComment`, which
will be used by an upcoming version of Alembic, was incorrect for the MySQL
and Oracle databases.

Fixes: #4436
Change-Id: I196de09495a37adface4caa9dcbc29a6d0ad159a
2019-01-09 11:18:02 -05:00
Charles S. Givre 86f243a874 Update index.rst - Added link to Drill dialect.
Added link to Apache Drill dialect.
2019-01-08 14:45:19 -05:00
Mike Bayer 1e278de4cc Post black reformatting
Applied on top of a pure run of black -l 79 in
I7eda77fed3d8e73df84b3651fd6cfcfe858d4dc9,  this set of changes
resolves all remaining flake8 conditions for those codes
we have enabled in setup.cfg.

Included are resolutions for all remaining flake8 issues
including shadowed builtins, long lines, import order, unused
imports, duplicate imports, and docstring issues.

Change-Id: I4f72d3ba1380dd601610ff80b8fb06a2aff8b0fe
2019-01-06 18:23:11 -05:00
Mike Bayer 1e1a38e780 Run black -l 79 against all source files
This is a straight reformat run using black as is, with no edits
applied at all.

The black run will format code consistently, however in
some cases that are prevalent in SQLAlchemy code it produces
too-long lines.   The too-long lines will be resolved in the
following commit that will resolve all remaining flake8 issues
including shadowed builtins, long lines, import order, unused
imports, duplicate imports, and docstring issues.

Change-Id: I7eda77fed3d8e73df84b3651fd6cfcfe858d4dc9
2019-01-06 17:34:50 +00:00
Mike Bayer 404e69426b Assorted pre-Black fixes
Fixes to the test suite, a few errant imports, and setup.py:

- mysql and postgresql have unused 'json' imports; remove
- postgresql is exporting the 'json' symbol, remove
- make sure setup.py can find __version__ using " or '
- retry logic in provision create database for postgresql fixed
- refactor test_magazine to use cls.tables rather than globals
- remove unused class in test_scoping
- add a comment to test_deprecations that this test suite itself
  is deprecated
- don't use mapper() and orm_mapper() in test_unitofwork, just
  use mapper()
- remove dupe test_scalar_set_None test in test_attributes
- Python 2.7 and above includes unittest.SkipTest, remove pre-2.7
  fallback
- use imported SkipTest in profiling
- declarative test_reflection tests with "reflectable_autoincrement"
  already don't run on oracle or firebird; remove conditional logic
  for these, which also removes an "id" symbol
- clean up test in test_functions, remove print statement
- remove dupe test_literal_processor_coercion_native_int_out_of_range
  in test/sql/test_types.py
- fix psycopg2_hstore ref

Change-Id: I7b3444f8546aac82be81cd1e7b6d8b2ad6834fe6
2019-01-05 23:51:34 -05:00
Mike Bayer d229360a8d Prep for flake8 refactoring
a few code changes ahead of time to handle some __all__
issues better.  also include new flake8 rules, since the
existing flake8 doesn't pass in any case.

Change-Id: I1efdf75124ae7bcac719c22e505bb5b13db06c04
2019-01-03 22:28:09 -05:00
Mike Bayer 1eaf9dc777 rework the exclusions spec expression
The expression was expecting spaces which means we were skipping
Postgresql window function tests and possibly other things.

Change-Id: I57c4aed558f4011f2f7b882a2d9b1fee210f9eaf
2018-12-31 00:20:08 -05:00
Lele Gaifax c0f9708fde commit 1b774808c926665047bf353222ecd191679a95d1
Author: Lele Gaifax <lele@metapensiero.it>
Date:   Tue Dec 25 12:35:41 2018 +0100

    Consistently use "PostgreSQL", fixing also a few doc glitches

commit 0e382aaee4427193926f0dc10ad29056bc12c85e
Author: Lele Gaifax <lele@metapensiero.it>
Date:   Tue Dec 25 12:08:49 2018 +0100

    Remove duplicated words

Change-Id: Iaa586b9412f46a50fe6ff3bbb92e07d6cb1905c8
2018-12-30 21:16:52 -05:00
mike bayer cfc49b4571 Merge "Check collection less than two items remaining before firing scalar backref remove" 2018-12-29 07:59:58 +00:00
mike bayer 010dd34e7c Merge "Call __del() before remove()" 2018-12-29 07:58:21 +00:00
Mike Bayer 16f08cbed5 Add missing disambiguation to non-primary mapper example
The mapping to B over a join defines an alternate primary key
based on all the primary key columns in the join unless we
re-define it explicitly.   Similarly, people expect that
``.id`` looks the same.  make sure these line up with the
old mapping.

Change-Id: I1ab064c57019e79c34293f6588d1e033f7083974
2018-12-28 09:36:24 -05:00
Mike Bayer 847d135942 Check collection less than two items remaining before firing scalar backref remove
Fixed long-standing issue where duplicate collection members would cause a
backref to delete the association between the member and its parent object
when one of the duplicates were removed, as occurs as a side effect of
swapping two objects in one statement.

Fixes: #1103
Change-Id: Ic12877f7bd5a4eb688091725a78410748e7fdf16
2018-12-28 08:40:44 -05:00
Mike Bayer 07cea66ccb Call __del() before remove()
The "remove" event for collections is now called before the item is removed
in the case of the ``collection.remove()`` method, as is consistent with the
behavior for most other forms of collection item removal (such as
``__delitem__``, replacement under ``__setitem__``).  The ``pop()`` methods
are now the only exception as the target item is not available until after
the pop operation proceeds.

This allows ``remove()`` to be consistent in its behavior with all
the other collection operations, allows the "before_delete" hook
to be local to "pop()" operations only, and removes some method overhead.

We are also looking here to gain some more predictability in terms
of the fix for #1103.

Change-Id: I4fdea911517d65cc300fae0e9c351a471e52e4ab
2018-12-28 08:37:03 -05:00
Mike Bayer ec5c9ebe6e Implement SynonymProperty.get_history()
Implemented the ``.get_history()`` method, which also implies availability
of :attr:`.AttributeState.history`, for :func:`.synonym` attributes.
Previously, trying to access attribute history via a synonym would raise an
``AttributeError``.

Fixes: #3777
Change-Id: I20810a8b1a1bf630dbcb6622193c13cf4236b94a
2018-12-27 12:39:15 -05:00
Mike Bayer eae62d0004 - remove non-working dialects some of which are 404's
- put the five major dialect names on the front page
- remove old change messages

Change-Id: Ibf1dc2c499f10f98efb6c97d6c53e442e7746200
2018-12-24 00:07:22 -05:00
mike bayer d27023a30d Merge "Add before_mapper_configured event" 2018-12-23 15:44:37 +00:00
mike bayer 504432ed57 Merge "Maintain compiled_params / replacement_expressions within expanding IN" 2018-12-22 13:54:11 +00:00
Mike Bayer c495769751 Maintain compiled_params / replacement_expressions within expanding IN
Fixed issue in "expanding IN" feature where using the same bound parameter
name more than once in a query would lead to a KeyError within the process
of rewriting the parameters in the query.

Fixes: #4394
Change-Id: Ibcadce9fefbcb060266d9447c2044ee6efeccf5a
2018-12-21 21:50:55 -05:00
mike bayer 1ae613f4e4 Merge "Handle PostgreSQL enums in remote schemas" 2018-12-21 22:23:07 +00:00
Mike Bayer 41f47fb72c add pull request template
Change-Id: I850c246e4f0feb62dca083909e5d010ce8288a3d
2018-12-21 14:13:41 -05:00
Mike Bayer 0b0a4c8ba2 Handle PostgreSQL enums in remote schemas
Fixed issue where a :class:`.postgresql.ENUM` or a custom domain present
in a remote schema would not be recognized within column reflection if
the name of the enum/domain or the name of the schema required quoting.
A new parsing scheme now fully parses out quoted or non-quoted tokens
including support for SQL-escaped quotes.

Fixed issue where multiple :class:`.postgresql.ENUM` objects referred to
by the same :class:`.MetaData` object would fail to be created if
multiple objects had the same name under different schema names.  The
internal memoization the Postgresql dialect uses to track if it has
created a particular :class:`.postgresql.ENUM` in the database during
a DDL creation sequence now takes schema name into account.

Fixes: #4416
Change-Id: I8cf03069e10b12f409e9b6796e24fc5850979955
2018-12-21 13:53:16 -05:00
Mike Bayer 7f12f63c3a Rewrite the convert_unicode docs and add tons of dragons
These flags will all be going away as Python 3 has solved
all of this.

Change-Id: I4f581d8dd7826dd823b671d0d8e72250284236c8
2018-12-21 12:13:13 -05:00
mike bayer b5592de30e Merge "Fix the "greatest" example." 2018-12-20 15:32:12 +00:00
mike bayer f834238d44 Merge "Omit include of no longer existing files" 2018-12-20 15:29:34 +00:00
Michael Howitz 69273bef0a Omit include of no longer existing files
Warnings are generated during setup.py install such as:

```
Getting distribution for 'SQLAlchemy==1.2.15'.
warning: no files found matching '*.jpg' under directory 'doc'
warning: no files found matching '*.mako' under directory 'doc'
warning: no files found matching 'distribute_setup.py'
warning: no files found matching 'sa2to3.py'
warning: no files found matching 'ez_setup.py'
```

This change removes those expressions from MANIFEST.in.

Closes: #4408
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4408
Pull-request-sha: 448b3a9dc8f25d841f20bcd67130acaea68cb745

Change-Id: Id6373611fb384e230427f87b9e75672d78483000
2018-12-20 14:55:32 +00:00
Konstantin Tretyakov 8722fb84a6 Fix the "greatest" example.
The current example code does not pass `**kw` down to the `compiler.process` calls, thus the example does not work when invoked with, `literal_binds=True`.

Besides, the calls to `process` each argument twice are wasteful, and reusing the built-in `case` expression instead of hard-coding the SQL statements is slightly nicer overall, isn't it?

Closes: #4402
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4402
Pull-request-sha: 24ee93f63e21fccae6cbc1cc1c154dd56f1e1963

Change-Id: I02424d9eb2b35abd5cdec5c2cd5d464a56e7fae6
2018-12-17 17:21:03 -05:00
mike bayer 3b6ff1b9f9 Merge "Add missing parameter to docstring" 2018-12-17 21:22:58 +00:00
Agam Rafaeli b1e4b59781 Add missing parameter to docstring
Closes: #4410
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4410
Pull-request-sha: 070a0f44f3a6ce651e6b8e9dcc84d2d507d00845

Change-Id: I7a026bf6a2041e7686d90d5f155b88d8001f2ba8
2018-12-17 12:58:19 -05:00
Agam Rafaeli 99fc012d72 Set a reading order to the compatibility import file
The order is as follows:
1. Imports, in the same format of "import X"
2. Members denoting versions of python
3. Members of imports that are shadowed for usage across the system
4. Global variables
5. If conditions of imports. (internally organized by this order)
6. Function definitions

Closes: #4409
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4409
Pull-request-sha: a7eb52d39f9758572e6a3314865bb633260aa8e1

Change-Id: I2fa44d1aebd7575df968f2e3f3fc7d474fa3c6d7
2018-12-17 11:20:09 -05:00
Mike Bayer d4a130bb1b Document and support nested composites
Composites can behave in a "nested" fashion by defining the
class in that way.   To make the constructor more convenient,
a callable can be passed to :func:`.composite` instead of the
class itself.  This works now, so add a test to ensure this
pattern remains available.

Change-Id: Ia009f274fca7269f41d6d824e0f70b6fb0ada081
2018-12-12 12:54:20 -05:00
Mike Bayer 7206308e7f cherry-pick changelog update for 1.2.16 2018-12-11 16:56:37 -05:00
Mike Bayer 9e98a2c864 cherry-pick changelog from 1.2.15 2018-12-11 16:56:37 -05:00
Chris Wilson 65ea042302 Add before_mapper_configured event
This event is intended to allow a specific mapper to be skipped during the
configure step, by returning a value of `.orm.interfaces.EXT_SKIP` which means
the mapper will be skipped within this configure run. The "new mappers" flag
will remain set in this case and the configure operation will occur again.

This event, and its return value, make it possible to query one base while a
different one still needs configuration, which cannot be completed at this
time.

Fixes: #4397

Change-Id: I122e556f6a4ff842ad15315dcf39e19bb7f9a744
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4403
2018-12-10 22:31:21 -05:00
mike bayer 0d4c0c1a27 Merge "Refer to existing of_type when resolving string attribute name" 2018-12-08 14:19:28 +00:00
mike bayer bfd3a685d6 Merge "Take instance into account when determining AssociationProxyInstance" 2018-12-08 14:18:53 +00:00
Mike Bayer d6f406e633 Take instance into account when determining AssociationProxyInstance
Fixed a regression in 1.3.0b1 caused by 🎫`3423` where association
proxy objects that access an attribute that's only present on a polymorphic
subclass would raise an ``AttributeError`` even though the actual instance
being accessed was an instance of that subclass.

Fixes: #4401
Change-Id: Ie62c48aa9142adff45cbf9a297184987c72f30f3
2018-12-07 22:40:50 -05:00
Mike Bayer 099f3fd812 Refer to existing of_type when resolving string attribute name
Fixed bug where chaining of mapper options using
:meth:`.RelationshipProperty.of_type` in conjunction with a chained option
that refers to an attribute name by string only would fail to locate the
attribute.

Fixes: #4400
Change-Id: I01bf449ec4d8f56bb8c34e25153c1c9b31ff8012
2018-12-07 16:03:17 -05:00
Mike Bayer 5851bf1138 Add versioned_update_old_row example
A modification to the "turn UPDATE into INSERT" recipe that
also UPDATEs the previous row.  The example is using timestamps
to maintain a relationship between two objects.

Change-Id: Ifdb8ee73616190384263bbe88c71d9278d616f6b
2018-12-07 14:01:23 -05:00
Mike Bayer c89729cf67 - fix formatting on examples to list the description first, some flake8
Change-Id: I57144a559f20abab02e745d052be5ff84edec7f8
2018-12-07 12:17:59 -05:00
adriennefranke 09856b911b Fixed typo in docs
Fixes: #4166
Fixes: #4399
Change-Id: I49494209463089114e77dfc737c811837d49ea20
2018-12-05 20:31:31 -05:00
Agam Rafaeli 23224f6e99 Removed the leading underscore for visitor_iterator property
A leading underscore usually denotes a private member. Since this
is a property and it is used in Query I removed the leading underscore

Change-Id: I8a35c09fd6d20ee0a13568ed7257a08b7bee2a08
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4398
2018-12-05 16:12:59 -05:00
mike bayer e0200cf6f0 Merge "Move CRUDTest, InlineDefaultTest from test_compiler" 2018-12-04 14:28:10 +00:00
Mike Bayer 89f95e9bad All sphinx dependencies move under the github sqlalchemy organization
Change-Id: I7a0dc1ef320b6abad0eeac8b24c20f821e5b8c81
2018-12-03 17:02:23 -05:00
mike bayer 656c5f3113 Merge "Fix PostgreSQL reflection of domains expressed as arrays" 2018-12-03 02:35:11 +00:00
Mike Bayer eacb31a89f "left" -> "accidentally placed at"
since "left" is kind of ambiguous, use more explicit terminology
here.

Also update the test to use a positive assertion that the
warning is emitted; quote the attribute name.

Change-Id: Ic2284c200a26b32b2da063cfaf6d59547309d587
References: https://github.com/zzzeek/sqlalchemy/pull/488
2018-12-02 18:58:47 -05:00
Mike Bayer 87cdda0086 Move CRUDTest, InlineDefaultTest from test_compiler
test_compiler is mostly related to SELECT statements as well
as smaller SQL elements.  While it still has some DDL related
tests, move out all the remaining insert/update tests into
the already present test_insert.py, test_update.py

Fixes: #2630
Change-Id: I4167618543fd1235d12d1717c8c629d2374b325a
2018-12-01 14:28:57 -05:00
Jakub Synowiec 46f9c3c7d4 Fix PostgreSQL reflection of domains expressed as arrays
Fixed issue where reflection of a PostgreSQL domain that is expressed as an
array would fail to be recognized.  Pull request courtesy Jakub Synowiec.

Fixes: #4377
Change-Id: I252c79ca435b87d4d9172b1c84e0e74e789ef676
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4380
2018-12-01 13:30:42 -05:00
mike bayer c8dea359db Merge "Apply path generation for superclasses to Load._set_path_strategy()" 2018-12-01 16:52:22 +00:00
Mike Bayer fb05e085fe Apply path generation for superclasses to Load._set_path_strategy()
Extended the fix first made as part of 🎫`3287`, where a loader option
made against a subclass using a wildcard would extend itself to include
application of the wildcard to attributes on the super classes as well, to a
"bound" loader option as well, e.g. in an expression like
``Load(SomeSubClass).load_only('foo')``.  Columns that are part of the
parent class of ``SomeSubClass`` will also be excluded in the same way as if
the unbound option ``load_only('foo')`` were used.

Fixes: #4373
Change-Id: I2eee0e587c34323a77df077b9cb699da370c403d
2018-11-30 14:36:20 -05:00
mike bayer 7940e7dc9c Merge "Add __clause_element__ to ColumnProperty" 2018-11-30 18:12:02 +00:00
mike bayer f916fa3b31 Merge "Add the write_timeout option for mysql." 2018-11-30 18:11:06 +00:00
mike bayer 39596f3398 Merge "Allow optional *args with base AnsiFunction" 2018-11-30 15:18:44 +00:00
jun923.gu 6a8454ded3 Add the write_timeout option for mysql.
As MySQLdb support read_timeout and write_timeout option, and
sqlalchemy just support read_timeout option. So sqlalchemy need to add
write_timeout option.

Fixes: #4381
Change-Id: I2bea80bdd6f20fafc72b48fa0e5d795626d9d9b9
Pull-request: https://github.com/sqlalchemy/sqlalchemy/pull/4385
2018-11-30 00:22:58 -05:00
Mike Bayer 3ff3975767 Allow optional *args with base AnsiFunction
Amended the :class:`.AnsiFunction` class, the base of common SQL
functions like ``CURRENT_TIMESTAMP``, to accept positional arguments
like a regular ad-hoc function.  This to suit the case that many of
these functions on specific backends accept arguments such as
"fractional seconds" precision and such.  If the function is created
with arguments, it renders the the parenthesis and the arguments.  If
no arguents are present, the compiler generates the non-parenthesized form.

Fixes: #4386
Change-Id: Ic492ef177e4987cec99ec4d95f55292be8daa087
2018-11-29 23:46:42 -05:00
Raphael 0a0b36686d typo
typo
2018-11-29 19:11:24 -05:00
Mike Bayer 576b33d46a Merge remote-tracking branch 'origin/pr/4382'
Change-Id: I957a13fa77be659a1ce2371342af4e33b1c5a304
2018-11-28 12:32:24 -05:00
Mike Bayer 6837e875a3 Add a test harness for MySQL connect args
This is to assist with #4381.

Change-Id: I5ebfc0da906a13edc4fb3f0ca7ab2d843d43bb00
2018-11-28 11:27:46 -05:00
cclauss 971f086785 print() is a function in Python 3 2018-11-28 10:38:57 +01:00
Mike Bayer 835444be72 Add __clause_element__ to ColumnProperty
Added a ``__clause_element__()`` method to :class:`.ColumnProperty` which
can allow the usage of a not-fully-declared column or deferred attribute in
a declarative mapped class slightly more friendly when it's used in a
constraint or other column-oriented scenario within the class declaration,
though this still can't work in open-ended expressions; prefer to call the
:attr:`.ColumnProperty.expression` attribute if receiving ``TypeError``.

Fixes: #4372
Change-Id: I5d3d1adb9c77de0566298bc2c46e9001d314b0c7
2018-11-27 20:12:16 -05:00
mike bayer ce3cab93d5 Merge "Warn for lower-case column attribute on declarative" 2018-11-27 07:54:43 +00:00
Mike Bayer 50417cf758 Move links etc. to github, new alembic links
Change-Id: I59392d355a216ae59552a04c5508f548b901aa7b
2018-11-26 22:58:50 -05:00
Mike Bayer 6ec40eca1a Warn for lower-case column attribute on declarative
A warning is emitted in the case that a :func:`.column` object is applied to
a declarative class, as it seems likely this intended to be a
:class:`.Column` object.

Fixes: #4374
Change-Id: I2e617ef65547162e3ba6587c168548ad0cf6203d
2018-11-26 01:12:01 -05:00
Mike Bayer b5cb68ac43 - remove @HEAD indicator from docs requirements, fixes #4375
Change-Id: I50b1622c2c2236bf9e436f61c7eea31faaeaa3e1
2018-11-25 23:54:44 -05:00
Mike Bayer f39a6216ee Version 1.3.0b2 placeholder 2018-11-16 23:13:08 -05:00
Mike Bayer 19590812c0 - 1.3.0b1 2018-11-16 23:04:42 -05:00
Mike Bayer b7fd3a3fc9 - edits
Change-Id: Ia8e1b5b51acc2b249499796ac36a7a3b68c941a1
2018-11-16 22:46:20 -05:00
Mike Bayer 9addf77342 - edits for 1.3 migration notes
Change-Id: Id2065053088481df5a703c63bfc88799a9943a5e
2018-11-16 18:52:42 -05:00
Mike Bayer 670ace18ae - we don't have a separate contributors doc anymore...
Change-Id: I0d09d3aa386336263829a98aeb1237caab78b789
2018-11-16 18:51:35 -05:00
mike bayer d1f187ecfd Merge "Modernize cx_Oracle parameters" 2018-11-16 03:14:54 +00:00
Mike Bayer 60a8648776 - fix spacing
Change-Id: I460d873b4c6a250594e291b5f47fff5a06280817
2018-11-15 19:51:03 -05:00
Mike Bayer 477a64e2b2 Repair tutorial code example to be deterministic
A few queries featured an aggregate without a GROUP BY
or a complete ordering, causing the doctests to fail
with recent versions of SQLite.  The queries are now made
to include a GROUP BY as well as ORDER BY both columns.

Fixes: #4370
Change-Id: I904bddb4372224158fcecff9f0dbbbe7c1bf36b3
2018-11-15 19:48:45 -05:00
Mike Bayer e0e6fe44e3 Modernize cx_Oracle parameters
Updated the parameters that can be sent to the cx_Oracle DBAPI to both allow
for all current parameters as well as for future parameters not added yet.
In addition, removed unused parameters that were deprecated in version 1.2,
and additionally we are now defaulting "threaded" to False.

Fixes: #4369
Change-Id: I599668960e7b2d5bd1f5e6850e10b5b3ec215ed3
2018-11-15 12:56:37 -05:00
Mike Bayer 996727ed89 Modernize cx_oracle connect documentation
in preparation for #4369, however the documentation was
also inaccurate in that it did not mention connect_args.

Change-Id: I992e5f53ce16cc9c72d2c893a3ca798a9c2b4d07
2018-11-15 12:52:33 -05:00
mike bayer 1f69e9b94c Merge "Add secondary selectable to FROM clauses for correlated exists" 2018-11-15 15:17:59 +00:00
mike bayer bfd6f76a7d Merge "Allow join() to pick the best candidate from multiple froms/entities" 2018-11-15 15:05:11 +00:00
Mike Bayer 7dcfd1e019 Allow join() to pick the best candidate from multiple froms/entities
Refactored :meth:`.Query.join` to further clarify the individual components
of structuring the join. This refactor adds the ability for
:meth:`.Query.join` to determine the most appropriate "left" side of the
join when there is more than one element in the FROM list or the query is
against multiple entities.  In particular this targets the regression we
saw in 🎫`4363` but is also of general use.   The codepaths within
:meth:`.Query.join` are now easier to follow and the error cases are
decided more specifically at an earlier point in the operation.

Fixes: #4365
Change-Id: I403f451243904a020ceab4c3f94bead550c7b2d5
2018-11-14 21:35:15 -05:00
Mike Bayer fdfd168060 Add secondary selectable to FROM clauses for correlated exists
In continuing with a similar theme as that of very recent 🎫`4349`,
repaired issue with :meth:`.RelationshipProperty.Comparator.any` and
:meth:`.RelationshipProperty.Comparator.has` where the "secondary"
selectable needs to be explicitly part of the FROM clause in the
EXISTS subquery to suit the case where this "secondary" is a :class:`.Join`
object.

Fixes: #4366
Change-Id: Icd0d0c3871bbd0059f0c9256e2b980edc2c90551
2018-11-14 17:37:02 -05:00
mike bayer 0a07fd99db Merge "Add new parameters for IDENTITY start/increment in mssql" 2018-11-14 22:35:19 +00:00
Mike Bayer 6629d9f892 Add new parameters for IDENTITY start/increment in mssql
Deprecated the use of :class:`.Sequence` with SQL Server in order to affect
the "start" and "increment" of the IDENTITY value, in favor of new
parameters ``mssql_identity_start`` and ``mssql_identity_increment`` which
set these parameters directly.  :class:`.Sequence` will be used to generate
real ``CREATE SEQUENCE`` DDL with SQL Server in a future release.

Fixes: #4362
Change-Id: I1e69378c5c960ff0bc28137c923589692f1a918f
2018-11-14 17:34:52 -05:00
mike bayer fd8f0044fe Merge "Deannotate "parententity" in primaryjoin/secondaryjoin" 2018-11-14 19:22:25 +00:00
mike bayer 5eafe15901 Merge "Insert primary entity in dynamic "secondary"" 2018-11-14 19:20:30 +00:00
Mike Bayer 4ee5b2c4a9 Deannotate "parententity" in primaryjoin/secondaryjoin
Fixed bug where the ORM annotations could be incorrect for the
primaryjoin/secondaryjoin a relationship if one used the pattern
``ForeignKey(SomeClass.id)`` in the declarative mappings.   This pattern
would leak undesired annotations into the join conditions which can break
aliasing operations done within :class:`.Query` that are not supposed to
impact elements in that join condition.  These annotations are now removed
up front if present.

Also add a test suite for has/any into test_query which will
form the basis for new tests to be added in 🎫`4366`.

Fixes: #4367
Change-Id: I929ef983981bb49bf975f346950ebb0e19c986b8
2018-11-14 11:35:45 -05:00
mike bayer 616b226f74 Merge "Add Sequence to StrSQLCompiler" 2018-11-13 23:37:33 +00:00
Mike Bayer 40c1a46e99 Insert primary entity in dynamic "secondary"
Fixed regression caused by 🎫`4349` where adding the "secondary"
table to the FROM clause for a dynamic loader would affect the ability of
the :class:`.Query` to make a subsequent join to another entity.   The fix
adds the primary entity as the first element of the FROM list since
:meth:`.Query.join` wants to jump from that.   Version 1.3 will have
a more comprehensive solution to this problem as well (🎫`4365`).

Fixes: #4363
Change-Id: I1abbb6207722619dc5369e1fd96de43d60a1ee62
2018-11-13 18:36:24 -05:00
Mike Bayer a698bdbc57 Convert to spaces
Change-Id: I219f7f6ef4f644f64fcb04fed224c6415465df0b
2018-11-10 21:56:52 -05:00
Mike Bayer 8318a98a60 Add Sequence to StrSQLCompiler
Added :class:`.Sequence` to the "string SQL" system that will render a
meaningful string expression (``"<next sequence value: my_sequence>"``)
when stringifying without a dialect a statement that includes a "sequence
nextvalue" expression, rather than raising a compilation error.

Fixes: #4144
Change-Id: Ia910f0e22008a7cde7597365954ede324101cf4d
2018-11-10 21:10:51 -05:00
mike bayer 6b84db83e0 Merge "Add new "all columns" naming convention tokens" 2018-11-11 01:58:18 +00:00
mike bayer 680835f815 Merge "Modernize deferred callable for many-to-one comparison" 2018-11-11 01:56:41 +00:00
Mike Bayer d5c2db437e Modernize deferred callable for many-to-one comparison
Improved the behavior of a relationship-bound many-to-one object expression
such that the retrieval of column values on the related object are now
resilient against the object being detached from its parent
:class:`.Session`, even if the attribute has been expired.  New features
within the :class:`.InstanceState` are used to memoize the last known value
of a particular column attribute before its expired, so that the expression
can still evaluate when the object is detached and expired at the same
time.  Error conditions are also improved using modern attribute state
features to produce more specific messages as needed.

To support the value being mutated while also being resilient towards
expiration, a new feature to InstanceState is added ._last_known_values
which holds onto the expired value when an individual key is expired.
Only takes effect specific to keys and InstanceState objects that
received a special instruction so this does not add to overall
memory/latency.

Fixes: #4359
Change-Id: Iff272e667bf741074549db550bf65348553ca8e7
2018-11-10 20:55:57 -05:00
Mike Bayer be70559584 Add new "all columns" naming convention tokens
Added new naming convention tokens ``column_0N_name``, ``column_0_N_name``,
etc., which will render the names / keys / labels for all columns referenced
by a particular constraint in a sequence.  In order to accommodate for the
length of such a naming convention, the SQL compiler's auto-truncation
feature now applies itself to constraint names as well, which creates a
shortened, deterministically generated name for the constraint that will
apply to a target backend without going over the character limit of that
backend.

Additional notes:

1. the SQLite dialect had a format_index method that was apparently not
used, removed.

2. the naming convention logic has been applying the foreign key
remote column spec to the naming convention, and not the actual
column name.  In the case where the referenced Table object uses
.key inside the columns and these are what ForeignKey() references,
the naming convention was doing the wrong thing.   The patch here
fixes this, however this isn't noted in the migration notes.

Fixes: #3989
Change-Id: Ib24f4754b886676096c480fc54b2e5c2463ac99a
2018-11-10 16:13:01 -05:00
Mike Bayer ec88a22a94 cherry-pick changelog update for 1.2.15 2018-11-10 15:59:12 -05:00
Mike Bayer 056fb6d952 cherry-pick changelog from 1.2.14 2018-11-10 15:59:12 -05:00
Mike Bayer ab1e6fb08f Fix typo
Change-Id: I411466dc1952cf57f73d1453c73b0ca449842c35
2018-11-10 11:26:31 -05:00
Mike Bayer af159c5695 Use case insensitive matching on lower_case_table_names=1,2
Fixed regression caused by 🎫`4344` released in 1.2.13, where the fix
for MySQL 8.0's case sensitivity problem with referenced column names when
reflecting foreign key referents is worked around using the
``information_schema.columns`` view.  The workaround was failing on OSX /
``lower_case_table_names=2`` which produces non-matching casing for the
``information_schema.columns`` vs. that of ``SHOW CREATE TABLE``, so in
case-insensitive SQL modes case-insensitive matching is now used.

Fixes: #4361
Change-Id: I748549bc4c27fad6394593f8ec93fc22bfd01f6c
2018-11-09 23:22:22 -05:00
mike bayer 07de512bf1 Merge "Implement SQLite ON CONFLICT for constraints" 2018-11-09 22:43:20 +00:00
Denis Kataev de804d7245 Implement SQLite ON CONFLICT for constraints
Implemented the SQLite ``ON CONFLICT`` clause as understood at the DDL
level, e.g. for primary key, unique, and CHECK constraints as well as
specified on a :class:`.Column` to satisfy inline primary key and NOT NULL.
Pull request courtesy Denis Kataev.

Fixes: #4360
Change-Id: I4cd4bafa8fca41e3101c87dbbfe169741bbda3f4
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/431
2018-11-07 18:26:40 -05:00
Mike Bayer 1f13c8c833 Improve documentation re: Session.binds and partitioning strategies
Update documentation to include background on arbitrary superclass
usage, add full cross-linking between all related methods and parameters.
De-emphasize "twophase" and document that it is not well-supported
in drivers.

Change-Id: Id99894bb62cc506e896c9aa7c256e9f6e602243e
2018-11-06 15:13:03 -05:00
Mike Bayer 15ac07f7b6 Merge remote-tracking branch 'origin/pr/486'
Change-Id: I90596d4fc238b913146906db0ab700dd767c5615
2018-11-03 12:45:31 -04:00
Mike Bayer b4e4325a7c Merge remote-tracking branch 'origin/pr/450'
Change-Id: I50c0dd75199a34f68f9a2fa0f89208a887193969
2018-11-03 12:37:19 -04:00
mike bayer 4811e35fa3 Merge "Deannotate ORM columns in ColumnEntity" 2018-11-03 16:17:04 +00:00
Mike Bayer 664290ab54 - block py.test 3.9.1 and 3.9.2, 3.9.3 is OK
Change-Id: I35ecd78b92ea420ef7909de65f82e005b92bf986
2018-11-02 16:54:21 -04:00
Mike Bayer 88bfa1b89c Deannotate ORM columns in ColumnEntity
Fixed a minor performance issue which could in some cases add unnecessary
overhead to result fetching, involving the use of ORM columns and entities
that include those same columns at the same time within a query.  The issue
has to do with hash / eq overhead when referring to the column in different
ways.

Fixes: #4347
Change-Id: I191d4d1b1623898060a9accdfd186de16f89a6b7
2018-11-02 16:40:59 -04:00
Iwo Herka 9a29ae2267 Tweak code-style and readability in events/base.py
This includes a few low-key, syntax-level tweaks and:

1. Rewrite of the if-statment in `Events._accept_with`.
2. Property name change, i.e. from `dispatcher.dispatch_cls` to
`dispatcher.dispatch`. In this case postfix `_cls` is confusing as
the property is not a class, but an instance of one.
2018-11-02 19:06:25 +01:00
Mike Bayer bc04e63475 Add new NO_RAISE attribute flag and specify for m2o history load
Added new behavior to the lazy load that takes place when the "old" value of
a many-to-one is retrieved, such that exceptions which would be raised due
to either ``lazy="raise"`` or a detached session error are skipped.

Fixes: #4353
Change-Id: I6c6c77613e93061a909f5062b70b17e8913fc9ee
2018-11-02 09:23:24 -04:00
mike bayer bc7c212370 Merge "Implement __delete__" 2018-11-02 13:21:15 +00:00
Mike Bayer 2e2af8d918 Implement __delete__
A long-standing oversight in the ORM, the ``__delete__`` method for a many-
to-one relationship was non-functional, e.g. for an operation such as ``del
a.b``.  This is now implemented and is equivalent to setting the attribute
to ``None``.

Fixes: #4354
Change-Id: I60131a84c007b0bf6f20c5cc5f21a3b96e954046
2018-11-02 01:22:41 -04:00
Mike Bayer e991684a39 Use attr keys when testing bulk update params for primary key
Fixed bug in :meth:`.Session.bulk_update_mappings` where alternate mapped
attribute names would result in the primary key column of the UPDATE
statement being included in the SET clause, as well as the WHERE clause;
while usually harmless, for SQL Server this can raise an error due to the
IDENTITY column.  This is a continuation of the same bug that was fixed in
🎫`.3849`, where testing was insufficient to catch this additional
flaw.

Fixes: #4357
Change-Id: Iead058c0465dfa31c5b8a8780769278b7000acc8
2018-11-01 21:54:10 -04:00
Mike Bayer 7d372da738 cherry-pick changelog update for 1.2.14 2018-10-31 16:49:15 -04:00
Mike Bayer c4d372d5b6 cherry-pick changelog from 1.2.13 2018-10-31 16:49:14 -04:00
Chris Macklin 1c3b2d7186 Add missing index method to _AssociationList.
Added missing ``.index()`` method to list-based association collections
in the association proxy extension.

Change-Id: Ice81dc4bcccd520638c5bc9a0f8bb2027946c846
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/485
2018-10-31 11:29:26 -04:00
mike bayer abb12a9d81 Merge "Move pk on single-inh subclass check below conflict resolution check" 2018-10-31 15:24:55 +00:00
mike bayer 4c487b9477 Merge "Add reserved word 'function' for MySQL" 2018-10-30 21:23:49 +00:00
Tom Manderson 3ed79a5c18 Move pk on single-inh subclass check below conflict resolution check
The column conflict resolution technique discussed at
:ref:`declarative_column_conflicts` is now functional for a :class:`.Column`
that is also a primary key column.  Previously, a check for primary key
columns declared on a single-inheritance subclass would occur before the
column copy were allowed to pass.

Fixes: #4352
Change-Id: Id4c025da53c28e58db6b549fe398f25f8a90d355
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/483
2018-10-30 13:21:52 -04:00
Alex Hall 38c81328e9 Add reserved word 'function' for MySQL
Added word ``function`` to the list of reserved words for MySQL, which is
now a keyword in MySQL 8.0

Fixes: #4348
Change-Id: Idd30acda7e99076810f65d0ee860055a18dc9193
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/481
2018-10-30 13:12:13 -04:00
wodim f041f1d198 Add missing space 2018-10-30 13:04:36 -04:00
David Poggi 83864ffe63 re-word recycle parameter documentation
Change-Id: I80cabcd9fa3f3b45e5355bf6c774a8eee02e7f1b
2018-10-30 13:02:45 -04:00
Mike Bayer 65af4fc74a Merge remote-tracking branch 'origin/pr/478'
Change-Id: I0f27b6426dbfd665edf2a119b1cfaadb54511dd0
2018-10-30 12:53:42 -04:00
mike bayer 64c3c81629 Merge "Create object- and column-oriented versions of AssociationProxyInstance" 2018-10-27 14:08:44 -04:00
Mike Bayer 90574aabef Create object- and column-oriented versions of AssociationProxyInstance
The :class:`.AssociationProxy` now has standard column comparison operations
such as :meth:`.ColumnOperators.like` and
:meth:`.ColumnOperators.startswith` available when the target attribute is a
plain column - the EXISTS expression that joins to the target table is
rendered as usual, but the column expression is then use within the WHERE
criteria of the EXISTS.  Note that this alters the behavior of the
``.contains()`` method on the association proxy to make use of
:meth:`.ColumnOperators.contains` when used on a column-based attribute.

Fixes: #4351
Change-Id: I310941f4e8f778c200f8144a26a89e5364cd4dfb
2018-10-26 16:34:33 -04:00
Mike Bayer 580d114405 Pin pytest *before* 3.9.1 totally
Unfortunately they have released
3.9.2 before fixing issue 4181, which means we will have to
re-pin a third time after they eventually release with
a fix

Change-Id: I9b6fab1b535f883a035f002264c41ad0166790ab
Reference: https://github.com/pytest-dev/pytest/issues/4181
2018-10-24 09:09:32 -04:00
Mike Bayer ac358a04a7 Use the same "current_timestamp" function for both sides of round trip
this test was using sysdate() and current_timestamp() together
in conjunction with a truncation to DAY, however for four hours
on saturday night (see commit time :) ) these two values will
have a different value if one side is EDT and the other is UTC.

tox does not transmit environment variables including TZ by
default, so even if the server is set up for EDT, running tox
will not set TZ and at least Oracle client seems to use this
value, producing UTC for session time but the database on CI
was configured for EDT, producing EDT for sysdate.

Change-Id: I56602d2402a475a0c4fdf61c1c5fc2618c82f915
2018-10-20 22:20:06 -04:00
Mike Bayer 1963fdceae - also correct for dbapi is a Mock without __version__...
Change-Id: I9e6b61a3292a2a6c8bb281c2375f2326282bcb76
2018-10-20 17:52:39 -04:00
mike bayer ead6fee1a7 Merge "Check more specifically for hybrid attr and not mapped property" 2018-10-20 16:55:01 -04:00
Mike Bayer 3cd9c81c1c - correct for dbapi not present in some tests
Change-Id: Iaa81a00658060d40add26c95cc69cee7edd5966a
2018-10-20 16:04:35 -04:00
Mike Bayer 801b37bd2a Enable decimal implicit bind for mysqlclient, is fixed as of
post 1.3.13

Change-Id: Ic7a2055597d06038ab330f1114416e4538964a2b
2018-10-20 12:32:25 -04:00
Mike Bayer 9335c24d6c Check more specifically for hybrid attr and not mapped property
Fixed regression caused by 🎫`4326` in version 1.2.12 where using
:class:`.declared_attr` with a mixin in conjunction with
:func:`.orm.synonym` would fail to map the synonym properly to an inherited
subclass.

Fixes: #4350
Change-Id: Ib2a9b6a125a2ac7c7ff80201746b7f10e5596226
2018-10-19 17:12:26 -04:00
Mike Bayer d080aae128 Add prop.secondary to FROM for dynamic loader
Fixed bug where "dynamic" loader needs to explicitly set the "secondary"
table in the FROM clause of the query, to suit the case where the secondary
is a join object that is otherwise not pulled into the query from its
columns alone.

Fixes: #4349
Change-Id: I397f62abd5603efa4fb273586d0f772bf8c8fbbf
2018-10-17 11:50:52 -04:00
Mike Bayer b4d42a84e2 block py.test 3.9.1
references:

https://github.com/pytest-dev/pytest/issues/4181

Change-Id: I216fde19dd0f5c4910d76c08400f2329b09ad584
2018-10-17 11:49:47 -04:00
Mike Bayer c5e888a3dd Don't use "is" to compare exceptions
psycopg2 is introducing a fine grained exception model where
most exceptions will be specialized subclasses, so don't use
"is" to compare an expression type

Change-Id: I2eac7503e38136f0dcc0da6f77b0b1d83ea1c6dc
2018-10-15 01:44:13 -04:00
Mike Bayer a8781b51b4 Don't call rollback on DBAPI connection that's "closed"
Use the existence of ConnectionRecord.connection to estimate
that this connection is likely closed, and if so, don't
try to call "rollback" on it.  This rollback is normally harmless
but is causing segfaults in mysqlclient due to
https://github.com/PyMySQL/mysqlclient-python/issues/270.

Change-Id: I1d7c5f5a520527d8268b6334795c2051f7ceeea6
2018-10-14 15:55:46 -04:00
Mike Bayer 7405392299 - get the "now" date for this test in terms of the database to accommodate
for local timezone doesn't match that of the DB

Change-Id: I0899d9294e8a2bd8f7f2c3e66cf396e2e8bd4bcc
2018-10-12 23:02:12 -04:00
Jayson ReisandMike Bayer 21fbb5e38f selectinload omit join
The "selectin" loader strategy now omits the JOIN in the case of a
simple one-to-many load, where it instead relies upon the foreign key
columns of the related table in order to match up to primary keys in
the parent table.   This optimization can be disabled by setting
the :paramref:`.relationship.omit_join` flag to False.
Many thanks to Jayson Reis for the efforts on this.

As part of this change, horizontal shard no longer relies upon
the _mapper_zero() method to get the query-bound mapper, instead
using the more generalized _bind_mapper() (which will use mapper_zero
if no explicit FROM is present).  A short check for the particular
recursive condition is added to BundleEntity and it no longer assigns
itself as the "namespace" to its ColumnEntity objects which creates
a reference cycle.

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Fixes: #4340
Change-Id: I649587e1c07b684ecd63f7d10054cd165891baf4
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/7
2018-10-10 13:28:02 -04:00
mike bayer bb65193bff Merge "Route bulk update/delete exec through new Query._execute_crud method" 2018-10-04 15:53:51 -04:00
Mike Bayer 3081269e6f Route bulk update/delete exec through new Query._execute_crud method
Added support for bulk :meth:`.Query.update` and :meth:`.Query.delete`
to the :class:`.ShardedQuery` class within the horiziontal sharding
extension.  This also adds an additional expansion hook to the
bulk update/delete methods :meth:`.Query._execute_crud`.

Fixes: #4196
Change-Id: I65f56458176497a8cbdd368f41b879881f06348b
2018-10-04 13:59:41 -04:00
mike bayer 96bb76222e Merge "Support tuples of heterogeneous types for empty expanding IN" 2018-10-04 13:49:42 -04:00
James Owen 681bd7eb88 Add warning to hybrid property expression and fixup crosslinks 2018-10-04 17:12:41 +02:00
Mike Bayer aa21284270 Support tuples of heterogeneous types for empty expanding IN
Pass a list of all the types for the left side of an
IN expression to the visit_empty_set_expr() method, so that
the "empty expanding IN" can produce clauses for each element.

Fixes: #4271
Change-Id: I2738b9df2292ac01afda37f16d4fa56ae7bf9147
2018-10-03 10:40:38 -04:00
Mike Bayer 56fb68ca86 Perform additional retrieval of correct column names
Added a workaround for a MySQL bug #88718 introduced in the 8.0 series,
where the reflection of a foreign key constraint is not reporting the
correct case sensitivity for the referred column, leading to errors during
use of the reflected constraint such as when using the automap extension.
The workaround emits an additional query to the information_schema tables in
order to retrieve the correct case sensitive name.

Fixes: #4344
Change-Id: I08020d6eec43cbe8a56316660380d3739a0b45f7
2018-10-03 09:52:38 -04:00
Mike Bayer ffd27cef48 Add additional documentation for ORM fetched defaults
Add additional examples to the section first added as part
of #4317 to cover the use cases requested in #3921.

Fixes: #3921
Change-Id: I6ec283aa0a6fbabedef40bb4320751ab4cd990ea
2018-10-02 13:54:00 -04:00
mike bayer 2b9ba4049e Merge "Fix dependency_for final argument" 2018-10-02 09:10:24 -04:00
mike bayer acebd2df11 Merge "Add .info to InstanceState" 2018-10-01 21:37:49 -04:00
mike bayer 76963dc49c Merge "Add reflection support for Postgresql partitioned tables" 2018-10-01 21:36:47 -04:00
mike bayer d9c6bbbd94 Merge "Strong reference parent object in association proxy" 2018-10-01 21:34:05 -04:00
Joe Urciuoli cacc3c2057 Fix dependency_for final argument
Fixed issue where part of the utility language helper internals was passing
the wrong kind of argument to the Python ``__import__`` builtin as the list
of modules to be imported.  The issue produced no symptoms within the core
library but could cause issues with external applications that redefine the
``__import__`` builtin or otherwise instrument it. Pull request courtesy Joe
Urciuoli.

Per the submitter: "The fourth argument provided to `__import__`  (which
`import_` feeds in to) is supposed to be a a list of strings, but this code is
passing a single string. This was causing the sqlalchemy `import_` function to
break the string (for example 'interfaces') into an array of single characters
['i', 'n', ...], which causes the actual `__import__` to not find the module
`sqlalchemy.orm.i` (since it's trying to import `sqlalchemy.orm.i` and
`sqlalchemy.orm.n` .. etc)"

No issue could be reproduced locally as it seems you can put anything non-
empty/None into that last argument, even a list like ``['X']``, and  all the
sub-modules seem to appear.  Omit it, and then the sub-modules aren't present.
Perhaps it just runs the module or not if this attribute is present.

Change-Id: Ia15c74620f24d24f0df4882f9b36a04e2c3725b8
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/473
2018-10-01 16:57:51 -04:00
Mike Bayer 11947c3f1f Strong reference parent object in association proxy
Considering the reversal of #597 as well as
84420a1d0f as I am unable to reproduce
the original issues from that release.

The long-standing behavior of the association proxy collection maintaining
only a weak reference to the parent object is reverted; the proxy will now
maintain a strong reference to the parent for as long as the proxy
collection itself is also in memory, eliminating the "stale association
proxy" error. This change is being made on an experimental basis to see if
any use cases arise where it causes side effects.

Change-Id: I051334be90a343dd0e8a1f35e072075eb14b14a7
Fixes: #4268
2018-10-01 16:54:29 -04:00
Mike Bayer b171a2ed03 Add .info to InstanceState
Added ``.info`` dictionary to the :class:`.InstanceState` class, the object
that comes from calling :func:`.inspect` on a mapped object.

Fixes: #4257
Change-Id: I32d043f369edb708a17eec2e0b8876db0c1891b4
2018-10-01 16:35:27 -04:00
Mike Bayer f1ca155cea Add reflection support for Postgresql partitioned tables
Added rudimental support for reflection of Postgresql
partitioned tables, e.g. that relkind='p' is added to reflection
queries that return table information.

Fixes: #4237
Change-Id: I66fd10b002e4ed21ea13b13a7e35a85f66bdea75
2018-10-01 16:24:55 -04:00
Mike Bayer 313879d6ad Add test and retroactive changelog for issue 4040
Fixes: #4040
Change-Id: I707c1cd2708a37102ad8184bec21be35cb6242d7
2018-10-01 14:00:39 -04:00
Mike Bayer 29d54ab69b Add link to Code of Conduct
Change-Id: Ib07db7c2fc97739a172e541a0681176a67f89a2f
2018-09-29 19:12:40 -04:00
Denis Kataev fc5dbc3016 Remove unnecessary unicode and raw string prefix 2018-09-28 12:40:30 +05:00
mike bayer 4085b10ec2 Merge "Import from collections.abc" 2018-09-27 21:55:01 -04:00
Mike Bayer 888d122dcf Add non-primary mapper example illustrating a row-limited relationship
Change-Id: Ifcb3baa6b220e375dc029794dd10c111660eac94
2018-09-27 21:27:59 -04:00
mike bayer d0c4873dc7 Merge "Break association proxy into a descriptor + per-class accessor" 2018-09-27 17:10:21 -04:00
Mike Bayer 6446e0dfd3 Break association proxy into a descriptor + per-class accessor
Reworked :class:`.AssociationProxy` to store state that's specific to a
parent class in a separate object, so that a single
:class:`.AssocationProxy` can serve for multiple parent classes, as is
intrinsic to inheritance, without any ambiguity in the state returned by it.
A new method :meth:`.AssociationProxy.for_class` is added to allow
inspection of class-specific state.

Change-Id: I634f88aae6306ac5c5237a0e1acbe07d0481d6b6
Fixes: #3423
2018-09-27 17:09:28 -04:00
xtreak 2d2fa49130 Import from collections.abc
Fixed additional warnings generated by Python 3.7 due to changes in the
organization of the Python ``collections`` and ``collections.abc`` packages.
Previous ``collections`` warnings were fixed in version 1.2.11. Pull request
courtesy xtreak.

See I2d1c0ef97c8ecac7af152cc56263422a40faa6bb for the original collections.abc
fixes.

Fixes: #4339
Change-Id: Ia92d2461f20309fb33ea6c6f592f7d4e7e32ae7a
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/475
2018-09-27 15:49:18 -04:00
mike bayer 5f2a934e3d Merge "Remove MappedCollection converter; deprecate @converter" 2018-09-27 15:44:45 -04:00
Mike Bayer fe8ddb71d9 Remove MappedCollection converter; deprecate @converter
Removed the collection converter used by the :class:`.MappedCollection`
class. This converter was used only to assert that the incoming dictionary
keys matched that of their corresponding objects, and only during a bulk set
operation.  The converter can interfere with a custom validator or
:meth:`.AttributeEvents.bulk_replace` listener that wants to convert
incoming values further.  The ``TypeError`` which would be raised by this
converter when an incoming key didn't match the value is removed; incoming
values during a bulk assignment will be keyed to their value-generated key,
and not the key that's explicitly present in the dictionary.

Overall, @converter is superseded by the
:meth:`.AttributeEvents.bulk_replace` event handler added as part of
🎫`3896`.

Fixes: #3604
Change-Id: Id0f7bd2cec938f5975eb2ab94df9ba5754dd43c3
2018-09-27 15:43:51 -04:00
mike bayer d945ee87a1 Merge "Copy create_constraint flag for Enum" 2018-09-25 20:16:33 -04:00
mike bayer f109e623f1 Merge "Accept multiple expressions for aggregate_order_by order_by" 2018-09-25 20:15:54 -04:00
Mike Bayer 54768815c6 Merge remote-tracking branch 'origin/pr/476' into pep-8-mxodbc
Change-Id: I0aa585719737c03a6ebb99b8ccb9f4ffdfd3fed5
2018-09-25 11:44:33 -04:00
Mike Bayer b7ba3f0d93 Accept multiple expressions for aggregate_order_by order_by
Added support for the :class:`.aggregate_order_by` function to receive
multiple ORDER BY elements, previously only a single element was accepted.

Fixes: #4337
Change-Id: I411ac31697a0d65b568ad65ce5b5181717afbd65
2018-09-25 11:14:32 -04:00
Mike Bayer 0737f45d4f Copy create_constraint flag for Enum
Fixed bug where the :paramref:`.Enum.create_constraint` flag on  the
:class:`.Enum` datatype would not be propagated to copies of the type, which
affects use cases such as declarative mixins and abstract bases.

Fixes: #4341
Change-Id: I978be65f33a616fe4d5f5de03fb3eaab6f6a2272
2018-09-25 10:38:40 -04:00
Agam Rafaeli a6419eeb3c PEP8 mxodbc.py 2018-09-24 15:01:44 +03:00
Mike Bayer fb991a4474 Add use_nchar_for_unicode flag; don't use nchar types for generic unicode
The Oracle dialect will no longer use the NCHAR/NCLOB datatypes to
represent generic unicode strings or clob fields in conjunction with
:class:`.Unicode` and :class:`.UnicodeText` unless the flag
``use_nchar_for_unicode=True`` is passed to :func:`.create_engine`.
Additionally, string types under Oracle now coerce to unicode under Python
2 in all cases, however unlike in previous iterations, we use SQLAlchemy's
native unicode handlers which are very performant (when C extensions are
enabled; when they are not, we use cx_Oracle's handlers).

Change-Id: I3939012e9396520875bc52e69bf81f27393836ee
Fixes: #4242
2018-09-22 21:34:32 -04:00
Mike Bayer a4da6452c3 move callcounts up to python 3.7
Change-Id: I1d17c2cd05b0dc3b787609925b6ebf2075752394
2018-09-21 13:54:40 -04:00
mike bayer 0e1ee3f5ce Merge "Allow dialects to customize group by clause compilation" 2018-09-20 21:54:25 -04:00
Samuel Chou 33fccc4861 Allow dialects to customize group by clause compilation
Refactored :class:`.SQLCompiler` to expose a
:meth:`.SQLCompiler.group_by_clause` method similar to the
:meth:`.SQLCompiler.order_by_clause` and :meth:`.SQLCompiler.limit_clause`
methods, which can be overridden by dialects to customize how GROUP BY
renders.  Pull request courtesy Samuel Chou.

Change-Id: I0a7238e55032558c27a0c56a72907c7b883456f1
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/474
2018-09-20 19:04:46 -04:00
Mike Bayer f704f47a49 - forgot the colon
Change-Id: I954d939ace775b5e6d94b8b1a909a9eddb7f352f
2018-09-19 16:12:50 -04:00
Mike Bayer 2280000005 Allow pip opts to be specified in environment
To allow a custom requirements file to be passed in,
add a generic passthrough to the tox install command.

Change-Id: Ic2e46a27914b76802dc26143e34ad507978af474
2018-09-19 14:55:09 -04:00
Mike Bayer 8e3d7b026c cherry-pick changelog update for 1.2.13 2018-09-19 14:15:19 -04:00
Mike Bayer f8631b98ee cherry-pick changelog from 1.2.12 2018-09-19 14:15:18 -04:00
mike bayer 95094d3789 Merge "Adapt right side in join if lateral detected" 2018-09-19 09:30:34 -04:00
mike bayer 5981e43281 Merge "Add LIFO for connection pooling" 2018-09-18 23:29:34 -04:00
Taem Park b64a3dd87a Add LIFO for connection pooling
Added new "lifo" mode to :class:`.QueuePool`, typically enabled by setting
the flag :paramref:`.create_engine.pool_use_lifo` to True.   "lifo" mode
means the same connection just checked in will be the first to be checked
out again, allowing excess connections to be cleaned up from the server
side during periods of the pool being only partially utilized.  Pull request
courtesy Taem Park.

Change-Id: Idb5e299c5082b3e6b547bd03022acf65fdc34f35
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/467
2018-09-18 21:58:02 -04:00
Mike Bayer 43f2c66ea7 Adapt right side in join if lateral detected
Fixed bug where use of :class:`.Lateral` construct in conjunction with
:meth:`.Query.join` as well as :meth:`.Query.select_entity_from` would not
apply clause adaption to the right side of the join.   "lateral" introduces
the use case of the right side of a join being correlatable.  Previously,
adaptation of this clause wasn't considered.

Fixes: #4334
Change-Id: I3631e562092769d30069a2aa5e50a580f4661a23
2018-09-18 17:23:32 -04:00
Romuald Brunet 505941259e Look for dict builtin in InstanceState cleanup
Added a check within the weakref cleanup for the :class:`.InstanceState`
object to check for the presence of the ``dict`` builtin, in an effort to
reduce error messages generated when these cleanups occur during interpreter
shutdown.  Pull request courtesy Romuald Brunet.

Change-Id: If27b94d50a32767de8b4147c09fa423f71596004
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/472
2018-09-18 13:57:29 -04:00
Mike Bayer 67a2cd9229 Use cx_Oracle dml_ret_array_val
Fixed issue for cx_Oracle 7.0 where the behavior of Oracle param.getvalue()
now returns a list, rather than a single scalar value, breaking
autoincrement logic throughout the Core and ORM. The dml_ret_array_val
compatibility flag is used for cx_Oracle 6.3 and 6.4 to establish compatible
behavior with 7.0 and forward, for cx_Oracle 6.2.1 and prior a version
number check falls back to the old logic.

Fixes: #4335
Change-Id: Ia60f5514803a505898c1ac9252355990c6203dda
2018-09-17 16:43:28 -04:00
Mike Bayer c94d67892e Merge remote-tracking branch 'origin/pr/471'
Change-Id: I1ddafb5d145c892d86fa130a6fed2402d3e388bb
2018-09-17 09:20:39 -04:00
Mike Bayer 5abaaaf7eb Don't list 1.2.x bugfixes as 1.3.0b1 bugfixes
We will still list features in 1.3 as backported but
it is too verbose to have all of 1.2.x's bugfixes listed as part
of 1.3.0b1 also.

Change-Id: Icb09050734af86a66a72b3f92a6bd60ee3e2f6ee
2018-09-13 17:43:12 -06:00
Mike Bayer 92bccc796b Add explicit note about @hybrid_property mutators re: method name
Fixes: #4332
Change-Id: I7c52140d3a3055a71b192fea020c795a57356d90
2018-09-12 09:44:57 -06:00
Wouter Overmeire 82006fcc93 Fix doc type 2018-09-11 14:17:02 +02:00
Glyph 35a458c782 minor spelling correction 2018-09-06 15:58:12 -07:00
Mike Bayer 71b01adc7b Clarify init_scalar event use case
Since I didn't even realize what this was for when reading the docs,
make it clearer that this is to mirror a Column default and remove
the extra verbiage about the mechanics of INSERTs.

Change-Id: Id2c6a29800f7b723573610e4707aec7e6ea38f5f
2018-09-06 10:44:09 -04:00
Mike Bayer 081d4275cf MariaDB 10.3 updates
MariaDB seems to handle some additional UPDATE/DELETE FROM
syntaxes as well as some forms of INTERSECT and EXCEPT. Open
up tests that expect failure for MySQL to allow success for
MariaDB 10.3.

Change-Id: Ia9341a82485ef7201bb8130d8dbf4a9b6976035a
2018-08-30 17:12:58 -04:00
Mike Bayer d8bb208a85 Fix links and update verbiage for reset_on_return
Change-Id: I642056b78570b44fdefe7f0874a8e4c720389f14
2018-08-28 14:58:46 -04:00
mike bayer e6c2a65159 Merge "Add option to sort into inserts/updates to bulk_save_objects" 2018-08-28 09:26:11 -04:00
mike bayer fe6d4a8eca Merge "Add python_requires and update classifiers" 2018-08-28 09:03:15 -04:00
Alessandro Cucci cbd661e0cd Add option to sort into inserts/updates to bulk_save_objects
Added new flag :paramref:`.Session.bulk_save_objects.preserve_order` to the
:meth:`.Session.bulk_save_objects` method, which defaults to True. When set
to False, the given mappings will be grouped into inserts and updates per
each object type, to allow for greater opportunities to batch common
operations together.  Pull request courtesy Alessandro Cucci.

Change-Id: I0d041f7696cf733655a74beeceee3fa80640efd7
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/6
2018-08-27 16:10:55 -04:00
Mike Bayer b601051b21 Add BakedQuery.to_query() method
Added new feature :meth:`.BakedQuery.to_query`, which allows for a
clean way of using one :class:`.BakedQuery` as a subquery inside of another
:class:`.BakedQuery` without needing to refer explicitly to a
:class:`.Session`.

Fixes: #4318
Change-Id: I528056c7d140036c27b95500d7a60dcd14784016
2018-08-27 14:59:08 -04:00
Mike Bayer 90a772b193 document expanding bound parameters, in_(), and baked query use cases
Change-Id: I09ccd73ebabbea4b5098ba5b170786ac065444c8
2018-08-27 14:51:59 -04:00
Mike Bayer d3dee71c24 - pep8 cleanup
Change-Id: I1d6eaf91c069bd5dd55a40ddd38e2f440b259fea
2018-08-27 11:11:04 -04:00
Mike Bayer ebd2c1323d fix link typos
Change-Id: I49233bf67caadf5ba69aa3b686f0ef6e5df3f15b
2018-08-27 10:25:59 -04:00
Mike Bayer b1aa737a05 Correct expanding docs to support empty lists
Change-Id: I9375b2055602216f9f25d32b2f7c035ae4280bd0
2018-08-27 10:18:45 -04:00
Mike Bayer c09b07fbb3 Include Session._query_cls as part of the cache key
Fixed issue where :class:`.BakedQuery` did not include the specific query
class used by the :class:`.Session` as part of the cache key, leading to
incompatibilities when using custom query classes, in particular the
:class:`.ShardedQuery` which has some different argument signatures.

Fixes: #4328
Change-Id: I829c2a8b09c91e91c8dc8ea5476c0d7aa47028bd
2018-08-26 15:49:06 -04:00
Hugo fb9f4c4d44 Add python_requires and update classifiers
- bump minimum Python 3 version to 3.4 in docs
- set up setup.py classifiers to cover 2.7, 3.4, 3.5, 3.6, 3.7 explicitly
- add python_requires

These are also the ones supported by the core Python team.
https://en.wikipedia.org/wiki/CPython#Version_history

Change-Id: I2ffa632c73c39bf38ba9d8b5dcc86d552b61aa68
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/468
2018-08-26 13:53:37 -04:00
mike bayer c6427fe140 Merge "Unwrap Proxy objects when scanning declared_attr" 2018-08-23 17:58:04 -04:00
Mike Bayer 626356842d Unwrap Proxy objects when scanning declared_attr
Fixed bug where the declarative scan for attributes would receive the
expression proxy delivered by a hybrid attribute at the class level, and
not the hybrid attribute itself, when receiving the descriptor via the
``@declared_attr`` callable on a subclass of an already-mapped class. This
would lead to an attribute that did not report itself as a hybrid when
viewed within :attr:`.Mapper.all_orm_descriptors`.

Fixes: #4326
Change-Id: I582d03f05c3768b3344f93e3791240e9e69b9d1e
2018-08-23 12:47:08 -04:00
Mike Bayer 1b5393db36 Don't run postfetch_post_update for a DELETE
Fixed 1.2 regression caused by 🎫`3472` where the handling of an
"updated_at" style column within the context of a post-update operation
would also occur for a row that is to be deleted following the update,
meaning both that a column with a Python-side value generator would show
the now-deleted value that was emitted for the UPDATE before the DELETE
(which was not the previous behavor), as well as that a SQL- emitted value
generator would have the attribute expired, meaning the previous value
would be unreachable due to the row having been deleted and the object
detached from the session.The "postfetch" logic that was added as part of
🎫`3472` is now skipped entirely for an object that ultimately is to
be deleted.

Fixes: #4327
Change-Id: Ieac845348979df296bcf7e785c0353bdc6074220
2018-08-23 11:55:13 -04:00
Mike Bayer 469931514a Propagate **kw in postgresql distinct on compilation
Fixed bug in PostgreSQL dialect where compiler keyword arguments such as
``literal_binds=True`` were not being propagated to a DISTINCT ON
expression.

Fixes: #4325
Change-Id: I9949387dceb7fabe889799f42e92423572368b29
2018-08-22 17:19:45 -04:00
Mike Bayer 52a3f5b763 Pass desired array type from pg.array_agg to functions.array_agg
Fixed the :func:`.postgresql.array_agg` function, which is a slightly
altered version of the usual :func:`.functions.array_agg` function, to also
accept an incoming "type" argument without forcing an ARRAY around it,
essentially the same thing that was fixed for the generic function in 1.1
in 🎫`4107`.

Fixes: #4324
Change-Id: I399a29f59c945a217cdd22c65ff0325edea8ea65
2018-08-22 11:13:54 -04:00
Mike Bayer 32ce703a98 Strip quotes from format_type in addition to other characters
Fixed bug in PostgreSQL ENUM reflection where a case-sensitive, quoted name
would be reported by the query including quotes, which would not match a
target column during table reflection as the quotes needed to be stripped
off.

Fixes: #4323
Change-Id: I668f3acccc578e58f23b70c82d31d5c1ec194913
2018-08-21 21:03:44 -04:00
Mike Bayer aafc4cb2c9 cherry-pick changelog update for 1.2.12 2018-08-20 17:00:53 -04:00
Mike Bayer 8065c54fe9 cherry-pick changelog from 1.2.11 2018-08-20 17:00:53 -04:00
Mike Bayer 3e2f61c439 Add missing range_ / rows parameters to additional over() methods
Added missing window function parameters
:paramref:`.WithinGroup.over.range_` and :paramref:`.WithinGroup.over.rows`
parameters to the :meth:`.WithinGroup.over` and
:meth:`.FunctionFilter.over` methods, to correspond to the range/rows
feature added to the "over" method of SQL functions as part of
🎫`3049` in version 1.1.

Fixes: #4322
Change-Id: I77dcdac65c699a4b52a3fc3ee09a100ffb4fc20e
2018-08-19 22:22:24 -04:00
Mike Bayer c3869f2383 Document binary_prefix for mysqlclient and PyMySQL
Also, remove the section on "use_unicode=0", there is no reason
anyone should be using that now.

Fixes: #4216
Change-Id: I5b8b53e40903adf339af2934a4f2d8b068818ebf
2018-08-17 19:32:42 -04:00
mike bayer debc3b5bbb Merge "Accommodate for classically mapped base classes in declarative" 2018-08-17 14:55:26 -04:00
mike bayer 2759899646 Merge "Add concept of "implicit boolean", treat as native" 2018-08-17 11:51:22 -04:00
Mike Bayer 4c931b2ec7 Accommodate for classically mapped base classes in declarative
Fixed issue in previously untested use case, allowing a declarative mapped
class to inherit from a classically-mapped class outside of the declarative
base, including that it accommodates for unmapped intermediate classes. An
unmapped intermediate class may specify ``__abstract__``, which is now
interpreted correctly, or the intermediate class can remain unmarked, and
the classically mapped base class will be detected within the hierarchy
regardless. In order to anticipate existing scenarios which may be mixing
in classical mappings into existing declarative hierarchies, an error is
now raised if multiple mapped bases are detected for a given class.

Fixes: #4321
Change-Id: I8604ecfd170d2589d9d1b1c87ba303762071fc30
2018-08-17 11:42:31 -04:00
Mike Bayer 9a5be7bb92 Add test support for #4036
Add a test that asserts MySQL can't implicitly treat a decimal
bound parameter without context and everyone else can.

Change-Id: I40e24a463d6eb03fd677195895891e73624776c3
2018-08-16 13:38:33 -04:00
Mike Bayer 462ccd9ff1 Add concept of "implicit boolean", treat as native
Fixed issue that is closely related to 🎫`3639` where an expression
rendered in a boolean context on a non-native boolean backend would
be compared to 1/0 even though it is already an implcitly boolean
expression, when :meth:`.ColumnElement.self_group` were used.  While this
does not affect the user-friendly backends (MySQL, SQLite) it was not
handled by Oracle (and possibly SQL Server).   Whether or not the
expression is implicitly boolean on any database is now determined
up front as an additional check to not generate the integer comparison
within the compliation of the statement.

Fixes: #4320
Change-Id: Iae0a65e5c01bd576e64733c3651e1e1a1a1b240c
2018-08-15 17:15:24 -04:00
Maxim Bublis dfa47b454a Add ability to preserve order in MySQL ON DUPLICATE KEY UPDATE.
Added support for the parameters in an ON DUPLICATE KEY UPDATE statement on
MySQL to be ordered, since parameter order in a MySQL UPDATE clause is
significant, in a similar manner as that described at
:ref:`updates_order_parameters`.  Pull request courtesy Maxim Bublis.

Pull-request: https://github.com/zzzeek/sqlalchemy/pull/462
Change-Id: If508d8e26dbd3c55ab1e83cf573fb4021e9d091e
2018-08-13 15:41:58 -04:00
Mike Bayer c85378d984 Correct for the INSERT statement, typos
Change-Id: I036f3eb9b5e591515920678bc9a76f707fda142c
2018-08-09 14:35:52 -04:00
Mike Bayer 82dfcf43de Write a much better section about server defaults
Include information about eager_defaults etc.  These
docs were written before we had all the features
we do now.

Change-Id: Ie62e58c5986698824f717e9f8c802b07a27517d4
Fixes: #4317
2018-08-09 13:35:05 -04:00
Mike Bayer f03c791879 Fixed issue with :meth:.TypeEngine.bind_expression and
:meth:`.TypeEngine.column_expression` methods where these methods would not
work if the target type were part of a :class:`.Variant`, or other target
type of a :class:`.TypeDecorator`.  Additionally, the SQL compiler now
calls upon the dialect-level implementation when it renders these methods
so that dialects can now provide for SQL-level processing for built-in
types.

Change-Id: Ic7b39575184db582e628e6ecee48dcda7d03a817
Fixes: #3981
2018-08-08 17:29:32 -04:00
Nicolas Rolin b17fa2513e Add support of empty list in exanding of bindparam
Added new logic to the "expanding IN" bound parameter feature whereby if
the given list is empty, a special "empty set" expression that is specific
to different backends is generated, thus allowing IN expressions to be
fully dynamic including empty IN expressions.

Fixes: #4271
Change-Id: Icc3c73bbd6005206b9d06baaeb14a097af5edd36
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/432
2018-08-07 17:04:10 -04:00
Mike Bayer abeea1d82d Include UPDATE/DELETE extra_froms in correlation
Fixed bug where the multi-table support for UPDATE and DELETE statements
did not consider the additional FROM elements as targets for correlation,
when a correlated SELECT were also combined with the statement.  This
change now includes that a SELECT statement in the WHERE clause for such a
statement will try to auto-correlate back to these additional tables in the
parent UPDATE/DELETE or unconditionally correlate if
:meth:`.Select.correlate` is used.  Note that auto-correlation raises an
error if the SELECT statement would have no FROM clauses as a result, which
can now occur if the parent UPDATE/DELETE specifies the same tables in its
additional set of tables ; specify :meth:`.Select.correlate` explicitly to
resolve.

Change-Id: Ie11eaad7e49af3f59df11691b104d6359341bdae
Fixes: #4313
2018-08-04 13:46:19 -04:00
mike bayer e9e869f4d5 Merge "Handle association proxy delete and provide for scalar delete cascade" 2018-08-01 23:20:01 -04:00
mike bayer 887bd34b2f Merge "Bind Integers to int for cx_Oracle" 2018-08-01 23:18:58 -04:00
Mike Bayer 75d48e65ea Bind Integers to int for cx_Oracle
For cx_Oracle, Integer datatypes will now be bound to "int", per advice
from the cx_Oracle developers.  Previously, using cx_Oracle.NUMBER caused a
loss in precision within the cx_Oracle 6.x series.

Change-Id: I4c6b2cca490aff5b98b7ceff3414715202881c89
Fixes: #4309
2018-08-01 19:21:13 -04:00
Mike Bayer 19cd4d4bc0 Handle association proxy delete and provide for scalar delete cascade
Fixed multiple issues regarding de-association of scalar objects with the
association proxy.  ``del`` now works, and additionally a new flag
:paramref:`.AssociationProxy.cascade_scalar_deletes` is added, which when
set to True indicates that setting a scalar attribute to ``None`` or
deleting via ``del`` will also set the source association to ``None``.

Change-Id: I1580d761571d63eb03a7e8df078cef97d265b85c
Fixes: #4308
2018-08-01 18:06:48 -04:00
mike bayer 0fc34a1139 Merge "Fix collections ABC access before Python 3.8" 2018-08-01 17:39:58 -04:00
Korn, Uwe 85dd766853 Mention Properties keys in __dir__
The Python builtin ``dir()`` is now supported for a SQLAlchemy "properties"
object, such as that of a Core columns collection (e.g. ``.c``),
``mapper.attrs``, etc.  Allows iPython autocompletion to work as well.
Pull request courtesy Uwe Korn.

Change-Id: I8696729542d1b74a566642a3a63fd500f64588cd
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/458

Mention Properties keys in __dir__

Change-Id: I88939955857c8df5eed0b87bc27c45357780b17d
2018-08-01 12:30:57 -04:00
Nathaniel Knight a51b0528d3 Fix collections ABC access before Python 3.8
Started importing "collections" from "collections.abc" under Python 3.3 and
greater for Python 3.8 compatibility.  Pull request courtesy Nathaniel
Knight.

In Python 3.3, the abstract base classes (Iterable, Mapping, etc.)
were moved from the `collections` module and put in the
`collections.abc` module. They remain in the `collections` module for
backwards compatibility, and will until Python 3.8.

This commit adds a variable (`collections_abc`) to the `util/compat`
module, which will be the `collections` module for Python < 3.3 and
before, or the `collections.abc` module for Python >= 3.3. It also
uses the new variable, getting rid of some deprecation warnings that
were seen when running under Python 3.7.

Change-Id: I2d1c0ef97c8ecac7af152cc56263422a40faa6bb
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/464
2018-08-01 12:30:09 -04:00
Mike Bayer 1c32206120 Correct sharding tests for provisioned follower
The sharding tests created named sqlite databases that were
shared across test suites.  It is unknown why these suddenly
started failing and were not failing before.

Change-Id: If2044f914ddaea0db594aa18b9278e24e2c818ea
2018-08-01 12:27:22 -04:00
Mike Bayer 65469442ad Do some pep8 and other cruft removal around association proxy
Change-Id: I33130022a7e223318b65388620828d539f6dacfd
2018-08-01 12:13:33 -04:00
Mike Bayer 1370b308e2 Merge branch 'migration-12-typo-fix' of https://bitbucket.org/nbasu02/sqlalchemy
Change-Id: I4682c1f7f94f25b813be686fdce0a2e0839412fe
2018-07-31 22:11:22 -04:00
Neil Basu 09f21f1e21 Add comma in migration-12 2018-07-31 14:27:18 -07:00
Kevin Horn 8601e86f11 Replace 'with' with 'which' 2018-07-27 11:06:50 -05:00
mike bayer 1ed3803654 Merge "Fix quoting schemas in _get_table_sql for the SQLite backend" 2018-07-18 14:00:33 -04:00
Phillip Cloud 893eac06e5 Fix quoting schemas in _get_table_sql for the SQLite backend
Fixed issue where the "schema" name used for a SQLite database within table
reflection would not quote the schema name correctly.  Pull request
courtesy Phillip Cloud.

Change-Id: I2770788c1f094a7743209250ec26b5ef5fb2d9e8
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/463
2018-07-18 10:48:27 -04:00
Alex Rothberg 5469dd1b8f Add postgresql_psycopg2binary install extra that installs psycopg2-binary
Fixes: #4306
Change-Id: I26edc1a4ac8a7f9f3f258bb03009ebfa4cc00e1a
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/465
2018-07-18 10:41:26 -04:00
Mike Bayer fb377229cd Don't apply no-traverse to query.statement
Fixed long-standing issue in :class:`.Query` where a scalar subquery such
as produced by :meth:`.Query.exists`, :meth:`.Query.as_scalar` and other
derivations from :attr:`.Query.statement` would not correctly be adapted
when used in a new :class:`.Query` that required entity adaptation, such as
when the query were turned into a union, or a from_self(), etc. The change
removes the "no adaptation" annotation from the :func:`.select` object
produced by the :attr:`.Query.statement` accessor.

Change-Id: I554e0e909ac6ee785ec3b3b14aaec9d235aa28cf
Fixes: #4304
2018-07-14 13:11:53 -04:00
Mike Bayer a5d4653b6e cherry-pick changelog update for 1.2.11 2018-07-13 19:03:48 -04:00
Mike Bayer 46c89fa3e9 cherry-pick changelog from 1.2.10 2018-07-13 19:03:48 -04:00
Mike Bayer 2fdf260208 Use exprs for bundle __clause_element__
Fixed bug in :class:`.Bundle` construct where placing two columns of the
same name would be de-duplicated, when the :class:`.Bundle` were used as
part of the rendered SQL, such as in the ORDER BY or GROUP BY of the statement.

Change-Id: Ia528c9fbb399a6beb5ea7cdd3a8a83ad530f5831
Fixes: #4295
2018-07-13 18:56:22 -04:00
Mike Bayer 2c44fc22a7 Correct the bug number for 🎫4288, which was erroneously
given as 🎫`4228`.

Change-Id: I6525560c1bcf3f3d861d6254723f5facdba6adae
Fixes: #4288
2018-07-13 12:44:50 -04:00
Mike Bayer 16cca68de8 - fix typo
Change-Id: I78692e821e34afe654c1131cd3465e4a6dfe773f
2018-07-13 12:41:04 -04:00
Mike Bayer cfe0bfd911 Correct fastexecutemany test for lower pyodbc version
some builds on CI have a pyodbc that is < 4.0.19, make
the check more specific

Change-Id: I69b33c2367d4a03adb00bcf52fb6d1483b0327f8
2018-07-12 22:55:01 -04:00
mike bayer 3cad4e0371 Merge "Don't null FK for collection-removed item with passive_deletes='all'" 2018-07-12 17:41:25 -04:00
Mike Bayer 9f09b6ef18 Don't null FK for collection-removed item with passive_deletes='all'
Fixed issue regarding passive_deletes="all", where the foreign key
attribute of an object is maintained with its value even after the object
is removed from its parent collection.  Previously, the unit of work would
set this to NULL even though passive_deletes indicated it should not be
modified.

Change-Id: I5ba98bc388cbdd6323d255b764e02506c2e66896
Fixes: #3844
2018-07-11 14:23:18 -04:00
mike bayer 5e6cfc3062 Merge "Drop default-related structures after the Table is dropped." 2018-07-11 09:30:17 -04:00
Mike Bayer aaa60cd17e Add pyodbc fast_executemany
Added ``fast_executemany=True`` parameter to the SQL Server pyodbc dialect,
which enables use of pyodbc's new performance feature of the same name
when using Microsoft ODBC drivers.

Change-Id: I743fa7280e8f709addd330cfc7682623701cbb2e
Fixes: #4158
2018-07-10 23:57:11 -04:00
mike bayer 5fedaa0eb8 Merge "Add all "like", "between", "is" operators as comparison operators" 2018-07-10 23:15:33 -04:00
Mike Bayer 532566ba1f Drop default-related structures after the Table is dropped.
Fixed bug where a :class:`.Sequence` would be dropped explicitly before any
:class:`.Table` that refers to it, which breaks in the case when the
sequence is also involved in a server-side default for that table, when
using :meth:`.MetaData.drop_all`.   The step which processes sequences
to be dropped via non server-side column default functions is now invoked
after the table itself is dropped.

Change-Id: I185f2cc76d2011ad4dd3ba9bde5d8aef0ec335ae
Fixes: #4300
2018-07-10 22:38:52 -04:00
Ilja Everilä 62d59088df Sqlite json
Added support for SQLite's json functionality via the new
SQLite implementation for :class:`.sqltypes.JSON`, :class:`.sqlite.JSON`.
The name used for the type is ``JSON``, following an example found at
SQLite's own documentation. Pull request courtesy Ilja Everilä.

Fixes: #3850
Change-Id: I3d2714fb8655343a99d13dc751b16b93d05d7dda
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/434
2018-07-10 18:55:31 -04:00
Mike Bayer 321265aa3b Add all "like", "between", "is" operators as comparison operators
Added "like" based operators as "comparison" operators, including
:meth:`.ColumnOperators.startswith` :meth:`.ColumnOperators.endswith`
:meth:`.ColumnOperators.ilike` :meth:`.ColumnOperators.notilike` among many
others, so that all of these operators can be the basis for an ORM
"primaryjoin" condition.

Change-Id: Idb13961f0c74462a139fc3444626e042f798ff08
Fixes: #4302
2018-07-10 17:00:21 -04:00
Mike Bayer 3cc832992d Document sticky behavior of loader options
References #4301

Change-Id: If921e3b8369e2cd5312b5964a99bcf7731b3ecfc
2018-07-10 13:31:07 -04:00
mike bayer 260c604942 Merge "Use MySQL protocol-level ping." 2018-07-09 21:51:58 -04:00
mike bayer 19497a9bf2 Merge "Expire memoizations on setattr/delattr, check in delattr" 2018-07-09 21:51:10 -04:00
Mike Bayer f7076ecf36 support functions "as binary comparison"
Added new feature :meth:`.FunctionElement.as_comparison` which allows a SQL
function to act as a binary comparison operation that can work within the
ORM.

Change-Id: I07018e2065d09775c0406cabdd35fc38cc0da699
Fixes: #3831
2018-07-09 21:48:39 -04:00
mike bayer 9d74387072 Merge "Refactor pool.py into a package" 2018-07-09 18:38:27 -04:00
Mike Bayer f34f634824 Expire memoizations on setattr/delattr, check in delattr
Fixed bug where declarative would not update the state of the
:class:`.Mapper` as far as what attributes were present, when additional
attributes were added or removed after the mapper attribute collections had
already been called and memoized.  Addtionally, a ``NotImplementedError``
is now raised if a fully mapped attribute (e.g. column, relationship, etc.)
is deleted from a class that is currently mapped, since the mapper will not
function correctly if the attribute has been removed.

Change-Id: Idaca8e0237b31aa1d6564d94c3a179d7dc6b5df9
Fixes: #4133
2018-07-09 18:24:12 -04:00
Maxim Bublis bd3255760b Use MySQL protocol-level ping.
Utilizes MySQL protocol-level pings for disconnection detection.
This is just a 5-byte packet followed by a 7-byte response.

Affects MySQLdb, MySQL Connector and PyMySQL dialects.

Change-Id: I672f75e3746878d88987a31750444dde0cf8eb9b
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/460
2018-07-09 17:59:20 -04:00
Mike Bayer 941143858b - add docs for PG REGCLASS
- remove __init__ docs for types without an init

Change-Id: I254ecb3763eaeb29aa71743c87ce2e021507fe28
2018-07-09 17:44:31 -04:00
Mike Bayer ec8695bc13 - add changelog 13 and links
Change-Id: I658a5958c0b053a26308aba213d9da3a67b75a1c
2018-07-09 17:39:56 -04:00
Mike Bayer 9700eb126b Refactor pool.py into a package
for better separation of concerns split out the
core pooling constructs from the implementations.  also
makes more room for new pool classes should we decide to
add them.  The DBProxy feature is never used so remove it
from documentation and split it out.

Change-Id: I04c9d7ae1882b17f3cf5c37ed05b781b05ef88fa
Fixes: #4255
2018-07-09 16:59:00 -04:00
Mike Bayer aec57258b3 Check tokens in chop path for inspectionattr before calling is_mapper
Fixed regression in 1.2.9 due to 🎫`4287` where using a
:class::`.Load` option in conjunction with a string wildcard would result
in a TypeError.

Change-Id: I2997ead0b8b9fa0edd009aa6f3161f4618fab97b
Fixes: #4298
2018-07-08 19:10:36 -04:00
Mike Bayer 284009683d - add some context to the declarative section indicating this is not
the introductory material for these topics

Change-Id: I358ba8c32520ce3950a727216bc019e33377e7b9
2018-07-05 00:05:42 -04:00
Mike Bayer 4f4d47fdf2 block cx_Oracle 6.4
Prevents https://github.com/oracle/python-cx_Oracle/issues/199

Change-Id: I0f94bde38919a027f094ca016621c1364e845332
2018-07-04 23:33:16 -04:00
Mike Bayer b6fb6f6b60 - fix linking for the query.rst page
Change-Id: I269fdd72e372e1bf4f0f85e9fc8e6938adc4f686
2018-07-04 17:49:37 -04:00
Mike Bayer c7d364b385 - add "leaks memory" to documented issues w/ mysqlconnector,
references #4296

Change-Id: I5b663d3444d3732a83a32443c128faffe62f11d9
2018-06-30 18:30:25 -04:00
Mike Bayer 3e37848f07 cherry-pick changelog update for 1.2.10 2018-06-29 13:45:17 -04:00
Mike Bayer bc76a5d184 cherry-pick changelog from 1.2.9 2018-06-29 13:45:16 -04:00
mike bayer 562dcfd295 Merge "Add unique_constraint_name to MSSQL FK reflection" 2018-06-29 12:26:29 -04:00
Mike Bayer 18f1b32ecb Merge remote-tracking branch 'origin/pr/456'
Change-Id: Id1d26d756f26e8cece921f476bc3f49689a3b782
2018-06-29 11:08:23 -04:00
Sean Dunn ca94ea8ab5 Add unique_constraint_name to MSSQL FK reflection
Fixed bug in MSSQL reflection where when two same-named tables in different
schemas had same-named primary key constraints, foreign key constraints
referring to one of the tables would have their columns doubled, causing
errors.   Pull request courtesy Sean Dunn.

Fixes: #4228
Change-Id: I7dabaaee0944e1030048826ba39fc574b0d63031
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/457
2018-06-29 10:52:47 -04:00
Logan Rosen b694a309e8 Update URL for PyMySQL documentation 2018-06-28 16:04:27 -04:00
Mike Bayer 9d2dc7911b Reflect ASC/DESC in MySQL index columns
Fixed bug in index reflection where on MySQL 8.0 an index that includes
ASC or DESC in an indexed column specfication would not be correctly
reflected, as MySQL 8.0 introduces support for returning this information
in a table definition string.

Change-Id: I21f64984ade690aac8c87dbe3aad0c1ee8e9727f
Fixes: #4293
2018-06-28 14:34:51 -04:00
mike bayer 6ad882c861 Merge "Vendor python3 formatargspec" 2018-06-28 13:41:18 -04:00
Mike Bayer 536d5187a0 Vendor python3 formatargspec
Replaced the usage of inspect.formatargspec() with a vendored version
copied from the Python standard library, as inspect.formatargspec()
is deprecated and as of Python 3.7.0 is emitting a warning.

Change-Id: I751652fac7f605a3a10b547ba8c5f34fef1de945
Fixes: #4291
2018-06-28 11:49:02 -04:00
mike bayer 9809eed735 Merge "Add do_setinputsizes event for cx_Oracle" 2018-06-28 10:43:00 -04:00
Mike Bayer 83750628d1 Try to get mysqlconnector somewhat working
Add CI support for MySQL connector and try to fix some of the
more obvious issues.  CI tests will run against MySQL 5.7
only for starters as there appear to be issues with
MySQL 8.0

Change-Id: Id8971143a8385a5c84f0646c21c4c21e793ce3a2
2018-06-27 19:15:19 -04:00
Mike Bayer c270efdfb3 Add do_setinputsizes event for cx_Oracle
Added a new event currently used only by the cx_Oracle dialect,
:meth:`.DialectEvents.setiputsizes`.  The event passes a dictionary of
:class:`.BindParameter` objects to DBAPI-specific type objects that will be
passed, after conversion to parameter names, to the cx_Oracle
``cursor.setinputsizes()`` method.  This allows both visibility into the
setinputsizes process as well as the ability to alter the behavior of what
datatypes are passed to this method.

Change-Id: I43b97c8e3c840cad6f01edb274dc9cfed19cb5fc
Fixes: #4290
2018-06-27 14:13:43 -04:00
mike bayer a0d1030096 Merge "Ensure BakedQuery is cloned before we add options to it" 2018-06-26 18:00:47 -04:00
Mike Bayer f243c00dda Ensure BakedQuery is cloned before we add options to it
Fixed bug in new polymorphic selectin loading where the BakedQuery used
internally would be mutated by the given loader options, which would both
inappropriately mutate the subclass query as well as carry over the effect
to subsequent queries.

Change-Id: Iaceecb50557f78484d09e55b3029a0483dfe873f
Fixes: #4286
2018-06-26 15:41:00 -04:00
mike bayer 1827af37cf Merge "fix TypeReflectionTest for sqlite 3.24" 2018-06-25 23:51:07 -04:00
mike bayer d5ee9957f9 Merge "Look up adapter info for previous left side in chained query.join()" 2018-06-25 23:48:52 -04:00
Mike Bayer f683ddf16b Look up adapter info for previous left side in chained query.join()
Fixed issue where chaining multiple join elements inside of
:meth:`.Query.join` might not correctly adapt to the previous left-hand
side, when chaining joined inheritance classes that share the same base
class.

Change-Id: I4b846430b7362912dbebf50599ec15a1eb978fd4
Fixes: #3505
2018-06-25 23:47:51 -04:00
mike bayer 441bf421cf Merge "Fix UnboundLocalError in mssql during isolation level grab" 2018-06-25 22:42:40 -04:00
mike bayer 6778187074 Merge "Support JOIN in UPDATE..FROM" 2018-06-25 18:38:11 -04:00
Nils Philippsen 40a5d0a4b0 fix TypeReflectionTest for sqlite 3.24
Fixed issue in test suite where SQLite 3.24 added a new reserved word that
conflicted with a usage in TypeReflectionTest.  Pull request courtesy Nils
Philippsen.

Change-Id: I396562cecb5ca774f29e9234845bcc6a399fc5cb
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/452
2018-06-25 18:37:23 -04:00
Mike Bayerandwikiped e2913f65c4 Fix UnboundLocalError in mssql during isolation level grab
Fixed issue within the SQL Server dialect under Python 3 where when running
against a non-standard SQL server database that does not contain either the
"sys.dm_exec_sessions" or "sys.dm_pdw_nodes_exec_sessions" views, leading
to a failure to fetch the isolation level, the error raise would fail due
to an UnboundLocalError.

Fixes: #4273
Co-authored-by: wikiped <wikiped@yandex.ru>
Change-Id: I39877c1f65f9cf8602fb1dceaf03072357759564
2018-06-25 18:35:41 -04:00
Mike Bayer c99345ee99 Use utf8mb4 (or utf8mb3) for all things MySQL
Fixed bug in MySQLdb dialect and variants such as PyMySQL where an
additional "unicode returns" check upon connection makes explicit use of
the "utf8" character set, which in MySQL 8.0 emits a warning that utf8mb4
should be used.  This is now replaced with a utf8mb4 equivalent.
Documentation is also updated for the MySQL dialect to specify utf8mb4 in
all examples.  Additional changes have been made to the test suite to use
utf8mb3 charsets and databases (there seem to be collation issues in some
edge cases with utf8mb4), and to support configuration default changes made
in MySQL 8.0 such as explicit_defaults_for_timestamp as well as new errors
raised for invalid MyISAM indexes.

Change-Id: Ib596ea7de4f69f976872a33bffa4c902d17dea25
Fixes: #4283
Fixes: #4192
2018-06-25 16:43:37 -04:00
Alex Grönholm 6daffe5406 Fixed typo
The name of the strategy is `raise_on_sql` as indicated elsewhere in the documentation.
2018-06-25 15:35:31 +03:00
Mike Bayer 7d2a581a58 Compare mappers more accurately in Load._chop_path
Fixed bug in cache key generation for baked queries which could cause a
too-short cache key to be generated for the case of eager loads across
subclasses.  This could in turn cause the eagerload query to be cached in
place of a non-eagerload query, or vice versa, for a polymorhic "selectin"
load, or possibly for lazy loads or selectin loads as well.

Change-Id: I2a69349d3e38814e2c7e6012fc04fbc0e47658a4
Fixes: #4287
2018-06-25 00:23:54 -04:00
mike bayer 647382b08d Merge "render WITH clause after INSERT for INSERT..SELECT on Oracle, MySQL" 2018-06-24 11:57:21 -04:00
Mike Bayer c352257070 Merge remote-tracking branch 'origin/pr/454'
Change-Id: I88ef3f7b3151d213285b9d9164f14a1fe0582fcc
2018-06-19 22:39:03 -04:00
Andrew Gaul 6bb50e1293 Remove stale ON UPDATE/ON DELETE comment.
SQLite supports both of these features.
2018-06-19 17:29:34 -07:00
mike bayer 33f874d0cf Merge "Add oracle, mssql to profiling" 2018-06-18 18:42:07 -04:00
Mike Bayer ef78334c0f Add oracle, mssql to profiling
As we are changing Oracle typing *again*, we should start tracking
if we trip over a big performance hit on the unicode stuff.

Change-Id: I72719cca4b9424171b32e1f2e58d655426e3bbba
2018-06-18 17:42:29 -04:00
Mike Bayer 3619edcb8a render WITH clause after INSERT for INSERT..SELECT on Oracle, MySQL
Fixed INSERT FROM SELECT with CTEs for the Oracle and MySQL dialects, where
the CTE was being placed above the entire statement as is typical with
other databases, however Oracle and MariaDB 10.2 wants the CTE underneath
the "INSERT" segment. Note that the Oracle and MySQL dialects don't yet
work when a CTE is applied to a subquery inside of an UPDATE or DELETE
statement, as the CTE is still applied to the top rather than inside the
subquery.

Also adds test suite support CTEs against backends.

Change-Id: I8ac337104d5c546dd4f0cd305632ffb56ac8bf90
Fixes: #4275
Fixes: #4230
2018-06-18 09:12:19 -04:00
Lele Gaifax e0dd82f267 Minor cosmetic tweaks to reST markup 2018-06-15 18:06:44 +02:00
Lele Gaifax cca5482221 Fix typo 2018-06-15 18:06:10 +02:00
Lele Gaifax 8581059c3a Consistently use "PostgreSQL", fixing a couple of mistypes 2018-06-15 18:05:45 +02:00
Mike Bayer 8f7766cc61 Lookup index columns in parent table by key for copy
Fixed regression in 1.2 due to 🎫`4147` where a :class:`.Table` that
has had some of its indexed columns redefined with new ones, as would occur
when overriding columns during reflection or when using
:paramref:`.Table.extend_existing`, such that the :meth:`.Table.tometadata`
method would fail when attempting to copy those indexes as they still
referred to the replaced column.   The copy logic now accommodates for this
condition.

Change-Id: I521aa2c9f3baa0e84598bbdd6ffe4bf07b6e3ba8
Fixes: #4279
2018-06-14 22:56:21 -04:00
Mike Bayer 58540ae93d Support JOIN in UPDATE..FROM
The :class:`.Update` construct now accommodates a :class:`.Join` object
as supported by MySQL for UPDATE..FROM.  As the construct already
accepted an alias object for a similar purpose, the feature of UPDATE
against a non-table was already implied so this has been added.

Change-Id: I7b2bca627849384d5377abb0c94626463e4fad04
Fixes: #3645
2018-06-13 21:38:20 -04:00
Andru1999andMike Bayer b1fcd83797 Use INITERROR macro in utils.c
Remove py3k check where we initialize the module and
instead make this look like the same init sequence
as resultproxy.c, processors.c

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Ia6352e50eaf760d95ab2bbf66d90c023c37f1193
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/429
2018-06-13 14:59:49 -04:00
Mike Bayer da5323c2fa update client-side/server-side SQL default expression documentation
These docs were inaccurate and verbose, try to modernize them
with up to date information and add cues to allow the reader
to understand them quickly.

Change-Id: I997d9b8963d90c73f5960fe29d8f1b5005299da7
2018-06-13 12:01:20 -04:00
hendawy 7ab8d60458 Importing InspectionAttr twice, now once
Change-Id: Ifc250d9361bf277d4269f8b58d40ce056b29dd83
(cherry picked from commit 07444e39e3b0cc9cde620e67bea27708ff0fc3bc)
2018-06-13 10:36:28 -04:00
mike bayer 2e286dad30 Merge "Iterate options per path for baked cache key" 2018-06-07 10:18:22 -04:00
Mike Bayer 006da86a39 Iterate options per path for baked cache key
Fixed an issue that was both a performance regression in 1.2 as well as an
incorrect result regarding the "baked" lazy loader, involving the
generation of cache keys from the original :class:`.Query` object's loader
options.  If the loader options were built up in a "branched" style using
common base elements for multiple options, the same options would be
rendered into the cache key repeatedly, causing both a performance issue as
well as generating the wrong cache key.  This is fixed, along with a
performance improvement when such "branched" options are applied via
:meth:`.Query.options` to prevent the same option objects from being
applied repeatedly.

Change-Id: I955fe2f50186abd8e753ad490fd3eb8f017e26f9
Fixes: #4270
2018-06-06 23:58:14 -04:00
mike bayer 0dd06d666f Merge "Support undocumented non-entity sequence Query argument" 2018-06-06 09:31:20 -04:00
mike bayer b5e0f01d74 Merge "Add Query.lazy_load_from attribute for sharding" 2018-06-06 09:29:28 -04:00
Fokko Driesprong 5bdab5b0ee Add the kwargs to the Adapt method
This will override the original signature of the method:
https://github.com/zzzeek/sqlalchemy/blob/master/lib/sqlalchemy/sql/type_api.py#L522
2018-06-04 21:37:18 +02:00
BR 63307d201e Small docs style fixes in inheritance.rst
Change-Id: I01d217cf1a8a1a8791e3b44167dfc4d6a0c77cdb
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/445
2018-06-04 12:33:39 -04:00
Mike Bayer a574b40929 Add Query.lazy_load_from attribute for sharding
Added new attribute :attr:`.Query.lazy_loaded_from` which is populated
with an :class:`.InstanceState` that is using this :class:`.Query` in
order to lazy load a relationship.  The rationale for this is that
it serves as a hint for the horizontal sharding feature to use, such that
the identity token of the state can be used as the default identity token
to use for the query within id_chooser().

Also repaired an issue in the :meth:`.Result.with_post_criteria`
method added in I899808734458e25a023142c2c5bb37cbed869479
for 🎫`4128` where the "unbake subquery loaders" version was calling
the post crtieria functions given the :class:`.Result` as the argument
rather than applying them to the :class:`.Query`.

Change-Id: I3c0919ce7fd151b80fe2f9b5f99f60df31c2d73d
Fixes: #4243
2018-06-04 12:30:05 -04:00
Mike Bayer 5628da627c Support undocumented non-entity sequence Query argument
Fixed regression caused by 🎫`4256` (itself a regression fix for
🎫`4228`) which breaks an undocumented behavior which converted for a
non-sequence of entities passed directly to the :class:`.Query` constructor
into a single-element sequence.  While this behavior was never supported or
documented, it's already in use so has been added as a behavioral contract
to :class:`.Query`.

Change-Id: I97546f5ab5af29f37c86321f39d564f98a12daf5
Fixes: #4269
2018-06-04 11:42:49 -04:00
Mike Bayer 45b22c9c3f cherry-pick changelog update for 1.2.9 2018-05-28 15:23:41 -04:00
Mike Bayer 72e2062176 cherry-pick changelog from 1.2.8 2018-05-28 15:23:41 -04:00
mike bayer 59ef300206 Merge "Mutex on _CONFIGURE_MUTEX in automap.prepare()" 2018-05-28 12:41:08 -04:00
Mike Bayer 2ac7cad717 Mutex on _CONFIGURE_MUTEX in automap.prepare()
Fixed a race condition which could occur if automap
:meth:`.AutomapBase.prepare` were used within a multi-threaded context
against other threads which  may call :func:`.configure_mappers` as a
result of use of other mappers.  The unfinished mapping work of automap
is particularly sensitive to being pulled in by a
:func:`.configure_mappers` step leading to errors.

Change-Id: I6d36df6639bf5cb8f137187dff68f386f5e84f88
Fixes: #4266
2018-05-28 09:28:12 -04:00
Mike Bayer 6c27bf5048 Turn oracle BINARY_DOUBLE, BINARY_FLOAT, DOUBLE_PRECISION into floats
The Oracle BINARY_FLOAT and BINARY_DOUBLE datatypes now participate within
cx_Oracle.setinputsizes(), passing along NATIVE_FLOAT, so as to support the
NaN value.  Additionally, :class:`.oracle.BINARY_FLOAT`,
:class:`.oracle.BINARY_DOUBLE` and :class:`.oracle.DOUBLE_PRECISION` now
subclass :class:`.Float`, since these are floating point datatypes, not
decimal.  These datatypes were already defaulting the
:paramref:`.Float.asdecimal` flag to False in line with what
:class:`.Float` already does.

Added reflection capabilities for the :class:`.oracle.BINARY_FLOAT`,
:class:`.oracle.BINARY_DOUBLE` datatypes.

Change-Id: Id99b912e83052654a17d07dc92b4dcb958cb7600
Fixes: #4264
2018-05-25 10:29:10 -04:00
Mike Bayer c7ae04d1c5 call setinputsizes() for integer types
Altered the Oracle dialect such that when an :class:`.Integer` type is in
use, the cx_Oracle.NUMERIC type is set up for setinputsizes().  In
SQLAlchemy 1.1 and earlier, cx_Oracle.NUMERIC was passed for all numeric
types unconditionally, and in 1.2 this was removed to allow for better
numeric precision.  However, for integers, some database/client setups
will fail to coerce boolean values True/False into integers which introduces
regressive behavior when using SQLAlchemy 1.2.  Overall, the setinputsizes
logic seems like it will need a lot more flexibility going forward so this
is a start for that.

Change-Id: Ida80cc2c2c37ffc0e05da4b5df2dadfab55a01f2
Fixes: #4259
2018-05-18 19:29:16 -04:00
Mike Bayer d2bacad469 Skip for SQL Server on non-native boolean unconstrained
As SQL Server is now non-native boolean as of
I4765d2a2a00b0d14f50282603cc4d48d4739dac1 but uses the BIT
type, we need to constrain this test to continue to not
run against SQL Server.

Change-Id: I214faf2b788a0e8e10725622e3e71f3b70805533
2018-05-17 19:57:01 -04:00
mike bayer 5957c212a7 Merge "Update dogpile.cache example to be compatible with baked query." 2018-05-17 17:25:48 -04:00
mike bayer 9f7814c8b8 Merge "Fix string formatting TypeError if tuple is passed" 2018-05-17 17:24:55 -04:00
Mike Bayer 2c7f2954f7 Update dogpile.cache example to be compatible with baked query.
Updated the dogpile.caching example to include new structures that
accommodate for the "baked" query system, which is used by default within
lazy loaders and some eager relationship loaders. The dogpile.caching
"relationship_caching" and "advanced" examples were also broken due to
🎫`4256`.  The issue here is also worked-around by the fix in
🎫`4128`.

Note that this recipe requires
I3f86fcb12a6a9a89aa308b335e75c25969bcc30e in order for the
"advanced" example to work.

Change-Id: I9d35417f1d6c1906555583b8225d3da7f81736f7
Fixes: #4258
2018-05-17 12:43:44 -04:00
Miguel Ventura 0b0b58c938 Fix string formatting TypeError if tuple is passed
Fixed issue where the "ambiguous literal" error message used when
interpreting literal values as SQL expression values would encounter a
tuple value, and fail to format the message properly. Pull request courtesy
Miguel Ventura.

Change-Id: I50d5d32d5f80ec79703a42d4b19b42c2f9701f24
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/442
2018-05-17 12:23:10 -04:00
mike bayer b9441c769b Merge "Prevent double-checkins and guard during reset-on-return invalidations" 2018-05-16 23:20:13 -04:00
mike bayer 9ac5135a68 Merge "Change query._identity_lookup into a normal instance method" 2018-05-16 23:19:06 -04:00
Mike Bayer b9f428a589 Clarify dogpile.cache differences which occur via #4128.
The fix for 🎫`4128` which failed to be included
in the 1.2.5 release also works around an issue in the dogpile.cache
"advanced" example, which will also be fixed independently.

Change-Id: I5eb0da9b93f13f05a8cbe4559e2ed177b1f91a52
2018-05-16 15:47:50 -04:00
Mike Bayer 3fa38a1a23 Change query._identity_lookup into a normal instance method
Fixed regression in 1.2.7 caused by 🎫`4228`, which itself was fixing
a 1.2-level regression, where the ``query_cls`` callable passed to a
:class:`.Session` was assumed to be a subclass of :class:`.Query`  with
class method availability, as opposed to an arbitrary callable.    In
particular, the dogpile caching example illustrates ``query_cls`` as a
function and not a :class:`.Query` subclass.

Change-Id: I3f86fcb12a6a9a89aa308b335e75c25969bcc30e
Fixes: #4256
2018-05-16 15:41:32 -04:00
Mike Bayer 2e46f73f35 Correct from version 1.2.5 to 1.2.8 for #4128
Change-Id: I3c9ec52a15e7cd083725d40f19078a783f1a4e23
2018-05-16 15:16:25 -04:00
Mike Bayer 220e35674b Restore missing changelog files for #4128
The fix merged in 4a31c30fa5
failed to get backported to 1.2 and the changelog files
got blown away in the release process.  Restore the
changelog files to master before cherry-picking
the whole thing to 1.2.

Change-Id: I899808734458e25a023142c2c5bb37cbed869479
Fixes: #4128
2018-05-16 15:12:34 -04:00
Mike Bayer dada909a10 Prevent double-checkins and guard during reset-on-return invalidations
Fixed connection pool issue whereby if a disconnection error were raised
during the connection pool's "reset on return" sequence in conjunction with
an explicit transaction opened against the enclosing :class:`.Connection`
object (such as from calling :meth:`.Session.close` without a rollback or
commit, or calling :meth:`.Connection.close` without first closing a
transaction declared with :meth:`.Connection.begin`), a double-checkin would
result, which could then lead towards concurrent checkouts of the same
connection. The double-checkin condition is now prevented overall by an
assertion, as well as the specific double-checkin scenario has been
fixed.

Change-Id: If5bb6941e36326846b14918c33ebfdd5604f642e
Fixes: #4252
2018-05-15 16:16:59 -04:00
mike bayer 432d24ab1a Merge "Use identity_token for refresh(), unexpire, undefer" 2018-05-13 11:25:40 -04:00
mike bayer 43d54f9ce7 Merge "Default server_version_info to (0, )" 2018-05-11 13:33:24 -04:00
Mike Bayer 29ce87273e Default server_version_info to (0, )
Fixed a bug in the test suite where if an external dialect returned
``None`` for ``server_version_info``, the exclusion logic would raise an
``AttributeError``.

Change-Id: I9124d3ac5484941081127274e6eb71f392fb94f7
Fixes: #4249
2018-05-11 09:23:18 -04:00
Mike Bayer bd1d6012dc SQL Server is not native boolean; add new flag for CHECK constraint
Fixed a 1.2 regression caused by 🎫`4061` where the SQL Server
"BIT" type would be considered to be "native boolean".  The goal here
was to avoid creating a CHECK constraint on the column, however the bigger
issue is that the BIT value does not behave like a true/false constant
and cannot be interpreted as a standalone expression, e.g.
"WHERE <column>".   The SQL Server dialect now goes back to being
non-native boolean, but with an extra flag that still avoids creating
the CHECK constraint.

Change-Id: I4765d2a2a00b0d14f50282603cc4d48d4739dac1
Fixes: #4250
2018-05-10 15:27:05 -04:00
Mike Bayer 513a6e5bce - add a tl;dr to postgresql search_path section as it's long
and will be easier to read if we know where it's going first.

Change-Id: I2766cf4655451ed514d4dc95ac60406b9f4a8ddb
2018-05-06 09:02:02 -04:00
Mike Bayer 70f8f6a169 - modernize versioning examples
- add new example versioned_rows_w_versionid

Change-Id: I592cd5eb7db50162b4c4ad6191813d9def2b6d7c
2018-05-05 18:21:08 -04:00
Mike Bayer 4b71933489 Use identity_token for refresh(), unexpire, undefer
The horizontal sharding extension now makes use of the identity token
added to ORM identity keys as part of 🎫`4137`, when an object
refresh or column-based deferred load or unexpiration operation occurs.
Since we know the "shard" that the object originated from, we make
use of this value when refreshing, thereby avoiding queries against
other shards that don't match this object's identity in any case.

Change-Id: Ib91637a65d94ace7405998b8410d62944a83f2eb
Fixes: #4247
2018-05-03 12:35:23 -04:00
Mike Bayer 67fe179d1b - add sap-hana
Change-Id: Id3ddd78fceb31df40c5f00f8b21320b0da8488af
(cherry picked from commit 21b6ec97318e87ab1bf36acf469eb9deb9823e0e)
2018-05-03 10:00:43 -04:00
Mike Bayer 453cdfd756 Render FOR UPDATE on the inner subquery as well as the outer
The ORM now doubles the "FOR UPDATE" clause within the subquery that
renders in conjunction with joined eager loading in some cases, as it has
been observed that MySQL does not lock the rows from a subquery.   This
means the query renders with two FOR UPDATE clauses; note that on some
backends such as Oracle, FOR UPDATE clauses on subqueries are silently
ignored since they are unnecessary.  Additionally, in the case of the "OF"
clause used primarily with Postgresql, the FOR UPDATE is rendered only on
the inner subquery when this is used so that the selectable can be targeted
to the table within the SELECT statement.

Change-Id: Ie5520d08d82bf0afd9e1bd2d43a0b2a0db0de16d
Fixes: #4246
2018-05-01 20:52:44 -04:00
Mike Bayer 29c5f7a5d5 - block cx_Oracle 6.3 due to https://github.com/oracle/python-cx_Oracle/issues/176
Change-Id: If13288789f5f32eb3ffb18c774752bb68a9ffb2a
2018-05-01 13:16:40 -04:00
Mike Bayer 7541d9b258 - add space invaders example
Change-Id: I439b6012af8c2bd8f555744657b8091ac168242b
2018-04-27 15:05:56 -04:00
Olivier Grisel 30b02003a7 Fix reference leak in compiled cache
Fixed a reference leak issue where the values of the parameter dictionary
used in a statement execution would remain referenced by the "compiled
cache", as a result of storing the key view used by Python 3 dictionary
keys().  Pull request courtesy Olivier Grisel.

Change-Id: Icfb0f38111a165780f6dd3e4e3382a03df79ce26
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/441
2018-04-25 15:16:06 -04:00
Mike Bayer a81468c45f cherry-pick changelog update for 1.2.8 2018-04-20 16:35:53 -04:00
Mike Bayer e5630e1c6a cherry-pick changelog from 1.2.7 2018-04-20 16:35:53 -04:00
Mike Bayer 43f278356d Refactor "get" to allow for pluggable identity token schemes
Fixed regression in 1.2 within sharded query feature where the
new "identity_token" element was not being correctly considered within
the scope of a lazy load operation, when searching the identity map
for a related many-to-one element.   The new behavior will allow for
making use of the "id_chooser" in order to determine the best identity
key to retrieve from the identity map.  In order to achieve this, some
refactoring of 1.2's "identity_token" approach has made some slight changes
to the implementation of ``ShardedQuery`` which should be noted for other
derivations of this class.

Change-Id: I04fa60535deec2d0cdec89f602935dfebeb9eb9d
Fixes: #4228
2018-04-20 14:36:00 -04:00
Mike Bayer 65ba2606be - more type cache warmup
Change-Id: I1b4327d38b5a09b73298c99f37919ee9f48aad0b
2018-04-20 14:34:52 -04:00
Mike Bayer c8bb359b74 bump variance for these sqlite-sensitive tests
Change-Id: I351c277afca7e53afc887c77a8b6dcaccf75d165
2018-04-20 13:53:18 -04:00
Mike Bayer e6e1c02c96 Document how to opt-out of NCHAR for cx_Oracle
Unfortunately, we need to bind Python unicode values as
NCHAR as in the case where non-ascii characters are present,
it's necessary.  We can't know in all cases how this value is being
used, so in those cases where Oracle will not accept NCHAR the
user should explicitly cast a value down to String.

Change-Id: I1a70739033435a7bf5effe2fa810ab064cea9188
Fixes: #4242
2018-04-20 13:31:45 -04:00
Mike Bayer 887636beb1 update callcounts for py36, get rid of old callcounts
Change-Id: Ib732ffa57c6c398d77ae2d3e0ac9b5cc09b40b4b
2018-04-20 12:42:07 -04:00
Mike Bayer cfff4106f1 - add version 1.3.0b1
Change-Id: If993c37ead1497b246816663bb65038630822676
2018-04-19 18:21:13 -04:00
mike bayer ae15530bfe Merge "Ensure select_from_entity adapter is used in adjust_for_single_inheritance" 2018-04-19 18:20:22 -04:00
Mike Bayer 4f2d0913fe Ensure select_from_entity adapter is used in adjust_for_single_inheritance
Fixed issue in single-inheritance loading where the use of an aliased
entity against a single-inheritance subclass in conjunction with the
:meth:`.Query.select_from` method would cause the SQL to be rendered with
the unaliased table mixed in to the query, causing a cartesian product.  In
particular this was affecting the new "selectin" loader when used against a
single-inheritance subclass.

Change-Id: Ic2cbe94a5269c101b1f98da9a466180dd4452783
Fixes: #4241
2018-04-19 17:11:47 -04:00
mike bayer 546c67c49b Merge "Render and reflect MySQL WITH PARSER index options" 2018-04-17 19:46:28 -04:00
Mike Bayer 6c2a1e1760 Render and reflect MySQL WITH PARSER index options
Support added for the "WITH PARSER" syntax of CREATE FULLTEXT INDEX
in MySQL, using the ``mysql_with_parser`` keyword argument.  Reflection
is also supported, which accommodates MySQL's special comment format
for reporting on this option as well.  Additionally, the "FULLTEXT" and
"SPATIAL" index prefixes are now reflected back into the ``mysql_prefix``
index option.

Change-Id: I0209291978125d8cee1bb5ed386d4f66578697a0
Fixes: #4219
2018-04-17 13:27:02 -04:00
Pat Buxton 5d5b9fe63d Fix - Order of records is not guaranteed
* Causes intermittent failure against Greenplum cluster
 * Tested using Greenplum dialact:
     https://github.com/PlaidCloud/sqlalchemy-greenplum

Change-Id: I6387e98f17a3667612fdaaadb27a08f79ec46398
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/440
2018-04-16 10:06:13 -04:00
Kent Bower a3473c08d3 Reflect Oracle NUMBER(NULL, 0) as INTEGER
The Oracle NUMBER datatype is reflected as INTEGER if the precision is NULL
and the scale is zero, as this is how INTEGER values come back when
reflected from Oracle's tables.  Pull request courtesy Kent Bower.

Change-Id: I4627febd46cab7085299c0a5700ee0f0bdca513c
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/437
2018-04-12 18:41:59 -04:00
mike bayer 2cbaebe6c5 Merge "Correct join for FKs with schema in SQL Server" 2018-04-11 15:28:13 -04:00
Mike Bayer 9d5e117f6f Correct join for FKs with schema in SQL Server
Fixed 1.2 regression caused by 🎫`4060` where the query used to
reflect SQL Server cross-schema foreign keys was limiting the criteria
incorrectly.

Additionally, added some rework of the inter-schema reflection tests
so that MySQL, MSSQL can be included, breaking out some of the
Postgresql-specific behaviors into separate requirements.

Fixes: #4234
Change-Id: I20c8e70707075f1767b79127c2c27d4b313c6515
2018-04-11 12:16:23 -04:00
Michael Williamson 6ca11d1b6a Update argument name for distinct() to match docs
A tiny change so that the docs are more consistent. At the moment, the same argument is given two different names.

Change-Id: Ic487006887d048700f260b2ae4a05d9a380412c1
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/439
2018-04-11 11:21:20 -04:00
Mike Bayer 036cdbe7fb Raise informative exception for non-sortable PK
An informative exception is re-raised when a primary key value is not
sortable in Python during an ORM flush under Python 3, such as an ``Enum``
that has no ``__lt__()`` method; normally Python 3 raises a ``TypeError``
in this case.   The flush process sorts persistent objects by primary key
in Python so the values must be sortable.

Change-Id: Ia186968982dcd1234b82f2e701fefa2a1668a7e4
Fixes: #4232
2018-04-09 09:15:52 -04:00
mike bayer 5abeee69e3 Merge "Ensure all visit_sequence accepts **kw args" 2018-04-04 21:06:35 -04:00
Mike Bayer b4eb29253c Ensure all visit_sequence accepts **kw args
Fixed issue where the compilation of an INSERT statement with the
"literal_binds" option that also uses an explicit sequence and "inline"
generation, as on Postgresql and Oracle, would fail to accommodate the
extra keyword argument within the sequence processing routine.

Change-Id: Ibdab7d340aea7429a210c9535ccf1a3e85f074fb
Fixes: #4231
2018-04-04 16:46:16 -04:00
Mike Bayer e1ac5dc63c Use base __ne__ implementation for range types w/ None
Fixed bug where the special "not equals" operator for the Postgresql
"range" datatypes such as DATERANGE would fail to render "IS NOT NULL" when
compared to the Python ``None`` value.

Also break up range tests into backend round trip and straight
compilation suites.

Change-Id: Ibaee132b1ea7dac8b799495a27f98f82a7d9c028
Fixes: #4229
2018-04-03 15:36:48 -04:00
Sebastian Bank 9f986ce10c Add postgresl.REGCLASS type for casting table names to OIDs and vice versa
Fixes: #4160
Change-Id: Id0bdbad1be3a0950dc8f35895ee13d9264244722
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/435
2018-04-03 09:31:07 -04:00
Mike Bayer 55371f4cff Fix bindparam type param fixes #4220
Change-Id: I0f40bc3145d4cab1a12d2174b9f0f60b4ce736f5
2018-04-01 10:33:40 -04:00
Mike Bayer 54d530d448 cherry-pick changelog update for 1.2.7 2018-03-30 16:29:53 -04:00
Mike Bayer 544b9f3eed cherry-pick changelog from 1.2.6 2018-03-30 16:29:53 -04:00
mike bayer 1e5cda65a1 Merge "Add support for declarative partitioning in PostgreSQL 10" 2018-03-30 16:22:43 -04:00
mike bayer 85af25b7d1 Merge "Filter non-integer characters from pyodbc SQL Server version" 2018-03-30 12:55:58 -04:00
Vsevolod Solovyov 0174d698a8 Add support for declarative partitioning in PostgreSQL 10
Added support for "PARTITION BY" in Postgresql table definitions,
using "postgresql_partition_by".  Pull request courtesy
Vsevolod Solovyov.

Change-Id: Id74d6882d7193fae1e5fd44b6e12d6852866fcc4
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/430
2018-03-30 12:18:09 -04:00
Mike Bayer f55c4f6bd2 Filter non-integer characters from pyodbc SQL Server version
Adjusted the SQL Server version detection for pyodbc to only allow for
numeric tokens, filtering out non-integers, since the dialect does tuple-
numeric comparisons with this value.  This is normally true for all known
SQL Server / pyodbc drivers in any case.

Change-Id: I4ab18a07e19231091b5e877ba1fccd5eda72a992
Fixes: #4227
2018-03-30 11:22:30 -04:00
Mike Bayer c543729671 Invalidate on failed connect handler
Fixed bug in connection pool where a connection could be present in the
pool without all of its "connect" event handlers called, if a previous
"connect" handler threw an exception; note that the dialects themselves
have connect handlers that emit SQL, such as those which set transaction
isolation, which can fail if the database is in a non-available state, but
still allows a connection.  The connection is now invalidated first if any
of the connect handlers fail.

Change-Id: I61d6f4827a98ab8455f1c3e1c55d046eeccec09a
Fixes: #4225
2018-03-28 15:49:17 -04:00
Mike Bayer f9c4b5ea7d Link to the ExpireRelationshipOnFKChange recipe for deletes
The recipe now supports interception of delete() and a
corresponding update of related objects.

Change-Id: I2aa3bfdd477ceccff6cfb3e66ed73311705010c7
2018-03-26 18:11:20 -04:00
mike bayer dfb16b4493 Merge "Don't warn for mixin-based __table_args__, __mapper_args__ declared_attr" 2018-03-21 14:15:46 -04:00
Mike Bayer 37955a5299 Don't warn for mixin-based __table_args__, __mapper_args__ declared_attr
Removed a warning that would be emitted when calling upon
``__table_args__``, ``__mapper_args__`` as named with a ``@declared_attr``
method, when called from a non-mapped declarative mixin.  Calling these
directly is documented as the approach to use when one is overidding one
of these methods on a mapped class.  The warning still emits for regular
attribute names.

Change-Id: Iae7ed0bd625a2c163c910aa777cef4779128580a
Fixes: #4221
2018-03-21 13:08:19 -04:00
mike bayer 5cc8d872b4 Merge "Track if we're rendering within the CTE recursively" 2018-03-16 16:38:02 -04:00
Mike Bayer ef2859bbc8 Track if we're rendering within the CTE recursively
Fixed a regression that occurred from the previous fix to 🎫`4204` in
version 1.2.5, where a CTE that refers to itself after the
:meth:`.CTE.alias` method has been called would not refer to iself
correctly.

Change-Id: Iaa63d65ad2b90c8693f9953fbb32dbb10c73a037
Fixes: #4204
2018-03-14 11:38:15 -04:00
Mike Bayer 0fd508ad32 Ignore non-primary mappers within mutable instrumentation
Fixed bug where using :meth:`.Mutable.associate_with` or
:meth:`.Mutable.as_mutable` in conjunction with a class that has non-
primary mappers set up with alternatively-named attributes would produce an
attribute error.  Since non-primary mappers are not used for persistence,
the mutable extension now excludes non-primary mappers from its
instrumentation steps.

Change-Id: I2630d9f771a171aece03181ccf9159885f68f25e
Fixes: #4215
2018-03-12 12:50:52 -04:00
mike bayer f3e18baa00 Merge "Raise cx_Oracle minimum version to 5.2" 2018-03-08 12:36:38 -05:00
Mike Bayer ea20a11817 Make it much more clear that concrete mapping is limited
Change-Id: Icb2ea787b0defbf5f1244b144759c1e8acff3f0f
2018-03-07 18:05:07 -05:00
Mike Bayer 4982a250a9 Raise cx_Oracle minimum version to 5.2
The minimum cx_Oracle version supported is 5.2 (June 2015).  Previously,
the dialect asserted against version 5.0 but as of 1.2.2 we are using some
symbols that did not appear until 5.2.

Change-Id: I6fa4238f1722789924f4a6473fdce6f524333825
Fixes: #4211
2018-03-07 16:27:26 -05:00
Mike Bayer c4fcf55652 Add notes regarding flat=True
Start documenting that flat=True and aliased=True don't work
with selectable particularly when selectable is an aliased select
already.  References #4212

Change-Id: I6e576165f06387350ae97e43ad979e575a4912b9
(cherry picked from commit 39d7dfa08a)
2018-03-07 16:03:49 -05:00
Mike Bayer beab362b2e cherry-pick changelog update for 1.1.19 2018-03-06 14:10:39 -05:00
Mike Bayer 8cc7e589d2 cherry-pick changelog from 1.1.18 2018-03-06 14:10:39 -05:00
Mike Bayer f7b55967ba cherry-pick changelog update for 1.2.6 2018-03-06 13:58:22 -05:00
Mike Bayer e5f9de3aa7 cherry-pick changelog from 1.2.5 2018-03-06 13:58:22 -05:00
Mike Bayer 433eff476a - add missing versions for #4208
Change-Id: I307b4b81e472cb6473d201fece26753878dd38f1
2018-03-06 13:19:01 -05:00
mike bayer c5d79494d8 Merge "Add Query.enable_single_entity()" 2018-03-06 12:50:04 -05:00
mike bayer 59149b5702 Merge "Clone _cte_alias instead of assigning "self"" 2018-03-06 12:49:22 -05:00
Eric Atkin 611f7f4e94 Add Query.enable_single_entity()
Added new feature :meth:`.Query.only_return_tuples`.  Causes the
:class:`.Query` object to return keyed tuple objects unconditionally even
if the query is against a single entity.   Pull request courtesy Eric
Atkin.

Change-Id: Ib0b7f5f78431aa68082e5b200ed577daa4222336
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/425
2018-03-05 21:42:49 -05:00
Mike Bayer 9a13f007e2 Clone _cte_alias instead of assigning "self"
Fixed bug in :class:.`CTE` construct along the same lines as that of
🎫`4204` where a :class:`.CTE` that was aliased would not copy itself
correctly during a "clone" operation as is frequent within the ORM as well
as when using the :meth:`.ClauseElement.params` method.

Change-Id: Id68d72dd244dedfc7bd6116c9a5123c51a55ea20
Fixes: #4210
2018-03-05 21:37:12 -05:00
Mike Bayer 08a8e8cf3b Don't include AliasedClass when pickling options
Fixed 1.2 regression where a mapper option that contains an
:class:`.AliasedClass` object, as is typical when using the
:meth:`.QueryableAttribute.of_type` method, could not be pickled.   1.1's
behavior was to omit the aliased class objects from the path, so this
behavior is restored.

Change-Id: I4b36a422b7c0e6a6da7ee3ba3ab282c13917a31f
Fixes: #4209
2018-03-05 18:05:56 -05:00
mike bayer 0e14670605 Merge "Only replace first occurrence for COLLATE/ARRAY syntax" 2018-03-05 18:03:53 -05:00
Asif Saifuddin Auvi 9215c797bc fix version type in doc 2018-03-06 00:08:47 +06:00
Mike Bayer 7300469f71 Only replace first occurrence for COLLATE/ARRAY syntax
Fixed bug in Postgresql COLLATE / ARRAY adjustment first introduced
in 🎫`4006` where new behaviors in Python 3.7 regular expressions
caused the fix to fail.

Change-Id: Ied3893d7cac210befa0277b55b3b895b0ba1f0d2
Fixes: #4208
2018-03-05 11:33:30 -05:00
Mike Bayer 243f980479 Add python 3.7 environment
Change-Id: I4ed7bd6ffd1c8c9b5169cf21709ec19801580126
2018-03-05 09:43:26 -05:00
Mike Bayer 6ec0f97e37 Get MySQL version info from @@version
MySQL dialects now query the server version using ``SELECT @@version``
explicitly to the server to ensure we are getting the correct version
information back.   Proxy servers like MaxScale interfere with the value
that is passed to the DBAPI's connection.server_version value so this
is no longer reliable.

Change-Id: Iafd39be8c9bf1982d58b34cc997ae1016ad6c48c
Fixes: #4205
(cherry picked from commit 9ba77e8d3b682bff89fdab5e80271a96a52fe8c8)
(cherry picked from commit 5c1ebbc370)
2018-03-03 16:16:43 -05:00
Mike Bayer 15c458d349 Setup master as 1.3
Change-Id: I1e8240d19f891cb6575f10d93524b551d74864ea
2018-03-02 14:41:23 -05:00
Mike Bayer ea36338b2e - add some seealsos for the transient object that loads use case
Change-Id: Ibfa79a3721f31806223906cccf4547673b3d42f1
(cherry picked from commit 5de2e17b6e)
2018-03-02 11:59:11 -05:00
Mike Bayer a833c9f701 Fix enable_relationship_loading() works fine w/ one-to-many
Change-Id: I6efb62afa02be4d42482cfdbec739a5c6ab32bd7
2018-03-02 10:47:15 -05:00
mike bayer e3323df4bd Merge "Check existing CTE for an alias name when rendering FROM clause" 2018-03-01 12:38:45 -05:00
Mike Bayer 5f60dc649c Check existing CTE for an alias name when rendering FROM clause
Fixed bug in CTE rendering where a :class:`.CTE` that was also turned into
an :class:`.Alias` would not render its "ctename AS aliasname" clause
appropriately if there were more than one reference to the CTE in a FROM
clause.

Change-Id: If8cff27a2f4faa5eceb59aa86398db6edb3b9e72
Fixes: #4204
2018-03-01 10:54:35 -05:00
mike bayer 39444fd45f Merge "Merge existing query params in baked lazy load" 2018-02-28 10:53:53 -05:00
Mike Bayer 4a31c30fa5 Merge existing query params in baked lazy load
Fixed a long-standing regression that occurred in version
1.0, which prevented the use of a custom :class:`.MapperOption`
that alters the _params of a :class:`.Query` object for a
lazy load, since the lazy loader itself would overwrite those
parameters.   This applies to the "temporal range" example
on the wiki.  Note however that the
:meth:`.Query.populate_existing` method is now required in
order to rewrite the mapper options associated with an object
already loaded in the identity map.  Also, a custom defined
:class:`.MapperOption` will now cause lazy loaders related to
the target object to use a non-baked query by default unless
the :meth:`.MapperOption._generate_cache_key` method is implemented.

Fixed bug where the new :meth:`.baked.Result.with_post_criteria`
method would not interact with a subquery-eager loader correctly,
in that the "post criteria" would not be applied to embedded
subquery eager loaders.   This is related to 🎫`4128` in that
the post criteria feature is now used by the lazy loader.

Change-Id: I899808734458e25a023142c2c5bb37cbed869479
Fixes: #4128
2018-02-28 10:52:59 -05:00
Mike Bayer b055132b89 Merge remote-tracking branch 'origin/pr/421' 2018-02-27 14:46:30 -05:00
mike bayer a10bc4fdaa Merge "Ensure we have states to load when doing poly post load" 2018-02-23 15:14:46 -05:00
mike bayer 41c6b54243 Merge "Allow bind processors to work with expanding IN" 2018-02-23 14:21:44 -05:00
Mike Bayer 3859256312 Ensure we have states to load when doing poly post load
Fixed bug in new "polymorphic selectin" loading when a selection of
polymorphic objects were to be partially loaded from a relationship
lazy loader, leading to an "empty IN" condition within the load that
raises an error for the "inline" form of "IN".

Change-Id: I721cf5fdf0b9fd2289067d5d2c6bc87fb2436f07
Fixes: #4199
2018-02-23 14:19:13 -05:00
Mike Bayer d746ea9579 Allow bind processors to work with expanding IN
Fixed bug in new "expanding IN parameter" feature where the bind parameter
processors for values wasn't working at all, tests failed to cover this
pretty basic case which includes that ENUM values weren't working.

Change-Id: I8e2420d7229a3e253e43b5227ebb98f9fe0bd14a
Fixes: #4198
2018-02-23 13:10:08 -05:00
Mike Bayer f7dcac6967 cherry-pick changelog update for 1.1.18 2018-02-22 16:16:11 -05:00
Mike Bayer c18f81a67f cherry-pick changelog from 1.1.17 2018-02-22 16:16:11 -05:00
Mike Bayer 680ffffe9c Version 1.2.5 placeholder 2018-02-22 16:05:34 -05:00
Mike Bayer d5745e3595 - 1.2.4 2018-02-22 15:57:22 -05:00
Eric Atkin b6e4a16809 Quote cte alias if needed
Fixed bug where CTE expressions would not have their name or alias name
quoted when the given name is case sensitive or otherwise requires quoting.
Pull request courtesy Eric Atkin.

Fixes: #4197
Change-Id: Ib8573e82b9a1ca94b50c7c5d73ee98b79465d689
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/426
2018-02-22 15:06:01 -05:00
mike bayer 5614bffb25 Merge "Ensure mapping has no version_id_generator when checking missing version_id" 2018-02-22 13:41:14 -05:00
Mike Bayer 8ab7c96398 Ensure mapping has no version_id_generator when checking missing version_id
Fixed 1.2 regression in ORM versioning feature where a mapping against a
:func:`.select` or :func:`.alias` that also used a versioning column
against the underlying table would fail due to the check added as part of
🎫`3673`.

See also #4194 and #4195 for related issues found regarding
mapped selects and versioning.

Change-Id: Ifabe9a5c8c1bfa72db5029faa7a5dbf71f0a7ca0
Fixes: #4193
2018-02-22 11:36:34 -05:00
mike bayer 14eae5108d Merge "Default to using current mapped class as owner if none found" 2018-02-20 17:52:11 -05:00
Mike Bayer 66a246bd31 Default to using current mapped class as owner if none found
Repaired regression caused in 1.2.3 and 1.1.16 regarding association proxy
objects, revising the approach to 🎫`4185` when calculating the
"owning class" of an association proxy to default to choosing the current
class if the proxy object is not directly associated with a mapped class,
such as a mixin.

Change-Id: I87d0ac09f695dc285bd4bbe0a547f1d5ce23e068
Fixes: #4185
2018-02-20 16:41:48 -05:00
mike bayer 191dd0055c Merge "Implement remove() for _empty_collection" 2018-02-19 18:19:01 -05:00
Mike Bayer 5cb5b8b5f7 Rewrite the "deleting from collections" section
This section documents an aspect of the ORM that is
more generalized than just collections as well as more general
than just using session.delete(), even though session.delete()
with collections is the most common use case.   Try to expand
out the scope here to explain the situation from the perspective
of any kind of relationship, include example with delete cascade
with many-to-one as well.

Change-Id: Ifacb91f90951d1b0da6dbadc2d72273d79b756e2
Fixes: #4191
2018-02-19 18:13:24 -05:00
Mike Bayer 1393eac44c Implement remove() for _empty_collection
Fixed regression caused in 1.2.3 due to fix from 🎫`4181` where
the changes to the event system involving :class:`.Engine` and
:class:`.OptionEngine` did not accommodate for event removals, which
would raise an ``AttributeError`` when invoked at the class
level.

Change-Id: I1c9083829d74dd710716d28b0eaca4fa15e86313
Fixes: #4190
2018-02-19 17:01:43 -05:00
Mike Bayer 20aee85b44 Version 1.2.4 placeholder 2018-02-16 18:22:07 -05:00
Mike Bayer 0b11ce6656 - 1.2.3 2018-02-16 18:15:47 -05:00
Mike Bayer c94e4d888a Remove erroneous skip message
The logic here seems to try to say something different when
__backend__ is True but it produces a nonsensical message,
since __only_on__ doesn't tell us about the implementation
we are actually running.

Change-Id: I14e20cadcba975f8efe8fdefa439c8b8c480b3ed
2018-02-16 18:13:30 -05:00
Mike Bayer 0cdd822207 - add missing forwards ports for bug fixes
Change-Id: If94964cb0294f7f082759ecce71771c35ea4a2bd
2018-02-16 17:52:23 -05:00
Mike Bayer 8c8ec85aa4 cherry-pick changelog update for 1.1.17 2018-02-16 17:36:46 -05:00
Mike Bayer 3fa86f6f68 cherry-pick changelog from 1.1.16 2018-02-16 17:36:45 -05:00
Mike Bayer b0d37c8861 fix formatting
Change-Id: Ie4687c970508cf8bf183e342db6b89a8aca9d6f9
(cherry picked from commit 055821630b)
2018-02-16 16:55:13 -05:00
mike bayer 4bd1cf888c Merge "Test attributes for being non-mapped column properties more closely" 2018-02-16 09:39:26 -05:00
Mike Bayer 283a969d68 Test attributes for being non-mapped column properties more closely
Fixed bug in concrete inheritance mapping where user-defined
attributes such as hybrid properties that mirror the names
of mapped attributes from sibling classes would be overwritten by
the mapper as non-accessible at the instance level.  Also
ensured that user-bound descriptors are not implicitly invoked at the class
level during the mapper configuration stage.

Change-Id: I52b84a15c296b14efeaffb72941fc941d1d52c0d
Fixes: #4188
2018-02-15 17:59:15 -05:00
André Cruz 2f03ec08b5 Add ssl "operation timed out" message for psycopg2
Added "SSL SYSCALL error: Operation timed out" to the list
of messages that trigger a "disconnect" scenario for the
psycopg2 driver.  Pull request courtesy André Cruz.

Change-Id: Ie1a8fc97e74b6906ccacf53dad70fed973c42b7f
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/3
2018-02-15 12:46:02 -05:00
Mike Bayer 6c6a7720f2 Merge remote-tracking branch 'origin/pr/416' 2018-02-14 11:03:37 -05:00
Anton Vlasenko 31d28179c2 Fix typo in python example 2018-02-14 11:31:36 +01:00
Mike Bayer 15ea759813 Allow multiple plugin names
The :class:`.URL` object now allows query keys to be specified multiple
times where their values will be joined into a list.  This is to support
the plugins feature documented at :class:`.CreateEnginePlugin` which
documents that "plugin" can be passed multiple times. Additionally, the
plugin names can be passed to :func:`.create_engine` outside of the URL
using the new :paramref:`.create_engine.plugins` parameter.

Change-Id: Ifc48ad120bd6c6204eda567492caf79832aeeaa5
Fixes: #4170
2018-02-13 15:28:11 -05:00
mike bayer 030915208b Merge "Add dependency for parent_pre post updates to parent deletes" 2018-02-12 22:22:44 -05:00
Mike Bayer 8607ae51fc Add dependency for parent_pre post updates to parent deletes
Fixed issue in post_update feature where an UPDATE is emitted
when the parent object has been deleted but the dependent object
is not.   This issue has existed for a long time however
since 1.2 now asserts rows matched for post_update, this
was raising an error.

Change-Id: I31b1d22408e358962577435f0c4cb9a456ba0872
Fixes: #4187
2018-02-12 16:45:39 -05:00
Mike Bayer 650b9eddae Search through mapper superclass hierarchy for owner
Fixed regression caused by fix for issue 🎫`4116` affecting versions
1.2.2 as well as 1.1.15, which had the effect of mis-calculation of the
"owning class" of an :class:`.AssociationProxy` as the ``NoneType`` class
in some declarative mixin/inheritance situations as well as if the
association proxy were accessed off of an un-mapped class.  The "figure out
the owner" logic has been replaced by an in-depth routine that searches
through the complete mapper hierarchy assigned to the class or subclass to
determine the correct (we hope) match; will not assign the owner if no
match is found.  An exception is now raised if the proxy is used
against an un-mapped instance.

Change-Id: I611b590df2babe077ce6c19bea89e84251d1a7f4
Fixes: #4185
2018-02-09 16:30:42 -05:00
mike bayer 9ef891e82c Merge "Add initiator argument to set_attribute" 2018-02-09 08:41:33 -05:00
Mike Bayer c3ec789ecd Add initiator argument to set_attribute
Added new argument :paramref:`.attributes.set_attribute.inititator`
to the :func:`.attributes.set_attribute` function, allowing an
event token received from a listener function to be propagated
to subsequent set events.

Change-Id: I6ede21e42153026ab46a1d2ec33aa3f999db98e2
2018-02-08 17:40:39 -05:00
Mike Bayer 1e6b9b04de Ensure weakref finalize_fairy operates upon the current connection
Fixed a fairly serious connection pool bug where a connection that is
acquired after being refreshed as a result of a user-defined
:class:`.DisconnectionError` or due to the 1.2-released "pre_ping" feature
would not be correctly reset if the connection were returned to the pool by
weakref cleanup (e.g. the front-facing object is garbage collected); the
weakref would still refer to the previously invalidated DBAPI connection
which would have the reset operation erroneously called upon it instead.
This would lead to stack traces in the logs and a connection being checked
into the pool without being reset, which can cause locking issues.

Change-Id: Iabd9f3a63a1d0207d0de0054a6ced3560818cf9c
Fixes: #4184
2018-02-08 17:40:09 -05:00
Mike Bayer cf64e2574c - re-disable oracle tests here as we are getting lots
of oracle timeouts on CI now

Change-Id: I021d304d6aaf6bfa223dd0e5bb6b0c20e9c8657f
2018-02-08 17:39:19 -05:00
Mike Bayer ea3fd42495 - fix formatting
Change-Id: Ic919048462520de8de84174a5e366d6c85316e87
2018-02-08 16:46:56 -05:00
Jon Snyder a54b3bb0a8 Add values_callable feature to Enum
Added support for :class:`.Enum` to persist the values of the enumeration,
rather than the keys, when using a Python pep-435 style enumerated object.
The user supplies a callable function that will return the string values to
be persisted.  This allows enumerations against non-string values to be
value-persistable as well.  Pull request courtesy Jon Snyder.

Pull-request: https://github.com/zzzeek/sqlalchemy/pull/410
Fixes: #3906
Change-Id: Id385465d215d1e5baaad68368b168afdd846b82c
2018-02-07 21:22:27 -05:00
mike bayer ba957f84d3 Merge "Add flag for class-level disallow of events, apply to OptionEngine" 2018-02-07 20:58:47 -05:00
Mike Bayer 4065352c7e Add flag for class-level disallow of events, apply to OptionEngine
Fixed bug where events associated with an :class:`Engine`
at the class level would be doubled when the
:meth:`.Engine.execution_options` method were used.  To
achieve this, the semi-private class :class:`.OptionEngine`
no longer accepts events directly at the class level
and will raise an error; the class only propagates class-level
events from its parent :class:`.Engine`.   Instance-level
events continue to work as before.

The comments present another way of doing this where we would
copy events from the parent engine at option time rather
than linking the event listeners, but this would be a behavioral
change that adding new events to the parent engine would not
take effect for an already-created OptionEngine.

Change-Id: Id128516f54103fbad9a2210d6571eceb59c8b0cb
Fixes: #4181
2018-02-07 20:55:09 -05:00
mike bayer 9f657fee5b Merge "Check cx_Oracle error code on all exception classes" 2018-02-07 20:54:10 -05:00
Mike Bayer 2bc7dfebe6 Check cx_Oracle error code on all exception classes
Fixed bug in cx_Oracle disconnect detection, used by pre_ping and other
features, where an error could be raised as DatabaseError which includes a
numeric error code; previously we weren't checking in this case for a
disconnect code.

Change-Id: I359bb5ede25a4726ea632b81af83c6391f405ae1
Fixes: #4182
2018-02-06 19:38:59 -05:00
mike bayer b566fa8770 Merge "Support foreign key option reflection for Oracle" 2018-02-06 15:53:59 -05:00
mike bayer 9acd76b571 Merge "fix handling of native enum aliases in sqlalchemy enum columns" 2018-02-06 15:51:03 -05:00
Miroslav Shubernetskiy d53533fbd1 Support foreign key option reflection for Oracle
The ON DELETE options for foreign keys are now part of
Oracle reflection.  Oracle does not support ON UPDATE
cascades.  Pull request courtesy Miroslav Shubernetskiy.

Change-Id: I135cd6cd3436354a86b2c1e1437c3785c38eed26
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/418
2018-02-05 11:14:19 -05:00
Daniel Knell 2826484206 fix handling of native enum aliases in sqlalchemy enum columns
Fixed bug where the :class:`.Enum` type wouldn't handle
enum "aliases" correctly, when more than one key refers to the
same value.  Pull request courtesy Daniel Knell.

Fixes: #4180
Change-Id: Ia716c00ca6c67aeab56965f0fdd575ecb7c71416
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/420
2018-02-05 09:27:27 -05:00
Mike Bayer 00570a6ac9 Convert dialect modules to relative imports and test
For some reason the dialects were not consistently
converted to relative imports.  Also added a test to
ensure that __all__ is functioning within each dialect.

Change-Id: I8450ed724473be7e17678e9aba7ba0f661fdf134
2018-02-05 09:03:08 -05:00
Mike Bayer 56ff3c5270 - ensure it's clear that all DDLEvents can be associated
using propagate=True, which is consulted within the scope
of Table.tometadata().  Fixes: #4179

Change-Id: I0cb0d8f6a894bb645cfc94b3d9083339039c9193
2018-02-02 15:47:42 -05:00
Mike Bayer a721e7083f Look for __sa_reconstructor__ on original_init
Fixed bug where the :func:`.orm.reconstructor` event
helper would not be recognized if it were applied to the
``__init__()`` method of the mapped class.

It's not clear when this bug appeared, but was likely
during a refactoring of instrumentation mechanics somewhere
between 0.8 and 1.0.

Change-Id: Iaeb3baffef9e1b40a336d44294e68479f5d65fd3
Fixes: #4178
2018-02-02 09:36:25 -05:00
Mike Bayer 399988aaed - don't scare off developers with the word "advanced" here
Change-Id: I72a0295634e228bacf6c92088e650183f91e4585
2018-01-31 09:27:49 -05:00
mike bayer 0fa789c1f9 Merge "Disable set eq test for python < 2.7.8" 2018-01-30 17:29:55 -05:00
Mike Bayer 3d60b4158e Disable set eq test for python < 2.7.8
A test added in 1.2 thought to confirm a Python 2.7 behavior turns out to
be confirming the behavior only as of Python 2.7.8. Python bug #8743 still
impacts set comparison in Python 2.7.7 and earlier, so the test in question
involving AssociationSet no longer runs for these older Python 2.7
versions.

Change-Id: I4e5ab650fdcbfd215535c58438878e98ef924a9b
Fixes: #3265
2018-01-30 15:52:43 -05:00
Mike Bayer 606eefa5c6 Ensure _BundleEntity provides .mapper
Fixed bug where the :class:`.Bundle` object did not
correctly report upon the primary :class:`.Mapper` object
represened by the bundle, if any.   An immediate
side effect of this issue was that the new selectinload
loader strategy wouldn't work with the horizontal sharding
extension.

Change-Id: I54a626100b2f4da497597e8944fa8dd853de47a3
Fixes: #4175
2018-01-29 21:24:04 -05:00
robin 5fac520b2a Raise the sqlite3 import error, not the pysqlite2 one
Fixed the import error raised when a platform
has neither pysqlite2 nor sqlite3 installed, such
that the sqlite3-related import error is raised,
not the pysqlite2 one which is not the actual
failure mode.  Pull request courtesy Robin.

Origin version only print `No module named pysqlite2` even
it's actually the import error of line 337: `from
sqlite3 import dbapi2 as sqlite` which point user
to the wrong debug direction.

It should raise `e.message` as `No module named _sqlite3`.

Change-Id: Idc39cd0d226957fd670859df23a2386dea6eb3cc
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/417
2018-01-27 13:06:15 -05:00
Mike Bayer 1d435b9f49 Add a new FAQ section explaining how to ensure parenthesis
with op().

Not sure if this can be further improved at some point, such
as if a BinaryExpression automatically applied self_group()
when op() is called, however for the moment op() behaves consistently
as with all other operators without any ad-hoc effects.

Change-Id: Ia7f1ab43990450bd96757848b77a35e8fedeab63
References: #4174
2018-01-25 16:11:29 -05:00
Mike Bayer bc9cdd5de0 Further refine map_column verbiage
The verbiage here continues to be misleading as it implies that
a MapperProperty already exists for the Column when this is not
the case.

Change-Id: Iaa6990dc9693d47d50b15c4815c3c7f6f34d8577
2018-01-25 09:17:41 -05:00
Mike Bayer 9b08318077 Version 1.2.3 placeholder
Change-Id: Ic957e27114d3c22b7413255c188cea0b2ebc35a6
2018-01-24 21:30:47 -05:00
Mike Bayer 0db496e2b8 - 1.2.2 2018-01-24 21:24:36 -05:00
Mike Bayer 4e2d825c63 Ensure backrefs accommodate for op_bulk_replace
Fixed 1.2 regression regarding new bulk_replace event
where a backref would fail to remove an object from the
previous owner when a bulk-assignment assigned the
object to a new owner.

As this revisits the Event tokens associated with
AttributeImpl objects, remove the verbosity of the
"inline lazy init" pattern; the Event token is a simple
slotted object and should have minimal memory overhead.

Change-Id: Id188b4026fc2f3500186548008f4db8cdf7afecc
Fixes: #4171
2018-01-24 20:55:13 -05:00
mike bayer d41e73c79c Merge "Adjust tests for pyodbc 4.0.22" 2018-01-24 18:57:12 -05:00
Mike Bayer 907c3dc195 Adjust tests for pyodbc 4.0.22
pyodbc 4.0.22 is no longer allowing a datetime to be truncated
into a date, and additionally is asserting that numeric truncation
is not occurring; previously, it looks like we could send a
decimal of -1E-25 through the driver but we were only getting
back -1E-20, the test failed to check this.  Not clear if the
larger precision worked fully at some point, but in any case,
it doesn't work now so just remove those values from the test.

Change-Id: I66c7863b1708eb72f48173083b4ef78c93893b52
2018-01-24 18:07:35 -05:00
Mike Bayer 8250a4248f Rework synonym, synonym_for documentation
The map_column example was incorrect, and overall the purpose
of this parameter as well as that of synonym_for was not explained;
examples added along with more encouragement to use hybrids.

Change-Id: I20bd286f541f798daa81fa598c0f31db1f5aa6ed
2018-01-24 18:03:04 -05:00
mike bayer 6ddabc0f0f Merge "Add a few more MySQL 8.0 reserved words" 2018-01-19 12:05:44 -05:00
Riccardo Magliocchetti e46883e27e Add a few more MySQL 8.0 reserved words
Reference: https://dev.mysql.com/doc/refman/8.0/en/keywords.html

Change-Id: I3f2f1827b659559cbee0f2b8aa3573ddfd551289
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/414
2018-01-19 12:05:00 -05:00
mike bayer a05a6d06fa Merge "Normalize check constraints even more radically" 2018-01-17 18:09:00 -05:00
Florian Apolloner afb121b0af Normalize check constraints even more radically
This is the only way I could get this test pass on informix, basically I strip every whitespace.
The sql text as recorded in informix is:
```
((a > 1 ) AND (a < 5 ) )
((a = 1 ) OR ((a > 2 ) AND (a <5 ) ) )
```
Yes, this is absolutely bonkers, but that is what I get :(

Change-Id: I936e860f2b75b521e5560c05c452dbe72f0d3812
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/413
2018-01-17 16:38:50 -05:00
mike bayer e30d7e7f6c Merge "Use NCHAR + setinputsizes() for all NVARCHAR2" 2018-01-17 16:36:36 -05:00
Mike Bayer ff4898fd42 Use NCHAR + setinputsizes() for all NVARCHAR2
The cx_Oracle dialect now calls setinputsizes() with cx_Oracle.NCHAR
unconditionally when the NVARCHAR2 datatype, in SQLAlchemy corresponding
to sqltypes.Unicode(), is in use.  Per cx_Oracle's author this allows
the correct conversions to occur within the Oracle client regardless
of the setting for NLS_NCHAR_CHARACTERSET.

Change-Id: I3989b7aaf2178c263015a7433939196b76baf1e4
Fixes: #4163
2018-01-17 09:29:32 -05:00
Tim Shaffer 9feb900f3e Fixed link to Flask-SQLAlchemy in documentation 2018-01-17 07:04:16 -05:00
Mike Bayer 42cf8ea91d Add 10054 to ODBC / SQL Server disconnect codes
Change-Id: I6e2518232608f47515b96984b4b7a41b8385975a
Fixes: #4164
2018-01-16 13:02:17 -05:00
Mike Bayer 92cabe2d88 Version 1.2.2 placeholder
Change-Id: I216bad829f83062988b0a624ae4bef6716979ef3
2018-01-15 09:50:19 -05:00
Mike Bayer f9fbace89d - 1.2.1 2018-01-15 09:24:24 -05:00
Mike Bayer c3fe4b585b - add missing 2018 update to conf.py
Change-Id: Ie2d4ff9486375867ed6958b82cd2595bae43746d
2018-01-15 09:20:52 -05:00
mike bayer e72cf013cd Merge "Make column-level collation quoting dialect-specific" 2018-01-12 15:50:28 -05:00
Mike Bayer 699272e4dc happy new year
Change-Id: I3ef36bfd0cb0ba62b3123c8cf92370a43156cf8f
2018-01-12 14:23:53 -05:00
mike bayer f0b98d4fe4 Merge "Limit select in loading for correct types" 2018-01-12 13:47:35 -05:00
mike bayer 1c8101b707 Merge "Turn on testing for JSON under Mariadb 10.2.7 and greater" 2018-01-12 13:45:20 -05:00
mike bayer d5641efa10 Merge "ValuesBase.values inconsistency fix" 2018-01-12 13:43:46 -05:00
Mike Bayer 7402987fd2 Make column-level collation quoting dialect-specific
Fixed regression in 1.2 where newly repaired quoting
of collation names in 🎫`3785` breaks SQL Server,
which explicitly does not understand a quoted collation
name.   Whether or not mixed-case collation names are
quoted or not is now deferred down to a dialect-level
decision so that each dialect can prepare these identifiers
directly.

Change-Id: Iaf0a8123d9bf4711219e320896bb28c5d2649304
Fixes: #4154
2018-01-12 13:01:26 -05:00
mike bayer 0d1276157f Merge "Set up of_type variable for legacy loader option deserialize" 2018-01-12 13:00:49 -05:00
Mike Bayer a216625bd0 Limit select in loading for correct types
Fixed bug in new "selectin" relationship loader where the loader could try
to load a non-existent relationship when loading a collection of
polymorphic objects, where only some of the mappers include that
relationship, typically when :meth:`.PropComparator.of_type` is being used.

This generalizes the mapper limiting that was present
in _load_subclass_via_in() to be part of the PostLoad object
itself, and is used by both polymorphic selectin loading and
relationship selectin loading.

Change-Id: I31416550e27bc8374b673860f57d9dcf96abe87d
Fixes: #4156
2018-01-12 12:59:09 -05:00
mike bayer 4aaac3a91c Merge "Re-enable setinputsizes for Oracle TIMESTAMP" 2018-01-12 11:31:02 -05:00
Aubrey Stark-Toller ab2165e6d6 ValuesBase.values inconsistency fix
Fixed bug in :meth:`.Insert.values` where using the "multi-values"
format in combination with :class:`.Column` objects as keys rather
than strings would fail.   Pull request courtesy Aubrey Stark-Toller.

Change-Id: I9d3b40b5950df8f5bfdc8b1d22f9c3afb277f17f
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/412
Fixes: #4162
2018-01-12 11:28:41 -05:00
Mike Bayer fa2f0c93e6 Turn on testing for JSON under Mariadb 10.2.7 and greater
MariaDB adds a JSON alias for the LONGTEXT datatype and
all the same json functions work against it in any case.
What doesn't work is reflection, since it's just an alias,
and also the CAST we were using in one of our tests doesn't seem
to work for JSON which is probably also because it's not
a real datatype.

Change-Id: I44e5503db29ca2f04de8e521527978f34675a5e0
2018-01-12 11:21:28 -05:00
Mike Bayer 4332b970c9 Set up of_type variable for legacy loader option deserialize
Fixed regression where pickle format of a Load / _UnboundLoad object (e.g.
loader options) changed and ``__setstate__()`` was raising an
UnboundLocalError for an object received from the legacy format, even
though an attempt was made to do so.  tests are now added to ensure this
works.

Change-Id: Idccf643e010776817dd32512facdefa263188814
Fixes: #4159
2018-01-10 15:27:33 -05:00
Mike Bayer cdd090b11e Disable the singletonthreadpool test cleanup no gc
This test often fails on CI under load and reveals a small
race condition within SingleonThreadPool's "cleanup" system.
As this pool's "cleanup" system is pretty much never used in
any case since this pool is no longer used for SQLite file
databases, this race should have little impact, especially
since the occasional non-closed connection will get closed
out when it's GC'ed in any case.

Change-Id: I68aefc0f9bbfc708c95af0497844e65366fc8429
2018-01-09 23:35:23 -05:00
Mike Bayer 80a2241ec0 Re-enable setinputsizes for Oracle TIMESTAMP
Fixed regression where the removal of most setinputsizes
rules from cx_Oracle dialect impacted the TIMESTAMP
datatype's ability to retrieve fractional seconds.

Fixes: #4157
Change-Id: Ic53109fd199aea8b9c4da14355e125849b8b198f
2018-01-08 16:14:17 -05:00
Mike Bayer 3316890ffa turn off pytest's latest plugin we didn't ask for, logging
Change-Id: I24d57894c519366febbce268b04474182dfbb0a1
2018-01-05 15:31:10 -05:00
Mike Bayer 127ead7452 Don't try to iterate chopped path if it's None
Fixed regression caused by new lazyload caching scheme in 🎫`3954`
where a query that makes use of loader options with of_type would cause
lazy loads of unrelated paths to fail with a TypeError.

Change-Id: I705ea0ac012bcc3856ca04109454952cb07a2a8b
Fixes: #4153
2018-01-04 16:59:36 -05:00
mike bayer 350671ff86 Merge "Check for object was expunged before restoring after pk switch + rollback" 2018-01-04 16:31:10 -05:00
mike bayer 5a6885bac8 Merge "Add rule to prevent "GROUP BY <expr>" in tests" 2018-01-04 16:29:52 -05:00
mike bayer 2c713b5817 Merge "Remove cx_oracle test rule from requirements" 2018-01-04 16:29:27 -05:00
Mike Bayer 5811276bb7 Check for object was expunged before restoring after pk switch + rollback
Fixed bug where an object that is expunged during a rollback of
a nested or subtransaction which also had its primary key mutated
would not be correctly removed from the session, causing subsequent
issues in using the session.

Change-Id: I57e2888902015d67ee11857e44382818f1d2f8bc
Fixes: #4151
2018-01-04 14:09:32 -05:00
Mike Bayer 43c7c4f347 Add rule to prevent "GROUP BY <expr>" in tests
Added a new exclusion rule group_by_complex_expression
which disables tests that use "GROUP BY <expr>", which seems
to be not viable for at least two third party dialects.

Change-Id: I47284513382ae93f5a3d12c734b3a44643147c99
2018-01-04 10:44:53 -05:00
Mike Bayer 1071c3040c Remove cx_oracle test rule from requirements
Removed an oracle-specific requirements rule from the public
test suite that was interfering with third party dialect
suites.

Change-Id: Iebae510edcb8ef908dcd9be9222888e12caed97d
2018-01-04 10:41:03 -05:00
mike bayer 1ac897bc5e Merge "added missing , (comma) in dialects/oracle/__init__" 2018-01-03 10:41:02 -05:00
Mike Bayer dcf66590d2 Check for the endmost target when chaining contains()
Fixed regression in association proxy due to 🎫`3769`
(allow for chained any() / has()) where contains() against
an association proxy chained in the form
(o2m relationship, associationproxy(m2o relationship, m2o relationship))
would raise an error regarding the re-application of contains()
on the final link of the chain.

Change-Id: Iea51ce84c2c5a332416fff10b1ba0e676cf0bad7
Fixes: #4150
2018-01-02 18:00:11 -05:00
Miroslav Shubernetskiy 1bfe2230e4 added missing , (comma) in dialects/oracle/__init__
Fixed regression in Oracle imports where a missing comma caused
an undefined symbol to be present.  Pull request courtesy
Miroslav Shubernetskiy.

Change-Id: I91e79c810522dedd4f2a4f3bc60d484bc06f24c2
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/411
2018-01-02 16:38:20 -05:00
Mike Bayer 435aaff20e - Add notfound page
Change-Id: Ie62014ff70c2a517e11ac76f8022f87f706020df
2017-12-29 12:06:50 -05:00
Mike Bayer 51f404b448 Version 1.2.1 placeholder
Change-Id: I86523071ec947e368464411de3666cffb11fab6b
2017-12-27 15:10:45 -05:00
Mike Bayer fdece0a0cc - 1.2.0 2017-12-27 11:13:24 -05:00
mike bayer 8759e7d4d6 Merge "Implement an error lookup" 2017-12-27 11:12:41 -05:00
Mike Bayer 064f82986c Implement an error lookup
Add codes to commonly raised error messages and classes
that link back to fixed documentation sections
giving background on these messages.

Change-Id: I78d0660add7026bb662e20305a59283b20616954
2017-12-27 10:33:22 -05:00
Mike Bayer 6498e7a8fd - call this 1.2.0
Change-Id: If8d60e5d44f387eba97fd9bb1dfa85947ce7f42f
2017-12-26 14:18:27 -05:00
Mike Bayer 17e6921016 - move this migration note to the correct section
Change-Id: I321a29b4a7705221e905b2e5ca88bae8d04b7e99
2017-12-26 13:27:39 -05:00
Mike Bayer a88902ed7e - formatting fix
Change-Id: Ie03b9649c7fc1a41bd3072da2506917a1297702a
2017-12-26 13:25:49 -05:00
mike bayer fb964539b8 Merge "Add an identity_token to the identity key" 2017-12-26 13:04:52 -05:00
Mike Bayer c7f698e967 - put error messages into the TOC so they get a sidebar
toc entry

Change-Id: I5cd98e0bf396afd10a431af8a16a7c654f7a5ca7
2017-12-26 12:32:30 -05:00
Mike Bayer 1abc8e5500 Add new errors section
Adding this to master so that it can be published, in
advance of the exception-level site integration feature.

Change-Id: Ia2a61df8e5198b81ef8f5fbac91143767b70c26b
2017-12-22 12:35:30 -05:00
Mike Bayer 50d9f1687a Add an identity_token to the identity key
For the purposes of assisting with sharded setups, add a new
member to the identity key that can be customized.  this allows
sharding across databases where the primary key space is shared.

Change-Id: Iae3909f5d4c501b62c10d0371fbceb01abda51db
Fixes: #4137
2017-12-22 11:36:53 -05:00
mike bayer b60461fb95 Merge "Add TRUNCATE to postgres autocommit regexp" 2017-12-18 12:57:18 -05:00
Jacob Hayes 756d578287 Add TRUNCATE to postgres autocommit regexp
Extends AUTOCOMMIT_REGEXP for the postgres dialect to include `TRUNCATE`.

Change-Id: I315e03674b89bb89aae669b8655481e4d890491e
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/407
2017-12-18 11:33:09 -05:00
Mike Bayer a5d027ab66 Open up all cx_Oracle numeric tests, finish infinity support
Added some additional rules to fully handle ``Decimal('Infinity')``,
``Decimal('-Infinity')`` values with cx_Oracle numerics when using
``asdecimal=True``.

Allow remaining cx_Oracle numeric tests that were waiting
for the refactor to be finished and forgot to get enabled.

Change-Id: I1e2365176e34559c0230c84f800a7cfe0a034ed5
Fixes: #4064
2017-12-17 11:00:55 -05:00
Mike Bayer 19e13cf3d2 Merge remote-tracking branch 'origin/pr/403' 2017-12-15 09:52:23 -05:00
Mike Bayer f1aab6402f Merge remote-tracking branch 'origin/pr/399' 2017-12-15 09:49:43 -05:00
Mike Bayer 31dd4824d3 Fully copy index expressions
Fixed bug where the :meth:`.Table.tometadata` method would not properly
accommodate :class:`.Index` objects that didn't consist of simple
column expressions, such as indexes against a :func:`.text` construct,
indexes that used SQL expressions or :attr:`.func`, etc.   The routine
now copies expressions fully to a new :class:`.Index` object while
substituting all table-bound :class:`.Column` objects for those
of the target table.

Also refined the means by which tometadata() checks if an Index
or UniqueConstraint is generated by a column-level flag, by propagating
an attribute "_column_flag=True" to such indexes/constraints.

Change-Id: I7ef1b8ea42f9933357ae35f241a5ba9838bac35b
Fixes: #4147
2017-12-14 13:58:58 -05:00
mike bayer 04937652f4 Merge "Change visit name for ColumnElement" 2017-12-07 10:21:37 -05:00
mike bayer a51943ad52 Merge "Disable eager loads for exists()" 2017-12-07 10:21:00 -05:00
Mike Bayer 1cbaff643f Disable eager loads for exists()
The :meth:`.Query.exists` method will now disable eager loaders for when
the query is rendered.  Previously, joined-eager load joins would be rendered
unnecessarily as well as subquery eager load queries would be needlessly
generated.   The new behavior matches that of the :meth:`.Query.subquery`
method.

Fixes: #4032
Change-Id: Iacafc76aa9ae0b71928037fa9637e85ad434ee3a
2017-12-06 16:23:44 -05:00
Mike Bayer 5e8396a60e Change visit name for ColumnElement
No SQLA built-in subclasses ColumnElement without specifying
an alternate visit_name, and user defined ColumnElement
subclasses should avoid being treated like ColumnClause,
e.g. where a Table is present.

Fixes: #4142
Change-Id: I15ed09ba8bdebae4cb0c7e5e5df3f59351477577
2017-12-06 16:06:52 -05:00
mike bayer 29c0250d49 Merge "Allow delete where clause to refer multiple tables." 2017-12-06 01:01:07 -05:00
mike bayer d32a9d7ec3 Merge "Propagate attachment events for ARRAY" 2017-12-05 14:50:17 -05:00
inytar d12b37f90e Allow delete where clause to refer multiple tables.
Implemented "DELETE..FROM" syntax for Postgresql, MySQL, MS SQL Server
(as well as within the unsupported Sybase dialect) in a manner similar
to how "UPDATE..FROM" works.  A DELETE statement that refers to more than
one table will switch into "multi-table" mode and render the appropriate
"USING" or multi-table "FROM" clause as understood by the database.
Pull request courtesy Pieter Mulder.

For SQL syntaxes see:

Postgresql: https://www.postgresql.org/docs/current/static/sql-delete.html
MySQL: https://dev.mysql.com/doc/refman/5.7/en/delete.html#multiple-table_syntax
MSSQL: https://docs.microsoft.com/en-us/sql/t-sql/statements/delete-transact-sql
Sybase: http://infocenter.sybase.com/help/index.jsp?topic=/com.sybase.infocenter.dc00801.1510/html/iqrefso/X315721.htm

Co-authored by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: I6dfd57b49e44a095d076dc493cd2360bb5d920d3
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/392
Fixes: #959
2017-12-05 14:26:28 -05:00
Mike Bayer 76b5981b41 Add missing changelog note for #4109
No changelog note was written at all for #4109 despite
this feature being released as of 1.2.0b3 (based on merge
date of 10/10/2017 and 1.2.0b3 release date of 10/13/2017

Change-Id: Ic4bcdaad9450cb86ba0e7cd6a18dee48c21ab592
Fixes: #4109
2017-12-04 17:53:18 -05:00
mike bayer fb62b64201 Merge "Intercept contains_eager() with of_type, set aliased / polymorphic" 2017-12-04 17:37:51 -05:00
Mike Bayer 8ab652c6cb Intercept contains_eager() with of_type, set aliased / polymorphic
Fixed bug in :func:`.contains_eager` query option where making use of a
path that used :meth:`.PropComparator.of_type` to refer to a subclass
across more than one level of joins would also require that the "alias"
argument were provided with the same subtype in order to avoid adding
unwanted FROM clauses to the query; additionally,  using
:func:`.contains_eager` across subclasses that use :func:`.aliased` objects
of subclasses as the :meth:`.PropComparator.of_type` argument will also
render correctly.

Change-Id: Ie1c10924faa45251aab1a076a3ba7ef9fb1bdeee
Fixes: #4130
2017-12-04 17:35:40 -05:00
Mike Bayer 36d0a27770 Propagate attachment events for ARRAY
Fixed regression in :class:`.ARRAY` datatype caused by
🎫`3964`, which is essentially the same
issue as that of 🎫`3832`, where column attachment events
for :class:`.ARRAY` would not be invoked.   This breaks the use case
of using declarative mixins that declare a :class:`.Column` which
makes use of :meth:`.MutableList.as_mutable`.

Change-Id: If8c57615860883837f6cf72661e46180a77778c1
Fixes: #4141
2017-12-04 16:49:02 -05:00
Mike Bayer e6438cf8c3 Allow url.password to be an object
The "password" attribute of the :class:`.url.URL` object can now be
any user-defined or user-subclassed string object that responds to the
Python ``str()`` builtin.   The object passed will be maintained as the
datamember :attr:`.url.URL.password_original` and will be consulted
when the :attr:`.url.URL.password` attribute is read to produce the
string value.

Change-Id: I91d101c3b10e135ae7e4de60a5104b51776db84f
Fixes: #4089
2017-12-04 11:56:46 -05:00
Mike Bayer e447582b85 Fix regexp for expanding IN
Fixed bug in new "expanding bind parameter" feature whereby if multiple
params were used in one statement, the regular expression would not
match the parameter name correctly.

Change-Id: Ifaf7d627aac4ead2a13c8dddccb5c515253d88e6
Fixes: #4140
2017-12-01 16:32:27 -05:00
Mike Bayer 5da41e46d3 Merge remote-tracking branch 'origin/pr/401' 2017-12-01 12:51:26 -05:00
Martijn Pieters e80a5adfd4 Allow for the database to produce a UUID instance
Some database adapters (specifically, pg8000) already produce a uuid.UUID()
instance for UUID columns. Account for this.
2017-11-22 10:05:44 +00:00
mike bayer bb21dea84c Merge "add nullsfirst() / nullslast() to top-level imports" 2017-11-17 10:32:29 -05:00
mike bayer 436beea3a9 Merge "Add postgresql.MONEY" 2017-11-16 10:27:59 -05:00
Lele Gaifax d507ea00a9 add nullsfirst() / nullslast() to top-level imports
Change-Id: Ieefcc4c30c1c17f43f2908d961e00815bae862bb
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/378
2017-11-16 09:33:00 -05:00
Cleber J Santos da8ff6a7d8 Add postgresql.MONEY
Change-Id: I2b40faf583a84bc5b416e1ad3aa812896ea67a8c
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/395
2017-11-16 09:27:58 -05:00
Jeff Widman bcbff960a1 Add license to Wheel metadata
https://wheel.readthedocs.io/en/stable/index.html#including-the-license-in-the-generated-wheel-file

Change-Id: Icf91b96ba534c8f835ad287e7840ac2a9d2ac502
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/397
2017-11-15 18:10:25 -05:00
Randy Barlow 096bace0da Fix a typo in basic_relationships.rst.
Signed-off-by: Randy Barlow <randy@electronsweatshop.com>
2017-11-15 12:53:12 -05:00
mike bayer 63ea6ef4fb Merge "Add baked.Result.with_post_criteria method" 2017-11-13 14:46:43 -05:00
Mike Bayer 4f054550b7 Propagate kwargs for mysql concat, match
Fixed bug where the MySQL "concat" and "match" operators failed to
propagate kwargs to the left and right expressions, causing compiler
options such as "literal_binds" to fail.

Also adds non-interpreted **kw for visit_create_index, visit_typeclause

Change-Id: Iaf54ac18949cc6a54f50678125f010b4f12c5673
Fixes: #4136
2017-11-13 09:23:14 -05:00
Mike Bayer 3937fc7dfc Add baked.Result.with_post_criteria method
Added new method :meth:`.baked.Result.with_post_criteria` to baked
query system, allowing non-SQL-modifying transformations to take place
after the query has been pulled from the cache.  Among other things,
this method can be used with :class:`.horizontal_shard.ShardedQuery`
to set the shard identifier.   :class:`.horizontal_shard.ShardedQuery`
has also been modified such that its :meth:`.ShardedQuery.get` method
interacts correctly with that of :class:`.baked.Result`.

Change-Id: I04630c683240abbb4b99f0510a1a3dcb564815b4
Fixes: #4135
2017-11-12 18:44:41 -05:00
Mike Bayer 6448903b52 - fix loop logic that was leaving out 10K items from
example suites, fixes #4132

Change-Id: Icf07f33fc99a880d6165d300579ef5d2c366f6f5
2017-11-09 11:38:22 -05:00
Jacob Hayes e6b290df27 Fix import in Inspector.reflecttable doc 2017-11-08 22:14:37 -06:00
Mike Bayer 3c75a46be4 - add new FAQ section re: MySQL failure modes
Change-Id: I458dcf6290464c8bf140a376e9a8d2ee10937c08
2017-11-03 17:50:54 -04:00
Mike Bayer ca7d3b5a5b Version 1.1.16 placeholder
Change-Id: Ia563c801f5f467084c49fc367f31b2385e0777bb
(cherry picked from commit 0274d80f83)
2017-11-03 17:07:06 -04:00
Mike Bayer 4959f5da49 - 1.1.15
(cherry picked from commit 0b33a8c48f)

Change-Id: I1093dbb02844f6bea50639c0dd60d71de5c2d86f
2017-11-03 17:06:59 -04:00
Mike Bayer 75bdcd096f Fix as many RST parse warnings as possible.
Still a few I can't get.   Also 0.9 is EOL so hide the
unreleased notes.

Change-Id: If0e44d4a0b3e78e211f32d5c33b51b1a007c9c69
2017-11-03 14:45:18 -04:00
Mike Bayer 152522b3f2 Add doc note for contains_eager() w/ subclasses.
Change-Id: I9634136e1855a081c25b04bb6ae8248f0f94be1c
Fixes: #4130
2017-11-02 13:53:34 -04:00
Mike Bayer 5d1a718214 - cross-link of_type() correctly
Change-Id: Iaacab5d2fe45b0b87fea922ec914e258dba9e30d
2017-11-02 13:40:43 -04:00
Nicolas CANIART 5acc9b149a Accommodate tuples for ColumnDefault.__repr__
Fixed bug where ``__repr__`` of :class:`.ColumnDefault` would fail
if the argument were a tuple.  Pull request courtesy Nicolas Caniart.

Change-Id: I08aa2448ef91054c43d6068ac54cedbdf7a83d64
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/1
Fixes: #4126
2017-10-31 11:38:07 -04:00
Mike Bayer 8965f30215 - add notes that @comparator and @expression don't go together.
Change-Id: I3fb366f8b49454453e4b6dada565c24c5ccb975e
2017-10-30 20:02:21 -04:00
Mike Bayer fd4289c582 Filter attributes we don't map during a load_scalar_attributes
Fixed bug where a descriptor that is elsewhere a mapped column
or relationship within a hierarchy based on :class:`.AbstractConcreteBase`
would be referred towards during a refresh operation, causing an error
as the attribute is not mapped as a mapper property.
A similar issue can arise for other attributes like the "type" column
added by :class:`.AbstractConcreteBase` if the class fails to include
"concrete=True" in its mapper, however the check here should also
prevent that scenario from causing a problem.

Change-Id: I407b07a3a3e2c374da19fc86ed44b987d595dcfa
Fixes: #4124
2017-10-28 13:29:48 -04:00
mike bayer f7b957b589 Merge "Rework autoescape to be a simple boolean; escape the escape character" 2017-10-26 16:25:25 -04:00
Mike Bayer bda06f76c0 - fix formatting
Change-Id: I4085424656d8e7078dc46378129de6506c4141b2
2017-10-26 16:24:57 -04:00
mike bayer 139f31dc17 Merge "Test for EXCLUDE constraint duplicated index" 2017-10-25 20:05:34 -04:00
Mike Bayer 8d318dee6c Test for EXCLUDE constraint duplicated index
An EXCLUDE constraint makes an index just like a UNIQUE does;
get_indexes() will receive this.  Test that this works out the
same way as it does for a UNIQUE.

Change-Id: I02ac7cbbb1ca0d1fcdcdbe9a8b8bd1ffee3e496c
Fixes: #4122
2017-10-25 15:02:46 -04:00
Ben Shen cd3db26cc9 Fix / consolidate for SQL Server BINARY, VARBINARY
Fixed bug where sqltypes.BINARY and sqltypes.VARBINARY datatypes
would not include correct bound-value handlers for pyodbc,
which allows the pyodbc.NullParam value to be passed that
helps with FreeTDS.

Co-authored by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: I6e3c16a69465b4fbc7b17a1927fb5e66acee93cb
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/386
Fixes: #4121
2017-10-25 10:50:54 -04:00
Mike Bayer 654ca5463d Rework autoescape to be a simple boolean; escape the escape character
Reworked the new "autoescape" feature introduced in
:ref:`change_2694` in 1.2.0b2 to be fully automatic; the escape
character now defaults to a forwards slash ``"/"`` and
is applied to percent, underscore, as well as the escape
character itself, for fully automatic escaping.  The
character can also be changed using the "escape" parameter.

Change-Id: I74894a2576983c0f6eb89480c9e5727f49fa9c25
Fixes: #2694
2017-10-24 23:11:13 -04:00
Mike Bayer f34b180ca9 Modernize SQL server binary tests
In preparation for I6e3c16a69465b4fbc7b17a1927fb5e66acee93cb
let's first use simplified binary test fixtures.

Change-Id: Ie0ac3ad194a64019bfcea0e5001cc8bdcf8a05e5
2017-10-24 12:40:25 -04:00
Mike Bayer 73f2527486 Merge remote-tracking branch 'origin/pr/396' 2017-10-24 10:40:05 -04:00
Mike Bayer 9e5395c3da Merge remote-tracking branch 'origin/pr/394' 2017-10-24 10:39:54 -04:00
Mike Bayer 0236ab5694 Merge remote-tracking branch 'origin/pr/359' 2017-10-24 10:39:43 -04:00
Mike Bayer 9018be2dfd Merge remote-tracking branch 'origin/pr/393' 2017-10-24 10:39:35 -04:00
Yoichi NAKAYAMA 2f46856f95 Remove extra backslash 2017-10-24 16:09:45 +09:00
Yoichi NAKAYAMA 521951b55d Fix typo in "on duplicate key update" example 2017-10-24 16:00:21 +09:00
mike bayer da4b0a41e1 Merge "Resolve AliasedClass when determining owning class of association proxy" 2017-10-23 20:56:06 -04:00
mike bayer 7482ba0b3c Merge "Remove deprecation warnings mysql5 7 20" 2017-10-23 20:35:35 -04:00
Mike Bayer 1c025e9795 Add changelog for ticket #4097
A changelog was not added for #4097 even though this issue
was ticketed and backported to 1.1.

Change-Id: I1aeb5cb344c95ad86daa166e68eca7073eca0b87
Fixes: #4097
2017-10-23 18:58:37 -04:00
Mike Bayer 9a3b86908a Revert 860640fb8d
Revert 860640fb8d as this breaking change
was not actually released under 1.1

Change-Id: Ia1bfbebc5c34cd003de8657fedfccb6a41fc53fe
2017-10-23 18:48:00 -04:00
Mike Bayer 860640fb8d Issue #4115 will be backported to 1.1, move changelog file
Change-Id: Ib5039ad9cbdf036ab78b74266847fd67cdcfbfc3
2017-10-23 18:39:47 -04:00
Daniel Thorell 41cfe44b5e Remove deprecation warnings mysql5 7 20
MySQL 5.7.20 now warns for use of the @tx_isolation variable; a version
check is now performed and uses @transaction_isolation instead
to prevent this warning.

Co-authored by: Mike Bayer <mike_mp@zzzcomputing.com>
Fixes: #4120
Change-Id: I4d2e04df760c5351a71dde8b32145cdc69fa6115
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/391
2017-10-23 18:29:23 -04:00
Jeff Widman 16c237d3d1 Fix typo: srtategies --> strategies 2017-10-20 15:33:36 -07:00
Jeff Widman 975081a3a8 Fix typo: multidimentional --> multidimensional 2017-10-20 15:24:15 -07:00
Mike Bayer 57f7788ec2 Get MariaDB normalized version relative to "MariaDB" token
Fixed regression from 1.2.0b3 where "MariaDB" version comparison can
fail for some particular MariaDB version strings under Python 3.

Change-Id: Iedf49f40c1614ccedf63e0fa26719dd704da104d
Fixes: #4115
2017-10-20 16:08:47 -04:00
Mike Bayer f14a58dea4 Resolve AliasedClass when determining owning class of association proxy
Fixed bug where the association proxy would inadvertently link itself
to an :class:`.AliasedClass` object if it were called first with
the :class:`.AliasedClass` as a parent, causing errors upon subsequent
usage.

Change-Id: I9161bab67766bb75d73ca54d712ad1cad6de40dc
Fixes: #4116
2017-10-20 14:35:09 -04:00
Mike Bayer 55b511c396 Merge branch 'patch-1' of https://github.com/pletnes/sqlalchemy 2017-10-20 12:04:55 -04:00
mike bayer 62b3e73b25 Merge "Don't commit failed transaction" 2017-10-20 11:40:18 -04:00
Mike Bayer 1210f49bb5 Don't commit failed transaction
The test here commits even though integrityerror
was raised due to the fixture.  Postgresql seems to allow
this even though it's usually strict about this.  remove
the requirement that a database needs to be able to
commit after an integrity error was raised.

Change-Id: I437faadb04ff7a9c3f624c68646b4f4f504b504a
2017-10-18 21:17:00 -04:00
Jan 1de1623590 add order_by clause to make tests stable
I observed test runs that failed on 'test_bound_in_scalar' due to arbitrary ordering of the result set. The assertion not only tests for the elements to be present, but also for the correct ordering. Hence, the proposal to add an order_by clause to the select statements.

Change-Id: If1fbb864761e77dfd2a42ef857801c8aaf893bee
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/389
2017-10-17 21:23:19 -04:00
Paul Anton Letnes b343dc5611 Add missing space in repr of the sessionmaker class
The missing space was driving me nuts.
2017-10-16 12:32:38 +02:00
Mike Bayer 1fbed902ed Version 1.2.0b4 placeholder
Change-Id: I6f0a29360d70851398532e957722ae2a76b76f38
2017-10-13 13:58:46 -04:00
Mike Bayer 9cf6ac32d6 - 1.2.0b3 2017-10-13 13:16:59 -04:00
mike bayer 2942ecb230 Merge "Disallow all ambiguous boolean values for Boolean" 2017-10-12 14:41:37 -04:00
Mike Bayer c63658973c Disallow all ambiguous boolean values for Boolean
In release 1.1, the :class:`.Boolean` type was broken in that
boolean coercion via ``bool()`` would occur for backends that did not
feature "native boolean", but would not occur for native boolean backends,
meaning the string ``"0"`` now behaved inconsistently. After a poll, a
consensus was reached that non-boolean values should be raising an error,
especially in the ambiguous case of string ``"0"``; so the :class:`.Boolean`
datatype will now raise ``ValueError`` if an incoming value is not
within the range ``None, True, False, 1, 0``.

Change-Id: If70c4f79c266f0dd1a0306c0ffe7acb9c66c4cc3
Fixes: #4102
2017-10-12 13:39:06 -04:00
Mike Bayer 9ffee8c94a - make a note in 1.1 migration notes for ref #4102
Change-Id: If9edba3af476bc4303246e55d0ecb53009084342
2017-10-12 11:15:11 -04:00
Mike Bayer 3306d4d34d - psycopg2's batch mode isn't the multiple values thing,
it's just batching of statements

Change-Id: Ibb2e154d50ff3d9649822c9e4717ca5a3fd49430
2017-10-11 10:28:37 -04:00
Mike Bayer 4fbeec9d61 Add fast execution helper support.
Added a new flag ``use_batch_mode`` to the psycopg2 dialect.  This flag
enables the use of psycopg2's ``psycopg2.extras.execute_batch``
extension when the :class:`.Engine` calls upon ``cursor.executemany()``.
This extension provides a critical performance increase by over an order of magnitude
when running INSERT statements in batch.  The flag is False by default
as it is considered to be experimental for now.

Change-Id: Ib88d28bc792958d47109f644ff1d08c897db4ff7
Fixes: #4109
2017-10-10 13:43:35 -04:00
Mike Bayer 2b2cdee799 - add a note how to generate pg10 IDENTITY for now
Change-Id: I22dbf6ba322904a80c6df46f6a31daa2fcc1f946
2017-10-09 11:12:34 -04:00
mike bayer 1230016bf0 Merge "Don't include SelectBase when searching for surface column elements" 2017-10-08 21:43:09 -04:00
Mike Bayer 4bb8397ae3 Fix array_agg to accommodate ARRAY arguments
Fixed bug in :func:`.array_agg` function where passing an argument
that is already of type :class:`.ARRAY`, such as a Postgresql
:obj:`.postgresql.array` construct, would produce a ``ValueError``, due
to the function attempting to nest the arrays.

Change-Id: Ibe5f6275d90e4868e6ef8a733de05acd44c05d78
Fixes: #4107
2017-10-06 11:29:09 -04:00
Mike Bayer 1281e6e6c4 Don't include SelectBase when searching for surface column elements
Fixed bug where correlated select used against single-table inheritance
entity would fail to render correctly in the outer query, due to adjustment
for single inheritance discriminator criteria inappropriately re-applying
the criteria to the outer query.

Change-Id: I38df21f1392af1843e10119682fa0635d346e2a8
Fixes: #4103
2017-10-05 11:29:11 -04:00
mike bayer 2c28079188 Merge "Add SQL Server TIMESTAMP / ROWVERSION datatypes" 2017-10-04 10:12:39 -04:00
Mike Bayer fadebedff0 Add SQL Server TIMESTAMP / ROWVERSION datatypes
SQL Server has an entirely different use for the TIMESTAMP
datatype that is unrelated to the SQL standard's version of this
type.   It is a read-only type that returns an incrementing
binary value.  The ROWVERSION name will supersede the TIMESTAMP
name.  Implement datatype objects for both, separate from the
base DateTime/TIMESTAMP class hierarchy, and also implement
an optional integer coercion feature.

Change-Id: Ie2bd43b7aac57760b8ec6ff6e26460e2086a95eb
Fixes: #4086
2017-10-04 09:27:31 -04:00
mike bayer e86045694a Merge "Improve check for overlapping FK targets on sibling classes" 2017-10-04 09:21:36 -04:00
Mike Bayer 8ba8dd23b7 Improve check for overlapping FK targets on sibling classes
Fixed bug where ORM relationship would warn against conflicting sync
targets (e.g. two relationships would both write to the same column) for
sibling classes in an inheritance hierarchy, where the two relationships
would never actually conflict during writes.

Change-Id: I9367a7978cadc59066e89fc4917d7eb6c78dedee
Fixes: #4078
2017-10-03 12:58:38 -04:00
Mike Bayer f846a789b7 PG dialect test fixes
Make sure we clear the plugin registry before testing
that the "postgres" name raises.   Also move non-backend
tests out of MiscTest into a new suite.

Change-Id: Icd1bb4745aa07f52d585fcf959f76fcd8bdc7f24
2017-10-02 19:03:40 -04:00
mike bayer b07f883979 Merge "Support pg10" 2017-10-02 14:30:21 -04:00
Mike Bayer 67ee56be69 Support pg10
One test appears to use some awkward calling style
with the current_date function that isn't working in pg10
anymore, this looks like an extremely
old test that can be removed

Change-Id: I5f8aee0f5ed423461be5a9060c812eb0acdc7df5
2017-10-02 12:26:16 -04:00
Mike Bayer 6ff05dae07 use fails_if for check_constraint_reflection
Change-Id: Id66c563027561a4b3baf853093b0b408d032c173
2017-09-29 13:22:07 -04:00
Mike Bayer 29b752f8b2 Support mariadb 10.2
Fixed issue where CURRENT_TIMESTAMP would not reflect correctly
in the MariaDB 10.2 series due to a syntax change, where the function
is now represented as ``current_timestamp()``.

Fixes: #4096

MariaDB 10.2 now supports CHECK constraints (warning: use version 10.2.9
or greater due to upstream issues noted in 🎫`4097`).  Reflection
now takes these CHECK constraints into account when they are present in
the ``SHOW CREATE TABLE`` output.

Fixes: #4098

Change-Id: I8666d61814e8145ca12cbecad94019b44af868e3
2017-09-28 19:22:17 -04:00
Mike Bayer 68b52c48b7 Take schema name into account when querying sqlite_master
Fixed bug where SQLite CHECK constraint reflection would fail
if the referenced table were in a remote schema, e.g. on SQLite a
remote database referred to by ATTACH.

Also add suite support for general CHECK constraint reflection.

Change-Id: I073a72cb47dc4f8c5683000d708768523759332f
Fixes: #4099
2017-09-28 16:51:35 -04:00
Mike Bayer 21ff71b0eb Remove unused .cascading from unit test for __table_cls__ feature
Two independent gerrits for 04bbad660b
and ec1700ba29 produce a failure
when merged due to new warning.
will merge into rel_1_1 as well for completeness even though
warning is not there.

Change-Id: I1bd494d205107d8b2a30d475a22c61a59b70985b
2017-09-28 13:05:56 -04:00
Mike Bayer 21bf37f6e4 Warn for mariadb 10.2 < 9
There's a few CHECK constraint issues we managed
to get resolved as of MariaDB 10.2.8 then 10.2.9.   They
are pretty severe so warn users for these particular mariadb
versions.

Change-Id: Ie0899f94fda25960975ebee72f3044370f43eb7c
Fixes: #4097
2017-09-28 12:34:09 -04:00
mike bayer 4a2760ffd2 Merge "Add full list of pyodbc error codes for MSSQL" 2017-09-28 12:07:19 -04:00
Mike Bayer 1ec7ba52e1 - add more dragons to session.begin() / autocommit docs
Change-Id: I9e326f353d396321565dfbf53b7a30f18d8c86e9
2017-09-28 11:43:48 -04:00
Mike Bayer e1a923dc5a - tweak the handle_error docs a bit
Change-Id: Iebe5b13b3a568f3aa0f3ab02a55e2a9cbb4545c7
2017-09-28 09:59:16 -04:00
Mike Bayer 6a38697261 Add full list of pyodbc error codes for MSSQL
Moved the SQL server error codes out of connnectors/pyodbc.py
and into mssql/pyodbc.py.  Added complete list
of odbc-related disconnect codes.

Change-Id: Icd84a920dbfa1f188847f859654ff6f7a48170f1
Fixes: #4095
2017-09-28 09:39:54 -04:00
mike bayer 0d2d7e3a30 Merge "Support method form of any_(), all_()" 2017-09-27 18:10:04 -04:00
Mike Bayer 944c662d8a Support method form of any_(), all_()
Fixed bug where the recently added :meth:`.ColumnOperators.any_`
and :meth:`.ColumnOperators.all_` methods didn't work when called
as methods, as opposed to using the standalone functions
:func:`~.expression.any_` and :func:`~.expression.all_`.  Also
added documentation examples for these relatively unintuitive
SQL operators.

Change-Id: I3e56b463e9fd146a077b9970624f50cba27f9811
Fixes: #4093
2017-09-27 15:49:29 -04:00
mike bayer 5b75a623ef Merge "Accomodate for multidimensional array in rewriting for COLLATE" 2017-09-27 15:47:48 -04:00
mike bayer e111852270 Merge "Don't expire "deferred" attributes in make_transient_to_detached" 2017-09-27 15:47:10 -04:00
mike bayer 3d50251e0a Merge "Document and test __table_cls__" 2017-09-27 15:38:29 -04:00
mike bayer 5aa892995a Merge "Warnings for @declared_attr.cascading" 2017-09-27 15:37:18 -04:00
Mike Bayer 6652f72352 Accomodate for multidimensional array in rewriting for COLLATE
Made further fixes to the :class:`.ARRAY` class in conjunction with
COLLATE, as the fix made in 🎫`4006` failed to accommodate
for a multidimentional array.

Change-Id: If3e438f8ce94ebae2196671c88a4914f3b743e60
Fixes: #4006
2017-09-27 09:48:17 -04:00
Mike Bayer dc4d1ee7bd bump 4088 to test ticket autoclose
Issue resolved in 35a1f5481a

Change-Id: Ie1acae3d14467916b479192aebb5860ab31992f1
Fixes: #4088
2017-09-26 18:47:48 -04:00
Mike Bayer 5abb036e9b Don't expire "deferred" attributes in make_transient_to_detached
Fixed issue where the :func:`.make_transient_to_detached` function
would expire all attributes on the target object, including "deferred"
attributes, which has the effect of the attribute being undeferred
for the next refesh, causing an unexpected load of the attribute.

Change-Id: I82a385e3033e3f3c31569b1e908efb5f258d0f27
Fixes: #4084
2017-09-26 15:33:04 -04:00
Mike Bayer ac1c19dee7 Merge branch 'patch-1' of https://github.com/irushchyshyn/sqlalchemy 2017-09-26 11:49:31 -04:00
mike bayer 21af7fc4aa Merge "Make a common approach for "emulated" types" 2017-09-26 11:43:25 -04:00
Mike Bayer 04bbad660b Document and test __table_cls__
A use case has been identified for __table_cls__, which was
added in 1.0 just for the purpose of test fixtures.   Add this to
public API and ensure the target use case (conditional table generation)
stays supported.

Change-Id: I87be5bcb72205cab89871fa586663bf147450995
Fixes: #4082
2017-09-26 11:38:18 -04:00
Mike Bayer ec1700ba29 Warnings for @declared_attr.cascading
A warning is emitted if a subclass attempts to override an attribute
that was declared on a superclass using ``@declared_attr.cascading``
that the overridden attribute will be ignored. This use
case cannot be fully supported down to further subclasses without more
complex development efforts, so for consistency the "cascading" is
honored all the way down regardless of overriding attributes.

A warning is emitted if the ``@declared_attr.cascading`` attribute is
used with a special declarative name such as ``__tablename__``, as this
has no effect.

Ensure that documenation refers to the current inconsistency that
__tablename__ can be overridden by subclasses however
@declared_attr.cascading cannot.

Fixes: #4091
Fixes: #4092
Change-Id: I3aecdb2f99d408e404a1223f5ad86ae3c7fdf036
2017-09-26 11:36:08 -04:00
Iryna Shcherbina 8e002c87b3 Fix noseplugin to accept zeroarg_callback for --dbs option
./sqla_nose.py --dbs  works fine with zero arguments, so `zeroarg_callback` should be treated as `callback`.
2017-09-26 08:32:12 +02:00
mike bayer 1b0b35f254 Merge "Add table / column comments into tometadata()" 2017-09-25 19:32:11 -04:00
Mike Bayer 35a1f5481a Make a common approach for "emulated" types
Internal refinements to the :class:`.Enum`, :class:`.Interval`, and
:class:`.Boolean` types, which now extend a common mixin
:class:`.Emulated` that indicates a type that provides Python-side
emulation of a DB native type, switching out to the DB native type when a
supporting backend is in use.   The Postgresql :class:`.INTERVAL` type
when used directly will now include the correct type coercion rules for
SQL expressions that also take effect for :class:`.sqltypes.Interval`
(such as adding a date to an interval yields a datetime).

Change-Id: Ifb9f9d7cbd9f5990dcb2abb583193e9e92b789ad
Fixes: #4088
2017-09-25 19:30:51 -04:00
Mike Bayer f67b65eea8 Merge branch 'kishkin/fixed-a-typo-in-before_execute-doc-event-1503409727849' of https://bitbucket.org/kishkin/sqlalchemy 2017-09-25 17:24:57 -04:00
Mike Bayer 8e219c5661 Add table / column comments into tometadata()
Fixed bug in new SQL comments feature where table and column comment
would not be copied when using :meth:`.Table.tometadata`.

Change-Id: Ib3112e5e02930245daacb36c8ed38c01fa3e7dbd
Fixes: #4087
2017-09-23 12:08:40 -04:00
mike bayer 08430e689f Merge "Add __next__(), next() to ResultProxy" 2017-09-18 09:49:50 -04:00
Mike Bayer aed2324b4d Add multivalued insert context for defaults
Added a new method :class:`.DefaultExecutionContext.current_parameters`
which is used within a function-based default value generator in
order to retrieve the current parameters being passed to the statement.
The new function differs from the ``.current_parameters`` attribute in
that it also provides for optional grouping of parameters that
correspond to a multi-valued "insert" construct.  Previously it was not
possible to identify the subset of parameters that were relevant to
the function call.

Change-Id: I6894c7b4a2bce3e83c3ade8af0e5b2f8df37b785
Fixes: #4075
2017-09-16 12:52:25 -04:00
Mike Bayer 339416b821 Add __next__(), next() to ResultProxy
Added ``__next__()`` and ``next()`` methods to :class:`.ResultProxy`,
so that the ``next()`` builtin function works on the object directly.
:class:`.ResultProxy` has long had an ``__iter__()`` method which already
allows it to respond to the ``iter()`` builtin.   The implementation
for ``__iter__()`` is unchanged, as performance testing has indicated
that iteration using a ``__next__()`` method with ``StopIteration``
is about 20% slower in both Python 2.7 and 3.6.

Change-Id: I70569a4c48ad85a3c21a7ad422f270a559926cfb
Fixes: #4077
2017-09-15 14:03:27 -04:00
mike bayer d8cddf61f9 Merge "Implement placeholders for CUBE, ROLLUP, GROUPING SETS" 2017-09-14 15:40:22 -04:00
mike bayer d0c46d9ae5 Merge "Ensure (+) is rendered for all right-hand members" 2017-09-13 15:50:42 -04:00
SpitcynandMike Bayer 509d19e6fd Implement placeholders for CUBE, ROLLUP, GROUPING SETS
Fixes: #3429

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: I870ee7dc801d553c5309c291402ec468b671e9a9
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/383
2017-09-13 15:18:37 -04:00
Mike Bayer 01ed5c4009 Ensure (+) is rendered for all right-hand members
Fixed bug where Oracle 8 "non ansi" join mode would not add the
``(+)`` operator to expressions that used an operator other than the
``=`` operator.  The ``(+)`` needs to be on all columns that are part
of the right-hand side.

Change-Id: I952e2369f11b78f5b918456ae3a5b0768d9761ec
Fixes: #4076
2017-09-13 14:53:29 -04:00
Mike Bayer 7051653610 use the stack to get the insert statement in on conflict
Fixed bug in Postgresql :meth:`.postgresql.dml.Insert.on_conflict_do_update`
which would prevent the insert statement from being used as a CTE,
e.g. via :meth:`.Insert.cte`, within another statement.

Change-Id: Ie20972a05e194290bc9d92819750845872949ecc
Fixes: #4074
2017-09-12 12:58:23 -04:00
Mike Bayer 31f80b9eae Refactor for cx_Oracle version 6
Drops support for cx_Oracle prior to version 5.x, reworks
numeric and binary support.

Fixes: #4064

Change-Id: Ib9ae9aba430c15cd2a6eeb4e5e3fd8e97b5fe480
2017-09-11 14:17:10 -04:00
Mike Bayer 4c97ea116c Don't use repr() for Column/ColumnClause in warning
for #4073, use the string version of the column expression
in the warning, otherwise the repr() is showing the hex id
which causes unlimited warnings.

Change-Id: I6869b685b237e7f02c7b5071701dd63a3577182a
2017-09-10 23:08:30 -04:00
Mike Bayer db170dd452 Warn instead of raise for unmapped column that matches on key
Modified the change made to the ORM update/delete evaluator in
🎫`3366` such that if an unmapped column expression is present
in the update or delete, if the evaluator can match its name to the
mapped columns of the target class, a warning is emitted, rather than
raising UnevaluatableError.  This is essentially the pre-1.2 behavior,
and is to allow migration for applications that are currently relying
upon this pattern.  However, if the given attribute name cannot be
matched to the columns of the mapper, the UnevaluatableError is
still raised, which is what was fixed in 🎫`3366`.

Change-Id: I658ed0dbf485b7f8009774f9c12d9912447abd2a
Fixes: #4073
2017-09-10 00:01:18 -04:00
mike bayer ca2c42df6b Merge "Remove LRU warnings" 2017-09-09 10:28:56 -04:00
Mike Bayer e83024d3fa Remove LRU warnings
Removed the warnings that are emitted when the LRU caches employed
by the mapper as well as loader srtategies reach their threshold; the
purpose of this warning was at first a guard against excess cache keys
being generated but became basically a check on the "creating many
engines" antipattern.   While this is still an antipattern, the presense
of test suites which both create an engine per test as well as raise
on all warnings will be an inconvenience; it should not be critical
that such test suites change their architecture just for this warning
(though engine-per-test suite is always better).

Change-Id: I41ef8cd642d05a845f53119b196440f9d7879cd9
Fixes: #4071
2017-09-08 21:42:07 -04:00
Mike Bayer 70be7312f1 Rename MySQL dml.insert().values to .inserted
Changed the name of the ``.values`` attribute of the new MySQL
INSERT..ON DUPLICATE KEY UPDATE construct to ``.inserted``, as
:class:`.Insert` already has a method called :meth:`.Insert.values`.
The ``.inserted`` attribute ultimately renders the MySQL ``VALUES()``
function.

Change-Id: I8da8e30a3077698385a4b77e2c2032e2d1ff10b2
Fixes: #4072
2017-09-08 21:41:13 -04:00
Mike Bayer 5ae984b946 - skip oracle tests until we can merge refactor
Change-Id: Ie9bec6e8f51d52349dcbd8009981818e459e88b8
2017-09-08 21:40:53 -04:00
Mike Bayer 2e137b3954 - add separate oracle / oracle5 jobs so we can CI
on both series for now

Change-Id: Ide8938334c248119c1d5c2e1bf07070f17c86242
2017-09-05 17:20:05 -04:00
Mike Bayer 8a85729dc1 Version 1.1.15 placeholder
Change-Id: I81fd38694b19ee9dadaf89276dd4fe9bd6f67c94
(cherry picked from commit 21ca9b50c7)
2017-09-05 13:06:29 -04:00
Mike Bayer 47d4d87637 - 1.1.14
(cherry picked from commit 4b22b01ade)

Change-Id: I520fbff300ae034166a2f80685e0831ff2d1929e
2017-09-05 13:06:26 -04:00
Mike Bayer 2020486546 - 1.1.14 placeholder
Change-Id: I1648f7780cc0accdfe7650a62754b39c8e5552a8
(cherry picked from commit 2cdb0777c2)
2017-09-05 10:02:27 -04:00
mike bayer e76c012ec7 Merge "Guard against KeyError in session.merge after check for identity" 2017-09-05 09:46:17 -04:00
mike bayer eabdbd1d3c Merge "Check for non-mapped property in synonym" 2017-09-05 09:44:06 -04:00
mike bayer abf1296ed4 Merge "Ensure custom ops have consistent typing behavior, boolean support" 2017-09-04 19:49:23 -04:00
Mike Bayer 1e21f9c4f8 Guard against KeyError in session.merge after check for identity
Fixed bug in :meth:`.Session.merge` following along similar lines as that
of 🎫`4030`, where an internal check for a target object in
the identity map could lead to an error if it were to be garbage collected
immediately before the merge routine actually retrieves the object.

Change-Id: Ifecfb8b9d50c52d0ebd5a03e1bd69fe3abf1dc40
Fixes: #4069
2017-09-04 19:37:34 -04:00
Mike Bayer af8a815348 - add forwards-port versions
Change-Id: I5741f213d0edb989566f45140f5e7e1dd522e194
2017-09-04 19:02:19 -04:00
Mike Bayer 130f31ca79 Check for non-mapped property in synonym
An :class:`.InvalidRequestError` is raised when a :func:`.synonym`
is used against an attribute that is not against a :class:`.MapperProperty`,
such as an association proxy.  Previously, a recursion overflow would
occur trying to locate non-existent attributes.

Change-Id: If2ce38c429a69951df4c94b71b74edbd59d775e3
Fixes: #4067
2017-09-04 18:55:30 -04:00
Mike Bayer 37c5ed2ed9 Always check that discarded state is the expected one
Fixed race condition in ORM identity map which would cause objects
to be inappropriately removed during a load operation, causing
duplicate object identities to occur, particularly under joined eager
loading which involves deduplication of objects.  The issue is specific
to garbage collection of weak references and is observed only under the
Pypy interpreter.

Change-Id: I9f6ae3fe5b078f26146af82b15d16f3a549a9032
Fixes: #4068
2017-09-04 16:22:29 -04:00
Mike Bayer 919b8bc4ac Ensure custom ops have consistent typing behavior, boolean support
Refined the behavior of :meth:`.Operators.op` such that in all cases,
if the :paramref:`.Operators.op.is_comparison` flag is set to True,
the return type of the resulting expression will be
:class:`.Boolean`, and if the flag is False, the return type of the
resulting expression will be the same type as that of the left-hand
expression, which is the typical default behavior of other operators.
Also added a new parameter :paramref:`.Operators.op.return_type` as well
as a helper method :meth:`.Operators.bool_op`.

Change-Id: Ifc8553cd4037d741b84b70a9702cbd530f1a9de0
Fixes: #4063
2017-09-01 12:34:41 -04:00
Mike Bayer 65680b2343 Add InternalError for mysqlclient disconnect
mysqlclient as of 1.3.11 changed the exception
class for a particular disconnect situation from
InterfaceError to InternalError; the disconnection
detection logic now accommodates this.

Change-Id: I294f90f794491fd363548719222d8e3008480615
Fixes: #4065
2017-09-01 12:31:38 -04:00
Mike Bayer 56845d8cc2 include a note about the importance of type coerce for custom ops
Change-Id: Ia7dab65523d6a34fcc92ee785ffe03f7e2a33cfd
2017-09-01 10:52:16 -04:00
Mike Bayer 3feea4503f Consider merge key with (None, ) as non-persistent
Fixed bug in :meth:`.Session.merge` where objects in a collection that had
the primary key attribute set to ``None`` for a key that is  typically
autoincrementing would be considered to be a database-persisted key for
part of the internal deduplication process, causing only one object to
actually be inserted in the database.

Change-Id: I0a6e00043be0b2979cda33740e1be3b430ecf8c7
Fixes: #4056
(cherry picked from commit 5243341ed8)
2017-08-31 17:21:35 -04:00
Mike Bayer 2efd89d029 Add SQL Server CI coverage
Change-Id: Ida0d01ae9bcc0573b86e24fddea620a38c962822
2017-08-31 17:20:26 -04:00
Mike Bayer de73c6d1cd - pin on cx_Oracle 6.0.1 for the moment while we wait for
either https://github.com/oracle/python-cx_Oracle/issues/75
to be fixed or we can merge a workaround

Change-Id: Ia3927337fb48824e0fdc764ed3a9d4930ca7a9c6
2017-08-31 16:22:52 -04:00
Mike Bayer c4d6596ba3 Additional fixes to sane rowcount
Implement rowcount assertions and single row check
for post_update as well as deletes.

Change-Id: I4e5ba7e8747bf0e0b41f569089eb8cdbf064b7a9
Fixes: #4062
2017-08-31 15:27:26 -04:00
Mike Bayer b9b1e374bf Add new sane_rowcount_w_returning flag
Added a new class of "rowcount support" for dialects that is specific to
when "RETURNING", which on SQL Server looks like "OUTPUT inserted", is in
use, as the PyODBC backend isn't able to give us rowcount on an UPDATE or
DELETE statement when OUTPUT is in effect.  This primarily affects the ORM
when a flush is updating a row that contains server-calcluated values,
raising an error if the backend does not return the expected row count.
PyODBC now states that it supports rowcount except if OUTPUT.inserted is
present, which is taken into account by the ORM during a flush as to
whether it will look for a rowcount.

ORM tests are implicit in existing tests run against PyODBC

Fixes: #4062
Change-Id: Iff17cbe4c7a5742971ed85a4d58660c18cc569c2
2017-08-31 13:20:57 -04:00
Mike Bayer d0470e296e Use text_type, not unicode
Revise the fix from 03560c4b83
to use compat.text_type for py3k compatibility

Change-Id: Ia6807bd4de3bba4b33b5327a1be7e728b45eb093
2017-08-31 10:04:22 -04:00
Mike Bayer 888f112b78 Enable native boolean for SQL Server
SQL Server supports what SQLAlchemy calls "native boolean"
with its BIT type, as this type only accepts 0 or 1 and the
DBAPIs return its value as True/False.   So the SQL Server
dialects now enable "native boolean" support, in that a
CHECK constraint is not generated for a :class:`.Boolean`
datatype.  The only difference vs. other native boolean
is that there are no "true" / "false" constants so "1" and
"0" are still rendered here.

Tests are implicit in the existing suites.

Change-Id: I75bbcd549884099fb1a177e68667bf880c40fa7c
Fixes: #4061
2017-08-30 18:06:46 -04:00
mike bayer 22396493b2 Merge "Join key_constraints on schema as well for SQL server get_fks" 2017-08-30 12:30:44 -04:00
mike bayer 28e6c79cf3 Merge "Ignore SQL Server "heap" indexes" 2017-08-30 12:30:17 -04:00
Mike Bayer 51c2432918 Add preparer to pymssql that disables percent doubling
Fixed the pymssql dialect so that percent signs in SQL text, such
as used in modulus expressions or literal textual values, are
**not** doubled up, as seems to be what pymssql expects.  This is
despite the fact that the pymssql DBAPI uses the "pyformat" parameter
style which itself considers the percent sign to be significant.

Tests are part of standard suite already (CI has been disabled)

Change-Id: Ie05de403caefcba3292a967183a995e95a5854d5
Fixes: #4057
2017-08-30 12:27:21 -04:00
Mike Bayer 3e855cd277 Ignore SQL Server "heap" indexes
Added a rule to SQL Server index reflection to ignore the so-called
"heap" index that is implicitly present on a table that does not
specify a clustered index.

Tests are part of standard suite already (CI has been disabled)

Change-Id: I593b95551c40ee5d95d54203611112cbff10856f
Fixes: #4059
2017-08-30 12:27:03 -04:00
Mike Bayer 43447c4254 Join key_constraints on schema as well for SQL server get_fks
Fixed bug where the SQL Server dialect could pull columns from multiple
schemas when reflecting a self-referential foreign key constraint, if
multiple schemas contained a constraint of the same name against a
table of the same name.

Tests are part of standard suite already (CI has been disabled)

Change-Id: I04ff4a5dea9b82c8e517b3700a28fe994b5550f3
Fixes: #4060
2017-08-30 12:25:57 -04:00
Mike Bayer 812c08efb4 - rename SQL server autocommit issue to 4058
Fixes #4058

Change-Id: I5d56f4a4d8e42659860fa982abee4698118e4d84
2017-08-30 12:15:00 -04:00
Mike Bayer 56950a78db Implement AUTOCOMMIT for pyodbc, pymssql
In prep for CI coverage for SQL Server, allow AUTOCOMMIT
isolation level to work

Change-Id: I850b977e75f53385986f2c181be4e4412dd3b3f4
2017-08-29 14:32:35 -04:00
Mike Bayer ec4f567f31 Generalize autocommit testing
To support adding AUTOCOMMIT to more dialects, add a suite
test

Change-Id: I585dcce19fcdce70e8cf21aea4edaa97d7bf2bb9
2017-08-29 13:37:02 -04:00
mike bayer 4f34234492 Merge "Apply percent sign escaping to literal binds, comments" 2017-08-28 10:53:28 -04:00
mike bayer fd6a711f54 Merge "Don't do recovery operations under Empty/AttributeError" 2017-08-25 17:33:32 -04:00
Mike Bayer 2392ae1900 Apply percent sign escaping to literal binds, comments
Fixed bug in new percent-sign support (e.g. 🎫`3740`) where a bound
parameter rendered with literal_binds would fail to escape percent-signs
for relevant dialects.  In addition, ensured new table / column comment
support feature also fully makes use of literal-rendered parameters so that
this percent sign support takes place with table / column comment DDL as
well, allowing percent sign support for the mysql / psycopg2 backends that
require escaping of percent signs.

Change-Id: Ia4136a300933e9bc6a01a7b9afd5c7b9a3fee4e3
Fixes: #4054
Fixes: #4052
2017-08-25 16:53:49 -04:00
Mike Bayer f87069a3b0 Don't do recovery operations under Empty/AttributeError
Made some adjustments to :class:`.Pool` and :class:`.Connection` such
that recovery logic is not run underneath exception catches for
``pool.Empty``, ``AttributeError``, since when the recovery operation
itself fails, Python 3 creates a misleading stack trace referring to the
``Empty`` / ``AttributeError`` as the cause, when in fact these exception
catches are part of control flow.

Change-Id: Id3ed9a8f96ce4ccb4009c94af30ddc2ddb9818b9
Fixes: #4028
2017-08-25 16:12:30 -04:00
mike bayer 4baa9041cc Merge "Allow for multiple FOLLOWING/PRECEDING in a window range" 2017-08-25 15:29:25 -04:00
Mike Bayer 3a5bbe4cbe Allow for multiple FOLLOWING/PRECEDING in a window range
Altered the range specification for window functions to allow
for two of the same PRECEDING or FOLLOWING keywords in a range
by allowing for the left side of the range to be positive
and for the right to be negative, e.g. (1, 3) is
"1 FOLLOWING AND 3 FOLLOWING".

Change-Id: I7d3a6c641151bb49219104968d18dac2266f3db8
Fixes: #4053
2017-08-25 09:42:25 -04:00
mike bayer 887fb3ebaa Merge "Ensure col is not None when retrieving quick populators" 2017-08-24 11:00:50 -04:00
Mike Bayer e33cff44b5 - remove 3.4's
Change-Id: I16c9bceaf1ab68f72059b43bf01bb11f6395e6d5
2017-08-23 17:24:00 -04:00
Mike Bayer 827b495b8b Ensure col is not None when retrieving quick populators
Fixed bug where an :func:`.undefer_group` option would not be recognized
if it extended from a relationship that was loading using joined eager
loading.

In particular we need to double check the column both in terms of
the given "adapter" as well as without applying the "adapter"
when searching for the column in the result.

As we now avoid redoing the row processor step we also
improve on callcounts in joined eager loading.

Change-Id: I0f48766f12f7299f4626ff41a00bf1f5bfca5f3b
Fixes: #4048
2017-08-23 17:20:17 -04:00
Mike Bayer 3f9df2b86b Handle cache key for option that has no strategy
Fixed regression where the use of a :func:`.undefer_group` option
in conjunction with a lazy loaded relationship option would cause
an attribute error, due to a bug in the SQL cache key generation
added in 1.2 as part of 🎫`3954`.

Change-Id: Icd9a34f0b5aa96d6433a2ab9c8d3eaee0006f609
Fixes: #4049
2017-08-22 18:35:09 -04:00
Mike Bayer d8a80a35a0 - fix typos
Change-Id: Ibf8bc0e997ff989c7b0c16afad48a95414078052
2017-08-22 18:15:59 -04:00
Mike Bayer 2db5256143 - modernize the mysql connection timeout docs
Change-Id: Icb0474509539c1eb7536544749f2a48b4972078a
(cherry picked from commit 4ce46fb0a085c1cc739e21881cc25567e663f8dc)
2017-08-22 16:52:10 -04:00
Mike Bayer 8b53548b9e Deactivate transaction if rollback fails
Fixed regression introduced in 1.2.0b1 due to 🎫`3934` where the
:class:`.Session` would fail to "deactivate" the transaction, if a
rollback failed (the target issue is when MySQL loses track of a SAVEPOINT).
This would cause a subsequent call to :meth:`.Session.rollback` to raise
an error a second time, rather than completing and bringing the
:class:`.Session` back to ACTIVE.

Fixes: #4050
Change-Id: Id245e8dd3487cb006b2d6631c8bd513b5ce81abe
2017-08-22 16:17:39 -04:00
Mike Bayer 41549de960 - ensure identifier re-use doesn't make this break
Change-Id: I9fe6c42c097d31b50a479250d39a3cd8ebcbffaf
2017-08-22 13:55:49 -04:00
Mike Bayer 4c30681839 - allow a separate template database to be used for
PG CREATE DATABASE.  as nobody will connect to it that would
solve the contention issue here

Change-Id: I00a4d52091876e120faff4a8a5493c53280d96f1
2017-08-22 13:12:43 -04:00
Mike Bayer df01130bb1 - repair --dbs
Change-Id: I69e39d2368f50b126c369ecc35e01799fd013254
(cherry picked from commit 3fc6f32ddc)
2017-08-22 13:07:45 -04:00
Michael Smirnov e0ddf30bf6 Fixed a typo in before_execute doc.
events.py edited online with Bitbucket
2017-08-22 13:49:54 +00:00
Mike Bayer d4f8b12442 - add missing changelog file for #4045
Change-Id: I649cef3f4d91dec79dbd425a7dc5aad35abe87e5
2017-08-21 22:14:19 -04:00
Mike Bayer fe5eede555 - simplify and see if it still works
Change-Id: Id0cf7ae2223507d413aaa22e5f8df066b7ac2b46
2017-08-21 22:12:30 -04:00
Mike Bayer f3f6116c57 - keep trying to get PG dbs to build
Change-Id: Ib36949da8f079594494a482423d96e7509673481
2017-08-21 19:00:25 -04:00
Mike Bayer 1d82b4057a - add missing quotes
Change-Id: Ib6efc465cccd7c7661dd089856edfd4979b53517
2017-08-21 18:19:02 -04:00
Mike Bayer ddefe6cf8c - try to get PG database create to be more reliable
Change-Id: I9c9d101547f4484af447db924dc06afd0392a03e
2017-08-21 17:55:26 -04:00
Mike Bayer a61ff195b5 - sanitize class names for junit reporting
Change-Id: I42821d8324208b708adc17a10b1a2758797cb9db
2017-08-21 17:13:12 -04:00
Mike Bayer a2beb234e8 Merge branch 'fixtypo' of https://github.com/hsmtkk/sqlalchemy 2017-08-21 16:28:12 -04:00
Mike Bayer 97e455f21b - filter out non-oracle URLs
Change-Id: I475f744f8801bc923d738e466d208d662e707413
2017-08-21 12:08:01 -04:00
Mike Bayer 63d47c051d - this test doesn't work in strict mode, not that important
Change-Id: I3ed361af5c9f0c7acbeb8b534966828949f4958b
2017-08-20 23:11:57 -04:00
Mike Bayer 64032a35ae - a few mysql fixes, more to come
Change-Id: Icdcc8ed03374251b8d3815ae58e2726ea27c14b4
2017-08-20 18:57:05 -04:00
Mike Bayer cc741e1ac7 - rework oracle de-provisioning to write URLs to the file as well,
supporting custom dburi etc.

Change-Id: Ic0ab0b3b4223e40fd335ee3313fda4dfce942100
2017-08-20 18:21:34 -04:00
Mike Bayer 0030966200 - add some logging for the provisioning
Change-Id: I1ac16bc77642f4f576195ac10443ed8e641e0d49
2017-08-19 22:45:31 -04:00
Mike Bayer ed197d4c30 - dont run sql mode config tests if we aren't on mysql
Change-Id: Ia5a491ec505afed1511a17a167cd1f7d8371acd4
2017-08-19 18:20:48 -04:00
Mike Bayer a0b5840320 - do ten attempts to create database
Change-Id: I14a5dd920d14096aa4401cb8b9d71f47d3915879
2017-08-19 18:06:02 -04:00
mike bayer 0628499690 Merge "First level repair for cx_Oracle 6.0 test regressions" 2017-08-19 18:04:51 -04:00
Mike Bayer ecdd922d96 - correct server side cursor assertion for driver names
Change-Id: Id8156f6af15a36f7d5653dff56f68e81431692a6
2017-08-19 17:30:06 -04:00
Mike Bayer 9e6393c6b1 - name these TOX_ so that we can set them unconditionally
without them getting used unless we ask for them in the
build

Change-Id: Iec157ce9e70366af275acac959527461faebfdc1
2017-08-19 16:59:29 -04:00
Mike Bayer 31491a6acc - rework the unittests README which was very out of date
Change-Id: Id9bda43ea493a8d493be5ecb19da16a91a298f9d
2017-08-19 14:06:14 -04:00
Mike Bayer 03255a5a0f First level repair for cx_Oracle 6.0 test regressions
Fixed more regressions caused by cx_Oracle 6.0; at the moment, the only
behavioral change for users is disconnect detection now detects for
cx_Oracle.DatabaseError in addition to cx_Oracle.InterfaceError, as
this behavior seems to have changed.   Other issues regarding numeric
precision and uncloseable connections are pending with the upstream
cx_Oracle issue tracker.

Change-Id: Id61f1e33b21c155a598396340dfdecd28ff4066b
Fixes: #4045
2017-08-18 13:04:14 -04:00
Mike Bayer 04e4b63c20 - convert to spaces
Change-Id: Ic5eb90049358935995721765b2239cf91144895a
2017-08-17 13:37:53 -04:00
mike bayer d173662fe0 Merge "Enable uuid for pg8000" 2017-08-17 09:14:07 -04:00
hsmtkk 58fb83c45b fix a typo 2017-08-16 18:38:40 +09:00
mike bayer eb8db2303b Merge "Ensure Oracle index w/ col DESC etc. is reflected" 2017-08-14 13:54:12 -04:00
Mike Bayer 2c594da214 Isolate memory tests in forks
Swing the biggest hammer, run multiprocessing.Process() for
each memusage test individually so that they are fully isolated
from the parent process and any side effects of pytest-xdist

Also add --nomemory as a shortcut to exclude_tags=memory-intensive
and add this to the setup.py test runner as the memory tests
should not be running for quick runs

Change-Id: I3c16c781e21b33deb939a64e77a6e0e41fb86922
2017-08-14 12:41:58 -04:00
Mike Bayer bb9d511e52 Restore original test names
The change in de1f8f8345
modified how test classes are named, breaking logic that
extracts the class name for the profiling suite.
Add a new variable _sa_orig_cls_name if we've modified the
name so that the profiling logic doesn't need to guess
the original class name.

Change-Id: Ica15a97408b9e0749a78c87f62749c15c1627009
2017-08-14 09:34:28 -04:00
Mike Bayer 1a990ee332 Ensure Oracle index w/ col DESC etc. is reflected
Fixed bug where an index reflected under Oracle with an expression like
"column DESC" would not be returned, if the table also had no primary
key, as a result of logic that attempts to filter out the
index implicitly added by Oracle onto the primary key columns.

Reworked the "filter out the primary key index" logic in oracle
get_indexes() to be clearer.

This changeset also adds an internal check to ColumnCollection
to accomodate for the case of a column being added twice,
as well as adding a private _table argument to Index such that
reflection can specify the Table explicitly.  The _table
argument can become part of public API in a later revision
or release if needed.

Change-Id: I745711e03b3e450b7f31185fc70e10d3823063fa
Fixes: #4042
2017-08-14 01:18:06 -04:00
Mike Bayer e331da58a6 - since we can't isolate the memory tests to run withtout pytest-xdist,
add a new tag nomemory so we can at least limit on the build

Change-Id: I3935cf15047d77fc09f8ee229914e37e064e5b8b
2017-08-14 01:15:22 -04:00
Mike Bayer f1fd7f1e01 - try adding the prints back in and re-test
Change-Id: I3a82b06ecc3c065240cc05871dee2881f20e414e
2017-08-11 09:54:16 -04:00
Mike Bayer 3568e508d0 - take more print statements out, maybe this is not
the issue
- unblock pytest-xdist now that the upstream issue is fixed,
maybe this old version is the issue

Change-Id: I28dd7ae0872948a188651d42e2f4af60bcbafe81
2017-08-10 15:46:37 -04:00
Mike Bayer eaceeae0f7 Merge branch 'master--typos' of https://github.com/nphilipp/sqlalchemy 2017-08-09 09:32:51 -04:00
Mike Bayer c86b95038d Enable uuid for pg8000
Enabled UUID support for the pg8000 driver, which supports native Python
uuid round trips for this datatype.  Arrays of UUID are still not supported,
however.

Change-Id: I44ca323c5d9f2cd87327210233bc36a3556eb050
Fixes: #4016
2017-08-08 18:00:18 -04:00
Mike Bayer 03560c4b83 Add quoted_name to pg8000 py_types
Fixed bug where the pg8000 driver would fail if using
:meth:`.MetaData.reflect` with a schema name, since the schema name would
be sent as a "quoted_name" object that's a string subclass, which pg8000
doesn't recognize.   The quoted_name type is added to pg8000's
py_types collection on connect.

Change-Id: Id0f838320cb66563685e094e4eae2d5116100d27
Fixes: #4041
2017-08-08 17:25:28 -04:00
Mike Bayer 725298ea4b - dont print samples, this appears like it may be
itself causing the memory leak in conjunction with pytest-xdist

Change-Id: Ia8704e54186e6dd60ea0e32a246fcf1419686663
2017-08-08 17:24:23 -04:00
Mike Bayer 0a23654649 - allow the shrink phase for memusage to go until zeroed,
some MySQL-env element is causing memory growth that goes very
far before stopping

Change-Id: Ic0882dd78636067980fceba4e3a969de78d5b26a
2017-08-08 14:02:16 -04:00
Mike Bayer 68879d50fa Enable multi-level selectin polymorphic loading
Change-Id: Icc742bbeecdb7448ce84caccd63e086af16e81c1
Fixes: #4026
2017-08-07 15:05:00 -04:00
Mike Bayer 4b4f8fbf25 - modernize orm.reconstructor documentation a bit
Change-Id: Ied786e8f9ad78f524be03a382d002dada7dd218b
2017-08-05 21:46:24 -04:00
Nils Philippsen 7765724d51 fix "constrast" typos 2017-08-05 13:31:06 +02:00
Mike Bayer de1f8f8345 Allow multiple versions of single backend
Improve screen output to illustrate which server version is
running for a particular database config, and additionally
allow full overriding for the backend-specific targets in
tox.ini via environment variables, so that CI can inject
multiple server urls for a particular database such as MySQL/MariaDB.

Change-Id: Ibf443bb9fb82e4563efd1bb66058fa9989aa2fda
2017-08-04 16:16:49 -04:00
Mike Bayer 54cdda032e - fix one test for STRICT, which may be turned on by default
in mariadb 10.2.   more mariadb fixes coming

Change-Id: I6e3a94ae7340772663677b1082506adbb2d84a38
2017-08-04 11:28:20 -04:00
Mike Bayer 4e8b155c74 Pin to pytest<=3.0.7 pytest-xdist<=1.16.0
Until https://github.com/pytest-dev/pytest-xdist/issues/196 is fixed

Change-Id: I7dfd268e6078373ccaa0b5c13f9b6ffa1b2fd4b2
2017-08-04 10:02:32 -04:00
Mike Bayer e6432d78b2 - 1.0.19
Change-Id: I65ebe00fa7372151210a1f177f5417ac08c41586
(cherry picked from commit 90ef2c2314)
2017-08-03 11:37:00 -04:00
Mike Bayer a1160414b8 - convert to spaces
- restore unreleased directories

Change-Id: Ia5c1142ffbdba6372f800c2e2521660ab62d9c4f
2017-07-31 08:34:06 -04:00
mike bayer ace88cdd2c Merge "Revert cx_Oracle WITH_UNICODE change under > 5.0" 2017-07-28 18:06:21 -04:00
Mike Bayer 7997d7fdc3 Revert cx_Oracle WITH_UNICODE change under > 5.0
Fixed performance regression caused by the fix for 🎫`3937` where
cx_Oracle as of version 5.3 dropped the ``.UNICODE`` symbol from its
namespace,  which was interpreted as cx_Oracle's "WITH_UNICODE" mode being
turned on unconditionally, which invokes functions on the SQLAlchemy
side which convert all strings to unicode unconditionally and causing
a performance impact.  In fact, per cx_Oracle's author the
"WITH_UNICODE" mode has been removed entirely as of 5.1, so the expensive unicode
conversion functions are no longer necessary and are disabled if
cx_Oracle 5.1 or greater is detected under Python 2.  The warning against
"WITH_UNICODE" mode that was removed under 🎫`3937` is also restored.

Change-Id: Iddd38d81a5adb27c953a5ee2eae5529a21da16e1
Fixes: #4035
2017-07-28 17:36:08 -04:00
Mike Bayer 2ae2c25c5d - 1.1.13
- 1.0.19

Change-Id: I476213fe905a51826feeddb4e1c97416c2bac558
(cherry picked from commit f7beeb389d)
2017-07-28 15:16:48 -04:00
Mike Bayer 5467089770 - 1.2.0b3 prep
Change-Id: I9aa6e891ca896b90b97fbd0e52f0ad73494e38d7
2017-07-25 17:26:55 -04:00
Mike Bayer 32c4c8ace4 - 1.2.0b2 2017-07-24 17:22:23 -04:00
Mike Bayer 2b5a48232f - 1.1.12 release date
(cherry picked from commit ad5626cdb9)

Change-Id: Icd2f3ce68451e609c0d1c116256c2e1cf8baf7eb
2017-07-24 17:19:46 -04:00
Mike Bayer 295f5e5dee - 1.0.18 release date
(cherry picked from commit f00391a070)

Change-Id: I243a63d084d4b369ded7969d78e3ab033f6189bd
2017-07-24 17:18:05 -04:00
mike bayer 81f34b2f33 Merge "Ensure we check for boolean condition when we inspect __exit__()" 2017-07-24 16:54:13 -04:00
mike bayer fea7c7e48f Merge "Guard all indexed access in WeakInstanceDict" 2017-07-24 14:49:23 -04:00
Mike Bayer 5a628cf7d9 Merge branch 'patch-1' of https://github.com/feanil/sqlalchemy 2017-07-24 12:42:45 -04:00
Mike Bayer 7d4005156b Ensure we check for boolean condition when we inspect __exit__()
Fixed issue in testing fixtures which was incompatible with a change
made as of Python 3.6.2 involving context managers.

Change-Id: I0f12aa6cc15cba89153f7e4888ac347e7ce599c7
Fixes: #4034
2017-07-24 12:31:44 -04:00
Mike Bayer 3d8049e32d Guard all indexed access in WeakInstanceDict
Added ``KeyError`` checks to all methods within
:class:`.WeakInstanceDict` where a check for ``key in dict`` is
followed by indexed access to that key, to guard against a race against
garbage collection that under load can remove the key from the dict
after the code assumes its present, leading to very infrequent
``KeyError`` raises.

Change-Id: I881cc2899f7961d29a0549f44149a2615ae7a4ea
Fixes: #4030
2017-07-24 11:48:13 -04:00
Mike Bayer 8d4a4049f4 - Merge directory holder README from 1.0.x and also 1.0's changelog
Change-Id: I588eebd027b4ad3428bd522f36a6f1cd77f105bb
(cherry picked from commit 39c72682b8)
2017-07-24 10:52:07 -04:00
Feanil Patel c9b37f9689 Make flush logic slightly clearer in tutorial.
Improve the wording of how sessions commit changes.
2017-07-23 09:17:39 -04:00
Mike Bayer 39c72682b8 - move to file-per-changelog for unreleased change notes,
so that we no longer have to rely upon merges within
the changelog files.   because gerrit doesn't allow us
to use custom merge engines unlike git, we have no ability
to merge multiple changes into the changelog files without
going through conflicts.   new version of changelog
in git supports these new patterns.

Change-Id: I588eebd027b4ad3428bd522f36a6f1cd77f105bb
2017-07-22 16:32:01 -04:00
mike bayer 91e3c36e45 Merge "Check for column object in eval_none, not propkey" 2017-07-19 16:21:57 -04:00
Mike Bayer 7628ff39dc Check for column object in eval_none, not propkey
Fixed bug involving JSON NULL evaluation logic added in 1.1 as part
of 🎫`3514` where the logic would not accommodate ORM
mapped attributes named differently from the :class:`.Column`
that was mapped.

Change-Id: I1848afcfb63ad7f074f315d8d3097666069b42be
Fixes: #4031
2017-07-18 15:04:36 -04:00
Mike Bayer 3d41ea09a8 Check for non-entity when inspecting for subqueryload
Fixed issue where adding additional non-entity columns to
a query that includes an entity with subqueryload relationships
would fail, due to an inspection added in 1.1.11 as a result of
🎫`4011`.

Change-Id: I8ef082be649125bdc07b428cb9b0a77a65d73671
Fixes: #4033
2017-07-18 15:02:39 -04:00
Mike Bayer 32f67637cd Merge branch 'patch-1' of https://github.com/tomsitter/sqlalchemy 2017-07-17 10:31:07 -04:00
Mike Bayer 2eeea03973 Merge branch 'patch-2' of https://github.com/pablogamboa/sqlalchemy 2017-07-17 10:29:13 -04:00
Mike Bayer 3cb29af876 - 1.2.0b2 placeholder
Change-Id: I95ff7f4bb0048b363987344d359f252469b23b79
2017-07-14 18:05:41 -04:00
Tom Sitter 43f41fbfaa Replace Session class with session instance
The Session class was used instead of the session instance which resulted in an attribute error.
2017-07-12 11:54:25 -04:00
Pablo Marti c6b4675982 Fix typo, foriegn -> foreign 2017-07-10 19:43:58 +02:00
Mike Bayer e6555083d4 - 1.2.0b1 2017-07-10 09:23:28 -04:00
Pablo Marti 2456662e5e Fix typo in migration_12 2017-07-10 11:58:11 +01:00
Mike Bayer e478a8c00d - remove "under development" for 1.2 migration notes
Change-Id: I660a4966e7375859058025ef132c595f74293e4c
2017-07-09 14:09:36 -04:00
Mike Bayer 14253e7ff4 - fix exposed "sourcecode" tags
Change-Id: Ie1bdcf2773f3de96d5ca26ebf80657e5d72c70f9
2017-07-09 13:13:25 -04:00
Mike Bayer a66979fe1e - remove intersphinx usage, the overhead of re-fetching
inventory on every build not worth it

Change-Id: I3c4506b246d0f327c4b56afa723975daee984476
2017-07-09 13:02:59 -04:00
Mike Bayer e900aa97e2 - rst fixes
Change-Id: Ice3eeb8312fcb5a4d586113ee3e52be90fbcd95e
2017-07-09 11:13:10 -04:00
mike bayer 79285a0f46 Merge "Add support for CACHE and ORDER to sequences" 2017-07-06 09:03:29 -04:00
mike bayer 35ab498a87 Merge "Add .autocommit to scoped_session" 2017-07-05 16:23:57 -04:00
David Moore faa6609dac Add support for CACHE and ORDER to sequences
Added new keywords :paramref:`.Sequence.cache` and
:paramref:`.Sequence.order` to :class:`.Sequence`, to allow rendering
of the CACHE parameter understood by Oracle and PostgreSQL, and the
ORDER parameter understood by Oracle.  Pull request
courtesy David Moore.

Change-Id: I082c3f8ef56ef89dbaad5da9d5695be5313b0614
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/96
2017-07-05 16:21:44 -04:00
Mike Bayer b7a51f3a9c - 1.1.12 placeholder
Change-Id: I23ccfebfbaaf40739a4a538d232875135a5cd04c
2017-07-05 16:07:42 -04:00
Ben Fagin 5c30910759 Add .autocommit to scoped_session
Added ``.autocommit`` attribute to :class:`.scoped_session`, proxying
the ``.autocommit`` attribute of the underling :class:`.Session`
currently assigned to the thread.  Pull request courtesy
Ben Fagin.

Change-Id: Iff741978bd67762f4c7375a23cc151b26192042b
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/372
2017-07-05 15:11:48 -04:00
Michael DoroninandMike Bayer 7d3da6f850 Implement MySQL's ON DUPLICATE KEY UPDATE
Added support for MySQL's ON DUPLICATE KEY UPDATE
MySQL-specific :class:`.mysql.dml.Insert` object.
Pull request courtesy Michael Doronin.

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Resolves: #4009
Change-Id: Ic71424f3c88af6082b48a910a2efb7fbfc0a7eb4
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/365
2017-07-03 14:38:09 -04:00
Michael Stewart 1db3029abc Include missing import in example 2017-06-30 14:02:20 -07:00
Mike Bayer 563180f7d4 Coerce to float for Float with all native decimal backends
The result processor for the :class:`.Float` type now unconditionally
runs values through the ``float()`` processor if the dialect
specifies that it also supports "native decimal" mode.  While most
backends will deliver Python ``float`` objects for a floating point
datatype, the MySQL backends in some cases lack the typing information
in order to provide this and return ``Decimal`` unless the float
conversion is done.

Change-Id: I638f1480fb00a507036efaf0e0080f26893d98ad
Fixes: #4020
2017-06-26 16:50:24 -04:00
mike bayer 33d083c034 Merge "Support state expiration for with_expression(); rename deferred_expression" 2017-06-26 15:47:50 -04:00
Mike Bayer 9ac0f8119e Support state expiration for with_expression(); rename deferred_expression
The attributeimpl for a deferred_expression does not
support a scalar loader, add new configurability so that
the impl can have this flag turned off.   Document
that the with_expression() system currently does not
offer any deferred loading.

To eliminate confusion over "deferred", which refers to
lazy loading of column attributes, and "with_expression",
which refers to an attribute that is explicitly at
query time only, rename deferred_expression to query_expression.

Change-Id: I07c4a050ed68c79ccbde9492e9de1630b7470d74
2017-06-26 13:49:49 -04:00
Mike Bayer fae82dda00 Return given type when it matches the adaptation
The rules for type coercion between :class:`.Numeric`, :class:`.Integer`,
and date-related types now include additional logic that will attempt
to preserve the settings of the incoming type on the "resolved" type.
Currently the target for this is the ``asdecimal`` flag, so that
a math operation between :class:`.Numeric` or :class:`.Float` and
:class:`.Integer` will preserve the "asdecimal" flag as well as
if the type should be the :class:`.Float` subclass.

Change-Id: Idfaba17220d6db21ca1ca4dcb4c19834cd397817
Fixes: #4018
2017-06-26 12:46:53 -04:00
mike bayer e04594339c Merge "Coerce float Python type to Float; ensure Python float coming back" 2017-06-26 11:56:38 -04:00
Mike Bayer 1776597131 Coerce float Python type to Float; ensure Python float coming back
Added some extra strictness to the handling of Python "float" values
passed to SQL statements.  A "float" value will be associated with the
:class:`.Float` datatype and not the Decimal-coercing :class:`.Numeric`
datatype as was the case before, eliminating a confusing warning
emitted on SQLite as well as unecessary coercion to Decimal.

Change-Id: I1bb1810ff1d198c0d929ccba5656e55401d74119
Fixes: #4017
2017-06-26 11:05:38 -04:00
Jodok Batlogg 9f1a375f10 added link for CrateDB support 2017-06-23 21:16:18 +02:00
Eloy Felix bff001187f Don't erase reflected comment in _init_existing
Change-Id: Ie0b78c79367933486528ca0ba686d4a9f16922b1
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/370
2017-06-20 09:48:49 -04:00
Mike Bayer 83c1e03c5c Add ad-hoc mapped expressions
Added a new feature :func:`.orm.with_expression` that allows an ad-hoc
SQL expression to be added to a specific entity in a query at result
time.  This is an alternative to the SQL expression being delivered as
a separate element in the result tuple.

Change-Id: Id8c479f7489fb02e09427837c59d1eabb2a6c014
Fixes: #3058
2017-06-19 17:41:39 -04:00
Mike Bayer 735fcd5e77 - 1.1.11 release date
Change-Id: I351e5727368b67598d091e5153a66987e349f8f6
2017-06-19 11:00:59 -04:00
mike bayer 139cbe4f72 Merge "Handle SHOW VARIABLES returning no row" 2017-06-16 18:40:13 -04:00
mike bayer 6d8d89042b Merge "Add all versioning logic to _post_update()" 2017-06-16 16:41:14 -04:00
Mike Bayer 5650a0c306 Handle SHOW VARIABLES returning no row
MySQL 5.7 has introduced permission limiting for the "SHOW VARIABLES"
command; the MySQL dialect will now handle when SHOW returns no
row, in particular for the initial fetch of SQL_MODE, and will
emit a warning that user permissions should be modified to allow the
row to be present.

Change-Id: I98e7a69230da397b17eae07b7e9d024fa7aeeb26
Fixes: #4007
2017-06-16 15:52:46 -04:00
Mike Bayer a991eedcf5 Set complete FROM list for subquery eagerload's orig query
Instead of checking that the "orig_entity" we receive applies
as a correct FROM element for the subquery we're building,
set the FROM clause of the query to exactly what it already
is based on column_descriptions (assuming there is no FROM
list already), thereby ensuring that the FROM list will remain
intact, regardless of what orig_entity turns out to be and
what the target_cols ultimately refer towards.

Fixed issue with subquery eagerloading which continues on from
the series of issues fixed in 🎫`2699`, 🎫`3106`,
🎫`3893` involving that the "subquery" contains the correct
FROM clause when beginning from a joined inheritance subclass
and then subquery eager loading onto a relationship from
the base class, while the query also includes criteria against
the subclass. The fix in the previous tickets did not accommodate
for additional subqueryload operations loading more deeply from
the first level, so the fix has been further generalized.

Change-Id: Ic909590814f71e577d8266b1dbc4c393dc48e019
Fixes: #4011
2017-06-16 13:02:31 -04:00
Mike Bayer 3a314fcea8 Repair WithinGroup.get_children()
Fixed AttributeError which would occur in :class:`.WithinGroup`
construct during an iteration of the structure.

Change-Id: I563882d93c8c32292463a605b636aa60c77e9406
Fixes: #4012
2017-06-16 09:58:03 -04:00
Mike Bayer 64b0760faa Add all versioning logic to _post_update()
An UPDATE emitted as a result of the
:paramref:`.relationship.post_update` feature will now integrate with
the versioning feature to both bump the version id of the row as well
as assert that the existing version number was matched.

Fixes: #3496
Change-Id: I865405dd6069f1c1e3b0d27a4980e9374e059f97
2017-06-15 18:58:29 -04:00
Mike Bayer 7af05fcc93 - remove redundant fixture from base test class
Change-Id: I76f197d5b2b39ae476bfff924e899773aa123be0
2017-06-15 16:07:06 -04:00
Mike Bayer 9541e30e86 - ensure String has a length for mysql compatibility
Change-Id: Iaa1077ca5929bdc67300cc6bfb1ba98aff382246
2017-06-15 13:51:14 -04:00
Mike Bayer 770e1e399c Repair regression to pathing for subclasses
Issue #3963's initial commit narrowed the "current path"
match rules too much such that a path that matches current
path on subclass would no longer match.

Change-Id: I8c9a0db91a09d789cfb8666288a913f8bbcdb2e9
Fixes: #3963
2017-06-15 12:03:22 -04:00
Mike Bayer 740f6b0d5a Refinements for unitofwork internals
* remove "mapper" argument from SaveUpdateState, DeleteState
* use __slots__ for all uow action classes
* rename ".delete" to ".isdelete"
* rename issue_post_update to register_post_update since this
  doesn't actually issue the UPDATE
* rename IssuePostUpdate to PostUpdateAll

Change-Id: Ia6263b80d6a86eab1e8ed38df1421b1d0f249797
2017-06-14 12:54:53 -04:00
Mike Bayer 27a0bdcae0 Support AssociationProxy any() / has() / contains() to another AssociationProxy
The :meth:`.AssociationProxy.any`, :meth:`.AssociationProxy.has`
and :meth:`.AssociationProxy.contains`
comparison methods now support linkage to an attribute that
is itself also an :class:`.AssociationProxy`, recursively.

After some initial attempts it's clear that the any() / has()
of AssociationProxy needed to be reworked into a generic
_criterion_exists() to allow this to work recursively without
excess complexity.  For the case of the multi-linked associationproxy,
the usual checks of "any()" / "has()" correctness simply don't
take place; for a single-link association proxy the error
checking logic that takes place in relationship() has been
ported to the local any() / has() methods.

Change-Id: Ic5aed2a4e910b8138a737d215430113c31cce856
Fixes: #3769
2017-06-12 16:31:59 -04:00
Mike Bayer ec422fb70e Render ARRAY index embedded between type and COLLATE
Fixed bug where using :class:`.ARRAY` with a string type that
features a collation would fail to produce the correct syntax
within CREATE TABLE.

The "COLLATE" must appear to the right of the array dimensions,
so we are using regexp substitution to insert the brackets in the
appropriate place.  A more heavyweight solution would be that datatypes
know how to split up their base type vs. modifiers, but as this is
so specific to Postgresql ARRAY it's better to handle these cases
more locally.

Change-Id: I394c3c673eb60689e51b5301e51651972cfdb4c0
Fixes: #4006
2017-06-08 17:06:53 -04:00
Mike Bayer b6d3f60791 Parse for Postgresql version w/ "beta"
Continuing with the fix that correctly handles Postgresql
version string "10devel" released in 1.1.8, an additional regexp
bump to handle version strings of the form "10beta1".   While
Postgresql now offers better ways to get this information, we
are sticking w/ the regexp at least through 1.1.x for the least
amount of risk to compatibility w/ older or alternate Postgresql
databases.

Change-Id: I12ddb06465f7dcf80563c27632441ef5963f60d4
Fixes: #4005
2017-06-07 12:30:22 -04:00
Mike Bayer acf64c4178 - assert passive_deletes='all' does not affect collection/scalar
membership removal

in issue #3844 we hypotheized that passive_deletes='all' was broken
because it sets to NULL a foreign key attribute when the child
object is removed or replaced.   However, not doing the NULL
set means that nothing happens at all and the operation silently
fails.

Change-Id: I11834e7e324349e172dc797bac62731008b6b95a
2017-06-06 18:53:03 -04:00
Mike Bayer f1faec8829 - make sure ticket # is here
Change-Id: I7d54026da9a9a9331a4fd7e675dbfe9c433fe2e4
2017-06-06 17:59:19 -04:00
Mike Bayer 4e1f5377d1 Warn when declared_attr.cascading detected on mapped class
A warning is emitted if the :attr:`.declared_attr.cascading` modifier
is used with a declarative attribute that is itself declared on
a class that is to be mapped, as opposed to a declarative mixin
class or ``__abstract__`` class.  The :attr:`.declared_attr.cascading`
modifier currently only applies to mixin/abstract classes.

Also add a test for @declared_attr.cascading when used on an attribute
on __abstract__.

Change-Id: Ib1b9dbe373e8be1cf24eadfed224a8988b3cd95d
Fixes: #3847
2017-06-06 17:16:58 -04:00
Mike Bayer 6b68a70b5f Re-send column value w/ onupdate default during post-update
Adjusted the behavior of post_update such that if a column with
an "onupdate" default has received an explicit value for
INSERT, re-send the same data during a post-update UPDATE so
that the value remains in effect, rather than an onupdate
overwriting it.

Change-Id: I26bccb6f957dcad07a2bcbda2dd9e14c60b92b06
Fixes: #3471
2017-06-06 13:54:33 -04:00
mike bayer a2099ed44f Merge "Implement _postfetch_post_update to expire/refresh onupdates in post_update" 2017-06-06 13:40:27 -04:00
Mike Bayer 9dee44ae2f Implement _postfetch_post_update to expire/refresh onupdates in post_update
Fixed bug involving the :paramref:`.relationship.post_update` feature
where a column "onupdate" value would not result in expiration or
refresh of the corresponding object attribute, if the UPDATE for the
row were a result of the "post update" feature.  Additionally, the
:meth:`.SessionEvents.refresh_flush` event is now emitted for these
attributes when refreshed within the flush.

Fixes: #3472
Change-Id: I5ee2d715e773a306ab1e8143e4382c228991ac78
2017-06-05 18:39:08 -04:00
Mike Bayer e8ad398862 Implement in-place mutation operators for MutableSet, MutableList
Implemented in-place mutation operators ``__ior__``, ``__iand__``,
``__ixor__`` and ``__isub__`` for :class:`.mutable.MutableSet`
and ``__iadd__`` for :class:`.mutable.MutableList` so that change
events are fired off when these mutator methods are used to alter the
collection.

Change-Id: Ib357a96d3b06c5deb6b53eb304a8b9f1dc9e9ede
Fixes: #3853
2017-06-05 15:49:04 -04:00
Mike Bayer bb6a1f690d selectin polymorphic loading
Added a new style of mapper-level inheritance loading
"polymorphic selectin".  This style of loading
emits queries for each subclass in an inheritance
hierarchy subsequent to the load of the base
object type, using IN to specify the desired
primary key values.

Fixes: #3948

Change-Id: I59e071c6142354a3f95730046e3dcdfc0e2c4de5
2017-06-05 11:27:00 -04:00
Mike Bayer 6bb97495ba Merge branch 'fix-typo' of https://github.com/lelit/sqlalchemy 2017-06-02 18:35:54 -04:00
Lele Gaifax 4779ddd865 Fix a few doc typos 2017-06-02 23:38:26 +02:00
Eloy Felix f8b4f7289e Implement get_unique_constraints, get_check_constraints for Oracle
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/326
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/342

Fixes: #4002
Change-Id: I221fe8ba305fc455a03e3a5d15f803bf8ee2e8fb
2017-05-30 17:14:22 -04:00
Mike Bayer 8b82369347 Don't hard-evaluate non-ORM @declared_attr for AbstractConcreteBase
Fixed bug where using :class:`.declared_attr` on an
:class:`.AbstractConcreteBase` where a particular return value were some
non-mapped symbol, including ``None``, would cause the attribute
to hard-evaluate just once and store the value to the object
dictionary, not allowing it to invoke for subclasses.   This behavior
is normal when :class:`.declared_attr` is on a mapped class, and
does not occur on a mixin or abstract class.  Since
:class:`.AbstractConcreteBase` is both "abstract" and actually
"mapped", a special exception case is made here so that the
"abstract" behavior takes precedence for :class:`.declared_attr`.

Change-Id: I6160ebb3a52c441d6a4b663c8c9bbac6d37fa417
Fixes: #3848
2017-05-26 13:28:15 -04:00
Mike Bayer b1369b4721 Add placeholder XML support
Added a placeholder type :class:`.mssql.XML` to the SQL Server
dialect, so that a reflected table which includes this type can
be re-rendered as a CREATE TABLE.  The type has no special round-trip
behavior nor does it currently support additional qualifying
arguments.

Change-Id: I651fa729bd8e9b31a0b5effe0839aff077d77c46
Fixes: #3973
2017-05-26 11:24:25 -04:00
mike bayer 915012950c Merge "Raise if ForeignKeyConstraint created with different numbers of local and remote columns." 2017-05-25 16:24:25 -04:00
Michael BirtwellandMike Bayer f8a3f14e4f Flatten operator precedence for comparison operators
The operator precedence for all comparison operators such as LIKE, IS,
IN, MATCH, equals, greater than, less than, etc. has all been merged
into one level, so that expressions which make use of these against
each other will produce parentheses between them.   This suits the
stated operator precedence of databases like Oracle, MySQL and others
which place all of these operators as equal precedence, as well as
Postgresql as of 9.5 which has also flattened its operator precendence.

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Fixes: #3999
Change-Id: I3f3d5124a64af0d376361cdf15a97e2e703be56f
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/367
2017-05-25 16:02:13 -04:00
Mike Bayer a78718b934 Raise if ForeignKeyConstraint created with different numbers of
local and remote columns.

An :class:`.ArgumentError` is now raised if a
:class:`.ForeignKeyConstraint` object is created with a mismatched
number of "local" and "remote" columns, which otherwise causes the
internal state of the constraint to be incorrect.   Note that this
also impacts the condition where a dialect's reflection process
produces a mismatched set of columns for a foreign key constraint.

Downstream DB2 dialect has been reported as potentially causing this
scenario.

Change-Id: Id51c34a6c43749bb582639f9c1dc28723482f0e5
Fixes: #3949
References: #3998
2017-05-25 15:57:03 -04:00
Mike Bayer de11c5217b Add with_for_update() support in session.refresh()
Session.refresh() is still hardcoded to legacy lockmode,
come up with a new API so that the newer argument style
works with it.

Added new argument :paramref:`.with_for_update` to the
:meth:`.Session.refresh` method.  When the :meth:`.Query.with_lockmode`
method were deprecated in favor of :meth:`.Query.with_for_update`,
the :meth:`.Session.refresh` method was never updated to reflect
the new option.

Change-Id: Ia02a653746b7024699b515451525a88d7a17d63a
Fixes: #3991
2017-05-24 16:23:56 -04:00
Mike Bayer 9a37503bbe - add forwards-version
Change-Id: Id1652beb13209aac203456c88acff629048e00cc
2017-05-23 15:44:52 -04:00
mike bayer fd7239af69 Merge "Remove twophase for cx_Oracle 6.x" 2017-05-23 15:42:27 -04:00
Mike Bayer 1b98ce355a Remove twophase for cx_Oracle 6.x
Support for two-phase transactions has been removed entirely for
cx_Oracle when version 6.0b1 or later of the DBAPI is in use.  The two-
phase feature historically has never been usable under cx_Oracle 5.x in
any case, and cx_Oracle 6.x has removed the connection-level "twophase"
flag upon which this feature relied.

Change-Id: I2e8161cc2bc12f4845c9224cd483038112fe9734
Fixes: #3997
2017-05-23 15:42:06 -04:00
Mike Bayer f46551de45 Add AttributeEvents.modified
Added new event handler :meth:`.AttributeEvents.modified` which is
triggered when the func:`.attributes.flag_modified` function is
invoked, which is common when using the :mod:`sqlalchemy.ext.mutable`
extension module.

Change-Id: Ic152f1d5c53087d780b24ed7f1f1571527b9e8fc
Fixes: #3303
2017-05-23 15:14:04 -04:00
Mike Bayer a987942761 - add option to disable py.test warnings plugin;
lift cap on py.test.
references: https://github.com/pytest-dev/pytest/issues/2430

Change-Id: Ieb8a6258ba1d15efa570d9cda2b51cf021499a23
2017-05-23 12:24:26 -04:00
mike bayer 1d0067a873 Merge "Add clause adaptation for AliasedClass to with_parent()" 2017-05-23 12:08:51 -04:00
Mike Bayer 7fc7492d86 - add session.close() w/ rationale to top-level "using transactions"
section.  References #3974

Change-Id: Idb650cbe9825cfae893ee917132b5b9d693f0c6c
2017-05-23 11:35:12 -04:00
Mike Bayer 1c692f019b Add clause adaptation for AliasedClass to with_parent()
Fixed bug where :meth:`.Query.with_parent` would not work if the
:class:`.Query` were against an :func:`.aliased` construct rather than
a regular mapped class.  Also adds a new parameter
:paramref:`.util.with_parent.from_entity` to the standalone
:func:`.util.with_parent` function as well as
:meth:`.Query.with_parent`.

Change-Id: Ic684dd63cc90b582c7580c9bba3c92fa3f286da7
Fixes: #3607
2017-05-23 11:13:18 -04:00
Mike Bayer eed7888f85 - pin py.test at 3.0.7 due to https://github.com/pytest-dev/pytest/issues/2430
Change-Id: I587282da141aa6ea92f944eeb4c9e5782d0b5f29
2017-05-23 11:12:22 -04:00
Mike Bayer 024e8b107e - remove .gitattributes and merge=union as this isn't really
working anyway.   need to try something else.

Change-Id: Iabcefa4b66d242acb74a8135c2f5a6a4345441a7
2017-05-22 18:42:17 -04:00
Kataev Denis 42b6ef8ccd Repair formatting throughout documentation
1. Section decorators to [one style](http://docutils.sourceforge.net/docs/ref/rst/restructuredtext.html#sections):
without inset at both side and with same length as text.
2. Fix broken [reference](http://docs.sqlalchemy.org/en/latest/core/type_basics.html#generic-types).
3. Convert tabs to space in some small files.
4. Some python code snippets have python+sql syntax hint.

Change-Id: I39a7a41ef0b0591c6bf1e610748e2b5c19fc5379
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/361
2017-05-22 17:53:09 -04:00
Diana Clarke 990d4c799f detect and raise for version_id is NULL
The versioning feature does not support NULL for the version counter.
An exception is now raised if the version id is programmatic and
was set to NULL for an UPDATE.  Pull request courtesy Diana Clarke.

Fixes: #3673
Change-Id: I8b0da56234a7c7f5e7fde35536e09a6216a5e48a
2017-05-22 16:25:54 -04:00
mike bayer 92f789eba4 Merge "Detect no params w/ manual version_id counter and set to itself" 2017-05-22 16:25:20 -04:00
Mike Bayer 9f0fb6c601 Allow metadata.reflect() to recover from unreflectable tables
Added support for views that are unreflectable due to stale
table definitions, when calling :meth:`.MetaData.reflect`; a warning
is emitted for the table that cannot respond to ``DESCRIBE``
but the operation succeeds.  The MySQL dialect now
raises UnreflectableTableError which is in turn caught by
MetaData.reflect().  Reflecting the view standalone raises
this error directly.

Change-Id: Id8005219d8e073c154cc84a873df911b4a6cf4d6
Fixes: #3871
2017-05-22 15:51:07 -04:00
Mike Bayer 0a67c13052 Detect no params w/ manual version_id counter and set to itself
Fixed bug where programmatic version_id counter in conjunction with
joined table inheritance would fail if the version_id counter
were not actually incremented and no other values on the base table
were modified, as the UPDATE would have an empty SET clause.  Since
programmatic version_id where version counter is not incremented
is a documented use case, this specific condition is now detected
and the UPDATE now sets the version_id value to itself, so that
concurrency checks still take place.

Change-Id: I80e385bffeed4851cc20131cbe983c173a46f655
Fixes: #3996
2017-05-22 14:47:26 -04:00
Mike Bayer da1bc9878b - add a note to versioning that version id col cannot be null,
is not supported.

Change-Id: I3724fea3f2d508210e35827eb1ea17f5e334da19
Fixes: #3673
(cherry picked from commit fcaf17766fdd22e67407e432f7666d63439d7a39)
(cherry picked from commit 8cce3beef7)
2017-05-22 14:33:30 -04:00
Mike Bayer 1a08c41048 Remove "scope" keyword from scoped_session.__call__()
Removed a very old keyword argument from :class:`.scoped_session`
called ``scope``.  This keyword was never documented and was an
early attempt at allowing for variable scopes.

Change-Id: I9a26498a1a66d1eafb0723e98b527688a60f9d9b
Fixes: #3796
2017-05-22 13:00:38 -04:00
Mike Bayer 2574ca4b21 Prevent SQL server isolation level from failing
Fixed bug where SQL Server transaction isolation must be fetched
from a different view when using Azure data warehouse, the query
is now attempted against both views and then a NotImplemented
is raised unconditionally if failure continues to provide the
best resiliency against future arbitrary API changes in new
SQL Server versions.

Change-Id: I621b5089febe8ace136428fa133fde1a7e21cda4
Fixes: #3994
2017-05-22 10:58:08 -04:00
Mike Bayer ccbd68bb3c - add 1.1.11 placeholder
Change-Id: Ia45668f2882ac0e59ade390262b09cbb62ecac0b
2017-05-21 15:24:49 -04:00
Mike Bayer de42925264 - 1.1.10 release date
Change-Id: I6418052571c86b53f44b1a083fca932a65448d95
2017-05-19 16:20:59 -04:00
Mike Bayer 4d4ea792e7 - Document the most transparent way to set JSON.NULL for
a column default.

The JSON.NULL value is special in that while it is a Python-side
value, it represents "do this special behavior", and is not at all
like any other Python-side value for which normally, that's exactly
the type of data we want back.   So in this case, encourage the user
to use a SQL expression that is exact, so in the ORM context, you get
back what was actually persisted in the column.  There's some variants
of this such as literal(JSON.NULL, JSON) but text("'null'") is simpler.

Change-Id: I0339fafdc03e4b2f533d53970b2f74c774f2687b
Fixes: #3923
2017-05-18 17:44:10 -04:00
Mike Bayer 912fb6c2d5 Add new configuration, inspection for baked queries
Added new flag :paramref:`.Session.enable_baked_queries` to the
:class:`.Session` to allow baked queries to be disabled
session-wide, reducing memory use.   Also added new :class:`.Bakery`
wrapper so that the bakery returned by :paramref:`.BakedQuery.bakery`
can be inspected.

Change-Id: I5657af7a99d2b24c89d6aee1343f432728e3f807
2017-05-17 17:08:23 -04:00
Mike Bayer 4c6917e1d6 - add complete parameter /return value docs to session.begin() /
session.begin_nested().  Fixes #3993

Change-Id: If485d77b364c34d94061d2f48efbde3f8a8adec9
2017-05-17 10:58:37 -04:00
Mike Bayer 2869b86ea4 - give SelectinLoader its own bakery, dont use mapper
level cache
- include SelectinLoader itself in the cache key, though
this is currently not critical

Change-Id: I8e4bcd579277fbe53d9c7eca3552a0b8ab9d7a39
2017-05-16 22:13:40 -04:00
Mike Bayer 75c8b88cdd - move additional sections under with_polymorphic missed
in the previous change

Change-Id: I20217d4d4ebfc033229d87e472ad82d32202617a
2017-05-16 11:00:41 -04:00
Mike Bayer 6079158b21 - categorize these two with_polymorphic subsections under with_polymorphic
Change-Id: I8bd49ac241df4b8645c8f78938d6f8122952d75a
2017-05-16 10:51:14 -04:00
Mike Bayer 7aa50b9b19 - fix broken link
Change-Id: I2f3b5ae29600696b34a6afdddc2f94920febf31d
2017-05-16 09:59:38 -04:00
Mike Bayer 5329fc481e modernize and repair inheritance examples
remarkably, the examples for concrete and single were still
using classical mappings.    Ensure all three examples use
modern declarative patterns, each illustrate the identical set
of query operations.  Use back_populates, flat=True for joins,
etc. ensure flake8 linting, correct links and add a link back
from newly reworked inheritance documentation.

Change-Id: I8465a9badbb0eda804f457ccac599f051ee3c27c
2017-05-16 09:51:06 -04:00
mike bayer b569733478 Merge "Demote innerjoin to outerjoin coming from with_polymorphic" 2017-05-12 18:07:49 -04:00
Mike Bayer 94a089bc2b Demote innerjoin to outerjoin coming from with_polymorphic
a with_polymorphic, regardless of inheritance type, represents
multiple classes.  A subclass that wants to joinedload with innerjoin=True
needs to be demoted to an outerjoin because the parent entity rows
might not be of that type.   Looks more intuitive with a joined
inheritance load, but applies just as well to single or concrete.

Change-Id: I4d3d76106ae20032269f8848aad70a8e2f9422f9
Fixes: #3988
2017-05-12 15:18:45 -04:00
Mike Bayer 0f8721fa52 Cascade mappers in terms of the instance's mapper
Fixed a (extremely old) bug in cascade_mappers where the
first cascade we do is against the "self" mapper, and not the
one that actually corresponds to the state given. These are
different in the case where we start with a relationship
to a class, and the instance is of a subclass, which itself
can have relationships that aren't on the base mapper.

A pretty severe bug that somehow has avoided the radar
since the beginning.

Change-Id: I512956b9757b07e06f3ca1ccb507a33fb10bed31
Fixes: #3986
2017-05-12 10:53:54 -04:00
Mike Bayer 4352e220ac Add links to with_only_columns to Select.column, append_column
Provide a brief example for these two methods
indicating that typically a table-bound (or other selectable)
column is appended here, then link to with_only_columns
documentation which has in-depth guidelines already including
that one should not append columns from the current select to itself.

Change-Id: I0742405a7f3c41450d337b9c633519d9cc101dfb
Fixes: #3987
2017-05-12 09:23:44 -04:00
mike bayer 159f595117 Merge "Update inheritance documentation." 2017-05-10 20:26:30 -04:00
Mike Bayer 6194483b73 Update inheritance documentation.
The inheritance documentation is confused, disorganized, and out
of date.  Reorganize and clarify, in particular in preparation
for new inheritance features.

Change-Id: Ibe6a35b4b0432bad866a6afb0598b2cf1b509f10
2017-05-10 20:21:40 -04:00
mike bayer 7455e7eba9 Merge "Add conditionals specific to deferred for expire ro properties" 2017-05-10 14:21:33 -04:00
Mike Bayer c4f28097aa Add conditionals specific to deferred for expire ro properties
Fixed bug where a :func:`.column_property` that is also marked as
"deferred" would be marked as "expired" during a flush, causing it
to be loaded along with the unexpiry of regular attributes even
though this attribute was never accessed.

Change-Id: Iaa9e17b66ece30a8e729e4af746b31ff99b1ec9a
Fixes: #3984
2017-05-10 14:21:07 -04:00
Denis Kataev 3e3554d37c Fix docs syntax error 2017-05-10 17:36:09 +05:00
mike bayer 1ed19fc623 Merge "Use regexp to parse cx_oracle version string" 2017-05-09 15:51:08 -04:00
Mike Bayer 13c2a8a510 Use regexp to parse cx_oracle version string
Fixed bug in cx_Oracle dialect where version string parsing would
fail for cx_Oracle version 6.0b1 due to the "b" character.  Version
string parsing is now via a regexp rather than a simple split.

Change-Id: I2af7172b0d7184e3ea3bd051e9fa8d6ca2a571cd
Fixes: #3975
2017-05-09 12:18:27 -04:00
Jacob Hayes 735fbfdf49 Support autocommit for GRANT and REVOKE on postgresql
Extends `AUTOCOMMIT_REGEXP` for the postgres dialect to include `GRANT` and `REVOKE`.

Change-Id: Iba15f1ebf5bd7bc0fc1193fdf561417e53bf5d57
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/357
2017-05-09 10:34:45 -04:00
Mike Bayer 22570c3181 Protect against cls weakref becoming None
Protected against testing "None" as a class in the case where
declarative classes are being garbage collected and new
automap prepare() operations are taking place concurrently, very
infrequently hitting a weakref that has not been fully acted upon
after gc.

Change-Id: I32e1dfc5ac46bac4127fe808cfd18368e2fad9dd
2017-05-08 18:36:57 -04:00
Mike Bayer a2e7b4c5fa Merge branch 'master' of https://github.com/aflyhorse/sqlalchemy 2017-05-08 17:55:28 -04:00
Mike Bayer 735c0f8414 - add 1.2 forwards-port version
Change-Id: I093f3939be8858a2f327c5ee5884b9629b216855
2017-05-08 17:54:15 -04:00
Mike Bayer 271a098b64 Merge branch 'patch-1' of https://github.com/UnquietCode/sqlalchemy 2017-05-08 16:21:20 -04:00
LunarShaddow 3d19fb6d53 Break the lines to fit pdf and fix another broken syntax 2017-05-08 12:31:50 +08:00
wodim 3380390b7a fix typo 2017-05-05 22:40:16 +02:00
Mike Bayer 654514c5b2 - big rewrite of the Sequence documentation:
1. Sequence should be associated with MetaData always,
except in the really weird case someone is sharing a Sequence
among multiple metadatas.  Make this a "best practice", end the
confusion of #3951, #3979

2. "optional" is not a thing people use, trim this way down

3. remove confusing language

Change-Id: Iab5aec319da2582092fe2615ee50430f76441aff
(cherry picked from commit a1dcf23e371695d8d3be2e1d7875fad10f16a656)
2017-05-05 15:05:20 -04:00
Mike Bayer 8f830d78ba - add another note re: 339e2c13b0
which clarifies that ForeignKey circumvents this logic as a
"convenience".   issue #3978 is updated to address trying to make
this consistent.

Change-Id: I089acaa89f11b7a6310c2bf32916e26eb62ab9c0
2017-05-05 10:39:18 -04:00
Mike Bayer 339e2c13b0 - add a note to MetaData.schema indicating that the Table
will be cataloged in the .tables collection with its fully
qualified name.   Fixes #3978

Change-Id: I65fa063918efc22658e93c39a0680cb83553dec8
2017-05-05 09:19:18 -04:00
LunarShaddow 8e17496421 remove ambiguous line breakers to help sphinx identify code block 2017-05-05 14:38:41 +08:00
Ben Fagin 6224df56a6 fixes a typo 2017-05-01 10:30:11 -07:00
Mike Bayer 69adef7ed5 - typo
Change-Id: Iab741ce3739ed4172196f99c519c9333637383fd
2017-04-28 10:36:15 -04:00
Mike Bayer 36275b0c2d Call proxied collection before invoking creator in associationlist.append()
Improved the association proxy list collection so that premature
autoflush against a newly created association object can be prevented
in the case where ``list.append()`` is being used, and a lazy load
would be invoked when the association proxy accesses the endpoint
collection.  The endpoint collection is now accessed first before
the creator is invoked to produce the association object.

Change-Id: I008a6dbdfe5b1c0dfd02189c3d954d83a65f3fc5
Fixes: #3941
2017-04-28 10:14:09 -04:00
Mike Bayer cedb11925f - keep trying to identify the race here. can reproduce locally
now and it seems like mock might not be doing the right thing.

Change-Id: I5c108d82631c9217da54a8ace68d7728c3e204d8
2017-04-27 17:44:29 -04:00
Mike Bayer 433d2ee9f1 Enforce boolean result type for all eq_, is_, isnot, comparison
Repaired issue where the type of an expression that used
:meth:`.ColumnOperators.is_` or similar would not be a "boolean" type,
instead the type would be "nulltype", as well as when using custom
comparison operators against an untyped expression.   This typing can
impact how the expression behaves in larger contexts as well as
in result-row-handling.

Change-Id: Ib810ff686de500d8db26ae35a51005fab29603b6
Fixes: #3873
2017-04-27 16:08:02 -04:00
Mike Bayer 1b63306a97 - try to work around a race that can occur in STP when
used in this intentionally broken scenario

Change-Id: I88ea6fa710da2189e6d47e2d12f5f0fd6f6bb7d4
2017-04-27 15:26:35 -04:00
Mike Bayer 63ff014070 - ensure that sqlalchemy.ext is set up for importlater
otherwise, it fails if you import from ext before orm:

    from sqlalchemy import *
    from sqlalchemy.ext.declarative import declarative_base
    from sqlalchemy.orm import *

and then do a lazyload, as the ext.baked importlater is not
initialized.

Change-Id: I24dcbfc9ca9022316da28507772562833e45dd95
2017-04-27 14:33:54 -04:00
Mike Bayer 19d2424e05 Add selectin loading
Adding a new kind of relationship loader that is
a cross between the "immediateload" and the "subquery"
eager loader, using an IN criteria to load related items
in bulk immediately after the lead query result is loaded.

Change-Id: If13713fba9b465865aef8fd50b5b6b977fe3ef7d
Fixes: #3944
2017-04-26 16:08:57 -04:00
Mike Bayer 029d0f7538 test / document postgresql_ops against a labeled expression
Since postgresql_ops explicitly states that it expects
string keys, to apply to a function call or expression one
needs to give the SQL expression a label that can be referred
to by name in the dictionary.   test / document this.

Change-Id: I4bc4ade46dac27f9c1b92e7823433292beab97b9
Fixes: #3970
2017-04-24 16:22:29 -04:00
Mike Bayer 6560bf82f3 - edits
Change-Id: If2445c4cbcd7eb18e06823e8821940a391890979
2017-04-22 16:43:31 -04:00
Mike Bayer f36837398c Merge branch 'master' of ssh://gerrit.sqlalchemy.org:29418/zzzeek/sqlalchemy 2017-04-21 18:24:10 -04:00
Mike Bayer e53009e253 - update relationship loader docs, backport from
1.2 wip

Change-Id: I0a3c4a0166f6feed23a021723233d281fad597ec
2017-04-21 18:12:56 -04:00
Mike Bayer 920f77e3c1 Add _negate() to Label to negate inner element
Fixed the negation of a :class:`.Label` construct so that the
inner element is negated correctly, when the :func:`.not_` modifier
is applied to the labeled expression.

Change-Id: Ia99917b2959bdfbff28689c962b4203911c57b85
Fixes: #3969
2017-04-21 13:35:38 -04:00
Mike Bayer ae3ffcf4ea Merge branch 'UnmappedInstanceError_typo_fix' of https://github.com/suever/sqlalchemy 2017-04-17 15:34:46 -04:00
Mike Bayer c2834f9298 - remove errant doctest comment
Change-Id: Idb8520ff807074ceca36645728a63b79d1cdff6c
2017-04-17 15:33:12 -04:00
Mike Bayer 212132958f Accommodate for query._current_path in subq eager load join_depth
Fixed bug in subquery eager loading where the "join_depth" parameter
for self-referential relationships would not be correctly honored,
loading all available levels deep rather than correctly counting
the specified number of levels for eager loading.

Change-Id: Ifa54085cbab3b41c2196f3ee519f485c63e4cb8d
Fixes: #3967
2017-04-17 12:02:18 -04:00
mike bayer 868fa20bc9 Merge "Use baked lazyloading by default" 2017-04-14 10:18:10 -04:00
Mike Bayer b7644319e8 Use baked lazyloading by default
The ``lazy="select"`` loader strategy now makes used of the
:class:`.BakedQuery` query caching system in all cases.  This
removes most overhead of generating a :class:`.Query` object and
running it into a :func:`.select` and then string SQL statement from
the process of lazy-loading related collections and objects.  The
"baked" lazy loader has also been improved such that it can now
cache in most cases where query load options are used.

Change-Id: Ic96792fffaa045ae9aa0a4657d6d29235d3efb85
Fixes: #3954
2017-04-13 14:22:59 -04:00
Mike Bayer c0b85ad6ad Remove MySQL UTC_TIMESTAMP rule
Removed an ancient and unnecessary intercept of the UTC_TIMESTAMP
MySQL function, which was getting in the way of using it with a
parameter.

Change-Id: I6e6b52c051418bcb9d31987e78299310810cb78d
Fixes: #3966
2017-04-13 10:11:41 -04:00
Mike Bayer e3b4042c9c - typos and formatting
Change-Id: I88a304e315b68eded31e91da04265da583bc417b
2017-04-12 16:28:55 -04:00
Mike Bayer 755da17974 - OK, take oracle out of memory-intensive, if it doesn't leak memory
then we get the TNS error from too many connections

Change-Id: Ie685173cd1490d99c5f37a1045e1312c4d9125ea
2017-04-12 16:18:11 -04:00
Mike Bayer bfaef1eaf5 - try one more test, then we're likely going to give up on cx_Oracle
Change-Id: I7f9a1265664b0368ee7a771d01c7ca1612156d1f
2017-04-12 15:28:05 -04:00
Mike Bayer b1f8d46fca - move a few memusage tests out of "backend". something is up w/ cx_Oracle
when the suite runs, such as a background thread or something like that,
which is affecting these tests a bit.

Change-Id: I52d50a44778ec1eecb8e335ae59b1a4773e80a79
2017-04-12 15:15:16 -04:00
Mike Bayer cef4e5ff38 Warn on _compiled_cache growth
Added warnings to the LRU "compiled cache" used by the :class:`.Mapper`
(and ultimately will be for other ORM-based LRU caches) such that
when the cache starts hitting its size limits, the application will
emit a warning that this is a performance-degrading situation that
may require attention.   The LRU caches can reach their size limits
primarily if an application is making use of an unbounded number
of :class:`.Engine` objects, which is an antipattern.  Otherwise,
this may suggest an issue that should be brought to the SQLAlchemy
developer's attention.

Additionally, adjusted the test_memusage algorithm again as the
previous one could still allow a growing memory size to be missed.

Change-Id: I020d1ceafb7a08f6addfa990a1e7acd09f933240
2017-04-12 12:53:40 -04:00
Mike Bayer 1b463058e3 Set up base ARRAY to be compatible with postgresql.ARRAY.
For some reason, when ARRAY was added to the base it was never linked
to postgresql.ARRAY.   Link the two types and also make base
ARRAY the schema event target so that it supports the same
features as postgresql.ARRAY.

Change-Id: I82fa6c9d2b8c5028dba3a009715f7bc296b2bc0b
Fixes: #3964
2017-04-11 10:49:30 -04:00
mike bayer 5b81dbcfa3 Merge "Compare entities also on chop_path" 2017-04-10 14:59:14 -04:00
Mike Bayer 86c43d2e0f Compare entities also on chop_path
When comparing query._current_path to options, the path chop
was not taking into account that the query or the options are
against aliased classes that don't match the mapper.

The issue does not seem to take place for the Load() version
of _chop_path.

Fixed bug to improve upon the specificity of loader options that
take effect subsequent to the lazy load of a related entity, so
that the loader options will match to an aliased or non-aliased
entity more specifically if those options include entity information.

Fixes: #3963
Change-Id: Ifdff37d579042fcc62bdeabce9e2413e9a03fbba
2017-04-10 14:36:16 -04:00
Mike Bayer 7d9f241d63 Add new "expanding" feature to bindparam()
Added a new kind of :func:`.bindparam` called "expanding".  This is
for use in ``IN`` expressions where the list of elements is rendered
into individual bound parameters at statement execution time, rather
than at statement compilation time.  This allows both a single bound
parameter name to be linked to an IN expression of multiple elements,
as well as allows query caching to be used with IN expressions.  The
new feature allows the related features of "select in" loading and
"polymorphic in" loading to make use of the baked query extension
to reduce call overhead.   This feature should be considered to be
**experimental** for 1.2.

Fixes: #3953
Change-Id: Ie708414a3ab9c0af29998a2c7f239ff7633b1f6e
2017-04-07 15:53:49 -04:00
Jonathan Suever 90c72c31a5 Fix of minor typo in the UnmappedInstanceError message 2017-04-06 15:52:10 -04:00
Mike Bayer 93b11905e5 Consider mysql partition options separately from other table options
Move down all the PARTITION, SUBPARTITION options
into a separate segment so that they come out at the
end of CREATE TABLE after the table options.

Change-Id: Iaa1c823848c93680ca22d72bda1b7c49742b9060
Fixes: #3961
2017-04-06 12:12:26 -04:00
Mike Bayer 764126039c - add placeholder for 1.1.10
Change-Id: I068dd3b47dec200740db617891a64798db8f1734
2017-04-06 09:55:04 -04:00
Mike Bayer b39b6023c5 Support Postgresql INTERVAL fields spec/reflection
Added support for all possible "fields" identifiers when reflecting the
Postgresql ``INTERVAL`` datatype, e.g. "YEAR", "MONTH", "DAY TO
MINUTE", etc..   In addition, the :class:`.postgresql.INTERVAL`
datatype itself now includes a new parameter
:paramref:`.postgresql.INTERVAL.fields` where these qualifiers can be
specified; the qualifier is also reflected back into the resulting
datatype upon reflection / inspection.

Change-Id: I33816e68c533b023e0632db6f4e73fefd2de4721
Fixes: #3959
2017-04-05 13:55:10 -04:00
mike bayer 06a90199c5 Merge "Double percent signs based on paramstyle, not dialect" 2017-04-05 13:06:00 -04:00
Mike Bayer 86ef507cc7 Double percent signs based on paramstyle, not dialect
This patch moves the "doubling" of percent signs into
the base compiler and makes it completely a product
of whether or not the paramstyle is format/pyformat or
not.   Without this paramstyle, percent signs
are not doubled across text(), literal_column(), and
column().

Change-Id: Ie2f278ab1dbb94b5078f85c0096d74dbfa049197
Fixes: #3740
2017-04-05 12:18:36 -04:00
mike bayer 1e7b730ce8 Merge "Recognize brackets, quoted_name in SQL Server schema" 2017-04-04 14:28:39 -04:00
Mike Bayer 87b1404eda - 1.1.9 release date
Change-Id: I8d1d55bde6424e4013c5b16bb27d6fc15fa225c2
2017-04-04 14:11:05 -04:00
Mike Bayer 9f82afea25 Recognize brackets, quoted_name in SQL Server schema
The SQL Server dialect now allows for a database and/or owner name
with a dot inside of it, using brackets explicitly in the string around
the owner and optionally the database name as well.  In addition,
sending the :class:`.quoted_name` construct for the schema name will
not split on the dot and will deliver the full string as the "owner".
:class:`.quoted_name` is also now available from the ``sqlalchemy.sql``
import space.

Change-Id: I77491d63ce47638bd23787d903ccde2f35a9d43d
Fixes: #2626
2017-04-04 13:45:06 -04:00
Mike Bayer 0a44f97cb8 Add much more detail to the "unhashable types" change
Change-Id: I34cbf54913b81ef2ae8b2e60f03feb78601460e5
Fixes: 3958
(cherry picked from commit 10a3004f2c)
2017-04-04 13:10:29 -04:00
mike bayer b4686a0f78 Merge "Apply SQL compilation to sqltext for column-level CHECK constraint" 2017-04-04 10:22:32 -04:00
mike bayer e28c3c7ec0 Merge "Ensure we check that SQL expression has an .info attribute" 2017-04-04 10:08:49 -04:00
Mike Bayer 4a4b17e0d3 Apply SQL compilation to sqltext for column-level CHECK constraint
Fixed bug where a column-level :class:`.CheckConstraint` would fail
to compile the SQL expression using the underlying dialect compiler
as well as apply proper flags to generate literal values as
inline, in the case that the sqltext is a Core expression and
not just a plain string.   This was long-ago fixed for table-level
check constraints in 0.9 as part of 🎫`2742`, which more commonly
feature Core SQL expressions as opposed to plain string expressions.

Change-Id: I1301ba4b40063e91bc47726aecc5f4990ffcaeda
Fixes: #3957
2017-04-04 10:02:39 -04:00
Bertrand Janin 6524838950 Fix typo. 2017-04-04 09:11:25 -04:00
Mike Bayer d13734add3 Ensure we check that SQL expression has an .info attribute
Fixed regression released in 1.1.8 due to 🎫`3950` where the
deeper search for information about column types in the case of a
"schema type" or a :class:`.TypeDecorator` would produce an attribute
error if the mapping also contained a :obj:`.column_property`.

Change-Id: I38254834d3d79c9b339289a8163eb4789ec4c931
Fixes: #3956
2017-04-04 09:06:13 -04:00
Mike Bayer 9609f5ffb5 ResultProxy won't autoclose connection until state flag is set
Changed the mechanics of :class:`.ResultProxy` to unconditionally
delay the "autoclose" step until the :class:`.Connection` is done
with the object; in the case where Postgresql ON CONFLICT with
RETURNING returns no rows, autoclose was occurring in this previously
non-existent use case, causing the usual autocommit behavior that
occurs unconditionally upon INSERT/UPDATE/DELETE to fail.

Change-Id: I235a25daf4381b31f523331f810ea04450349722
Fixes: #3955
(cherry picked from commit 8ee363e4917b0dcd64a83b6d26e465c9e61e0ea5)
(cherry picked from commit f52fb5282a)
2017-04-03 21:13:08 -04:00
Mike Bayer d2c733742f - fix version identifier
Change-Id: I63abfb167f54ea2ea2f8bf4ba22ab38b60c5d59c
2017-04-03 17:31:18 -04:00
mike bayer 6dfc5b36b8 Merge "Use consistent method signature for Alias.self_group()" 2017-04-03 12:37:35 -04:00
Mike Bayer 7bb4923391 Use consistent method signature for Alias.self_group()
Fixed bug where the use of an :class:`.Alias` object in a column
context would raise an argument error when it tried to group itself
into a parenthesized expression.   Using :class:`.Alias` in this way
is not yet a fully supported API, however it applies to some end-user
recipes and may have a more prominent role in support of some
future Postgresql features.

Change-Id: I81717e30416e0350f08d1e022c3d84656e0a9735
Fixes: #3939
2017-04-03 12:14:33 -04:00
Mike Bayer 6d7d48af0d Return self when Variant.coerce_compared_value would return impl
Fixed regression released in 1.1.5 due to 🎫`3859` where
adjustments to the "right-hand-side" evaluation of an expression
based on :class:`.Variant` to honor the underlying type's
"right-hand-side" rules caused the :class:`.Variant` type
to be inappropriately lost, in those cases when we *do* want the
left-hand side type to be transferred directly to the right hand side
so that bind-level rules can be applied to the expression's argument.

Change-Id: Ia54dbbb19398549d654b74668753c4152599d900
Fixes: #3952
2017-04-01 13:47:42 -04:00
Mike Bayer b32a0fd286 - 1.1.9 placeholder
Change-Id: Ic7897b5e05d7a20b280d4412d3bdf2ebc85905d4
2017-04-01 11:36:52 -04:00
Mike Bayer 1daacdb408 - 1.1.8 release date
Change-Id: I6243e620e55ad862e8494d64cc754badce25097d
2017-03-31 14:31:13 -04:00
Mike Bayer 07b63894cb Track SchemaEventTarget types in as_mutable()
Fixed bug in :mod:`sqlalchemy.ext.mutable` where the
:meth:`.Mutable.as_mutable` method would not track a type that had
been copied using :meth:`.TypeEngine.copy`.  This became more of
a regression in 1.1 compared to 1.0 because the :class:`.TypeDecorator`
class is now a subclass of :class:`.SchemaEventTarget`, which among
other things indicates to the parent :class:`.Column` that the type
should be copied when the :class:`.Column` is.  These copies are
common when using declarative with mixins or abstract classes.

Change-Id: Ib04df862c58263185dbae686c548fea3e12c46f1
Fixes: #3950
2017-03-30 17:52:10 -04:00
Mike Bayer 4eb4010c1a Apply type processing to untyped preexec default clause
Fixed bug where a SQL-oriented Python-side column default could fail to
be executed properly upon INSERT in the "pre-execute" codepath, if the
SQL itself were an untyped expression, such as plain text.  The "pre-
execute" codepath is fairly uncommon however can apply to non-integer
primary key columns with SQL defaults when RETURNING is not used.

Tests exist here to ensure typing is applied to
a typed expression for default, but in the case of
an untyped SQL value, we know the type from the column,
so apply this.

Change-Id: I5d8b391611c137b9f700115a50a2bf5b30abfe94
Fixes: #3923
2017-03-30 14:58:50 -04:00
Malaclypse The Younger 74f6c21747 Add bindparams support for baked Result count() method
Added support for bound parameters, e.g. those normally set up
via :meth:`.Query.params`, to the :meth:`.baked.Result.count`
method.  Previously, support for parameters were omitted. Pull request
courtesy Pat Deegan.

Change-Id: I8c33548cf2a483699767e459731694c8cadebff6
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/350
2017-03-30 12:33:33 -04:00
Ihor Kalnytskyi a4c17c1397 Docs/faq/performance
Some updates for FAQ/Performance documentation page:

* Fix typo in testing script.
* Populate testing script with one more way to achieve higher performance.

See commit messages for details.

Change-Id: Id6fbf328164b14b3b58ca9616b103a35e72f7b8f
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/345
2017-03-30 10:15:29 -04:00
Sean McCully a86764d99b Support Postgresql development version numbers
Added support for parsing the Postgresql version string for
a development version like "PostgreSQL 10devel".  Pull request
courtesy Sean McCully.

Change-Id: I7bc18bc4d290349c23e9796367b7d694d0873096
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/351
2017-03-29 16:17:30 -04:00
Mike Bayer 6220e09f61 - start changelog for 1.1.8
Change-Id: I6c23f43ca76aeca469980fc8be228af20c2c700d
2017-03-29 16:15:53 -04:00
Mike Bayer cabd14fa15 - reorg migration notes a bit
Change-Id: Id2a727a2a13eb84ad104ab049ae37b9e708af6b5
2017-03-28 09:26:56 -04:00
Mike Bayer f3c368357c - update release date for 1.1.7
Change-Id: I6ce86e2e0c54135194c60d99b433b2f38c467dbd
2017-03-27 17:34:15 -04:00
Mike Bayer a4cdd0bc00 Allow aliased() to be passed to Query.select_entity_from().
An :func:`.aliased()` construct can now be passed to the
:meth:`.Query.select_entity_from` method.   Entities will be pulled
from the selectable represented by the :func:`.aliased` construct.
This allows special options for :func:`.aliased` such as
:paramref:`.aliased.adapt_on_names` to be used in conjunction with
:meth:`.Query.select_entity_from`.

Additionally rewrote the docstring for :meth:`.Query.select_entity_from`,
including starting with explicit use of :func:`.aliased` as the
usual idiomatic pattern.  An example using text().columns() is added
as well as the use case from 🎫`3933` using name matching.

Change-Id: If7e182965236993064a2a086e3b6d55a4f097ca8
Fixes: #3933
2017-03-27 14:39:51 -04:00
mike bayer 6eae79ac55 Merge "Add safe_reraise() + warnings only to Connection._autorollback" 2017-03-27 12:27:56 -04:00
Mike Bayer ecf85cb083 Merge branch 'patch-1' of https://github.com/tamentis/sqlalchemy 2017-03-27 11:30:37 -04:00
Mike Bayer c0a224aba3 Add safe_reraise() + warnings only to Connection._autorollback
Added an exception handler that will warn for the "cause" exception on
Py2K when the "autorollback" feature of :class:`.Connection` itself
raises an exception. In Py3K, the two exceptions are naturally reported
by the interpreter as one occurring during the handling of the other.
This is continuing with the series of changes for rollback failure
handling that were last visited as part of 🎫`2696` in 1.0.12.

Change-Id: I600ba455a14ebaea27c6189889181f97c632f179
Fixes: #3946
2017-03-27 11:14:24 -04:00
Mike Bayer f214f4d4f4 Pre-load alias.c within JoinedEagerLoader cached AliasedClass
Fixed a race condition which could occur under threaded environments
as a result of the caching added via 🎫`3915`.   An internal
collection of ``Column`` objects could be regenerated on an alias
object inappropriately, confusing a joined eager loader when it
attempts to render SQL and collect results and resulting in an
attribute error.   The collection is now generated up front before
the alias object is cached and shared among threads.

Change-Id: I97d5b205992d38af8d2b4307178a15c086ef9993
Fixes: #3947
2017-03-25 22:17:17 -04:00
Mike Bayer 0883d8213b Treat collation names as identifiers
The expression used for COLLATE as rendered by the column-level
:func:`.expression.collate` and :meth:`.ColumnOperators.collate` is now
quoted as an identifier when the name is case sensitive, e.g. has
uppercase characters.  Note that this does not impact type-level
collation, which is already quoted.

Change-Id: I83d5d9cd1e66a4f20b96303bb84c5f360d5d6a1a
Fixes: #3785
2017-03-23 15:31:05 -04:00
Mike Bayer 1fcbc17b7d Support hybrids/composites with bulk updates
The :meth:`.Query.update` method can now accommodate both
hybrid attributes as well as composite attributes as a source
of the key to be placed in the SET clause.   For hybrids, an
additional decorator :meth:`.hybrid_property.update_expression`
is supplied for which the user supplies a tuple-returning function.

Change-Id: I15e97b02381d553f30b3301308155e19128d2cfb
Fixes: #3229
2017-03-22 17:44:56 -04:00
Mike Bayer 28edc2604a Use config.db global opts as defaults for all testing_engine()
Some options need to be passed to engines in all cases,
such as currently the oracle 12516 workaround.   make sure
calls to testing_engine also set up the dictionary with
defaults even if options is passed.    not clear if this affects
other backends yet.

Change-Id: I5a1f7634e4ce5af6fe55dc21a24db6afacd19bb7
2017-03-22 10:13:15 -04:00
Mike Bayer 711d29f8e4 Raise on flag_modified() for non-present attribute
The :func:`.attributes.flag_modified` function now raises
:class:`.InvalidRequestError` if the named attribute key is not
present within the object, as this is assumed to be present
in the flush process.  To mark an object "dirty" for a flush
without referring to any specific attribute, the
:func:`.attributes.flag_dirty` function may be used.

Change-Id: I6c64e4d253c239e38632f38c27bb16e68fe8dfbe
Fixes: #3753
2017-03-21 17:35:12 -04:00
Diana ClarkeandMike Bayer caeb274e28 Allow reuse of hybrid_property across subclasses
The :class:`sqlalchemy.ext.hybrid.hybrid_property` class now supports
calling mutators like ``@setter``, ``@expression`` etc. multiple times
across subclasses, and now provides a ``@getter`` mutator, so that
a particular hybrid can be repurposed across subclasses or other
classes.  This now matches the behavior of ``@property`` in standard
Python.

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Fixes: #3911
Fixes: #3912
Change-Id: Iff033d8ccaae20ded9289cbfa789c376759381f5
2017-03-21 15:42:42 -04:00
Mike Bayer f881dae817 Integrate "pre-ping" into connection pool.
Added native "pessimistic disconnection" handling to the :class:`.Pool`
object.  The new parameter :paramref:`.Pool.pre_ping`, available from
the engine as :paramref:`.create_engine.pool_pre_ping`, applies an
efficient form of the "pre-ping" recipe featured in the pooling
documentation, which upon each connection check out, emits a simple
statement, typically "SELECT 1", to test the connection for liveness.
If the existing connection is no longer able to respond to commands,
the connection is transparently recycled, and all other connections
made prior to the current timestamp are invalidated.

Change-Id: I89700d0075e60abd2250e54b9bd14daf03c71c00
Fixes: #3919
2017-03-20 18:01:23 -04:00
Bertrand Janin 5df05d1670 Fix a title typo
Utilites -> Utilities
2017-03-19 18:05:54 -04:00
Mike Bayer 9e06ab17b9 Merge branch 'master' of https://bitbucket.org/jalessio/sqlalchemy 2017-03-18 14:57:41 -04:00
Paul Brown a40467152c fix pep8 errors in association example
(cherry picked from commit 6aad7fb4217ef294f68f693be5b3137c28184949)
2017-03-18 14:42:48 -04:00
Paul Brown 8dad0f93e8 fix pep8 errors in adjacency_list example
(cherry picked from commit ff230f1862892eb2b479ed85e6858a82159b435f)
2017-03-18 14:42:43 -04:00
Катаев Денис 8f7cf2990f New features from python 2.7
After bump minimum supported version to 2.7 (1da9d37521), we can use new syntax.

Change-Id: Ib064c75a00562e641d132f9c57e5e69744200e05
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/347
2017-03-17 14:19:21 -04:00
mike bayer d96fc5d02a Merge "Implement comments for tables, columns" 2017-03-17 14:16:27 -04:00
Frazer McLeanandMike Bayer fadb8d61ba Implement comments for tables, columns
Added support for SQL comments on :class:`.Table` and :class:`.Column`
objects, via the new :paramref:`.Table.comment` and
:paramref:`.Column.comment` arguments.   The comments are included
as part of DDL on table creation, either inline or via an appropriate
ALTER statement, and are also reflected back within table reflection,
as well as via the :class:`.Inspector`.   Supported backends currently
include MySQL, Postgresql, and Oracle.

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Fixes: #1546
Change-Id: Ib90683850805a2b4ee198e420dc294f32f15d35d
2017-03-17 14:02:15 -04:00
Mike Bayer 9974e9a46b Add bulk_replace event, integrate with @validates
Added new attribute event :meth:`.AttributeEvents.bulk_replace`.
This event is triggered when a collection is assigned to a
relationship, before the incoming collection is compared with the
existing one.  This early event allows for conversion of incoming
non-ORM objects as well.  The event is integrated with the
``@validates`` decorator.

The ``@validates`` decorator now allows the decorated method to receive
objects from a "bulk collection set" operation that have not yet
been compared to the existing collection.  This allows incoming values
to be converted to compatible ORM objects as is already allowed
from an "append" event.   Note that this means that the
``@validates`` method is called for **all** values during a collection
assignment, rather than just the ones that are new.

Change-Id: I27f59db008d9e521d31a3e30143d7cd997e4b7b3
Fixes: #3896
2017-03-16 17:16:49 -04:00
Mike Bayer 63a7b2d2d9 Annotate parentmapper in primaryjoin / secondaryjoin
This patch applies the "parentmapper" annotation to the columns
in the primaryjoin/secondaryjoin, but more dramatically,
also removes all the "deannotate" steps that were historically
applied to the relationship primaryjoin/secondaryjoin.
These deannotation steps were left over from the initial
implementations of annotations where the behaviors were not
as reliable.

By ensuring these annotations are present,
the evaluator no longer needs to do a name-based lookup
when it sees a column that has no "parentmapper",
because it can be assured this is not a mapped column.
This fixes the issue where the expression were based on
a relationship primaryjoin but the name of a column
in the join condition didn't match the attribute name.

Change-Id: I8c1d4594116d4109fef314a87c96a24d2efa0058
Fixes: #3366
2017-03-16 12:34:40 -04:00
Mike Bayer 2bfe19152d Don't mutate old collection on bulk replace
For a bulk replace, assume the old collection is no longer
useful to the attribute system and only send the removal events,
not actually mutated the collection.

this changes behavior significantly and also means that dispose_collection
now receives the old collection intact.

Change-Id: Ic2685c85438191f07797d9ef97833a2cfdc4fcc2
Fixes: #3913
2017-03-15 17:22:59 -04:00
mike bayer b5b6e95748 Merge "Consult _select_from_entity in _adjust_for_single_inheritance" 2017-03-15 17:12:03 -04:00
Mike Bayer 7b056709c0 Consult compiled paramstyle on execute_compiled
Fixed bug where in the unusual case of passing a
:class:`.Compiled` object directly to :meth:`.Connection.execute`,
the dialect with which the :class:`.Compiled` object were generated
was not consulted for the paramstyle of the string statement, instead
assuming it would match the dialect-level paramstyle, causing
mismatches to occur.

Change-Id: I114e4db2183fbb75bb7c0b0641f5a161855696ee
Fixes: #3938
2017-03-15 10:40:30 -04:00
Jamie Alessio 3771af0af4 Fix typos ('expicit' -> 'explicit') 2017-03-14 19:04:03 -07:00
Mike Bayer b6a6ffa4c0 Consult _select_from_entity in _adjust_for_single_inheritance
Fixed bug in single-table inheritance where the select_from()
argument would not be taken into account when limiting rows
to a subclass.  Previously, only expressions in the
columns requested would be taken into account.

Change-Id: Id353c45eade52b264d8f6685a58ba53975669eea
Fixes: #3891
2017-03-14 19:41:21 -04:00
mike bayer 0a35ccc6bd Merge "Add "empty in" strategies; default to "static"" 2017-03-14 19:39:37 -04:00
mike bayer 18b2dea9a4 Merge "Improve serializer behavior" 2017-03-14 19:38:06 -04:00
Mike Bayer b705e19082 - add missing hyperlink for change 3934
Change-Id: I4f6f1d24588f5f8aa8cf8f7f67627a08552d4c93
2017-03-14 17:14:02 -04:00
Mike Bayer f3b6f4f8da Add "empty in" strategies; default to "static"
The longstanding behavior of the :meth:`.Operators.in_` and
:meth:`.Operators.not_in_` operators emitting a warning when
the right-hand condition is an empty sequence has been revised;
a new flag :paramref:`.create_engine.empty_in_strategy` allows an
empty "IN" expression to generate a simple boolean expression, or
to invoke the previous behavior of dis-equating the expression to
itself, with or without a warning.  The default behavior is now
to emit the simple boolean expression, allowing an empty IN to
be evaulated without any performance penalty.

Change-Id: I65cc37f2d7cf65a59bf217136c42fee446929352
Fixes: #3907
2017-03-14 17:01:07 -04:00
Mike Bayer 86cf3eb71c Improve serializer behavior
Fix an issue where the Annotated system needs to have a
__reduce__ method, also see why we can't default to HIGHEST_PROTOCOL.
This latter part might not be a good idea until 1.2 for compatibility
reasons.

Change-Id: I0239e38259fc768c9e3b6c448c29161e271a969c
Fixes: #3918
2017-03-14 16:58:17 -04:00
Mike Bayer 4ece86eb41 Emit after_rollback() event before snapshot removal
The state of the :class:`.Session` is now present when the
:meth:`.SessionEvents.after_rollback` event is emitted, that is,  the
attribute state of objects prior to their being expired.   This is now
consistent with the  behavior of the
:meth:`.SessionEvents.after_commit` event which  also emits before the
attribute state of objects is expired.

Change-Id: I9c572656ec5a9bfaeab817e9c95107c75aca1b51
Fixes: #3934
2017-03-14 15:40:31 -04:00
Mike Bayer 596e322543 Enable sane_multi_rowcount for cx_Oracle
Also add some tests to test_rowcount.

Change-Id: Idaa18fdc4fcfeb615725531c37de77decf76a783
Fixes: #3932
2017-03-14 13:38:12 -04:00
Diana Clarke 2895c57b29 add autoescape option to startswith, endswith, and contains
Fixes: #2694
Change-Id: I34c0bdcb01c2b76b9ab6cd315dae13e3dd8a502b
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/207
2017-03-14 09:49:52 -04:00
Mike Bayer 7b07ea67dc - add ad_hoc_engines to remove RealReconnectTest from oracle
Change-Id: Ie40aeba87dcfe9e8216abb8be050e7c2cc5b5ec9
2017-03-14 09:14:37 -04:00
Mike Bayer 6b0e12fd6f Normalize Oracle reflected FK constraint name
Oracle reflection now "normalizes" the name given to a foreign key
constraint, that is, returns it as all lower case for a case
insensitive name.  This was already the behavior for indexes
and primary key constraints as well as all table and column names.
This will allow Alembic autogenerate scripts to compare and render
foreign key constraint names correctly when initially specified
as case insensitive.

Change-Id: Ibb34ec6ce7cb244d1c4ae9d44ce2d37d37227e69
Fixes: #3276
2017-03-13 19:31:30 -04:00
Mike Bayer 4a886e519f - re-set no ad-hoc-engines for oracle, previously low-connections
disabled this

Change-Id: I3ceceaea7a3969248121ff4dc97c11296831fc99
2017-03-13 18:08:43 -04:00
Mike Bayer 0612829fb0 Add tests for empty association set comparison
This seems to only occur in python 2.6, adding tests
to ensure it stays

Change-Id: Id714680970bf1f70e2fe06b0c8688b7c5a6b6b0c
Fixes: #3265
2017-03-13 14:44:50 -04:00
Mike Bayer fb33f9c54b Repair _execute_scalar for WITH_UNICODE mode
cx_Oracle 5.3 seems to code this flag ON now, so
remove the warning and ensure WITH_UNICODE handling works.

Additionally, the XE setup on jenkins is having more
problems here, in particular low-connections mode is
causing cx_Oracle to fail more frequently now.  Turning
off low-connections fixes those but then we get the
TNS errors, so adding an emergency "retry" flag that
is not yet a feature available to users.  Real world
applications are not dropping/creating thousands of
tables the way our test suite is.

Change-Id: Ie95b0e697276c404d3264c2e624e870463d966d6
Fixes: #3937
2017-03-13 14:16:42 -04:00
Mike Bayer 1da9d37521 - bump minimum python version to 2.7
- add placeholder 1.2 release documentation, update intro numbers

Change-Id: I9f9969cbb9e95c2f750a5c16798e92c35a5ef6cf
2017-03-10 14:28:49 -05:00
Mike Bayer e82df50d98 - begin the 1.2 branch in master, diverge from 1.1
Change-Id: I446f7528046873bf2d547daec043737b1bffe5f4
2017-03-10 14:08:31 -05:00
Mike Bayer 75ceae6ea6 - add a note as to why we have this very complicated Annotated
system

Change-Id: I7d4048b92fcd3a7c7630c43aa9390d983f447c0a
2017-03-09 17:38:21 -05:00
Mike Bayer c04870ba7b Allow SchemaType and Variant to work together
Added support for the :class:`.Variant` and the :class:`.SchemaType`
objects to be compatible with each other.  That is, a variant
can be created against a type like :class:`.Enum`, and the instructions
to create constraints and/or database-specific type objects will
propagate correctly as per the variant's dialect mapping.

Also added testing for some potential double-event scenarios
on TypeDecorator but it seems usually this doesn't occur.

Change-Id: I4a7e7c26b4133cd14e870f5bc34a1b2f0f19a14a
Fixes: #2892
2017-03-07 16:24:18 -05:00
Mike Bayer 9e62715973 Repair missing "checkfirst" for test suite
the test_metadata tests trigger the before_create dispatch without
the checkfirst flag.  Postgresql backend should be able to
tolerate this.

Change-Id: Ife497cc3a4eb2812462116f94aad732864225f3f
2017-03-07 15:00:18 -05:00
Mike Bayer 74bec18c2a - document ForeignKeyConstraint columns / elements, fixes #2904
Change-Id: Ia50a3100d1bd88020c30224932b16aeadd7f4c75
2017-03-07 14:54:53 -05:00
mike bayer b54cefc379 Merge "Don't cache savepoint identifiers" 2017-03-06 19:12:40 -05:00
Mike Bayer f4c4f784cd Don't cache savepoint identifiers
Fixed bug in compiler where the string identifier of a savepoint would
be cached in the identifier quoting dictionary; as these identifiers
are arbitrary, a small memory leak could occur if a single
:class:`.Connection` had an unbounded number of savepoints used,
as well as if the savepoint clause constructs were used directly
with an unbounded umber of savepoint names.   The memory leak does
**not** impact the vast majority of cases as normally the
:class:`.Connection`, which renders savepoint names with a simple
counter starting at "1", is used on a per-transaction or
per-fixed-number-of-transactions basis before being discarded.

The savepoint name in virtually all cases does not require quoting
at all, however to support potential third party use cases
the "check for quotes needed" logic is retained, at a small
performance cost.   Uncondtionally quoting the name is another
option, but this would turn the name into a case sensitive name
which runs the risk of poor interactions with existing deployments
that may be looking at these names in other contexts.

Change-Id: I6b53c96abf7fdf1840592bbca5da81347911844c
Fixes: #3931
2017-03-06 17:20:06 -05:00
Mike Bayer 3a6b75870b - update asktom link, fixes #3925
Change-Id: Ibd63311dfccebbdf67e8ad7dc56ad311bf573895
2017-03-06 16:50:13 -05:00
Mike Bayer 66e483ebdc Update profiles for psycopg2 2.7
psycopg2 has updated their unicode / string handling, greatly
reducing callcounts on Python 2.x.

Change-Id: Idffd242b303ffea9c7733068a4be290da4dbe679
2017-03-06 16:10:57 -05:00
Mike Bayer b4e880534e Only use schema_translate_map on SchemaItem subclasses
Fixed bug in new "schema translate" feature where the translated schema
name would be invoked in terms of an alias name when rendered along
with a column expression; occurred only when the source translate
name was "None".   The "schema translate" feature now only takes
effect for :class:`.SchemaItem` and :class:`.SchemaType` subclasses,
that is, objects that correspond to a DDL-creatable structure in
a database.

Change-Id: Ie8cb35aeaba2c67efec8c8c57c219e4dd346e44a
Fixes: #3924
2017-02-28 14:52:28 -05:00
Mike Bayer ff2090336f - 1.1.7 prep
Change-Id: I7d738e194339ffd6edf3ff6a078808fc5251fe50
2017-02-28 14:49:04 -05:00
Mike Bayer d8080933f5 - 1.1.6 2017-02-28 11:41:24 -05:00
Hanno Schlichting b2820e190f Add new reserved words for MySQL 8.0 (beta).
Based on https://dev.mysql.com/doc/refman/8.0/en/keywords.html#table-keywords-new-8.0

Change-Id: I128c93520e57331e0ec4d40b0c0e752bf9b982d9
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/346
2017-02-28 11:11:58 -05:00
Mike Bayer fe1cabb88a Performance within instances()
Continuing from Ie43beecf37945b2bb7fff0aaa597a597293daa18,
also observed is the overhead of PathRegsitry memoized token
functions, as these paths are not cached in the case of
long joinedloader chains.  The memoizations here were made
with short paths in mind, and have been replaced with
an inlined straight create of these paths up front, producing
callcounts very similar to 0.8. Combined with the previous
optimizations, 1.1 now runs the "joined eager load of one row"
worst case test in about 40% fewer calls than 0.8 and 60%
fewer than 1.1.5.

Change-Id: Ib5e1c1345a1dd8edfbdb3fed06eb717d4e164d31
Fixes: #3915
2017-02-23 16:56:20 -05:00
mike bayer 4c5cfa8bc6 Merge "Memoize AliasedClass, ClauseAdapter objects in joined eager load" 2017-02-22 17:16:28 -05:00
Mike Bayer 42bb865689 - add test for inserting PG array w/ NULL, references #3916
Change-Id: I87be274c1ba019b41744a5a76c1b5e9334564ec8
2017-02-16 13:00:28 -05:00
Mike Bayer 1a7e8d77ba Memoize AliasedClass, ClauseAdapter objects in joined eager load
Addressed some long unattended performance concerns within the
joined eager loader query construction system.  The use of ad-hoc
:class:`.AliasedClass` objects per query, which produces lots of column
lookup overhead each time, has been replaced with a cached approach
that makes use of a small pool of :class:`.AliasedClass` objects
that are reused between invocations of joined eager loading.
Callcount reduction of SQL query generation for worst-case joined
loader scenarios (lots of joins, lots of columns) is reduced by
approximately 270%.

Change-Id: Ie43beecf37945b2bb7fff0aaa597a597293daa18
Fixes: #3915
2017-02-16 11:31:26 -05:00
Mike BayerFrazer McLeanPaweł Stiasny
3b6004e6ab Add new DDL autocommit expressions for Postgresql
Added regular expressions for the "IMPORT FOREIGN SCHEMA",
"REFRESH MATERIALIZED VIEW" Postgresql statements so that they
autocommit when invoked via a connection or engine without
an explicit transaction.  Pull requests courtesy Frazer McLean
and Paweł Stiasny.

Fixes: #3840
Co-authored-by: Frazer McLean
Co-authored-by: Paweł Stiasny
Change-Id: I92b2b61683d29d57fa23a66a3559120cb1241c2f
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/323
2017-02-13 14:45:40 -05:00
Mike Bayer f107dd78ec - limit to MySQL dialect
Change-Id: I2781e1e2221d89c75dd65ff49490d9c409967930
2017-02-13 14:40:55 -05:00
Mike Bayer 4e54f9fc07 - pull autocommit suite into the mysql suite as well
Change-Id: If1106f7f125739e69ad2482f65b8f37672a76c9e
2017-02-13 14:33:21 -05:00
Mike Bayer 02ae6ab3fd - add a test suite that ensures textual autocommit works
for correct expressions

Change-Id: I17d35169be914924828487abba05658dff380f2a
2017-02-13 14:17:11 -05:00
Grzegorz Makarewicz aa3b59af54 pytds based connector for MS-SQL 2017-02-12 20:10:43 +01:00
Mike Bayer 540bcff90d Check for columns not part of mapping, correct mapping for eager_defaults
Fixed two closely related bugs involving the mapper eager_defaults
flag in conjunction with single-table inheritance; one where the
eager defaults logic would inadvertently try to access a column
that's part of the mapper's "exclude_properties" list (used by
Declarative with single table inheritance) during the eager defaults
fetch, and the other where the full load of the row in order to
fetch the defaults would fail to use the correct inheriting mapper.

Fixes: #3908
Change-Id: Ie745174c917d512e2c46d9e3cc14512cde53cc9a
2017-02-09 10:49:13 -05:00
Mike Bayer 000e960306 Don't post-SELECT columns w/o a server default/onupdate for eager_defaults
Fixed a major inefficiency in the "eager_defaults" feature whereby
an unnecessary SELECT would be emitted for column values where the
ORM had explicitly inserted NULL, corresponding to attributes that
were unset on the object but did not have any server default
specified, as well as expired attributes on update that nevertheless
had no server onupdate set up.   As these columns are not part of the
RETURNING that eager_defaults tries to use, they should not be
post-SELECTed either.

Change-Id: I0d4f1e9d3d9717d68dcc0592f69456a1f1c36df8
Fixes: #3909
2017-02-08 22:00:28 -05:00
Mike Bayer 7db699163b - document Query.with_session(), direct constructor usage
Change-Id: I47499d040623202dd9b3be0ea65f2d9ad03c11a4
2017-02-08 17:47:29 -05:00
Khairi Hafsham 772374735d Make all tests to be PEP8 compliant
tested using pycodestyle version 2.2.0

Fixes: #3885
Change-Id: I5df43adc3aefe318f9eeab72a078247a548ec566
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/343
2017-02-07 11:21:56 -05:00
mike bayer d71f4b4718 Merge "Accept FetchedValue, text() for column "default" value" 2017-02-01 18:13:06 -05:00
Mike Bayer 8342ca6c69 - add a note referring to the enum value as not currently persisted,
reference #3906

Change-Id: I2274c356cc88cd011c5a34a69e75a2548a93e87a
2017-02-01 18:09:45 -05:00
Mike Bayer 388d8db68d Accept FetchedValue, text() for column "default" value
Fixed bug whereby the :meth:`.DDLEvents.column_reflect` event would not
allow a non-textual expression to be passed as the value of the
"default" for the new column, such as a :class:`.FetchedValue`
object to indicate a generic triggered default or a
:func:`.sql.expression.text` construct.  Clarified the documentation
in this regard as well.

Fixes: #3905

Change-Id: I829796c3e9f87f375149bebee7eef133a6876d4d
2017-02-01 17:00:42 -05:00
Mike Bayer 6b27d78030 - clarify Enum validation rules, fixes #3904
Change-Id: I221f161ae77ee1b9487329330bc520ab65e97611
2017-02-01 16:39:48 -05:00
Mike Bayer 9a5943bf76 Union the exclude_properties of the inheriting mapper in declarative
Fixed bug where the "automatic exclude" feature of declarative that
ensures a column local to a single table inheritance subclass does
not appear as an attribute on other derivations of the base would
not take effect for multiple levels of subclassing from the base.

Change-Id: Ibf67b631b4870dd1bd159f7d6085549d299fffe0
Fixes: #3895
2017-01-30 17:28:22 -05:00
mike bayer 5ef2fde8fb Merge "Add count(), scalar() to baked query" 2017-01-30 17:27:21 -05:00
Mike Bayer ecfda6512c Add count(), scalar() to baked query
Change-Id: I8af0d7b41ae2df384ce5d0ef274732352d81f376
Fixes: #3897
2017-01-30 13:02:29 -05:00
Jeong YunWon f411cac350 Fix nested index_property setter when there is no container value
Fixed bug in new :mod:`sqlalchemy.ext.indexable` extension
where setting of a property that itself refers to another property
would fail.

Fixes: #3901
Change-Id: I203a66117e2399afee11a34f43f0e93adfc6d571
2017-01-30 12:59:54 -05:00
Mike Bayer 1c578a710f Copy whereclause / using in ExcludeConstraint
Fixed bug in Postgresql :class:`.ExcludeConstraint` where the
"whereclause" and "using" parameters would not be copied during an
operation like :meth:`.Table.tometadata`.

Change-Id: I2f704981d4d4862f9c82a50272006fab8becebb6
Fixes: #3900
2017-01-30 12:10:16 -05:00
Mike Bayer f55d466cad - add missing param tag
Change-Id: Ic2cc0bdafbf3f1bc2993a9ad3475530eed91d0f1
2017-01-28 09:53:10 -05:00
Mike Bayer 5c26cfcb47 - cte() has moved to HasCTE(), since SelectBase is referred to
a lot just add inherited members so links to things like SelectBase.cte
continue to function

Change-Id: Ib57948d576d2063e10b0f528a5deaf07ea262322
2017-01-28 09:43:40 -05:00
Mike Bayer 3bd845f3ff - remove misleading comment, ref #3902
Change-Id: I481628146ff31bc9ea2f8a3687f375832b17e501
2017-01-27 12:08:57 -05:00
Mike Bayer 3757c0cdfb Don't check isolation level prior to SQL Server 2005
Added a version check to the "get_isolation_level" feature, which is
invoked upon first connect, so that it skips for SQL Server version
2000, as the necessary system view is not available prior to SQL Server
2005.

Change-Id: If4f860513f0aae6625803f449714aedfc5075f57
Fixes: #3898
2017-01-26 16:54:02 -05:00
Mike Bayer a24801ae8d - document that "column" and "where" are arbitrary SQL expressions
for ExcludeConstraint, if string is used then quoting must
be applied manually.  fixes #3899

Change-Id: I5885c90179e4056b84fc4776464bba7c8c70a80a
2017-01-26 16:01:20 -05:00
Mike Bayer 0d91796bb3 Merge branch 'doc_typo' of https://bitbucket.org/fredj/sqlalchemy 2017-01-24 17:36:49 -05:00
Mike Bayer 6e83259e7f Merge branch 'patch-1' of https://github.com/jeffwidman/sqlalchemy 2017-01-24 17:35:16 -05:00
Mike Bayer 0cc5561c93 Merge branch 'fix-example-re' of https://github.com/demoray/sqlalchemy 2017-01-24 17:33:01 -05:00
Frederic Junod 8795472c87 Fix typo in documentation 2017-01-20 09:52:15 +01:00
mike bayer 81518ae2e2 Merge "Dont set _set_select_from() for alias object" 2017-01-19 16:28:58 -05:00
Mike BayerandStéphane Raimbault 42027de3fc Improve server-side Sequence documentation
Include the metadata argument for the Sequence
and explain the rationale.  Correct inconsistencies
between Core / ORM examples and update language
regarding client side vs. server side Sequence
directive.

Co-authored-by: Stéphane Raimbault <stephane.raimbault@gmail.com>
Change-Id: I65c522acf9bdf25041a5baf2e10be41f0927999a
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/341
2017-01-19 14:43:13 -05:00
Mike Bayer 4ae02f46e9 Dont set _set_select_from() for alias object
Fixed bug first introduced in 0.9.7 as a result of 🎫`3106`
which would cause an incorrect query in some forms of multi-level
subqueryload against aliased entities, with an unnecessary extra
FROM entity in the innermost subquery.

Fixes: #3893

Change-Id: Ic4003c2c1c0206bd22a098fd497a7375c2758305
2017-01-19 13:49:08 -05:00
Mike Bayer 17b85b3445 - 1.1.6 prep
Change-Id: I95b9af4987ad26653a36bccfc88828ff22ce896b
2017-01-19 11:49:13 -05:00
Mike Bayer 6078165993 - 1.1.5 2017-01-17 16:23:00 -05:00
Mike Bayer 18d0509c75 - 1.0.17 release date 2017-01-17 16:22:28 -05:00
Mike Bayer 92385b6e1c Merge branch 'master' into rel_1_1 2017-01-17 16:19:54 -05:00
Mike Bayer 2f86267f07 - this test is too brittle under load, not worth it, remove it
Change-Id: I3f294b4d153979c308532360d03ab7be3c5d994a
2017-01-17 16:19:43 -05:00
Mike Bayer a75524561c Merge branch 'master' into rel_1_1 2017-01-17 15:51:18 -05:00
Mike Bayer f2028dc5af - further changes to avoid pytest warnings
Change-Id: Ia83a996ff97a6ba54a0666a32241e570f3852ab4
2017-01-17 15:51:02 -05:00
Mike Bayer 984235a12d Merge branch 'master' into rel_1_1 2017-01-17 14:42:35 -05:00
Gábor Lipták f624a3ae8b Correct pytest deprecation warning
WC1 None [pytest] section in setup.cfg files is deprecated, use [tool:pytest] instead.

Change-Id: I099c8207730ae1226f7357ff8be0d8ab149878ed
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/334
2017-01-17 12:13:34 -05:00
Mike Bayer dc66790e84 Merge branch 'master' into rel_1_1 2017-01-17 12:08:49 -05:00
Mike Bayer 3a6c55fb51 - repair an errant docstring w/o r
Change-Id: I2e9c8dbc79c00b54520748d1d7cae5230a612c96
2017-01-17 12:08:38 -05:00
Mike Bayer f7c8b08bd2 Merge branch 'master' into rel_1_1 2017-01-17 11:45:26 -05:00
Mike Bayer 5c2ef5b542 - update copyright in .c files
Change-Id: If905d1bc026b688ec7203674ff14c72bc4906abf
2017-01-17 11:45:18 -05:00
Mike Bayer a0de2bfa10 Merge branch 'master' into rel_1_1 2017-01-17 10:48:39 -05:00
mike bayer 99d65925e6 Merge "Parse (but don't record) COMMENT portion of MySQL table key" 2017-01-17 10:47:33 -05:00
Lele Long bd6ba3ac82 Parse (but don't record) COMMENT portion of MySQL table key
The MySQL dialect now will not warn when a reflected column has a
"COMMENT" keyword on it, but note however the comment is not yet
reflected; this is on the roadmap for a future release.  Pull request
courtesy Lele Long.

Fixes: #3867
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/324
Change-Id: I869e29aba6766d0eda1e59af09a3e8e3748a3942
2017-01-17 10:23:07 -05:00
Joseph Schorr 1f407c2a47 Add support for prefixes on CREATE INDEX statements in MySQL
Added a new parameter ``mysql_prefix`` supported by the :class:`.Index`
construct, allows specification of MySQL-specific prefixes such as
"FULLTEXT". Pull request courtesy Joseph Schorr.

Change-Id: I5a21fa466fdfd4d9e39e1fb4ecec1eab93b92c36
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/339
2017-01-17 10:21:47 -05:00
Mike Bayer 00b24eb0f4 Merge branch 'master' into rel_1_1 2017-01-16 16:28:01 -05:00
Mike Bayer 46828cc157 - correctly document LIKE / ILIKE, fixes #3890
Change-Id: Ie59e61f53d7c59a4777ab9e6e75a43c71d67523b
2017-01-16 16:27:48 -05:00
Mike Bayer 751887ad6e Merge branch 'master' into rel_1_1 2017-01-16 15:57:25 -05:00
mike bayer d8198c2d87 Merge "Better hide engine password" 2017-01-16 15:56:02 -05:00
Valery Yundin bccc1419a6 Better hide engine password
Avoid putting engine password in the exception message in
`MetaData.reflect` (since exception messages often appear in logs).
Use the same redacted `__repr__` implementation in
`TLEngine` as in its base class `Engine`

Change-Id: Ic0a7baea917a9c8d87dffdd82ef566673ab08e02
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/327
2017-01-16 14:02:26 -05:00
Mike Bayer 2e610cf155 Merge branch 'master' into rel_1_1 2017-01-16 14:00:50 -05:00
Mike Bayer 3aefc6e8a4 Add "existing" populators for subqueryload
Fixed bug in subquery loading where an object encountered as an
"existing" row, e.g. already loaded from a different path in the
same query, would not invoke subquery loaders for unloaded attributes
that specified this loading.  This issue is in the same area
as that of 🎫`3431`, 🎫`3811` which involved
similar issues with joined loading.

Change-Id: If111a76b0812010905b0ac811276a816779d297f
Fixes: #3854
2017-01-16 13:16:25 -05:00
Mike Bayer 67a0fd1fb7 Merge branch 'master' into rel_1_1 2017-01-16 09:21:13 -05:00
Mike Bayer 710ce4aaf9 - fix changelog
Change-Id: Ib1da230f6fd691753c4a5056b165d7397d198b09
2017-01-16 09:21:06 -05:00
Mike Bayer ff2b4adfd7 - fix changelog
Change-Id: Idca0cab9d2ffdf498cc57bee9d215b9f4b72ef13
2017-01-16 09:19:15 -05:00
mike bayer 9ef1913ed6 Merge "Use full column->type processing for ON CONFLICT SET clause" 2017-01-13 15:47:00 -05:00
mike bayer 2c13aa097b Merge "Support python3.6" 2017-01-13 15:41:20 -05:00
Mike Bayer afd78a37da Use full column->type processing for ON CONFLICT SET clause
Fixed bug in new "ON CONFLICT DO UPDATE" feature where the "set"
values for the UPDATE clause would not be subject to type-level
processing, as normally takes effect to handle both user-defined
type level conversions as well as dialect-required conversions, such
as those required for JSON datatypes.   Additionally, clarified that
the keys in the set_ dictionary should match the "key" of the column,
if distinct from the column name.  A warning is emitted
for remaining column names that don't match column keys; for
compatibility reasons, these are emitted as they were previously.

Fixes: #3888
Change-Id: I67a04c67aa5f65e6d29f27bf3ef2f8257088d073
2017-01-13 14:33:42 -05:00
Mike BayerandAndrii Soldatenko fa6dd376bb Support python3.6
Corrects some warnings and adds tox config.  Adds DeprecationWarning
to the error category.   Large sweep for string literals w/ backslashes
as this is common in docstrings

Co-authored-by: Andrii Soldatenko
Fixes: #3886
Change-Id: Ia7c838dfbbe70b262622ed0803d581edc736e085
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/337
2017-01-13 10:57:41 -05:00
Mike Bayer 0460bc79d9 - document how to use autocommit isolation level for CONCURRENTLY,
fixes #3887

Change-Id: I6d1a13b7bb4169204105c7a100d17cfed3ded9d1
2017-01-12 15:57:46 -05:00
mike bayer 073506bc55 Merge "Pass **kw to bound params in multi values" 2017-01-12 08:38:39 -05:00
Carlos García Montoro c703b9ce89 Set autoincrement to False; use sqlite_autoincrement in versioned_history
Ensure that the history table sets autoincrement=False, since these values
are copied in all cases; the flag will emit an error as of 1.1 if the
primary key is composite.   Additionally, use the sqlite_autoincrement flag
so that SQLite uses unique primary key identifiers for new rows even if
some rows have been deleted.

Fixes: #3872
Change-Id: I65912eb394b3b69d7f4e3c098f4f948b0a7a5374
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/93
2017-01-09 18:00:33 -05:00
mike bayer e251f64d68 Merge "Adapt from "localparent" in joinedloader" 2017-01-09 17:42:03 -05:00
Mike Bayer 4fec72f178 Pass **kw to bound params in multi values
Fixed bug where literal_binds compiler flag was not honored by the
:class:`.Insert` construct for the "multiple values" feature; the
subsequent values are now rendered as literals.

Change-Id: I81ac358fd59995885d482e7571620090210865d2
Fixes: #3880
2017-01-09 17:37:25 -05:00
mike bayer e6eefc0c5e Merge "Tighten rules for order_by(Label) resolution" 2017-01-09 14:25:13 -05:00
mike bayer bc4a96836d Merge "update for 2017 copyright" 2017-01-09 14:24:46 -05:00
Mike Bayer 51a72503b0 Adapt from "localparent" in joinedloader
Fixed bug involving joined eager loading against multiple entities
when polymorphic inheritance is also in use which would throw
"'NoneType' object has no attribute 'isa'".  The issue was introduced
by the fix for 🎫`3611`.

Change-Id: I296ecda38c01ec8f69dcd843beaebed6949cecfa
Fixes: #3884
2017-01-09 14:16:22 -05:00
Mike Bayer 6b489db899 Tighten rules for order_by(Label) resolution
- Fixed bug originally introduced in 0.9 via 🎫`1068` where
order_by(<some Label()>) would order by the label name based on name
alone, that is, even if the labeled expression were not at all the same
expression otherwise present, implicitly or explicitly, in the
selectable.  The logic that orders by label now ensures that the
labeled expression is related to the one that resolves to that name
before ordering by the label name; additionally, the name has to
resolve to an actual label explicit in the expression elsewhere, not
just a column name.  This logic is carefully kept separate from the
order by(textual name) feature that has a slightly different purpose.

Change-Id: I44fc36dab34380cc238c1e79ecbe23f1628d588a
Fixes: #3882
2017-01-06 17:56:41 -05:00
Mike Bayer 2b4d028a69 - add a section for ARRAY of JSON to complement ARRAY of ENUM. references #3467
Change-Id: I9836b842be01ef24138071fa022d80f5f77be14f
2017-01-05 10:03:55 -05:00
Mike Bayer 64e72b58fd update for 2017 copyright
Change-Id: I4e8c2aa8fe817bb2af8707410fa0201f938781de
2017-01-04 12:39:24 -05:00
plumSemPy cd95d4a5b9 Ensure session.no_autoflush uses finally
The :attr:`.Session.no_autoflush` context manager now ensures that
the autoflush flag is reset within a "finally" block, so that if
an exception is raised within the block, the state still resets
appropriately.  Pull request courtesy Emin Arakelian.

Change-Id: Ib19ddf32074b1df82a6a1f1ae14e3a962cd31a5f
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/335
2017-01-04 12:12:52 -05:00
mike bayer a030bc9f17 Merge "Correct any_, all_ spelling" 2016-12-28 16:50:09 -05:00
Mike Bayer f0e9469939 - fix bad merge to changelog
Change-Id: I1e7444d722414627ba2a31bce13bd737950abb0c
2016-12-28 16:15:22 -05:00
Mike Bayer 04d799863f Correct any_, all_ spelling
- Fixed 1.1 regression where "import *" would not work for
sqlalchemy.sql.expression, due to mis-spelled "any_" and "all_"
functions.

Change-Id: I25d1cd34c9239dbdcdb1889c5cda2474557e1418
Fixes: #3878
2016-12-28 16:14:31 -05:00
Jeff Widman 7083168295 Fix typo 2016-12-24 02:34:24 -08:00
Francisco Capdevila 8f191ec3b8 Typo 2016-12-22 15:08:23 -03:00
Mike Bayer f472405e59 Don't select lastrowid for inline=True
- Fixed bug where SQL Server dialects would attempt to select the
last row identity for an INSERT from SELECT, failing in the case when
the SELECT has no rows.  For such a statement,
the inline flag is set to True indicating no last primary key
should be fetched.

Change-Id: Ic40d56d9eadadc3024a4d71245f9eed4c420024a
Fixes: #3876
2016-12-21 13:41:25 -05:00
Mike Bayer d5bb919aa6 Call nextval() on sequence when doing INSERT from SELECT
Fixed bug where an INSERT from SELECT where the source table contains
an autoincrementing Sequence would fail to compile correctly.

Change-Id: I41eb9f65789a4007712ae61ed5fa23a9839a5128
Fixes: #3877
2016-12-21 13:39:56 -05:00
Mike Bayer afb3a52833 - these two tests require sane rowcount at the base
Change-Id: I7efcfb56826963e4702d19107db3c9d37c4fcb64
2016-12-21 10:31:33 -05:00
Mike Bayer c19ebfc3dc Use session for exec check
This was using a different connection which could deadlock on
SQL Server.

Change-Id: Ia7953f362c99d9247dd47c3f5c3b0b91c96db1a5
2016-12-21 10:20:19 -05:00
Mike Bayer 910347aef2 Bump "table compression" flag to Oracle 10.1
- Fixed bug where the "COMPRESSION" keyword was used in the ALL_TABLES
query on Oracle 9.2; even though Oracle docs state table compression
was introduced in 9i, the actual column is not present until
10.1.

Change-Id: Iebfa59bfcfdff859169df349a5426137ab006e67
Fixes: #3875
2016-12-20 09:15:55 -05:00
Mike Bayer 675f021368 Add real .entities to _BundleEntity
Fixed bug where the single-table inheritance query criteria would not
be inserted into the query in the case that the :class:`.Bundle`
construct were used as the selection criteria.

Change-Id: Ib7c128ceef5c3220a098cdfd0270c43a2a67716d
Fixes: #3874
2016-12-19 12:41:28 -05:00
Brian 3c0fc9b95f fix example re such that the listen modifier example works 2016-12-17 12:09:13 -05:00
Mike Bayer a1de76c42f - xmin example requires a server default declaration to function
correctly

Change-Id: I1cc50da6fe1c0eeef1d00201b45d998daddfd8ac
2016-12-12 12:07:11 -05:00
Mike Bayer 55ad10370f Add _extend_on deduplicating set for metadata.reflect()
The "extend_existing" option of :class:`.Table` reflection would
cause indexes and constraints to be doubled up in the case that the parameter
were used with :meth:`.MetaData.reflect` (as the automap extension does)
due to tables being reflected both within the foreign key path as well
as directly.  A new de-duplicating set is passed through within the
:meth:`.MetaData.reflect` sequence to prevent double reflection in this
way.

Change-Id: Ibf6650c1e76a44ccbe15765fd79df2fa53d6bac7
Fixes: #3861
2016-11-23 10:31:56 -05:00
Ionuț Ciocîrlan 868e98bf40 Allow the value 0 for Postgresql TIME/TIMESTAMP precision
Change-Id: Ie38c48369222d95849645f027e2c659f503cfd53
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/322
2016-11-23 09:48:34 -05:00
Mike Bayer df9b6492e5 Ensure Variant passes along impl right-hand type
Fixed issue in :class:`.Variant` where the "right hand coercion" logic,
inherited from :class:`.TypeDecorator`, would
coerce the right-hand side into the :class:`.Variant` itself, rather than
what the default type for the :class:`.Variant` would do.   In the
case of :class:`.Variant`, we want the type to act mostly like the base
type so the default logic of :class:`.TypeDecorator` is now overridden
to fall back to the underlying wrapped type's logic.   Is mostly relevant
for JSON at the moment.

This patch additionally adds documentation and basic tests to allow
for backend-agnostic comparison of JSON index elements to other objects.
A future version should attempt to improve upon this by providing
"astext", "asint" types of operators.

Change-Id: I7b7b45d604a4ae8d1dc236a5a1248695aab5232e
Fixes: #3859
2016-11-22 16:39:16 -05:00
Mike Bayer 7de0d17853 Disable single-inheritance critera on the outside of UNION
Fixed bug related to 🎫`3177`, where a UNION or other set operation
emitted by a :class:`.Query` would apply "single-inheritance" criteria
to the outside of the union (also referencing the wrong selectable),
even though this criteria is now expected to
be already present on the inside subqueries.  The single-inheritance
criteria is now omitted once union() or another set operation is
called against :class:`.Query` in the same way as :meth:`.Query.from_self`.

Change-Id: I0fd1331c7ba85a758a1c15e06c271914f2c717f3
Fixes: #3856
2016-11-18 11:53:33 -05:00
Mike Bayer 68d3018cee Port lower case quoted name fix to firebird
Ported the fix for Oracle quoted-lowercase names to Firebird, so that
a table name that is quoted as lower case can be reflected properly
including when the table name comes from the get_table_names()
inspection function.

Also genericize the test to the test suite for denormlized name
dialects.

Fixes: #3548

Change-Id: I8ca62e8d2b359e363ccb01cfe2daa0995354a3cb
2016-11-16 10:00:36 -05:00
Mike Bayer 772042ea85 - 1.1.5 setup
Change-Id: I937b12e464944221c2870e2fc62be15187c76b52
2016-11-16 09:58:35 -05:00
Mike Bayer ce17fd4bf3 - 1.1.4 2016-11-15 12:58:52 -05:00
Mike Bayer 2669488d85 - 1.0.16 release date 2016-11-15 12:57:24 -05:00
mike bayer 30abab5572 Merge "Add missing items to collection.__getstate__" 2016-11-14 20:47:42 -05:00
Mike Bayer 5def69c0cd - experiment with union merge for changelog
Change-Id: Ieed0199c58d7eacdb26db6e1754c1ef3ee5c8c7d
2016-11-14 16:26:50 -05:00
Mike Bayer 3e063525f3 Add missing items to collection.__getstate__
the refactor in b606e47ddc / ticket:3457 failed
to adjust __getstate__ / __setstate__.  need to memoize
a few more things including the class itself so that we
can navigate back to "attr".

Change-Id: I4ece2a616cb8b9dac7b50763ca59e47d0f26cfdf
Fixes: #3852
2016-11-14 16:25:47 -05:00
Mike Bayer 88ca587eae Count columns using PrimaryKeyConstraint.__len__ directly
PrimaryKeyConstraint is present on Table however
on table() and others it's a ColumnSet.  The warning
here only needs len() and PrimaryKeyConstraint supports that
directly in the same way as ColumnSet.

Change-Id: I19c11a39110bfef48cdea49a471e7ab80b537538
Fixes: #3842
2016-11-12 12:34:01 -05:00
Mike Bayer dd93c6a116 Merge remote-tracking branch 'origin/pr/318' 2016-11-11 16:33:01 -05:00
Mike Bayer 5fba7db9be Quote URL tokens with semicolons for pyodbc, adodbapi
Fixed bug in pyodbc dialect (as well as in the mostly non-working
adodbapi dialect) whereby a semicolon present in the password
or username fields could be interpreted as a separator for another
token; the values are now quoted when semicolons are present.

Change-Id: I5f99fd8db53ebf8e805e7d9d60bc09b8f1af603f
Fixes: #3762
2016-11-11 13:30:25 -05:00
Mike Bayer 91e7d46fe1 - oragnize the changelog with tokens per .. change:: to allow
three way merges to succeed (hopefully). requires bump of changelog
package.

Change-Id: Icd9bb7f4a4e01cc6ac66e8c7bb6631c3f6bb1d2c
2016-11-11 12:03:13 -05:00
Mike Bayer f2eb4aac95 Use configured props for mapper.attrs, mapper.all_orm_descriptors
Fixed bug where the :attr:`.Mapper.attrs`,
:attr:`.Mapper.all_orm_descriptors` and other derived attributes would
fail to refresh when mapper properties or other ORM constructs were
added to the mapper/class after these  accessors were first called.

(also trying different ways to get the changelog to merge cleanly)

Change-Id: Iaecdb4b3d8c3a3b44302a5880476e60a1f4e27d9
Fixes: #3778
2016-11-10 17:36:41 -05:00
mike bayer 0342981212 Merge "Consider version_id_prop when emitting bulk UPDATE" 2016-11-10 17:22:41 -05:00
Mike Bayer c9d8a67b52 Consider version_id_prop when emitting bulk UPDATE
The version id needs to be part of _changed_dict()
so that the value is present to send to
_emit_update_statements()

Change-Id: Ia85f0ef7714296a75cdc6c88674805afbbe752c8
Fixes: #3781
2016-11-10 16:30:11 -05:00
Kevin Jurczyk e81660d5c0 Add conditional import for pysqlcipher3
This is a Py3K supporting DBAPI for pysqlcipher.

Change-Id: I2a625274a371908f4de9d37f33e05408894b334b
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/320
2016-11-10 16:29:16 -05:00
mike bayer 33e277e856 Merge "Remove non-working Connection.default_schema_name() method" 2016-11-10 15:30:04 -05:00
Roman Podoliaka d1e31ab158 Add support for server side cursors to mysqldb and pymysql
This allows to skip buffering of the results on the client side, e.g.
the following snippet:

    table = sa.Table(
        'testtbl', sa.MetaData(),
        sa.Column('id', sa.Integer, primary_key=True),
        sa.Column('a', sa.Integer),
        sa.Column('b', sa.String(512))
    )
    table.create(eng, checkfirst=True)

    with eng.connect() as conn:
        result = conn.execute(table.select().limit(1)).fetchone()
        if result is None:
            for _ in range(1000):
                conn.execute(
                    table.insert(),
                    [{'a': random.randint(1, 100000),
                      'b': ''.join(random.choice(string.ascii_letters) for _ in range(100))}
                      for _ in range(1000)]
                )

    with eng.connect() as conn:
        for row in conn.execution_options(stream_results=True).execute(table.select()):
            pass

now uses ~23 MB of memory instead of ~327 MB on CPython 3.5.2 and
PyMySQL 0.7.9.

psycopg2 implementation and execution options (stream_results,
server_side_cursors) are reused.

Change-Id: I4dc23ce3094f027bdff51b896b050361991c62e2
2016-11-10 12:09:27 -05:00
Benjamin Dopplinger ea934b9539 Remove non-working Connection.default_schema_name() method
The method `engine.base.Connection.default_schema_name` is broken since
4b532e2 (this was when `engine.dialect.get_default_schema_name` was
replaced with `engine.dialect.default_schema_name`).  The method is
unused and also is not functional for end-user use, so remove it
for now.

Change-Id: I6ffbd9ce1b9b54ff6df63ed45d7d33591f183933
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/321
2016-11-10 11:19:09 -05:00
Mike Bayer 6a688b7364 Ensure attribute keys used for bulk update pk set
Fixed bug in :meth:`.Session.bulk_update_mappings` where an alternate-named
primary key attribute would not track properly into the UPDATE statement.

Change-Id: I33e9140f45827772768fa548adcfeb4dbfc2208d
Fixes: #3849
2016-11-10 11:08:52 -05:00
Kevin Jurczyk b141f9f3c8 Add quotes around PRAGMA values in pysqlcipher connect.
Arguments such as cipher, kdf_iter, cipher_page_size and
cipher_use_hmac may (always?) require quotes within the
PRAGMA directive.

Change-Id: I2c808f34e1c44f0593b72b304e170e4af0a6035a
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/319
2016-11-08 12:16:57 -05:00
Mike Bayer 942c2429c0 Put include_table=True for DO UPDATE..WHERE, but not ON CONFLICT
Fixed regression caused by the fix in 🎫`3807` (version 1.1.0)
where we ensured that the tablename was qualified in the WHERE clause
of the DO UPDATE portion of PostgreSQL's ON CONFLICT, however you
*cannot* put the table name in the  WHERE clause in the actual ON
CONFLICT itself.   This was an incorrect assumption, so that portion
of the change in 🎫`3807` is rolled back.

Change-Id: I442d8629496a8e405b54711cfcf487761810ae8a
Fixes: #3846
Fixes: #3807
2016-11-07 22:03:16 -05:00
Mike Bayer c4a8afa4c6 Move setup functionality into _register_attribute
Options like uselist and backref can be determined from
within _register_attribute based on parent_property
given; move this logic inside so that individual strategies
have less responsibility.  Also don't require that
_register_attribute consider the "strategy" itself
at all; it would be better if we could no longer require
that Joined/Subquery/etc loaders call upon the "lazy" strategy
in order to initialize attribute instrumentation and
this could be done more generically.

Fixes long-standing bug where the "noload" relationship loading
strategy would cause backrefs and/or back_populates options to be
ignored.   There is concern that some application that uses
"noload" might be surprised at a back-populating attribute
appearing suddenly, which may have side effects.  However,
"noload" itself must be extremely seldom used since as a
strategy, it already disables loading, population of attributes
is the only behavior that is even supported, so that this issue has existed
for at least through 0.7 four years ago without ever being
reported indicates extremely low use of this option.

Change-Id: Icffb9c83ac5782b76ce882ed1df4361a1efbfba3
Fixes: #3845
2016-11-06 12:46:28 -05:00
jfinkels d0d4e391c5 Adds missing word "of" in docs 2016-10-30 22:22:54 -04:00
Mike Bayer dd4e09d387 Add check for blank string coming from MySQL's enum
MySQL's native ENUM type supports any non-valid value being sent, and
in response will return a blank string.  A hardcoded rule to check for
"is returning the blank string" has been added to the  MySQL
implementation for ENUM so that this blank string is returned to the
application rather than being rejected as a non-valid value.  Note that
if your MySQL enum is linking values to objects, you still get the
blank string back.

Change-Id: I61f85c20293a48b0c11a31f2a19f6756c206bd20
Fixes: #3841
2016-10-28 14:17:40 -04:00
Mike Bayer 60b68ff4ee - 1.1.4 versioning
Change-Id: I6545ebfeeee103cac133d0b8270a860cba2d2996
2016-10-28 14:14:32 -04:00
Mike Bayer 2af8c15597 - 1.1.3 2016-10-27 10:47:26 -04:00
mike bayer 3f1fe4e33c Merge "Restore object to the identity_map upon delete() unconditionally" 2016-10-27 10:46:15 -04:00
Mike Bayer e56a9d85ac Restore object to the identity_map upon delete() unconditionally
Fixed regression caused by 🎫`2677` whereby calling
:meth:`.Session.delete` on an object that was already flushed as
deleted in that session would fail to set up the object in the
identity map (or reject the object), causing flush errors as the
object were in a state not accommodated by the unit of work.
The pre-1.1 behavior in this case has been restored, which is that
the object is put back into the identity map so that the DELETE
statement will be attempted again, which emits a warning that the number
of expected rows was not matched (unless the row were restored outside
of the session).

Change-Id: I9a8871f82cb1ebe67a7ad54d888d5ee835a9a40a
Fixes: #3839
2016-10-27 09:51:50 -04:00
Randy Barlow 9974ab67f5 Minor fixes in the ext.hybrid documentation. 2016-10-23 10:34:25 -04:00
Mike Bayer 1f32d014da Ensure .mapper is set on _ColumnEntity
_ColumnEntity didn't seem to have .mapper present, which
due to the way _mapper_zero() worked didn't tend to come
across it.   With 🎫`3608` _mapper_zero() has
been simplified so make sure this is now present.
Also ensure that _select_from_entity is an entity and
not a mapped class, though this does not seem to matter
at the moment.

Fixes: #3836

Change-Id: Id6dae8e700269b97de3b01562edee95ac1e01f80
2016-10-21 10:42:14 -04:00
Mike Bayer 232eec47d1 Don't set pg autoincrement if type affinity is not Integer
Postgresql table reflection will ensure that the
:paramref:`.Column.autoincrement` flag is set to False when reflecting
a primary key column that is not of an :class:`.Integer` datatype,
even if the default is related to an integer-generating sequence.
This can happen if a column is created as SERIAL and the datatype
is changed.  The autoincrement flag can only be True if the datatype
is of integer affinity in the 1.1 series.

This bug is related to a test failure in downstream sqlalchemy_migrate.

Change-Id: I40260e47e1927a1ac940538408983c943bbdba28
Fixes: #3835
2016-10-20 17:38:22 -04:00
mike bayer 78f2864b90 Merge "Convert expression type for concat + Enum" 2016-10-20 16:37:00 -04:00
Mike Bayer 39d5a97266 Document Enum.enums is now a list
Change-Id: I27251c262f919df1b084cbb08759f672f05cd3f7
Fixes: #3834
2016-10-20 16:29:30 -04:00
Mike Bayer c97b1b8228 Convert expression type for concat + Enum
Fixed bug involving new value translation and validation feature
in :class:`.Enum` whereby using the enum object in a string
concatenation would maintain the :class:`.Enum` type as the type
of the expression overall, producing missing lookups.  A string
concatenation against an :class:`.Enum`-typed column now uses
:class:`.String` as the datatype of the expression itself.

Change-Id: Id402054e3ef008e0250c740dbb7e1c80f339fe78
Fixes: #3833
2016-10-20 15:59:46 -04:00
Mike Bayer 30bd28fca2 Ensure TypeDecorator delegates _set_parent_with_dispatch
Ensure TypeDecorator delegates _set_parent_with_dispatch as well as
_set_parent to itself as well as its impl, as the TypeDecorator
class itself may have an active SchemaType implementation as well.

Fixed regression which occurred as a side effect of 🎫`2919`,
which in the less typical case of a user-defined
:class:`.TypeDecorator` that was also itself an instance of
:class:`.SchemaType` (rather than the implementation being such)
would cause the column attachment events to be skipped for the
type itself.

Change-Id: I0afb498fd91ab7d948e4439e7323a89eafcce0bc
Fixes: #3832
2016-10-20 14:14:50 -04:00
Mike Bayer 39ac195109 - open for 1.1.3
Change-Id: I283e52a7a63ec4f7a285aba1b41627f11b7ad41b
2016-10-20 11:46:41 -04:00
Mike Bayer 76ec285ba4 Rewrite migration notes for [ticket:3514]
The change to "evaluates none" datatypes in the ORM was
not fully described in the migration notes, missing the
key behavioral change that a column which is missing a default
entirely will not receive a value for a missing JSON column now.
The issue here touched upon a revisit of the assumptions
in [ticket:3514], but overall the old behavior "worked" mostly
because the ORM wants to explicitly render NULL into an INSERT
for column values that are missing, which itself is a legacy
behavior which should be considered for possible removal in
a future major release.  Given that "missing ORM value + no
column default set up == dont put it in the INSERT" would be
the most intuitive behavior, the move in [ticket:3514] represents
a step in this direction.

Change-Id: I454d5bb0773bd73d9864925dcc47f1f0810e33ba
Fixes: #3830
2016-10-19 13:09:16 -04:00
Mike Bayer 2ee5d42e24 - 1.1.2 2016-10-17 14:29:01 -04:00
Mike Bayer 480b4e467c - correct ticket link markup
Change-Id: I49df318c77f9f539541e7edea857bd256aca2844
2016-10-17 14:27:53 -04:00
mike bayer 7d8a6b2614 Merge "Add a qualifying character to multi INSERT..VALUES parameter names" 2016-10-17 12:49:12 -04:00
Mike Bayer f9432a0287 Remove the use of the word "fundamental" to describe ColumnElements
The context is unclear if "fundamental" refers to the object's
role within a SELECT composition or within the class hierarchy
of ClauseElement classes.

Change-Id: I10bbf324fc09034cc27398867b7eca6b6f127abe
Fixes: #3793
2016-10-17 12:35:26 -04:00
Mike Bayer f917b353e8 Add a qualifying character to multi INSERT..VALUES parameter names
Changed the naming convention used when generating bound parameters
for a multi-VALUES insert statement, so that the numbered parameter
names don't conflict with the anonymized parameters of a WHERE clause,
as is now common in a PostgreSQL ON CONFLICT construct.

Change-Id: I3188d100fe4d322a47d344d6a63d3e40b915f228
Fixes: #3828
2016-10-17 12:14:41 -04:00
Mike Bayer 8ef4f6a538 Add explicit copy() to Enum
The Boolean and Enum types both place SchemaType second in the
inheritance hierarchy.  In the case of Enum, this works
out that the copy() method is called from the base TypeEngine
which fails to transfer _create_events.   The test suite
doesn't seem to work with the inhertance hierarchy set up like
this as the event listeners don't work out, the _on_metadata_create
and _on_table_create hooks cause the production of an adapted type
which then adds event listeners that cause deque changed while
iteration.  It's not clear why Enum /Boolean don't have this problem.
But in any case it seems like the class mechanics for these types
remains fragile and would benefit from yet another refactor someday.

Change-Id: Ib641a5d2321b00f58bbe98dd0c5e789374db32b2
Fixes: #3827
2016-10-17 12:13:01 -04:00
Mike Bayer c02675b407 Memoize load_path in all cases, run quick populators for path change
Adds a new variant to the "isnew" state within entity loading
for isnew=False, but the load path is new.  This is to address
the use case of an entity appearing in multiple places in
the row in a more generalized way than the fixes in [ticket:3431],
[ticket:3811] in that loading.py will be able to tell the
populator that this row is not "isnew" but is a "new" path
for the entity.   For the moment, the new information is only
being applied to the use of "quick" populators so that
simple column loads can take place on top of a deferred loader
from elsewhere in the row.

As part of this change, state.load_path() will now always
be populated with the "path" that was in effect when this state
was originally loaded, which for multi-path loads of the
same entity is still non-deterministic.  Ideally there'd be some
kind of "here's all the paths that loaded this state and how"
type of data structure though it's not clear if that could be
done while maintaining performance.

Fixes: #3822
Change-Id: Ib915365353dfcca09e15c24001a8581113b97d5e
2016-10-17 11:29:23 -04:00
Mike Bayer ae7d2837b3 Assemble "don't joinedload other side" rule using query._current_path
Discovered during testing for [ticket:3822], the rule added
for [ticket:1495] will fail if the source object has propagated
options set up, which add elements to query._current_path.

Fixes: #3824
Change-Id: I3d96c96fee5f9b247f739d2136d18681ac61f2fe
2016-10-17 11:28:36 -04:00
mike bayer 4684cfb508 Merge "Check for __module__ not present in util.wrap_callable()" 2016-10-17 11:28:43 -04:00
Pierre Jaury d18221c542 Remove some legacy dead code from the declared_attr logic
The second 'if' condition was never called because the original
condition always returns.
2016-10-16 16:45:54 +02:00
Mike Bayer 665b92d83f Check for __module__ not present in util.wrap_callable()
The newly added wrap_callable() function assumes __module__
is present when this is not the case for objects such as
functools.partial.

Change-Id: Ia226260e9a65419e26d5c1f7187512f7fd4bb7c1
Fixes: #3823
2016-10-14 13:26:35 -04:00
Randy Barlow 055b207a9f Fix a minor grammatical error in the ORM tutorial.
Change-Id: I50daaee2645dd8aa2ee7217f4065589492ed0b7d
2016-10-13 13:02:26 -04:00
Mike Bayer 6b7b77896d - setup for next version
Change-Id: I4a7ef54bec3891821954061a9b4ed19d398989f3
2016-10-13 12:27:51 -04:00
Matt Riedemann 4b94ee113b Update the Column.nullable docstring for the primary_key=True case
While reviewing a change that created a new table, the
primary_key column value was set to True but nullable was not
explicitly set, which led to some confusion over the default
behavior for the nullable column value when setting a primary_key.

Looking at the docs it's not clear, but the code shows that if
nullable is not specified, then nullable = not primary_key, so
nullable defaults to False when primary_key is True.

This patch adds a simple clarification to the docs so people
don't have to check the code.

Change-Id: I8553339d56fbae11370c7c6af6d8d4723163be1c
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/312
2016-10-10 11:54:04 -04:00
Ville Skyttä b9d0e2d5c5 spelling: Mysql -> MySQL 2016-10-08 20:42:50 +03:00
Ville Skyttä e5a063a87c spelling: Postgis -> PostGIS 2016-10-08 20:42:50 +03:00
Ville Skyttä 8c2c464cb8 spelling: Postgresql -> PostgreSQL 2016-10-08 20:42:50 +03:00
Ville Skyttä e47063bfe0 Spelling fixes 2016-10-08 20:42:50 +03:00
Mike Bayer 80861dffa9 - 1.1.1 2016-10-07 11:04:37 -04:00
Mike Bayer 8a13957db7 Change autoincrement compileerror to a warning
Users are complaining that IntegrityError is no longer
raised.

Change-Id: I0855d5b7a98d4338f0910501b6e6d404ba33634d
Fixes: #3216
2016-10-07 09:54:39 -04:00
Mike Bayer ae9300cac0 Catch DBAPIError instead of ProgrammingError for pyodbc fail
Change-Id: Ide9e916d02fbbef549aa2838d1402c2b091e701d
Fixes: #3820
2016-10-07 09:17:46 -04:00
Mike Bayer b1fe748fea - set up for 1.1.1
Change-Id: I569a03a6e86aa096be6744ecb479fe8485f7def6
2016-10-05 22:31:31 -04:00
Mike Bayer 56e199416f - 1.1.0 2016-10-05 16:59:00 -04:00
mike bayer fe92820347 Merge "Propagate execution_options at compile stage" 2016-10-05 16:52:15 -04:00
Mike Bayer 71030d67bd Propagate execution_options at compile stage
Compiler can now set up execution options and additionally
will propagate autocommit from embedded CTEs.

Change-Id: I19db7b8fe4d84549ea95342e8d2040189fed1bbe
Fixes: #3805
2016-10-05 16:47:31 -04:00
Randy Barlow df4639ab71 Minor grammatical improvements in doc/build/intro.rst. 2016-10-05 15:07:57 -04:00
Mike Bayer 09b685b24b Check for __clause_element__() in ORM insert/update
ORM attributes can now be assigned any object that is has a
``__clause_element__()`` attribute, which will result in inline
SQL the way any :class:`.ClauseElement` class does.  This covers other
mapped attributes not otherwise transformed by further expression
constructs.

As part of this, it was considered that we could add
__clause_element__() to ClauseElement, however this causes endless loops
in a "while" pattern and this pattern has been identified in third
party libraries.  Add a test to ensure we never make that change.

Change-Id: I9e15b3f1c4883fd3909acbf7dc81d034c6e3ce1d
Fixes: #3802
2016-10-05 12:11:53 -04:00
Mike Bayer 20384e8945 Check row for None with implicit returning PK to accommodate ON CONFLICT
An adjustment to ON CONFLICT such that the "inserted_primary_key"
logic is able to accommodate the case where there's no INSERT or
UPDATE and there's no net change.  The value comes out as None
in this case, rather than failing on an exception.

Change-Id: I0794e95c3ca262cb1ab2387167d96b8984225fce
Fixes: #3813
2016-10-04 17:31:40 -04:00
mike bayer e5a5a72e17 Merge "Enhance "raise" strategy to include "raise_on_sql" option" 2016-10-04 16:48:08 -04:00
mike bayer aadbb5a1d1 Merge "Honor additional row coming in with value of None" 2016-10-04 14:41:43 -04:00
Mike Bayer ab8944b1bf - add a few more changes and try to break some out into
ORM behavioral changes

Change-Id: I633ff10907b60111d3d0de0970fd384be7931d00
2016-10-04 12:33:37 -04:00
Mike Bayer 95d4cd3042 Enhance "raise" strategy to include "raise_on_sql" option
The "raise_on_sql" option differentiates from "raise" in that
firing a lazy loader is OK as long as it does a simple
get from identity map.   Whereas "raise" is more useful
for the case that objects are to be detached.

As part of this, refactors the strategy initiation logic
a bit so that a LoaderStrategy itself knows what "key" was used
to create it, thus allowing variants of a single strategy
based on what the "lazy" argument is.  To achieve this we
have to also get rid of _get_strategy_by_cls().

Everything here is internal with the one exception of an apparently
undocumented, but not underscored, "strategy_class" key
on relationship().   Though it's not clear what
"strategy_class" accomplishes; at this point the strategy
system is extensible using Property.strategy_for().

Fixes: #3812
Change-Id: I812ad878ea5cf764e15f6f71cb39eee78a645d88
2016-10-04 12:09:29 -04:00
Mike Bayer c3abfe5064 Honor additional row coming in with value of None
The change in #3431 still checks that the instance() is
non-None, deferring to other loading schemes if it is.
These columns are dedicated towards the entity however, so if the value
is None, we should set it.  If it conflicts, we are detecting that
in any case.

Change-Id: I223768e2898e843f953e910da1f9564b137d95e4
Fixes: #3811
2016-10-04 12:07:08 -04:00
Mike Bayer cbe99b0667 - add a note to baked documentation indicating it is not
really of general use.  This extension is there only
for those who really want it based on observed performance
characteristics.

Change-Id: I2f612f26fdef4ddbeb1158ab1b344fad7083b11c
2016-10-04 12:01:12 -04:00
Mike Bayer 562e37ee7e Use schema_name() for SQL Server default schema
Changed the query used to get "default schema name", from one that
queries the database principals table to using the
"schema_name()" function, as issues have been reported that the
former system was unavailable on the Azure Data Warehouse edition.
It is hoped that this will finally work across all SQL Server
versions and authentication styles.

Change-Id: Ic11bd4162c0d6a60432ae44876e86512703c1f81
Fixes: #3810
2016-10-04 11:32:20 -04:00
Mike Bayer f0ea9e37f9 Use SQL Server SERVERPROPERTY for version info w/ pyodbc
Updated the server version info scheme for pyodbc to use SQL Server
SERVERPROPERTY(), rather than relying upon pyodbc.SQL_DBMS_VER, which
continues to be unreliable particularly with FreeTDS.

Change-Id: I4ff49ae13c8ff51bd764980131d41c18d73d87ce
Fixes: #3814
2016-10-04 11:17:26 -04:00
Mike Bayer 728ce8cc48 Ensure strong ref to obj before calling persistent_to_deleted, others
Add checks in spots where state.obj() might be late-GC'ed before
we get a chance to call the event.   There may be more cases
of these which we should address as they come up.  The Session
should always be maintaining strong refs to objects that have
pending operations left on them, so for these cases we need
to ensure that ref remains long enough for the event to be called.

Change-Id: I1a7c7bc57130acc11f54ad55924af2e36ac75101
Fixes: #3808
2016-10-03 12:25:42 -04:00
Mike Bayer 333414fe94 Add "eager_parenthesis" late-compilation rule, use w/ PG JSON/HSTORE
Added compiler-level flags used by Postgresql to place additional
parenthesis than would normally be generated by precedence rules
around operations involving JSON, HSTORE indexing operators as well as
within their operands since it has been observed that Postgresql's
precedence rules for at least the HSTORE indexing operator is not
consistent between 9.4 and 9.5.

Fixes: #3806
Change-Id: I5899677b330595264543b055abd54f3c76bfabf2
2016-10-01 09:46:11 -04:00
Mike Bayer 9bfd028938 - some documentation hits
Change-Id: I468fe70168804b08cf0d5e8b57e235bca904b1ff
2016-10-01 09:42:21 -04:00
Dmitry Bogun dce3206223 Remove extra "return" statement in orm.ext.declared_attr.cascading examples
Also improves some naming in the examples.

Change-Id: I51e5b1d9a730885aed10e5e6ade2123f5e736359
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/306
2016-10-01 09:27:47 -04:00
Mike Bayer 079df65dc0 Escape literal string values passed to server_default
A string sent as a column default via the
:paramref:`.Column.server_default` parameter is now escaped for quotes.

This change is backwards compatible with code that may have been
working around this previously.

Change-Id: I341298a76cc67bc0a53df4ab51ab9379f2294cdd
Fixes: #3809
2016-09-30 09:23:50 -04:00
Mike Bayer 800a18aff2 Enable include_table for ON CONFLICT whereclauses
Fixed issue in new PG "on conflict" construct where columns including
those of the "excluded" namespace would not be table-qualified
in the WHERE clauses in the statement.

Change-Id: Idfefc93e7e7b0d84805e23d5436d822d606f6a0a
Fixes: #3807
2016-09-28 18:08:30 -04:00
mike bayer f09056323e Merge "Handle BaseException in all _handle_dbapi_error" 2016-09-26 14:16:32 -04:00
Mike Bayer e9b2625753 - improve documentation for SessionTransaction re: parent
and nested attributes and what these mean
- improve linking for after_transaction_create() / after_transaction_end()
events
- add public .parent attribute to detect top-level transaction within
these events

Change-Id: Ie7382bc8fe5de226160dcb6a5019e19fcc5af38e
2016-09-24 00:49:22 -04:00
Mike Bayer 0cc8267286 - clarify documentation on timezone flag, since Oracle has both
DATE / TIMESTAMP separately the timezone flag will not bump the
type to TIMESTAMP WITH TIMEZONE on that backend.

Change-Id: I185992093472e1620b8cf84872631a4d48f8edc3
2016-09-22 11:08:09 -04:00
Mike Bayer 7827dfb672 Handle BaseException in all _handle_dbapi_error
Tests illustrate that exceptions like GreenletExit and
even KeyboardInterrupt can corrupt the state of a DBAPI
connection like that of pymysql and mysqlclient.   Intercept
BaseException errors within the handle_error scheme and
invalidate just the connection alone in this case, but not
the whole pool.

The change is backwards-incompatible with a program that
currently intercepts ctrl-C within a database transaction
and wants to continue working on that transaction.  Ensure
the event hook can be used to reverse this behavior.

Change-Id: Ifaa013c13826d123eef34e32b7e79fff74f1b21b
Fixes: #3803
2016-09-21 18:39:31 -04:00
Mike Bayer 97b2940936 Ensure mapper.polymorphic_on is polymorphic_prop.columns[0]
Fixed bug where joined eager loading would fail for a polymorphically-
loaded mapper, where the polymorphic_on was set to an un-mapped
expression such as a CASE expression.

Change-Id: Iffe68196aaac592165c89684f09f4c06cd78ce54
Fixes: #3800
2016-09-21 17:57:38 -04:00
mike bayer 930b07c3af Merge "Add exclude_tablespaces argument to Oracle" 2016-09-20 19:36:00 -04:00
mike bayer 11d24b6614 Merge "Add the "triggering mapper" to the configure_mappers error message." 2016-09-20 13:58:55 -04:00
David Fraser 319c49e64a Add exclude_tablespaces argument to Oracle
Allows the SYSTEM and SYSAUX tablespaces to be only
conditionally omitted when doing get_table_names()
and get_temp_table_names().

Change-Id: Ie6995873f05163f2ce473a6a9c2d958a30681b44
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/292
2016-09-20 13:57:40 -04:00
Mike Bayer 0c90cac2c3 - disable two phase testing for mysql entirely, build servers
have no time to deal with MySQL 5.7's issues

Change-Id: Ic5f4e5b0aff1b4b5210bc7b5da203f536561e585
2016-09-20 13:56:17 -04:00
John Perkins e95aa257aa Add the "triggering mapper" to the configure_mappers error message.
There are cases where the originating mapper name is not
present in the exception message, such as relationship initialization
against an unmapped class.   Ensure the originating mapper is named
in the string output.

Pull-request: https://github.com/zzzeek/sqlalchemy/pull/298
Change-Id: I9f23bfa90b26dde9229ab7ec812eec9ceae48153
2016-09-20 12:11:11 -04:00
mike bayer 5af3c90336 Merge "Allow SQL expressions to be set on PK columns" 2016-09-20 11:56:05 -04:00
mike bayer b9a7a74d5e Merge "Exclude eq and ne from associative operators" 2016-09-20 11:55:19 -04:00
mike bayer dea7c2bd8e Merge "Support bindparam() with callable for primaryjoin" 2016-09-20 11:54:47 -04:00
Mike Bayer f8ecdf47f0 Allow SQL expressions to be set on PK columns
Removes an unnecessary transfer of modified PK column
value to the params dictionary, so that if the modified PK column
is already present in value_params, this remains in effect.  Also
propagate a new flag through to _emit_update_statements() that will
trip "return_defaults()" across the board if a PK col w/ SQL expression
change is present, and pull this PK value in _postfetch as well assuming
we're an UPDATE.

Change-Id: I9ae87f964df9ba8faea8e25e96b8327f968e5d1b
Fixes: #3801
2016-09-20 11:33:16 -04:00
mike bayer e49292894a Merge "Fix ArgumentError access in Session._add_bind" 2016-09-19 18:15:02 -04:00
John Passaro 2c4119d1eb Exclude eq and ne from associative operators
The "eq" and "ne" operators are no longer part of the list of
"associative" operators, while they remain considered to be
"commutative".  This allows an expression like ``(x == y) == z``
to be maintained at the SQL level with parenthesis.  Pull request
courtesy John Passaro.

Fixes: #3799
Change-Id: I3759d8987b35649d7418b6524316c9e70c857e68
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/308
2016-09-19 17:17:07 -04:00
mike bayer dc7aef1d70 Merge "Additions to support HAAlchemy plugin" 2016-09-19 16:25:51 -04:00
Mike Bayer 8c3b9d6083 Support bindparam() with callable for primaryjoin
Fixes the comparison of bindparam() objects based on
the "callable" parameter being present which helps to correctly
detect use_get, and also checks for "callable" when detecting
parameters for value substitution and will not impact the
object if present.

Change-Id: I4c93ee5d404d2648dd9835beeae0c5fb67e37d19
Fixes: #3767
2016-09-19 16:22:08 -04:00
Mike Bayer 7ea5461151 Fix ArgumentError access in Session._add_bind
Fixes: #3798
Change-Id: Ib4e6344b599e871f9d46d36a5aeb7ba3104dc99b
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/293
2016-09-19 15:58:19 -04:00
Ken Robbins 881369b949 Add "message 20017" (unexpected EOF from the server) to mssql.
Fixes: #3791
Change-Id: I0dade4fe0ecbb53b4a66881594f362986ba73ae8
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/89
2016-09-19 12:31:57 -04:00
Mike Bayer 01a0a2d542 Additions to support HAAlchemy plugin
- add a connect=True key to connection record to support
  pre-loading of _ConnectionRecord objects
- ensure _ConnectionRecord.close() leaves the record in a good
  state for reopening
- add _ConnectionRecord.record_info for persistent storage
- add "in_use" accessor based on fairy_ref being present or not
- allow for the exclusions system and SuiteRequirements to be
  usable without the full plugin_base setup.
- move some Python-env requirements to the importable
  requirements.py module.
- allow starttime to be queried
- add additional events for engine plugins
- have "dialect" be a first-class parameter to the pool,
  ensure the engine strategy supplies it up front

Change-Id: Ibf549f7a1766e49d335cd6f5e26bacfaef9a8229
2016-09-16 16:20:18 -04:00
Mike Bayer 65d8deac95 - latest mysql 5.7 also crashing on XA recovery, disable
XA recovery for all MySQL

Change-Id: I4f77de521cd80c09fdf97e5bbe5dfd1c830dc3cb
2016-09-16 12:57:59 -04:00
Mike Bayer 25804aeae2 Repair foreign_keys population for Join._refresh_for_new_column
Fixed bug where setting up a single-table inh subclass of a joined-table
subclass which included an extra column would corrupt the foreign keys
collection of the mapped table, thereby interfering with the
initialization of relationships.

Change-Id: I04a0cf98fd456d12d5a5b9e77a46a01246969a63
Fixes: #3797
2016-09-15 00:54:15 -04:00
Mike Bayer 6e1f34ed62 - placeholder for 1.0.16 within 1.0 changelog
Change-Id: I33405513dc216ad33c5ec4796bff73f75d5866c4
(cherry picked from commit 4017b26964)
2016-09-15 00:53:17 -04:00
Mike Bayer c3d582d87b Merge branch 'keeyipchan/fix-typo-in-comment-1473614966363' of https://bitbucket.org/keeyipchan/sqlalchemy 2016-09-13 09:52:02 -04:00
Mike Bayer 6deb514992 - also caveats for update() / delete() regarding single
table inheritance

Change-Id: If1511812a22a53537409f902f73e2e52ae3e4a3d
(cherry picked from commit 9923443343)
2016-09-12 18:36:30 -04:00
Mike Bayer 2cd53196ea - add caveat for bulk deletes that they are generally not feasible
for joined inheritance

Change-Id: I043a5842401d586aa3ff96d05e06b443ff03fa60
2016-09-12 18:17:18 -04:00
keeyip chan 1e4f69d561 Fix typo in comment 2016-09-11 17:29:29 +00:00
mike bayer ce62fa2eed Merge "Allow stringify compiler to render unnamed column" 2016-09-02 12:23:31 -04:00
Mike Bayer ce577d4844 Repair clauselist comparison to account for clause ordering
Fixed bug where the "simple many-to-one" condition that allows  lazy
loading to use get() from identity map would fail to be  invoked if the
primaryjoin of the relationship had multiple clauses separated by AND
which were not in the same order as that of the primary key columns
being compared in each clause. This ordering
difference occurs for a composite foreign key where the table-bound
columns on the referencing side were not in the same order in the .c
collection as the primary key columns on the referenced side....which
in turn occurs a lot if one is using declarative mixins and/or
declared_attr to set up columns.

Change-Id: I66cce74f614c04ed693dc0d58ac8c952b2f8ae54
Fixes: #3788
2016-09-02 11:54:16 -04:00
Mike Bayer 9a6947427a Allow stringify compiler to render unnamed column
Stringify of expression with unnamed :class:`.Column` objects, as
occurs in lots of situations including ORM error reporting,
will now render the name in string context as "<name unknown>"
rather than raising a compile error.

Change-Id: I76f637c5eb4cfdb1b526964cb001565b97e296da
Fixes: #3789
2016-09-02 11:48:15 -04:00
Mike Bayer f6022839c2 - add 1.0.15 release date
Change-Id: I5d3f74c002f9d4593940ab4d68a3b35f3f227597
2016-09-01 13:20:31 -04:00
Mike Bayer 16dcc8bec1 Support all MySQL/Connector int/bool arguments
Added support for parsing MySQL/Connector boolean and integer
arguments within the URL query string: connection_timeout,
connect_timeout, pool_size, get_warnings,
raise_on_warnings, raw, consume_results, ssl_verify_cert, force_ipv6,
pool_reset_session, compress, allow_local_infile, use_pure.

Change-Id: I2a1a17d13d47d56871bff32e94fdbed8bc003ad7
Fixes: #3787
2016-09-01 09:34:33 -04:00
Mike Bayer c7b9c84312 Check for supports_execution at ClauseElement base
Raise a more descriptive exception / message when ClauseElement
or non-SQLAlchemy objects that are not "executable" are erroneously
passed to ``.execute()``; a new exception ObjectNotExecutableError
is raised consistently in all cases.

Change-Id: I2dd393121e2c7e5b6b9e40286a2f25670876e8e4
Fixes: #3786
2016-08-31 17:04:35 -04:00
Edouard Berthe 53c3119ebb Corrects typo
This example doesn't work with 'back_populates' because 'parent_associations' and 'child_associations' are not defined in Parent and Child classes respectively.
Alternatively, we could create 'parent_associations' and 'child_associations' into the classes.
2016-08-31 16:52:48 +10:00
Mike Bayer 7c59d681a0 Merge remote-tracking branch 'origin/pr/304' 2016-08-28 09:46:11 -04:00
Mike Bayer 56a005241c Merge remote-tracking branch 'origin/pr/303' 2016-08-28 09:45:54 -04:00
Michael Williamson 94fe6fe05d Provide more informative error when joining with no entities 2016-08-28 12:38:04 +01:00
Michael Williamson 2b0fa0f8a1 Fix table reference in PostgreSQL documentation 2016-08-28 12:22:42 +01:00
Vladimir Magamedov b42bcb2573 Fixed example of upsert in the HasCTE.cte docstring by
replacing it with more concrete and working example.
2016-08-27 14:21:56 +03:00
Mike Bayer 117997cd5b Raise when two validators conflict
Two @validates decorators that make use of the same name
is not supported.  Raise an exception.

Change-Id: Ia3e89ffdc9ef345a0de258e2ac0ac5e0bd421c61
Fixes: #3776
2016-08-26 12:56:01 -04:00
mike bayer f10eba00ea Merge "Add docstring to declarative_base" 2016-08-22 10:49:48 -04:00
Mike Bayer 5145f671a4 - fix wrong var name, credit to @RazerM
Change-Id: I36fbbfd1223ef5298c679f46db24e1bf3013cef0
2016-08-17 18:26:34 -04:00
Mike Bayer 5b86ae5e8a Merge remote-tracking branch 'origin/pr/299' 2016-08-16 12:04:41 -04:00
Mike Bayer 9f41f64cd2 Merge remote-tracking branch 'origin/pr/300' 2016-08-16 12:03:24 -04:00
Mike Bayer 323e6e7f9f Rework _apply_joins(), _prep_for_joins() totally
The approach here is still error prone
and hard to follow.  Reorganize the whole
thing to take a pretty blunt approach to
the structure of to_join().  Also fix some never-called
code (!) in _prep_for_joins() and ensure we re-use
an aliased object.

Fixes: #3774
Change-Id: Ie6319415ae7213b4a33eac2ab70803ad2880d340
2016-08-15 17:36:03 -04:00
mike bayer 94a95b3e8f Merge "Ensure final link in subqueryload join is correct" 2016-08-13 10:39:52 -04:00
Mike Bayer 14154b2910 - fill in forwards-ports for 1.1 in 1.0 changelog
Change-Id: I8d44b90bb9d05275de19d3ce2d9124050add5f01
2016-08-12 23:39:49 -04:00
Mike Bayer b07eb3cb45 Ensure final link in subqueryload join is correct
Fixed bug in subquery eager loading where a subqueryload
of an "of_type()" object linked to a second subqueryload of a plain
mapped class would fail to link the joins correctly.

Change-Id: I4be89e6f5e492438464a2ded01eb9c84d7ff7d4e
Fixes: #3773
2016-08-12 23:35:40 -04:00
Mike Bayer bec5d6991e - fix this test which did not allow for the A/ ASub to be loaded
polymorphically

Change-Id: Id82435fa16b0456f32bce49715c6606e3a1534c8
2016-08-12 22:58:34 -04:00
Mike Bayer c3ad6da0c4 - add another example for chained polymorphic eager loading
Change-Id: I87918ab4cd294d4b4a87a377c7b6b21105f4fd55
(cherry picked from commit 68b6984912)
2016-08-11 12:04:05 -04:00
Mike Bayer 09cf037652 - small updates to polymorphic eager loading, cross-link from
loading documentation

Change-Id: I3ce7e2cc521c4dd155195819a919017d4cc63b3c
2016-08-11 11:45:03 -04:00
Romuald Brunet 096a74d7c5 Fix documentation basic example (missing imports) 2016-08-11 17:24:05 +02:00
Ville Skyttä fd164a6c84 Spelling fixes 2016-08-08 16:39:15 +03:00
Frazer McLean 87d5982e58 Add docstring to declarative_base
Change-Id: I5ad44362515908592f1e8b1e6254a5270d43234a
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/295
2016-08-06 02:25:27 +01:00
Mike Bayer f2fa9d000b Build string/int processors for JSONIndexType, JSONPathType
Fixed regression in JSON datatypes where the "literal processor" for
a JSON index value, that needs to take effect for example within DDL,
would not be invoked for the value.  The native String and Integer
datatypes are now called upon from within the JSONIndexType
and JSONPathType.  This is applied to the generic, Postgresql, and
MySQL JSON types.

Change-Id: Ifa5f2acfeee57a79d01d7fc85d265a37bd27c716
Fixes: #3765
2016-08-04 12:38:58 -04:00
Mike Bayer af6f4ab938 Propagate kwargs to all MySQL CAST paths
Change-Id: I23a6abb26bbbe3d118887d043ce761fc4572d8d2
Fixes: #3766
2016-08-04 12:34:55 -04:00
brlnandMike Bayer ce1492ef3a Warn that bulk save groups inserts/updates by type
Users who pass many different object types to bulk_save_objects
may be surprised that the INSERT/UPDATE batches must necessarily
be broken up by type.  Add this to the list of caveats.

Co-authored-by: Mike Bayer
Change-Id: I8390c1c971ced50c41268b479a9dcd09c695b135
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/294
2016-08-02 18:45:59 -04:00
Mike Bayer 2dfa954e1f Merge remote-tracking branch 'origin/pr/296' 2016-08-02 18:34:05 -04:00
Mike Bayer a95c58df3b Merge branch 'declarative-constructor-reference' of https://bitbucket.org/michaelwilliamson/sqlalchemy 2016-08-02 18:29:11 -04:00
Mike Bayer 1269b08b1b Ensure post-__clause_element__() expression are used in Index
The change in Index for 1.1 combined with the fix for
ref #3763 still fails to deliver the correct object
resolved by __clause_element__() to the list of expressions
for compilation.   Make sure we use the expression that's
been unwrapped from __clause_element__().

Change-Id: Ie1df8db5090de665048331786f0024d52851923f
Fixes: #3763
2016-07-31 00:10:04 -04:00
mike bayer cda9defe58 Merge "Index should extract __clause_element__() early" 2016-07-30 12:54:10 -04:00
mike bayer 99248e843d Merge "Clarify order_by(False)" 2016-07-30 12:53:26 -04:00
Mike Bayer 6327c59d4f Index should extract __clause_element__() early
Fixed bug where :class:`.Index` would fail to extract columns from
compound SQL expressions if those SQL expressions were wrapped inside
of an ORM-style ``__clause_element__()`` construct.  This bug
exists in 1.0.x as well, however in 1.1 is more noticeable as
hybrid_property @expression now returns a wrapped element.

Fixes: #3763

Change-Id: I992536386503a1fb3f2305790abe008d72c44c4a
2016-07-30 10:11:53 -04:00
Mike Bayer e467e899e1 - Consoliate test/sql/test_constraint ConstraintAPITest
and test/sql/test_metadata IndexTest into
test/sql/test_metadata ConstraintTest

Change-Id: I7aeee9a1edbbd889200afc393695f73d5fbac3f3
2016-07-30 10:06:53 -04:00
mike bayer 5df226c2ab Merge "Allow None to cancel Query.group_by()" 2016-07-29 19:03:38 -04:00
Mike Bayer fb647e5219 Clarify order_by(False)
It wasn't clear how this differs from order_by(None);
add more tests and document that this has to do with whether or
not mapper.order_by will be re-enabled as well.

Change-Id: I332e8ac60c999b38c5a243f1cb72de3cf77891b6
2016-07-29 18:57:04 -04:00
Iuri Diniz 05f28ba2fb Allow None to cancel Query.group_by()
This replicates the same behavior as order_by().

order_by() will also be updated to deprecate passing
of False as this is no longer functionally different
than passing None.

Change-Id: I2fc05d0317d28b6c83373769a48f7eea32d56290
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/297
2016-07-29 18:44:34 -04:00
mike bayer 9130e5923e Merge "Enable JSON testing for pymysql" 2016-07-29 18:22:49 -04:00
Mike Bayer 64424b870b - next release is 1.1.0
Change-Id: I1d8ac48e6457e80e93b925152f434c13139b3d94
2016-07-29 18:18:10 -04:00
Mike Bayer 6f9e8f482c Enable JSON testing for pymysql
PyMySQL upstream has released 0.7.6 which should resolve
JSON encoding issues.

Change-Id: Icf543d48dace1419a0aac78bdb15ec666f0edafe
Fixes: #3754
2016-07-29 11:07:32 -04:00
Mike Bayer 0d92f79fd8 - Document how SQL Server does MAX with VARCHAR, NVARCHAR
Fixes #3760

Change-Id: I0613eb66bfdc9d7118688c74e29c8da322c3b4db
2016-07-27 10:04:52 -04:00
Mike Bayer 360b4e0565 - 1.1.0b3 2016-07-26 11:25:52 -04:00
Jeff Widman 4aad91f687 Fix typo 2016-07-25 19:07:19 -07:00
Michael Williamson 924a47fc4f Fix reference to _declarative_constructor in docstring 2016-07-25 13:08:43 +00:00
Mike Bayer 2c8643b0e9 Allow Table._reset_exported to silently pass
Fixed bug in :class:`.Table` where the internal method
``_reset_exported()`` would corrupt the state of the object.  This
method is intended for selectable objects and is called by the ORM
in some cases; an erroneous mapper configuration would could lead the
ORM to call this on on a :class:`.Table` object.

Change-Id: I63fa34ee0cdf16358bb125c556390df79758bcbc
Fixes: #3755
2016-07-24 23:17:11 -04:00
Mike Bayer 96c4208bf8 - MySQL's JSON shared implementation completely w/ sqltypes.JSON;
this must have been an oversight.   Leave mysql.JSON in place still
as we might need to add things to it.
- CAST(json, String) still confusing MySQL drivers even mysqlclient.
Since here we're checking for the raw form of the JSON and not a typical
round trip, add a force for unicode

Change-Id: I727f4526a01a0875037cf0dede45cd074da5205a
2016-07-24 23:14:47 -04:00
Mike Bayer 98c66d19a0 - don't use pymysql at all for JSON, there's Py2K failures also
Change-Id: I39a574ea72f5c7af0084dee3169679c5f534cb8b
2016-07-24 18:29:46 -04:00
Mike Bayer ab244748d6 - Workaround in tests for https://github.com/PyMySQL/PyMySQL/issues/488
Change-Id: I4f935cce878eb1678b432f4cb4ba6ee122f8e9d4
2016-07-24 17:48:33 -04:00
Mike Bayer 02190234a2 - a variety of test adjustments to accomodate for MySQL 5.7
Change-Id: Ied4245433d0d7b469dae6e7394c4931d8405f387
2016-07-24 16:36:27 -04:00
Mike Bayer 8952a30f0a Remove same-named relationship warning
Removed a warning that dates back to 0.4 which emits when a same-named
relationship is placed on two mappers that inherits via joined or
single table inheritance.   The warning does not apply to the
current unit of work implementation.

Change-Id: If528ec3a2f4dc60712d9044fd1ec6c4dfbf0eadb
Fixes: #3749
2016-07-19 12:36:21 -04:00
Mike Bayer ee5e815e2c - fix formatting
Change-Id: Ieba940a998a6aa287864e9748c2995ee4ae5bf54
2016-07-18 16:43:42 -04:00
mike bayer 888f296540 Merge "Add default parameter for index_property" 2016-07-13 14:10:00 -04:00
Mike Bayer 889c011a0f Ensure DML provides named_with_column for CTE(Alias)
Fixed bug in new CTE feature for update/insert/delete whereby
an anoymous (e.g. no name passed) :class:`.CTE` construct around
the statement would fail.  The Alias base class of CTE checks
for the "named_with_column" attribute in order to detect if
the underlying selectable has a name; UpdateBase now provides
this as False.

Change-Id: I4b0309db21379a4c0cb93085298c86da3cf840e4
Fixes: #3744
2016-07-13 11:49:34 -04:00
mike bayer d80b709ea0 Merge "Work w/ prefetch even for selects, if present" 2016-07-13 11:48:41 -04:00
Mike Bayer e486ef666f Work w/ prefetch even for selects, if present
Fixed bug in new CTE feature for update/insert/delete stated
as a CTE inside of an enclosing statement (typically SELECT) whereby
oninsert and onupdate values weren't called upon for the embedded
statement.

This is accomplished by consulting prefetch
for all statements.  The collection is also broken into
separate insert/update collections so that we don't need to
consult toplevel self.isinsert to determine if the prefetch
is for an insert or an update.  What we don't yet test for
are CTE combinations that have both insert/update in one
statement, though these should now work in theory provided
the underlying database supports such a statement.

Change-Id: I3b6a860e22c86743c91c56a7ec751ff706f66f64
Fixes: #3745
2016-07-12 16:43:49 -04:00
Mark Hahnenberg bfa57063d4 Fix issue with unbaking subqueries
Fix improper capture of a loop variable inside a lambda during unbaking
of subquery eager loaders, which would cause the incorrect query
to be invoked.

Fixes: #3743
Change-Id: I995110deb8ee2dae8540486729e1ae64578d28fc
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/290
2016-07-12 14:09:14 -04:00
Mike Bayer 6dd795bda0 - 1.0.15 for dev
Change-Id: I2d75b6d9ca533e662bc8160cf5fc52355e5e549e
2016-07-12 14:05:16 -04:00
Shige Takeda 2045689ff2 Update index.rst 2016-07-11 15:58:43 -07:00
Shige Takeda b5bf863217 Update index.rst 2016-07-11 15:56:12 -07:00
Jeong YunWon 21349b23dc Add default parameter for index_property
And force to use keyword arguments for trivial parameters in index_property

Change-Id: I12a178128182f77a2d06b52d7e36f59a36b45a33
2016-07-11 02:57:51 +09:00
Mike Bayer 6b6bdb3542 - fix typo
Change-Id: Ie66d419a5188529a64fcb2e2463c15c26863889f
2016-07-07 16:07:21 -04:00
Mike Bayer b33caa6418 Add additional documentation re: JSONEncodedDict
Add an example of how to use coerce_compared_value()
specific to JSONEncodedDict, as this example class
is frequently dropped into applications.

Change-Id: I61639ac03dc5a37673ee8201b99a3c36ab944f00
Fixes: #3742
2016-07-07 16:00:18 -04:00
Mike Bayer 9f98070a58 - 1.0.14 changelog update
(cherry picked from commit e9a1d7bc6a)

Change-Id: I5bab3fd6f2ec4986fd6b1049844f3851958d0c66
2016-07-06 17:27:47 -04:00
mike bayer 3e654204fd Merge "Adapt "FOR UPDATE OF" with Oracle limit/offset" 2016-07-06 10:13:56 -04:00
Mike Bayer f2ee514c75 Adapt "FOR UPDATE OF" with Oracle limit/offset
This modifies the Oracle ROWNUM limit/offset approach
to accommodate for the "OF" clause in a "FOR UPDATE"
phrase.  The column expressions must be added to the selected
subquery if necessary and adapted on the outside.

Change-Id: Ia71b5fc4df6d326e73863f8ae9f96e8f1a5acfc1
Fixes: #3741
2016-07-05 18:30:25 -04:00
Jeong YunWon 5a2d2f47d6 index_property catches IndexError as well as KeyError
It was raising AttributeError for key accessing in dict,
but raising IndexError for index accessing in array.

Change-Id: I58a2252a9e8d7f78cabcefcbe7223a4f3a729115
2016-07-05 18:24:47 -04:00
Mike Bayer 7c8c124dbe - version bump
Change-Id: I5ace1a90f36678c006d704b452fbbe8a3eb1cd0a
2016-07-05 13:05:07 -04:00
Mike Bayer 428dfeee48 Repair PG BIGSERIAL w/ TypeDecorator, Variant
Some of the dialect impl memoization for TypeDecorator
necessarily keeps the top-level TypeDecorator type
around, since a user-defined type will have bind and result
set processing behavior.  For both TypeDecorator and Variant,
PG dialect needs to ensure it's looking at the SQLAlchemy
type to check for SmallInteger / BigInteger.

Fixes: 3739
Change-Id: I2d45fb997f17c6272d6bb826a77d2dba665adae7
(cherry picked from commit 421fa6b8bf)
2016-07-04 16:54:01 -04:00
Mike Bayer f5ec60c881 Merge remote-tracking branch 'origin/pr/288' 2016-07-04 15:37:58 -04:00
Kristian Perkins ae13473895 fixed typo 2016-07-03 13:59:47 +10:00
Lele Gaifax ae7ef6f610 Fix some typos in 1.1's changelog and migration sections 2016-07-02 13:07:48 +02:00
Lele Gaifax 9ec1312bd5 Consistently use the official PostgreSQL casing 2016-07-02 13:05:27 +02:00
Mike Bayer 26c72fcd4e - add backports
Change-Id: Iee0bf9e60a5991bedbe29b305803b4c79ac5c511
(cherry picked from commit 849df799ec)
2016-07-01 14:59:18 -04:00
Mike Bayer 5c60aaefd3 Preserve type for math negation
Fixed issue in SQL math negation operator where the type of the
expression would no longer be the numeric type of the original.
This would cause issues where the type determined result set
behaviors.

Change-Id: If0e339614a3686e251235fc94b6f59310c4630a5
Fixes: #3735
2016-07-01 12:44:47 -04:00
Mike Bayer 0e4469150a - 1.1.0b2 2016-07-01 10:47:20 -04:00
Mike Bayer f8781840af - revert the RTD reqs workaround, we are self-hosting now
Change-Id: Ie11361147d497c6eb6418cdc850ed277dfbd1de4
2016-07-01 10:39:05 -04:00
mike bayer 07e5b7cf54 Merge "Repair pickling for Properties object" 2016-06-29 17:41:03 -04:00
Pieter Mulder fcfff77128 Repair pickling for Properties object
Fixed bug whereby the ``__getstate__`` / ``__setstate__``
methods for sqlalchemy.util.Properties were
non-working due to the transition in the 1.0 series to ``__slots__``.
The issue potentially impacted some third-party applications.
Pull request courtesy Pieter Mulder.

Fixes: #3728
Change-Id: I01ebd425bbfe145747fea2edd0d2d412c74fd84d
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/286
(cherry picked from commit cab57e9bab04fbdea44690c08dff379a29eaab32)
2016-06-29 17:21:31 -04:00
Mike Bayer acd8b1c107 Ensure @compiles calls down to the original compilation scheme
Made a slight behavioral change in the ``sqlalchemy.ext.compiler``
extension, whereby the existing compilation schemes for an established
construct would be removed if that construct was itself didn't already
have its own dedicated ``__visit_name__``.  This was a
rare occurrence in 1.0, however in 1.1 :class:`.postgresql.ARRAY`
subclasses :class:`.sqltypes.ARRAY` and has this behavior.
As a result, setting up a compilation handler for another dialect
such as SQLite would render the main :class:`.postgresql.ARRAY`
object no longer compilable.

Fixes: #3732
Change-Id: If2c1ada4eeb09157885888e41f529173902f2b49
2016-06-29 11:14:28 -04:00
Mike Bayer 7c74d702a9 Make boolean processors consistent between Py/C; coerce to 1/0
The processing performed by the :class:`.Boolean` datatype for backends
that only feature integer types has been made consistent between the
pure Python and C-extension versions, in that the C-extension version
will accept any integer value from the database as a boolean, not just
zero and one; additionally, non-boolean integer values being sent to
the database are coerced to exactly zero or one, instead of being
passed as the original integer value.

Change-Id: I01e647547fd7047bd549dd70e1fa202c51e8328b
Fixes: #3730
2016-06-23 19:58:43 -04:00
Mike Bayer bf03d4332a Don't reorder PrimaryKeyConstraint columns if explicit
Dialed back the "order the primary key columns per auto-increment"
described in :ref:`change_mysql_3216` a bit, so that if the
:class:`.PrimaryKeyConstraint` is explicitly defined, the order
of columns is maintained exactly, allowing control of this behavior
when necessary.

Change-Id: I9e7902c57a96c15968a6abf53e319acf15680da0
Fixes: #3726
2016-06-20 12:52:31 -04:00
Mike Bayer 91a1022227 Disable Enum string validation by default
Rolled back the validation rules a bit in :class:`.Enum` to allow
unknown string values to pass through, unless the flag
``validate_string=True`` is passed to the Enum; any other kind of object is
still of course rejected.  While the immediate use
is to allow comparisons to enums with LIKE, the fact that this
use exists indicates there may be more unknown-string-comparsion use
cases than we expected, which hints that perhaps there are some
unknown string-INSERT cases too.

Change-Id: I7d1d79b374a7d47966d410998f77cd19294ab7b0
Fixes: #3725
2016-06-20 11:45:24 -04:00
Mike Bayer 4e811fd72e - create space for 1.1.0b2
Change-Id: I8815a68dcf6e5d27f3f82b02f939f72d9a412337
2016-06-20 11:42:53 -04:00
Mike Bayer 13f9578082 - update alembic link
Change-Id: I5ac6ba8234873fdd19bee6c1decd311a9cb4d55e
2016-06-18 09:35:54 -04:00
Mike Bayer fe6b549184 - missing indexable.rst
Change-Id: Ida3ca92b496a1e3ebd761c100201d3660460c2bf
2016-06-18 09:31:11 -04:00
Mike Bayer d59cf4eb3f 1.1.0b1 2016-06-16 16:01:03 -04:00
Mike Bayer ec36df00af - dont need this 2016-06-16 16:01:00 -04:00
mike bayer 21f47e6f7a Merge "Add DDLCompiler.create_table_suffix()" 2016-06-16 15:00:49 -04:00
mike bayer d8da8e4e7d Merge "update pytest good practices link in PyTest class" 2016-06-16 11:53:18 -04:00
Mark Sandan 42078107f1 update pytest good practices link in PyTest class
Change-Id: Ie96edd05e962663e9ddeeda85b24858caabd3bfd
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/262
2016-06-16 11:51:53 -04:00
Mark Sandan d7b8b475f8 Add DDLCompiler.create_table_suffix()
Allows custom dialects to add keywords after the
CREATE TABLE section.

Change-Id: I6fa66dfcf00ef95122f491a9115410df2746cf88
2016-06-16 11:43:02 -04:00
Mike Bayer e5bdf96bc0 - dont use id() to test identity as these can be recycled
Change-Id: Ie4cb4924909d55c5962f66e36cd5325e8e8f0538
2016-06-15 18:15:46 -04:00
Mike Bayer 345cc1e304 - flake8
Change-Id: I74e369d1d71c98cb0af58dde80b7d535d17cbdf7
2016-06-15 18:10:46 -04:00
mike bayer 5c80400ec7 Merge "Add TABLESAMPLE clause support." 2016-06-15 15:17:10 -04:00
mike bayer ecca1f814e Merge "Interpret lateral, alias as from clauses" 2016-06-15 15:16:57 -04:00
saarni 20f2f5b169 Add TABLESAMPLE clause support.
The TABLESAMPLE clause allows randomly selecting an approximate percentage
of rows from a table. At least DB2, Microsoft SQL Server and recent
Postgresql support this standard clause.

Fixes: #3718
Change-Id: I3fb8b9223e12a57100df30876b461884c58d72fa
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/277
2016-06-15 14:42:08 -04:00
Mike Bayer 51e4512abd Interpret lateral, alias as from clauses
Also add doc members for Lateral.

Change-Id: Ic801c296377ce84230139c6a43ecb3e93a852832
2016-06-15 14:36:24 -04:00
Jeong YunWonandMike Bayer 0620a76b58 Add sqlalchemy.ext.index for indexed attributes for ORM
Add `sqlalchemy.ext.index.index_property`
which subscribe an index of a column with `Indexable` type.

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: I238c23131e4fded5dc7f7a25eb02e26008099d00
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/235
2016-06-15 13:05:21 -04:00
mike bayer cfb59ecc9b Merge "Add ON CONFLICT support for Postgresql" 2016-06-14 15:23:17 -04:00
Robin ThomasandMike Bayer 4e9ab7a72f Add ON CONFLICT support for Postgresql
Fixes: #3529
Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Ie3bf6ad70d9be9f0e44938830e922db03573991a
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/258
2016-06-14 15:03:14 -04:00
Mike Bayer f38f890849 Deprecate FromClause.count()
count() here is misleading in that it not only
counts from an arbitrary column in the table, it also
does not make accommodations for DISTINCT, JOIN, etc.
as the ORM-level function does.  Core should not be
attempting to provide a function like this.

Change-Id: I9916fc51ef744389a92c54660ab08e9695b8afc2
Fixes: #3724
2016-06-14 11:48:04 -04:00
Mike Bayer 7189d0bc82 Ensure CTE internals are handled during clone
The CTE construct was missing a _copy_internals() method
which would handle CTE-specific structures including _cte_alias,
_restates during a clone operation.

Change-Id: I9aeac9cd24d8f7ae6b70e52650d61f7c96cb6d7e
Fixes: #3722
2016-06-10 17:24:36 -04:00
Iuri de SilvioandMike Bayer 31a0da32a8 Support postgresql_concurrently on index dropping.
Also adds version detection so that DROP INDEX CONCURRENTLY
only renders if the Postgresql version is 9.2 or higher;
for CREATE INDEX CONCURRENTLY, version detection is added
to allow the phrase to omit if the Postgresql version is
less than 8.2.

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: I597287e0ebbbe256c957a3579b58ace6848ab4f4
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/84
2016-06-08 14:41:05 -04:00
mike bayer 24d29a63b6 Merge "Support normal /materialized views in PG separately" 2016-06-08 13:21:12 -04:00
Mike Bayer c99fc44e17 Use the "committed" values when extracting many-to-one lazyload value
The scalar object set() method calls upon the lazy loader
to get at the "old" value of the attriute, however doesn't
ensure that the "committed" value of the foreign key attributes
is used.  If the user has manipulated these attributes and they
themselves have pending, non committed changes, we get the
"new" value which these attributes would have set up if they
were flushed.  "old" vs "new" value is always about how the
value has changed since the load, so we always have to use the
DB-persisted values for everything when looking for "old".

Change-Id: I82bdc40ad0cf033c3a98f3361776cf3161542cd6
Fixes: #3708
2016-06-08 12:57:21 -04:00
mike bayer 65b3f4aaa0 Merge "Add 'FOR NO KEY UPDATE' / 'FOR KEY SHARE' support for Postgresql" 2016-06-08 11:52:22 -04:00
Sergey SkopinandMike Bayer 3ebd1b30eb Add 'FOR NO KEY UPDATE' / 'FOR KEY SHARE' support for Postgresql
Adds ``key_share=True`` for with_for_update().

Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: I74e0c3fcbc023e1dc98a1fa0c7db67b4c3693a31
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/279
2016-06-08 11:24:57 -04:00
Phillip CloudandMike Bayer d34063aa32 Support range specification in window function
Fixes: #3049
Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Ie572095c3e25f70a1e72e1af6858e5edd89fd25e
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/264
2016-06-07 15:17:22 -04:00
Sebastian Bank 824c8664ed Support normal /materialized views in PG separately
Fixes: #3588
Change-Id: Ifbfcab67375f289ddb5c4522f4b803cb8b7c34de
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/250
2016-06-06 18:57:10 -04:00
mike bayer a90b0101aa Merge "Add "render_nulls" flag to bulk_insert as optional performance optimization" 2016-06-06 18:56:20 -04:00
mike bayer 6bc0da30b0 Merge "Refine PG inspection methods" 2016-06-06 17:29:33 -04:00
tsauerwein 528509e1bc Add "render_nulls" flag to bulk_insert as optional performance optimization
Currently, ``Session.bulk_insert_mappings`` omits NULL values which
causes it to break up batches of inserts based on which batches
contain NULL and which do not.

By adding this flag, the same columns are rendered in the INSERT
for all rows allowing them to be batched.  The downside is that
server-side defaults are omitted.

Doctext-author: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Iec5969304d4bdbf57290b200331bde02254aa3a5
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/243
2016-06-06 16:22:11 -04:00
mike bayer 2860ae6c49 Merge "Add IS (NOT) DISTINCT FROM operators" 2016-06-06 15:57:06 -04:00
mike bayer bc4c6c44af Merge "Replace some uses of re.sub with str.lstrip/replace" 2016-06-06 15:54:53 -04:00
Sebastian Bank 3351f5f93c Add IS (NOT) DISTINCT FROM operators
None / True / False render as literals.
For SQLite, "IS" is used as SQLite lacks
"IS DISTINCT FROM" but its "IS" operator acts
this way for NULL.

Doctext-author: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: I9227b81f7207b42627a0349d14d40b46aa756cce
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/248
2016-06-06 15:53:25 -04:00
Sebastian Bank ec2004d8c2 Refine PG inspection methods
This refines get_schema_names(), get_table_names(),
get_view_defintion(), _get_foreign_table_names(),
and get_view_names() to use better queries and
remove unnecessary explicit encoding logic.

Pull-request: https://github.com/zzzeek/sqlalchemy/pull/250
Change-Id: I7e87b29c34b97b37f21bbc83392b2274af4db0ab
2016-06-06 15:41:36 -04:00
Saulius Žemaitaitisandmike bayer a5f92314ed Allow creating explicit non-clustered keys and indexes MS SQL.
mssql_clustered=False on Index, UniqueConstraint,
PrimaryKeyConstraint now renders NONCLUSTERED.
The default of mssql_clustered is now None.

Co-Authored-By: mike bayer <mike_mp@zzzcomputing.com>
Change-Id: Id6b8d840e355be8f8fa72360cb4b6d2617ba72cf
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/252
2016-06-06 14:27:31 -04:00
Ville Skyttä 9393317aff Replace some uses of re.sub with str.lstrip/replace
Change-Id: I98cd60b6830ee94e39ba9307523a9e8fb93bf4e8
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/280
2016-06-06 12:37:31 -04:00
Mike Bayer 991346d5bb - further adjustment to accomodate for the "ON" in "NO ACTION"
Change-Id: I734e4aec3701d7cf17813b561a1418cfeff1d473
2016-06-03 20:54:48 -04:00
Mike Bayer 6f71cb7c4e - missing test_needs_fk for this test, fixes mysql failure
Change-Id: I2dc6961f9b692a8bb6bfb2296d159df145dec679
2016-06-03 16:44:12 -04:00
Mike Bayer 061bae6e04 Ensure "options" present for unnamed / unlocatable FK
Also ensure the regular expression and subsequent matching
is case insensitive, add more tests

Change-Id: Ie4aa971dcbffca94e78965e22982478eccbf8597
2016-06-03 15:57:16 -04:00
Mike Bayer daf209bd6b Ensure 'options' is always present in foreign key info
Regarding 0e88bcc30e, "options"
needs to be present as a key in the dictionary because Alembic
uses this as a guide to know if the backend is even capable of
reporting on foreign key options.

Change-Id: I271090f75088cfeec24315a878060f9b8a265335
2016-06-03 15:07:14 -04:00
mike bayer a6817579ce Merge "Add SKIP LOCKED support for Postgresql, Oracle" 2016-06-03 10:56:06 -04:00
mike bayer 40f9bcf111 Merge "Reflect ON DELETE and ON UPDATE for SQLite foreign keys" 2016-06-03 10:55:54 -04:00
Mike Bayer 74ca7f627e - use a mock here, do away with timing problems for good. need to do this
for the rest of the timing tests

Change-Id: I06a815b1500222126a4dbc2a9a5da3ef7847e321
2016-06-02 18:40:46 -04:00
Michal PetruchaandMike Bayer 0e88bcc30e Reflect ON DELETE and ON UPDATE for SQLite foreign keys
Co-authored-by: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Icd77ddbf851b1950f767022d67c8142b1b3c50f3
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/244
2016-06-02 17:49:09 -04:00
mike bayer 59d90c95a1 Merge "Add schema argument to AutomapBase.prepare()" 2016-06-02 17:48:13 -04:00
mike bayer ad09d28e80 Merge "Add an init_scalar event for attributes" 2016-06-02 17:47:37 -04:00
Jack Zhou e8f97c9e35 Add SKIP LOCKED support for Postgresql, Oracle
This adds `SELECT ... FOR UPDATE SKIP LOCKED`/
`SELECT ... FOR SHARE SKIP LOCKED` rendering.

Change-Id: Id1dc4f1cafc1de23f397a6f73d54ab2c58d5910d
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/86
2016-06-02 17:46:16 -04:00
Mike Bayer eb28ebb0f8 - limit oracle DB reaps to identifiers generated from this
run to prevent race conditions against concurrent runs

Change-Id: I065d1cec346ea7af03792c3cc2f30766f73c2bd3
2016-06-02 17:42:51 -04:00
mike bayer dc9e35f08d Merge "Skip UniqueConstraint marked by unique=True in tometadata" 2016-06-02 14:42:38 -04:00
Mike Bayer e28b448137 Add an init_scalar event for attributes
This allows us to build default-setting recipes such
as one that allows us to actively read column-level
defaults.  An example suite is also added.

Change-Id: I7b022d52cc89526132d5bc4201ac27fea4cf088d
Fixes: #1311
2016-06-02 14:41:31 -04:00
Josh Marlow cafebe1604 Add schema argument to AutomapBase.prepare()
This allows automap to reflect tables from a schema other than the
default without the need to resort to calling MetaData.reflect
directly.

Change-Id: Ie73cb113bd6d115555c09c5efc33d27ad2c9c512
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/237
2016-06-02 14:00:13 -04:00
mike bayer 31699bd186 Merge "Add postgresql_tablespace option on Index" 2016-06-02 13:57:24 -04:00
Mike Bayer afb466fb8b Skip UniqueConstraint marked by unique=True in tometadata
Fixes an issue where a Column would be copied with unique=True
and at the same time the UniqueConstraint would also be copied,
leading to duplicate UniqueConstraints in the target table,
when tometadata() is used.   Imitates the same logic used
by index=True/Index to avoid duplicates.  For some reason
a fix was implemented for Index long ago but never for
UniqueConstraint.

Change-Id: Ie622ee912a6fb8bf0ea900a8b09d78c7ebc79fc0
Fixes: #3721
2016-06-02 13:54:07 -04:00
Mike Bayer 7a4aa46ae4 - don't raise for stray gc connection. this just happens
sometimes and it really breaks the build once this
error occurs.

Change-Id: I577c78d623b22a6429f8b083fe08821bc467eb7a
2016-06-02 12:46:45 -04:00
beenje ef0da7eb66 Add postgresql_tablespace option on Index
This complements the same-named parameter
available on Table.

Fixes: #3720
Change-Id: I56e081e2a551f37c3f392ca4b301c9ef82b94e59
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/233
2016-06-01 17:20:41 -04:00
Alex GrönholmandMike Bayer a8e7bb8782 Implemented CHECK constraint reflection for SQLite and PostgreSQL
Co-Authored-By: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Ie6cf2d2958d1c567324db9e08fef2d3186e97350
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/80
2016-06-01 12:57:36 -04:00
Sheila Allen 3f55039e7f Use new mxODBC 3.3.4 varbinary null symbol
Use new mxODBC 3.3.4 varbinary null symbol with VARBINARY
data types when value is None(based on similar change to pyodbc).
Fix a test to pass on mxODBC starting w 3.3.3 version

Change-Id: Id703ecb51ebc5db149c81fef124f673433606c7f
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/58
2016-05-31 11:03:34 -04:00
Adam Chainz 513a045395 Convert readthedocs link for their .org -> .io migration for hosted projects
As per their email ‘Changes to project subdomains’:

> Starting today, Read the Docs will start hosting projects from subdomains on the domain readthedocs.io, instead of on readthedocs.org. This change addresses some security concerns around site cookies while hosting user generated data on the same domain as our dashboard.

Test Plan: Manually visited all the links I’ve modified.
2016-05-29 14:28:55 +01:00
Mike Bayer 4856493efc Merge remote-tracking branch 'origin/pr/270' 2016-05-24 16:29:49 -04:00
Mike Bayer c1896741d4 Merge remote-tracking branch 'origin/pr/274' 2016-05-24 16:28:13 -04:00
Mike Bayer 4cec791774 Repair dictlike-polymorphic
dictlike-polymorphic was broken by the change
in 1714e0d6ef.  Use the new
style of inheritance.

Fixes: #3704

Change-Id: I3509ef4bf7772dd6994daf600accf4a2c5eb6973
2016-05-24 16:25:53 -04:00
Mike Bayer c124fa36d5 Support "blank" schema when MetaData.schema is set
Previously, it was impossible to have a Table that has
None for a schema name when the "schema" parameter on
MetaData was set.  A new symbol sqlalchemy.schema.BLANK_SCHEMA
is added which indicates that the schema name should unconditionally
be set to None.  In particular, this value must be passed within
cross-schema foreign key reflection, so that a Table which
is in the "default" schema can be represented properly.

Fixes: #3716
Change-Id: I3d24f99c22cded206c5379fd32a225e74edb7a8e
2016-05-18 11:43:38 -04:00
Mike Bayer fb45433f15 - 1.0.13 release date
Change-Id: I1873dc22c233b5c3585eb7a203bc2352c7cfdbef
2016-05-18 11:08:29 -04:00
mike bayer d3cf79bf87 Merge "Accommodate "callable" bound param in evaluator" 2016-05-16 13:12:51 -04:00
mike bayer 88cd6e4706 Merge "Fix TypeError during cx_Oracle connection" 2016-05-16 13:11:54 -04:00
Mike Bayer a51ab91662 Accommodate "callable" bound param in evaluator
Fixed bug in "evaluate" strategy of :meth:`.Query.update` and
:meth:`.Query.delete` which would fail to accommodate a bound
parameter with a "callable" value, as which occurs when filtering
by a many-to-one equality expression along a relationship.

Change-Id: I47758d3f5d8b9ea1a07e23166780d5f3c32b17f1
Fixes: #3700
2016-05-16 10:32:07 -04:00
Mike Bayer 1873d8107a Fix formatting on test_evaluator
Change-Id: Idcd77a570b19f1b022a74d67fa8253d922dadc67
2016-05-16 10:26:08 -04:00
John Vandenberg 9611ba3a9d Fix TypeError during cx_Oracle connection
cx_Oracle connection parameters user, password and dsn must be
either a string or NULL.  When they are passed a Python None object,
"TypeError: expecting string, unicode or buffer object" is raised.

Fixes: #3705

Change-Id: I8da5d8a227ca12c9bf17a6127460e413841951fb
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/271
2016-05-16 10:15:19 -04:00
vytotas ff71283e53 Fix typo in config result.py docs 2016-05-16 13:02:30 +02:00
Iuri de Silvio 8ecad78ba3 Handle SSL error: decryption failed or bad record mac
This is another psycopg2 error message representing an
unusable connection.

Fixes #3715
Change-Id: Ida6e212963e9c7336bf2944e7ef928619ac3a0e7
Pull-request: https://bitbucket.org/zzzeek/sqlalchemy/pull-requests/85
2016-05-13 21:23:17 -04:00
Mike Bayer 9e75d3ed8f Merge remote-tracking branch 'origin/pr/272' 2016-05-13 11:41:51 -04:00
Frank Carnovale fb289799f4 typo in glossary#release: s/proces/process/ 2016-05-12 17:57:11 +01:00
Frank Carnovale 1d81219aec typo in glossary#FROMclause: s/incicates/indicates/ 2016-05-12 17:57:11 +01:00
Frank Carnovale 2774113dab typo in glossary#instrumentation: s/behviors/behaviors/ 2016-05-12 17:57:11 +01:00
Mike Bayer 7f08d8c93a Add close_with_result to pessimistic connection example
For connectionless execution, the recipe here will fail unless
the should_close_with_result flag is temporarily set to False.

Change-Id: Ib77b4439e8361b24478108c413b1ba720a68350f
Fixes: #3712
2016-05-12 07:54:14 -04:00
Mike Bayer 0604116814 Fix label referencing in SQL Server OFFSET logic
Fixed bug where by ROW_NUMBER OVER clause applied for OFFSET
selects in SQL Server would inappropriately substitute a plain column
from the local statement that overlaps with a label name used by
the ORDER BY criteria of the statement.

Change-Id: Ic2500c886cbfc83a1ad5a2681783f008b9f23838
Fixes: #3711
2016-05-10 12:55:23 -04:00
Mike Bayer 743e9d4589 Check for duplicate calls to register_attribute_impl
Fixed bug whereby the event listeners used for backrefs could
be inadvertently applied multiple times, when using a deep class
inheritance hierarchy in conjunction with mutiple mapper configuration
steps.

Change-Id: I712beaf4674e2323bf5b282922658020a6d00b53
Fixes: #3710
2016-05-10 11:05:30 -04:00
Mark Sandan ba3d4aa5ba change "psotgresql" to 'postgresql' in decorator 2016-05-06 18:26:31 -07:00
Mike Bayer 9bdd6f2b1f Repair _orm_columns() to accommodate text()
Fixed bug whereby passing a :func:`.text` construct to the
:meth:`.Query.group_by` method would raise an error, instead
of intepreting the object as a SQL fragment.

Change-Id: I5fc2f590b76508d52e23b5fa9cf037ddea8080c3
fixes: #3706
2016-05-05 17:07:40 -04:00
Ville Skyttä 61f9e37612 Spelling fixes: "an SQL" -> "a SQL", see #266 2016-05-05 09:02:38 +03:00
Ville Skyttä 7a1e2dd92f Spelling fixes: "the a" 2016-05-05 09:00:28 +03:00
Mike Bayer f1920d2713 Merge remote-tracking branch 'origin/pr/269' 2016-05-04 15:53:05 -04:00
Mike Bayer cba9513bc9 Merge remote-tracking branch 'origin/pr/268' 2016-05-04 15:52:05 -04:00
Mike Bayer 6c47f66011 Merge remote-tracking branch 'origin/pr/267' 2016-05-04 15:49:28 -04:00
Mike Bayer d2656136ab Merge remote-tracking branch 'origin/pr/265' 2016-05-04 15:40:53 -04:00
Jeffrey Finkelstein 792083d23b Corrects typo: plural of vertex is vertices. 2016-05-03 21:09:36 -04:00
Jeffrey Finkelstein c31833e997 Adds parentheses around print statements in docs. 2016-05-03 21:02:29 -04:00
Jeffrey Finkelstein e6251c3e40 Corrects some references in ORM documentation. 2016-05-03 20:46:20 -04:00
Ville Skyttä 1322edc7b1 Let logging format messages on demand, use warning instead of deprecated warn 2016-05-03 18:29:41 +03:00
Mike Bayer 9a3c9ba7be Fix pymssql sample URL
A slash is required before building out the query string portion.

Change-Id: Ie97fd3d07047d78e17cbaffed4ff54960a2b956e
Fixes: #3696
(cherry picked from commit 83a9e6e1fa)
2016-04-27 15:09:39 -05:00
Mike Bayer 9e77f40a31 Merge remote-tracking branch 'origin/pr/263' 2016-04-27 14:02:09 -05:00
Mike Bayer f3bc60bdd8 Don't double-process ResultMetaData for BufferedColumnResultProxy
Fixed a bug in the result proxy used mainly by Oracle when binary and
other LOB types are in play, such that when query / statement caching
were used, the type-level result processors, notably that required by
the binary type itself but also any other processor, would become lost
after the first run of the statement due to it being removed from the
cached result metadata.

Change-Id: I751940866cffb4f48de46edc8137482eab59790c
Fixes: #3699
2016-04-27 11:37:58 -05:00
jfinkels 8aa7369125 Adds parentheses around prints in documentation
This makes the docstring example code compatible with both Python 2 and Python 3.
2016-04-27 02:35:55 -04:00
Mike Bayer 84ba09a7d7 Simplify directed graph example
Changed the "directed graph" example to no longer consider
integer identifiers of nodes as significant; the "higher" / "lower"
references now allow mutual edges in both directions.

Change-Id: Ibfd5b420f0451a6fc746f0bcbbbb062f8f88dc1d
Fixes: #3698
(cherry picked from commit c3de4061fd)
2016-04-26 19:01:22 -05:00
Mike Bayer ffb6fbf825 - don't use --dropfirst when we are using ad-hoc DBs. dropfirst
is unnecessary and causes collisions against other CI runs

Change-Id: I47e9bc98cd6ef4ab90be25bae45897dabae16308
2016-04-24 14:44:04 -04:00
Mike Bayer 1f3e5d9826 Fix result set handling for case insensitive dupe cols
Fixed bug where when using ``case_sensitive=False`` with an
:class:`.Engine`, the result set would fail to correctly accomodate
for duplicate column names in the result set, causing an error
when the statement is executed in 1.0, and preventing the
"ambiguous column" exception from functioning in 1.1.

Change-Id: If582bb9fdd057e4da3ae42f7180b17d1a1a2d98e
Fixes: #3690
2016-04-21 10:36:19 -04:00
mike bayer 8ab08cf805 Merge "Deprecate Mapper.order_by" 2016-04-19 18:50:04 -04:00
Mike Bayer 23825a2591 Deprecate Mapper.order_by
This is an old parameter no longer relevant to how SQLAlchemy
works, once the Query object was introduced.  By deprecating it
we establish that we aren't supporting non-working use cases
and that we encourage applications to move off of the use of this
parameter.

Fixes: #3394
Change-Id: I25b9a38142a1537bbcb27d3e8b66a8b265140072
2016-04-19 18:17:45 -04:00
Mike Bayer 81bd994c0a Rename Query._mapper_zero() to Query._entity_zero()
To be more descriptive of the use of _mapper_zero(), rename
it to _entity_zero(), but also supply a new _mapper_zero() function
that more strictly returns a mapper.  The existing
_entity_zero() function is renamed to _query_entity_zero.
_only_mapper_zero() is removed as it isn't used.  Divide up the
existing calling functions to refer to the appropriate new method.

Change-Id: I8780c3235e87b4936c6daf64d9d299b22b6e1260
Fixes: #3608
2016-04-19 15:53:50 -04:00
mike bayer 56dafa6c0d Merge "Add raise/raiseload relationship loading strategy" 2016-04-19 13:44:51 -04:00
Adrian MoennichandMike Bayer 33921261f8 Add raise/raiseload relationship loading strategy
Fixes: #3512
Co-Authored-By: Mike Bayer <mike_mp@zzzcomputing.com>
Change-Id: Ibd126c50eda621e2f4120ee378f7313af2d7ec3c
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/193
2016-04-19 13:04:41 -04:00
Mike Bayer 6f6e2c48ba Propagate hybrid properties / info
Keystone and others depend on the .property attribute being
"mirrored" when a @hybrid_property is linked directly to a
mapped attribute.  Restore this linkage and also create a defined
behavior for the .info dictionary; it is that of the hybrid itself.
Add this behavioral change to the migration notes.

Change-Id: I8ac34ef52039387230c648866c5ca15d381f7fee
References: #3653
2016-04-18 16:20:20 -04:00
Mike Bayer 243b222a23 Honor hybrid property / method docstrings
The docstring specified on a hybrid property or method is now honored
at the class level, allowing it to work with tools like Sphinx
autodoc.  The mechanics here necessarily involve some wrapping of
expressions to occur for hybrid properties, which may cause them
to appear differently using introspection.

Fixes: #3653
Change-Id: I02549977fe8b2a051802eed7b00cc532fbc214e3
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/239
2016-04-18 12:55:48 -04:00
mike bayer 35e93db7ff Merge "- Add support for PostgreSQL with PyGreSQL" 2016-04-15 12:47:33 -04:00
Christoph Zwerschke b59cbb5fd7 - Add support for PostgreSQL with PyGreSQL
Change-Id: I040b75ff3b4110e7e8b26442a4eb226ba8c26715
Pull-request: https://github.com/zzzeek/sqlalchemy/pull/234
2016-04-15 12:00:27 -04:00
Mike Bayer cf6ed33ba9 - .gitreview default branch
Change-Id: I7c70b2a4f92dbed5924e2592b204434e09fae007
2016-04-12 17:28:56 -04:00
Mike Bayer bde46e3359 Merge remote-tracking branch 'origin/pr/257' 2016-04-08 21:42:11 -04:00
Eoghan Murray 2880f24d93 Mention the correct way of adding multiple attributes which refer to the same column 2016-04-07 11:57:14 +01:00
Rachid Belaid c8db0862c1 Fix typo from "addreses" to "addresses" 2016-04-06 20:41:34 -07:00
mike bayer 829bd30834 Merge "- don't load deferred columns on unexpire for merge with load=False, fixes #3488" 2016-04-06 13:32:10 -04:00
Diana ClarkeandMike Bayer bef15a950e - don't load deferred columns on unexpire for merge with load=False,
fixes #3488

Change-Id: Ic9577b800e4a4e2465ec7f3a2e95bd231f5337ee
Co-Authored-By: Mike Bayer <mike_mp@zzzcomputing.com>
2016-04-06 13:28:25 -04:00
Mike Bayer 34be0bc781 Merge remote-tracking branch 'origin/pr/255' 2016-04-06 09:59:35 -04:00
Mike Bayer be7322b3da - Move review to gerrit.sqlalchemy.org
Change-Id: Id6e9014cfa8ad558b2f3e90815616f9c26dc884d
2016-04-06 09:35:18 -04:00
Ville Skyttä b1c9b3bd38 Fix some broken links in docs 2016-04-04 13:46:07 +03:00
Mike Bayer fdb6ab6a1d - Add a git review file
Change-Id: Ib19e9ee0854f0d123ea625fb976f1a398cf88c87
2016-03-31 15:24:14 -04:00
Mike Bayer 10def637d3 - callcount refresh due to negative indexes change for nocext 2016-03-31 09:55:20 -04:00
Mike Bayer fdb65744d4 - limit this to sqlite for now 2016-03-30 18:59:01 -04:00
Mike Bayer 03d35a833c - move all resultproxy tests intio test_resultset 2016-03-30 17:36:03 -04:00
Mike Bayer dd20f56bc9 - make sure negative row indexes are based on the size of the
number of columns we're actually reporting on
- add more tests for negative row index
- changelog/migration
2016-03-30 17:27:53 -04:00
Mike Bayer 4df1e07bb9 Merge remote-tracking branch 'origin/pr/231' into pr231 2016-03-30 17:05:30 -04:00
Patrick 4a3205df84 Docstring Fix
Change the docstring in short_selects example to match the code
2016-03-30 21:45:40 +01:00
Mike Bayer 5370f0503a - changelog for #3629, fixes #3629 2016-03-30 16:32:55 -04:00
Mike Bayer e6cbf44d6d Merge remote-tracking branch 'origin/pr/230' 2016-03-30 16:25:41 -04:00
NestorTejero 9bdbf19d54 redundant "using the by changing" -> "using the" 2016-03-30 08:48:48 +02:00
Mike Bayer fb9d481e89 - Added :meth:.Select.lateral and related constructs to allow
for the SQL standard LATERAL keyword, currently only supported
by Postgresql.  fixes #2857
2016-03-29 17:56:02 -04:00
Mike Bayer d619191180 - Added support for rendering "FULL OUTER JOIN" to both Core and ORM.
Pull request courtesy Stefan Urbanek.  fixes #1957
2016-03-28 11:50:09 -04:00
Mike Bayer 63d2a486bf - remember to not reassign self.connection now that __connect()
has no return value
2016-03-25 19:33:15 -04:00
Mike Bayer 8a776122a3 - Added connection pool events :meth:ConnectionEvents.close,
:meth:`.ConnectionEvents.detach`,
:meth:`.ConnectionEvents.close_detached`.
2016-03-25 18:31:17 -04:00
Mike Bayer d594691a1a - oracle doesn't release savepoints 2016-03-24 11:18:53 -04:00
Mike Bayer 0a29071b16 - Further continuing on the common MySQL exception case of
a savepoint being cancelled first covered in 🎫`2696`,
the failure mode in which the :class:`.Session` is placed when a
SAVEPOINT vanishes before rollback has been improved to allow the
:class:`.Session` to still function outside of that savepoint.
It is assumed that the savepoint operation failed and was cancelled.
fixes #3680
2016-03-23 16:54:03 -04:00
Mike Bayer 2d5b7a139f Merge remote-tracking branch 'origin/pr/251' 2016-03-21 11:05:40 -04:00
Mike Bayer 07a4b6cbcd - Fixed bug where the negation of an EXISTS expression would not
be properly typed as boolean in the result, and also would fail to be
anonymously aliased in a SELECT list as is the case with a
non-negated EXISTS construct.
fixes #3682
2016-03-21 10:57:40 -04:00
Marius Gedminas e3abb63293 ReST fix: missing backtick
Fixes a misrendering at http://docs.sqlalchemy.org/en/latest/dialects/mssql.html#nullability:
2016-03-21 12:00:49 +02:00
Benjamin Dopplinger 732c613eeb Fix typo 2016-03-16 14:30:04 +11:00
Mike Bayer edbb326499 - ensure engine is restored even if we had a failure in cleanup
for stray connection
2016-03-15 18:01:23 -04:00
Mike Bayer 4d147c3b16 - Added basic isolation level support to the SQL Server dialects
via :paramref:`.create_engine.isolation_level` and
:paramref:`.Connection.execution_options.isolation_level`
parameters.  fixes #3534
2016-03-15 17:47:34 -04:00
Mike Bayer 31f96c27a5 - changelog and docs for #3332, fixes #3332
- make docs for isolation level more consistent between postgresql
and mysql
- move mysql autocommit tests
2016-03-15 17:17:21 -04:00
Mike Bayer 224b03f9c0 Merge branch 'master' into pr157 2016-03-15 16:41:17 -04:00
Mike Bayer 8bc370ed38 - add notes for pyodbc limitations with rowcount fixes #3675 2016-03-15 11:16:21 -04:00
Mike Bayer af92f6763d - Fixed bug where a newly inserted instance that is rolled back
would still potentially cause persistence conflicts on the next
transaction, because the instance would not be checked that it
was expired.   This fix will resolve a large class of cases that
erronously cause the "New instance with identity X conflicts with
persistent instance Y" error.
fixes #3677
2016-03-14 17:56:57 -04:00
jfinkels 6e5e64e27e Adds documentation to Query.slice(). 2016-03-13 16:37:55 -04:00
falkerson f61194cb86 Update cascades.rst 2016-03-09 09:56:30 +02:00
Mike Bayer be7f8e0b81 - skip GC tests here when coverage is enabled, seems to interfere 2016-03-08 09:28:44 -05:00
Mike Bayer 0e7904e730 - not sure why MySQL DROP DBs fail but we can't just ignore the error
like this
2016-03-03 10:50:18 -05:00
Mike Bayer 6b7c207801 - move out unconsumed names tests from test_compiler out to test_insert, test_update
- establish consistent names between existing unconsumed names tests and new ones
added per ref #3666
2016-03-02 20:24:49 -05:00
Mike Bayer 3d83e1639e - changelog for #3666, fixes #3666 2016-03-02 20:13:42 -05:00
Athena Yao a1de176d23 Add test for inserting multiple values 2016-03-02 11:43:09 -08:00
Athena Yao 399f92cd11 Raise exception when we have multiple values with an unknown column. Fixes #3666. 2016-03-02 11:16:14 -08:00
Mike Bayer 8a20d277c5 - unfortunately calling upon "_label" here makes it unclear if
we're trying to hit columns without names yet and such, to suit the bug
right now just make it specific to FunctionElement

(cherry picked from commit 785224a92f)
2016-02-26 11:27:49 -05:00
Mike Bayer 0210695bd9 - Anonymous labeling is applied to a :attr:.func construct that is
passed to :func:`.column_property`, so that if the same attribute
is referred to as a column expression twice the names are de-duped,
thus avoiding "ambiguous column" errors.   Previously, the
``.label(None)`` would need to be applied in order for the name
to be de-anonymized.
fixes #3663
2016-02-26 00:20:39 -05:00
Mike Bayer f8914288f0 - An improvement to the workings of :meth:.Query.correlate such
that when a "polymorphic" entity is used which represents a straight
join of several tables, the statement will ensure that all the
tables within the join are part of what's correlating.
fixes #3662
2016-02-25 23:27:49 -05:00
Mike Bayer eff7b4f29d - additional adjustment to the fix made in 8ad968f331
for ref #3657.  The Oracle dialect makes more use of the "select_wraps_for"
feature than SQL server because Oracle doesn't have "TOP" for a limit-only
select, so tests are showing more happening here.  In the case where
the select() has some dupe columns, these are deduped from the .c collection
so a positional match between the wrapper and original can't use .inner_columns,
because these collections wont match.  Using _columns_plus_names
instead which is the deduped collection that determines the SELECT display,
which definitely have to match up.

(cherry picked from commit aa9ce3f521)
2016-02-21 22:49:29 -05:00
Mike Bayer 01809bddff - Fixed bug in "to_list" conversion where a single bytes object
would be turned into a list of individual characters.  This would
impact among other things using the :meth:`.Query.get` method
on a primary key that's a bytes object.
fixes #3660
2016-02-21 20:52:43 -05:00
Mike Bayer 6713817e11 - update the mssql autoincrement reflection test to accommodate
the new behavior of the autoincrement flag as per ref #3216
2016-02-20 20:43:36 -05:00
Mike Bayer 8ad968f331 - reworked the way the "select_wraps_for" expression is
handled within visit_select(); this attribute was added in the
1.0 series to accommodate the subquery wrapping behavior of
SQL Server and Oracle while also working with positional
column targeting and no longer relying upon "key fallback"
in order to target columns in such a statement.  The IBM DB2
third-party dialect also has this use case, but its implementation
is using regular expressions to rewrite the textual SELECT only
and does not make use of a "wrapped" select at this time.
The logic no longer attempts to reconcile proxy set collections as
this was not deterministic, and instead assumes that the select()
and the wrapper select() match their columns postionally,
at least for the column positions they have in common,
so it is now very simple and safe.  fixes #3657.
- as a side effect of #3657 it was also revealed that the
strategy of calling upon a ResultProxy._getter was not
correctly calling into NoSuchColumnError when an expected
column was not present, and instead returned None up to
loading.instances() to produce NoneType failures; added
a raiseerr argument to _getter() which is called when we
aren't expecting None, fixes #3658.
2016-02-20 20:22:38 -05:00
Jeff Widman 60a9d2da25 Add release date for 1.0.12 to changelog 2016-02-19 09:59:47 -08:00
Mike Bayer c97aa63789 - further edit the unnest() example to suit PG's esoteric requirements
exactly
2016-02-18 11:33:19 -05:00
Mike Bayer 594a974ede - Fixed bug which would cause an eagerly loaded many-to-one attribute
to not be loaded, if the joined eager load were from a row where the
same entity were present multiple times, some calling for the attribute
to be eagerly loaded and others not.  The logic here is revised to
take in the attribute even though a different loader path has
handled the parent entity already. fixes #3431
2016-02-17 18:01:20 -05:00
Mike Bayer 2965da0a5d - handle parameter sets that aren't correctly formed, so that
for example an exception object made within a test suite can
still repr (error seen in Keystone)
2016-02-17 16:53:01 -05:00
Mike Bayer bf1d03a9e5 - do the trailing comma logic of tuple repr() exactly 2016-02-17 15:21:00 -05:00
Mike Bayer 591e0cf08a - All string formatting of bound parameter sets and result rows for
logging, exception, and  ``repr()`` purposes now truncate very large
scalar values within each collection, including an
"N characters truncated"
notation, similar to how the display for large multiple-parameter sets
are themselves truncated.
fixes #2837
2016-02-17 13:31:29 -05:00
Mike Bayer a99a32d3d1 - add changelog, migration, version flags and some extra notes
to the new MutableList and MutableSet classes, fixes #3297
2016-02-16 15:50:25 -05:00
Mike Bayer c46b49496c Merge remote-tracking branch 'origin/pr/236' 2016-02-16 15:43:22 -05:00
Mike Bayer e310a8e423 - use same colname as the alias we give to the PG function
here, fixes #3652
2016-02-16 10:05:58 -05:00
Jeong YunWon f7354b43e4 Add sqlalchemy.ext.mutable.MutableSet
from https://bitbucket.org/zzzeek/sqlalchemy/issues/3297
2016-02-13 21:28:50 +09:00
Jeong YunWon 1b6422a603 Add sqlalchemy.ext.mutable.MutableList 2016-02-13 21:28:46 +09:00
Mike Bayer 366f97b561 - Fixed bug in :meth:.Session.merge where an object with a composite
primary key that has values for some but not all of the PK fields
would emit a SELECT statement leaking the internal NEVER_SET symbol
into the query, rather than detecting that this object does not have
a searchable primary key and no SELECT should be emitted.
fixes #3647
2016-02-11 22:29:18 -05:00
Mike Bayer e5f1a3fb7d - CTE functionality has been expanded to support all DML, allowing
INSERT, UPDATE, and DELETE statements to both specify their own
WITH clause, as well as for these statements themselves to be
CTE expressions when they include a RETURNING clause.
fixes #2551
2016-02-11 12:27:28 -05:00
Mike Bayer 287aaa9d41 - add more documentation to MutableDict explaining
that this structure is only intended to track additions
and removals from the dictionary, not recursive tracking
of embedded changes.  fixes #3646.
2016-02-10 10:17:45 -05:00
Mike Bayer 3f1f1895ac - don't drop the ts1/ts2 databases without seeing the primary DB,
because we never log in on the ts1/ts2.  races against other runs
and erases their DBs
2016-02-09 21:08:21 -05:00
Mike Bayer 29dcaa2b0a - Fixed bug in :func:.expression.text construct where a double-colon
expression would not escape properly, e.g. ``some\:\:expr``, as is most
commonly required when rendering Postgresql-style CAST expressions.
fixes #3644
2016-02-09 18:05:40 -05:00
Mike Bayer ff3be95620 - A refinement to the logic which adds columns to the resulting SQL when
:meth:`.Query.distinct` is combined with :meth:`.Query.order_by` such
that columns which are already present will not be added
a second time, even if they are labeled with a different name.
Regardless of this change, the extra columns added to the SQL have
never been returned in the final result, so this change only impacts
the string form of the statement as well as its behavior when used in
a Core execution context.   Additionally, columns are no longer added
when the DISTINCT ON format is used, provided the query is not
wrapped inside a subquery due to joined eager loading.
fixes #3641
2016-02-09 17:49:38 -05:00
Mike Bayer 7d2bed69ab - switch to 2 workers for oracle 2016-02-09 10:17:10 -05:00
Mike Bayer 11a8440bc4 - Testing reveals that we have *no* weak references to any cx_Oracle connections at all,
yet cx_Oracle still has open sessions that cannot be killed until process dies.
Oracle wins!   Add a completely separate DB reaper script that runs
after py.test is done.
2016-02-08 22:57:02 -05:00
Mike Bayer 00a05e357b - use config-based test schema 2016-02-08 22:56:02 -05:00
Mike Bayer 40c836172c - attempt a different style of session kill 2016-02-08 19:49:47 -05:00
Mike Bayer 7eff4e8f3e - fully hyperlink the docstring for make_transient
- establish make_transient and make_transient_to_detached as special-use,
advanced use only functions
- list all conditions under make_transient() under which an attribute
will not be loaded and establish that make_transient() does not attempt
to load all attributes before detaching the object from its
session, fixes #3640
2016-02-08 18:05:51 -05:00
Mike Bayer 7cb2a2d6c0 - additional fixes to get oracle + multiprocess to be reliable 2016-02-08 16:27:55 -05:00
Mike Bayer 0f6d1b7efb - py3k fix for enum feature 2016-02-08 16:27:44 -05:00
Mike Bayer 6831c67b8e - add missing __backend__ directives for SQL server 2016-02-08 14:20:12 -05:00
Mike Bayer 860d07ff89 - add missing __backend__ directives so that oracle tests actually run with --backend-only 2016-02-08 14:16:40 -05:00
Mike Bayer 308244a90b - detect "Enterprise" and assume compression stuff isn't available
if not
2016-02-08 14:08:03 -05:00
Mike Bayer 80853059a9 - adjust the MultiSchemaTest to handle multiple test_schemas / processes at the
same time
2016-02-08 13:35:36 -05:00
Mike Bayer 7e619d0be4 - adjust to allow dblink tests to work with multiprocess users.
unfortunately the synonym doesn't work for SQL statements here
when the dblink is on a different user, testing this is not really
critical so just removed it.
2016-02-08 13:13:39 -05:00
Mike Bayer c70d7226ee - add a session killer for oracle provisioning 2016-02-04 13:59:32 -05:00
Mike Bayer fd07c22e6e - add an impl for Enum to Oracle which has subclassing requirements
on unicode.   Enum would be better as a TypeDecorator
at this point but then that becomes awkward with native enum
types (Interval works that way, but we don't need the bind_processor for
native interval...)
2016-02-04 13:36:45 -05:00
Mike Bayer 93c5328e66 - more oracle fixes 2016-02-03 20:37:42 -05:00
Mike Bayer c1316a2992 - oracle requires GLOBAL here 2016-02-03 19:34:29 -05:00
Mike Bayer c01d11907c - add multi-database provisioning for oracle 2016-02-03 18:26:00 -05:00
Josh Friend d464933fd5 Fix typo in relationship persistance docs 2016-02-03 11:49:18 -05:00
Mike Bayer 150591f9e0 - add literal_binds for delete() statements in addition to insert()/update()
- move tests to CRUDTest
- changelog, fixes #3643
2016-02-03 11:07:44 -05:00
Tim Tate c9b03fa8af fix passing literal_binds flag through for update and insert 2016-02-02 15:40:07 -08:00
Mike Bayer 9149fd062b - changelog for #3621 fixes #3621 2016-02-02 17:29:42 -05:00
Mike Bayer 6d58934791 Merge branch 'master' of https://bitbucket.org/carlrivers/sqlalchemy 2016-02-02 17:27:09 -05:00
Mike Bayer ba1bfef0f2 - test fixes for metadata.enums value now being a list
- modernize those tests as well
2016-02-02 16:59:56 -05:00
Mike Bayer df55695f8e - add changelog and migration notes for new Enum features,
fixes #3095, #3292
- reorganize enum constructor to again work with the MySQL
ENUM type
- add a new create_constraint flag to Enum to complement that of
Boolean
- reinstate the CHECK constraint tests for enum, these already
fail /skip against the MySQL backend
- simplify lookup rules in Enum, have them apply to all varieties
of Enum equally
2016-02-02 15:04:46 -05:00
Alex Grönholm 5401c4d851 - Initial implementation of support for PEP-435 enumerated types
within the Enum type.
2016-02-02 14:21:54 -05:00
Mike Bayer 86660fef7e - D rules seem to have been added overnight to the flake8 plugin
I'm using and many of these seem contradictory and/or undesirable.
block all until individual rules can be approved.
2016-02-02 12:15:35 -05:00
Mike Bayer e0a580b3d0 - Fixed issue where inadvertent use of the Python `__contains__`
override with a column expression (e.g. by using ``'x' in col``)
would cause an endless loop in the case of an ARRAY type, as Python
defers this to ``__getitem__`` access which never raises for this
type.  Overall, all use of ``__contains__`` now raises
NotImplementedError.
fixes #3642
2016-02-02 10:20:54 -05:00
Mike Bayer c8b3d4ed3f - put a retry in for PG database provisioning as it locks
on database use
2016-01-29 12:19:17 -05:00
Mike Bayer c59bf0007f - The `sqlalchemy.dialects.postgres` module, long deprecated, is
removed; this has emitted a warning for many years and projects
should be calling upon ``sqlalchemy.dialects.postgresql``.
Engine URLs of the form ``postgres://`` will still continue to function,
however.
2016-01-29 11:44:58 -05:00
Mike Bayer 859379e2fc - happy new year 2016-01-29 11:20:22 -05:00
Diana Clarke abeb762f88 same logic, but without the inner function 2016-01-28 18:55:12 -05:00
Mike Bayer 14b1e6fe8e - use a StaticPool for componentreflectiontest to ensure
temp tables are reflectable on the same session they were
created
2016-01-28 18:10:42 -05:00
Mike Bayer 13dfc532ac - use schema argument correctly when we are dropping for a schema 2016-01-28 17:16:55 -05:00
Mike Bayer 8d1579cc3c - using extras here has the effect of defeating the usedevelop flag
since SQLAlchemy gets installed as develop and in the virtualenv
2016-01-28 16:23:48 -05:00
Mike Bayer 8a1e619fb2 - revert the change first made in a6fe4dc, as we are now generalizing
the warning here to all safe_reraise() cases in Python 2.
- Revisiting 🎫`2696`, first released in 1.0.10, which attempts to
work around Python 2's lack of exception context reporting by emitting
a warning for an exception that was interrupted by a second exception
when attempting to roll back the already-failed transaction; this
issue continues to occur for MySQL backends in conjunction with a
savepoint that gets unexpectedly lost, which then causes a
"no such savepoint" error when the rollback is attempted, obscuring
what the original condition was.

The approach has been generalized to the Core "safe
reraise" function which takes place across the ORM and Core in any
place that a transaction is being rolled back in response to an error
which occurred trying to commit, including the context managers
provided by :class:`.Session` and :class:`.Connection`, and taking
place for operations such as a failure on "RELEASE SAVEPOINT".
Previously, the fix was only in place for a specific path within
the ORM flush/commit process; it now takes place for all transational
context managers as well.
fixes #2696
2016-01-28 15:01:31 -05:00
Lele Gaifax f84ef1f83c - properly handle negative indexes in RowProxy.__getitem__() 2016-01-28 09:04:40 +01:00
Diana Clarke b3b3c68a4a sqlite: reflect primary key constraint names, fixes #3629 2016-01-27 22:54:05 -05:00
Mike Bayer 086ad9ce64 - experimental - try out a very open ended design for the factors, assume
many more combinations of factors are possible and basically make them
more akin to command options at the tox level.
2016-01-27 17:39:48 -05:00
Mike Bayer 516a442f23 - reinstate "dont set up integer index in keymap if we're on cexts",
and this time also fix the cext itself to properly handle int vs. long
on py2k
2016-01-27 14:49:40 -05:00
Mike Bayer 49dfeda6d7 - restore the use of PYTHONNOUSERSITE that was removed
in df3f125bd8, this flag is
explicitly checked within conftest.py and we need to continue to use
it, otherwise a tox build inside of .tox that isn't usedevelop
is ignored, including C extensions
- rework the whole system of running with coverage, so that
with coverage, we *are* using usedevelop, but also make sure
we rm the .so files for nocext, make sure we --cov-append, etc.
2016-01-27 14:23:33 -05:00
Mike Bayer 8aa95fa2cd Revert "- dont set up integer index in keymap if we're on cexts"
This reverts commit de0d144a39.

Apparently the test suite is not using the cextensions correctly at the moment.
2016-01-27 12:41:01 -05:00
Mike Bayer de0d144a39 - dont set up integer index in keymap if we're on cexts 2016-01-27 11:35:43 -05:00
Ruilin Huang 4b9f6f407c fix %x string format to compatible with Python 3.5 2016-01-27 08:21:59 +00:00
xghrl 324e532d60 fix %x string format to compatible with Python 3.5 2016-01-27 08:10:06 +00:00
Mike Bayer 5742e321b2 - unfortunately we need to match within join where col.key does not match
what's given so we need to use a set() here.  contains_column is not within
any performance paths
2016-01-26 17:28:40 -05:00
Carlos Rivas c6d630ca81 Merged zzzeek/sqlalchemy into master 2016-01-26 13:45:31 -08:00
Mike Bayer 8163de4cc9 - rework ColumnCollection to no longer persist "all_col_set"; we don't
need this collection except in the extend/update uses where we
create it ad-hoc.  simplifies pickling.  Compatibility with 1.0
should be OK as ColumnColleciton uses __getstate__ in any case
and the __setstate__ contract hasn't changed.
- Fixed bug in :class:`.Table` metadata construct which appeared
around the 0.9 series where adding columns to a :class:`.Table`
that was unpickled would fail to correctly establish the
:class:`.Column` within the 'c' collection, leading to issues in
areas such as ORM configuration.   This could impact use cases such
as ``extend_existing`` and others.  fixes #3632
2016-01-26 16:41:26 -05:00
Mike Bayer 9d9fc93b70 - The workaround for right-nested joins on SQLite, where they are rewritten
as subqueries in order to work around SQLite's lack of support for this
syntax, is lifted when SQLite version 3.7.16 or greater is detected.
fixes #3634
- The workaround for SQLite's unexpected delivery of column names as
``tablename.columnname`` for some kinds of queries is now disabled
when SQLite version 3.10.0 or greater is detected.
fixes #3633
2016-01-26 16:09:23 -05:00
Mike Bayer df3f125bd8 remove PYTHONNOUSERSITE, not sure why this was here, it apparently interferes with coverage 2016-01-26 13:38:34 -05:00
Mike Bayer d100bfcf60 - another approach at coverage 2016-01-26 12:57:18 -05:00
Mike Bayer ebefbb3d3d - try to improve the default coverage job 2016-01-26 12:06:24 -05:00
Mike Bayer 70e24adaba - fix the deps for the last change 2016-01-24 19:37:16 -05:00
Mike Bayer 0ad5599229 - unfortunately we have to force the paths to be shorter due to
https://github.com/pypa/virtualenv/issues/596
2016-01-24 19:29:26 -05:00
Mike Bayer 6b05150392 - add a new qualifier "native" vs. "dbapi" unicode to avoid
profiling problems here
- add extras_require to setup.py for the most common DBAPIs
- rework tox.ini to use extras, specify a test matrix built in
2016-01-24 18:28:09 -05:00
Mike Bayer 926784f513 - fix array test that was essentially taking a weird guess
at the primary key of a row based on other tests invoking around it

(cherry picked from commit 7d70dfd412)
2016-01-23 18:31:07 -05:00
Mike Bayer 2419bfe34c - fix stray connection 2016-01-23 17:31:02 -05:00
Mike Bayer 67a69da3aa - restate the "secondary" / AssociationProxy warning more strongly.
references #3638
2016-01-23 16:38:44 -05:00
Mike Bayer 77a4794ed2 - use regex here, columns dont matter, keep coming up with different orderings 2016-01-23 15:32:10 -05:00
Carlos Rivas 28365040ac Merged in carlrivers/removed-entry-that-causes-attributeerror-1453541002643 (pull request #1)
Removed entry that causes AttributeError (#3621) - Oracle zxJDBC fails with AttributeError in object OracleCompiler_zxjdbc
2016-01-23 12:19:28 -08:00
Mike Bayer 65010e97bc - use uuid fragments for provision names to enable multiple test suites
per server
2016-01-23 14:58:42 -05:00
Mike Bayer d18d6d9baf - native unicode expectations are too difficult to maintain
w/ the number of drivers /DBURIs /  python versions
2016-01-23 14:30:30 -05:00
Mike Bayer 269313218d - move out match compiler test to test_compiler
- test_query isn't assertscompiledsql
2016-01-23 14:29:25 -05:00
Carlos Rivas edc0b8678b Removed entry that causes AttributeError (#3621) - Oracle zxJDBC fails with AttributeError in object OracleCompiler_zxjdbc 2016-01-23 09:23:46 +00:00
Mike Bayer 24bad4bf1a - make this test deterministic 2016-01-21 17:20:52 -05:00
Mike Bayer 38958f7b3f - add a forwards-test here as well 2016-01-21 15:32:53 -05:00
Mike Bayer 89fa08792e - documenation updates to clarify specific SQLite versions
that have problems with right-nested joins and UNION column keys;
references #3633 references #3634.   backport from 1.1 to 0.9
announcing 1.1 as where these behaviors will be retired based
on version-specific checks
- fix test_resultset so that it passes when SQLite 3.10.0 is
present, references #3633
2016-01-21 15:21:33 -05:00
Mike Bayer 963aa30297 - Added new parameter :paramref:.orm.mapper.passive_deletes to
available mapper options.   This allows a DELETE to proceed
for a joined-table inheritance mapping against the base table only,
while allowing for ON DELETE CASCADE to handle deleting the row
from the subclass tables.
fixes #2349
2016-01-20 17:59:56 -05:00
Mike Bayer 61016f17d1 - The unsupported Sybase dialect now raises `NotImplementedError`
when attempting to compile a query that includes "offset"; Sybase
has no straightforward "offset" feature.  fixes #2278
2016-01-20 16:32:27 -05:00
Mike Bayer 47d8858c54 - generalize the verbiage on LargeBinary so that it doesn't
create confusion for inherited classes such as BYTEA, fixes
2016-01-20 16:20:08 -05:00
Mike Bayer 24dba714cb - update oracle JDBC driver URL, fixes #3554 2016-01-20 15:58:24 -05:00
Mike Bayer a53bd6f74b - cross link for concrete helper classes
- remove redundant concrete helper docs from declarative docs,
two places is enough
2016-01-20 15:28:35 -05:00
Mike Bayer baabf3bedb - typo
(cherry picked from commit b53667526e)
2016-01-20 14:03:49 -05:00
Mike Bayer 632c4f21fa - redo the docs for concrete inheritance to more strongly
favor declarative, fixes #2890
2016-01-20 13:34:57 -05:00
Mike Bayer 02271efd89 - clarify the "Adding" section also illustrates updates, fixes #2942 2016-01-20 12:22:17 -05:00
Mike Bayer 165fa15b0f - add a note that the literal_binds flag should be used
when cross-compiling from DDL to SQL, fixes #3615
2016-01-20 12:10:40 -05:00
Chase a2badb751f Fix ArrayOfEnum's handling of empty arrays.
Prior to this change a value of `'{}'` would split into the list `['']`.
2016-01-19 22:36:15 -08:00
Mike Bayer 5a279e7ae4 - the order in which _generate_backref() for different mappers is called
is random; therefore it may be called against the subclass mapper first, so
need to check .concrete on both sides, references #3630
2016-01-19 17:08:50 -05:00
Mike Bayer 39837686b0 - calling str() on a core sql construct has been made more "friendly",
when the construct contains non-standard sql elements such as
returning, array index operations, or dialect-specific or custom
datatypes.  a string is now returned in these cases rendering an
approximation of the construct (typically the postgresql-style
version of it) rather than raising an error. fixes #3631
- add within_group to top-level imports
- add eq_ignore_whitespace to sqlalchemy.testing imports
2016-01-19 16:47:16 -05:00
Mike Bayer b7bc704f3d - Fixed issue where two same-named relationships that refer to
a base class and a concrete-inherited subclass would raise an error
if those relationships were set up using "backref", while setting up the
identical configuration using relationship() instead with the conflicting
names would succeed, as is allowed in the case of a concrete mapping.
fixes #3630
2016-01-19 13:34:42 -05:00
Mike Bayer 2a7f37b7b0 - The `str() call for :class:.Query` will now take into account
the :class:`.Engine` to which the :class:`.Session` is bound, when
generating the string form of the SQL, so that the actual SQL
that would be emitted to the database is shown, if possible.  Previously,
only the engine associated with the :class:`.MetaData` to which the
mappings are associated would be used, if present.  If
no bind can be located either on the :class:`.Session` or on
the :class:`.MetaData` to which the mappings are associated, then
the "default" dialect is used to render the SQL, as was the case
previously.  fixes #3081
2016-01-19 12:44:42 -05:00
Mike Bayer d4d9a65248 - Fixed bug where some exception re-raise scenarios would attach
the exception to itself as the "cause"; while the Python 3 interpreter
is OK with this, it could cause endless loops in iPython.
fixes #3625
- add tests for reraise, raise_from_cause
- raise_from_cause is the same on py2k/3k, use just one function
2016-01-18 17:35:44 -05:00
Mike Bayer b985483c59 Merge remote-tracking branch 'origin/pr/227' 2016-01-16 22:06:29 -05:00
Mike Bayer 66560cef74 - fix People -> Person , fixes #3628 2016-01-16 22:04:10 -05:00
rmn f9b2185586 Fix typo in relationships docs 2016-01-16 21:19:02 +03:00
Mike Bayer a7cc296714 - update 2016-01-14 18:21:23 -05:00
Mike Bayer 7bb578b1bd - illustrate these using the newer exception doctest format.
unfortunately we can't show the SQL unless we filtered it out
from doctest...not worth it
2016-01-14 18:20:00 -05:00
Mike Bayer 1f7a1f777d - A deep improvement to the recently added :meth:.TextClause.columns
method, and its interaction with result-row processing, now allows
the columns passed to the method to be positionally matched with the
result columns in the statement, rather than matching on name alone.
The advantage to this includes that when linking a textual SQL statement
to an ORM or Core table model, no system of labeling or de-duping of
common column names needs to occur, which also means there's no need
to worry about how label names match to ORM columns and so-forth.  In
addition, the :class:`.ResultProxy` has been further enhanced to
map column and string keys to a row with greater precision in some
cases.  fixes #3501
- reorganize the initialization of ResultMetaData for readability
and complexity; use the name "cursor_description", define the
task of "merging" cursor_description with compiled column information
as its own function, and also define "name extraction" as a separate task.
- fully change the name we use in the "ambiguous column" error to be the
actual name that was ambiguous, modify the C ext also
2016-01-14 18:06:26 -05:00
Mike Bayer 0ff3f95d5b - there was a DATEPART test after all, fix format 2016-01-14 17:50:03 -05:00
Mike Bayer d5d7284bdd - fix some old verbiage that refers to text() as an "implicit" thing
for SQL fragments; we've deprecated that in 1.0 and its a good idea
to document like this for 0.9 as well.
2016-01-14 17:18:21 -05:00
Mike Bayer f2b00f1048 - convert keys to str for None not sortable against str on py3k 2016-01-12 10:49:14 -05:00
Mike Bayer 215167d8d3 - changelog for pr bitbucket:70, fixes #3624 2016-01-12 09:53:09 -05:00
Guillaume DOUMENC c4f415d979 Remove quote on first DATEPART paramater 2016-01-12 04:46:32 +00:00
Mike Bayer 6fbfadc738 - reorganize schema_translate_map to be succinct and gain the performance
back by using an attrgetter for the default case
2016-01-11 16:44:28 -05:00
Mike Bayer b301f009e1 - refactor a bit the loader options system to make it a bit more
intelligible, given the fixes for ref #3623.  unfortunately the system
is still quite weird even though it was rewritten to be... less weird
2016-01-10 17:47:38 -05:00
Mike Bayer d03477d4b7 - fix link to types in metadata, fixes #3618
- fix "version" got whacked into "f" in core tutorial
- fix short underline in automap
- fix unmatched boldface in session events
2016-01-10 11:48:53 -05:00
Mike Bayer ddba8b0e7f Merge remote-tracking branch 'origin/pr/225' 2016-01-10 10:31:51 -05:00
Mike Bayer 536e5cecea Merge remote-tracking branch 'origin/pr/226' 2016-01-09 22:27:12 -05:00
Mike Bayer 331caf11d3 - ensure we use a Connection for effective schema here since Engine doesn't
have it; keep it simple
2016-01-09 22:25:56 -05:00
Adrian Moennich bb29449755 Fix typo in session docs 2016-01-09 20:35:19 +01:00
Mike Bayer c7ae0daf0e - Fixed regression since 0.9 where the 0.9 style loader options
system failed to accommodate for multiple :func:`.undefer_group`
loader options in a single query.   Multiple :func:`.undefer_group`
options will now be taken into account even against the same
entity. fixes #3623
2016-01-09 10:10:20 -05:00
Mike Bayer 89facbed88 - Multi-tenancy schema translation for :class:.Table objects is added.
This supports the use case of an application that uses the same set of
:class:`.Table` objects in many schemas, such as schema-per-user.
A new execution option
:paramref:`.Connection.execution_options.schema_translate_map` is
added. fixes #2685
- latest tox doesn't like the {posargs} in the profile rerunner
2016-01-08 22:12:25 -05:00
Mike Bayer 777e25694f - fix docstrings 2016-01-08 16:27:37 -05:00
Mike Bayer 1539268cf7 Merged in jvanasco/sqlalchemy-alt/issue_docs_scoped_session (pull request #50)
updated docstrings for orm.scoping
2016-01-07 12:50:09 -05:00
Mike Bayer ff803b1a2a - pg8000 fixes for json 2016-01-07 11:04:58 -05:00
Mike Bayer cd8adfe418 - add a do-nothing for mock url _instantiate_plugins 2016-01-06 20:10:28 -05:00
Mike Bayer 5c8bdcab90 - add limiting criteria to the JSON tests so that we don't
attempt integer indexed access from a key/value object nor
string access from an integer-indexed array, as earlier Postgresql
versions (prior to 9.4) don't allow this
2016-01-06 17:27:30 -05:00
Mike Bayer c8b7729338 - Added a new entrypoint system to the engine to allow "plugins" to
be stated in the query string for a URL.   Custom plugins can
be written which will be given the chance up front to alter and/or
consume the engine's URL and keyword arguments, and then at engine
create time will be given the engine itself to allow additional
modifications or event registration.  Plugins are written as a
subclass of :class:`.CreateEnginePlugin`; see that class for
details.
fixes #3536
2016-01-06 17:20:57 -05:00
Mike Bayer cfb631e089 - long line 2016-01-06 13:21:14 -05:00
Mike Bayer 93d71b80f2 - add a few JSON tests specific to MySQL, including basic reflection 2016-01-06 13:18:04 -05:00
Mike Bayer a80bb4e5aa - Added :class:.mysql.JSON for MySQL 5.7. The JSON type provides
persistence of JSON values in MySQL as well as basic operator support
of "getitem" and "getpath", making use of the ``JSON_EXTRACT``
function in order to refer to individual paths in a JSON structure.
fixes #3547
- Added a new type to core :class:`.types.JSON`.  This is the
base of the PostgreSQL :class:`.postgresql.JSON` type as well as that
of the new :class:`.mysql.JSON` type, so that a PG/MySQL-agnostic
JSON column may be used.  The type features basic index and path
searching support.
fixes #3619
- reorganization of migration docs etc. to try to refer both to
the fixes to JSON that helps Postgresql while at the same time
indicating these are new features of the new base JSON type.
- a rework of the Array/Indexable system some more, moving things
that are specific to Array out of Indexable.
- new operators for JSON indexing added to core so that these can
be compiled by the PG and MySQL dialects individually
- rename sqltypes.Array to sqltypes.ARRAY - as there is no generic
Array implementation, this is an uppercase type for now, consistent
with the new sqltypes.JSON type that is also not a generic implementation.
There may need to be some convention change to handle the case of
datatypes that aren't generic, rely upon DB-native implementations,
but aren't necessarily all named the same thing.
2016-01-06 12:47:48 -05:00
Mike Bayer 16746dd1a6 - dont forwards-report tons of 1.0.x changes in the unreleased 1.1;
only when a 1.1.x is released would we want to capture what's still
sitting in a 1.0.x changelog
2016-01-05 15:12:56 -05:00
Mike Bayer 197ffa2be2 - Fixed 1.0 regression where the eager fetch of cursor.rowcount was
no longer called for an UPDATE or DELETE statement emitted via plain
text or via the :func:`.text` construct, affecting those drivers
that erase cursor.rowcount once the cursor is closed such as SQL
Server ODBC and Firebird drivers.
fixes #3622
2016-01-05 10:25:36 -05:00
Mike Bayer 04b1a52783 - break out mysql/base into modules as it's getting huge with more to come 2016-01-04 17:37:23 -05:00
Jeff Widman 56b76ce7a8 Update SQLAlchemy-Migrate link to the new repo 2015-12-24 02:17:02 -08:00
Mike Bayer c7d6c667b5 - Fixed an assertion that would raise somewhat inappropriately
if a :class:`.Index` were associated with a :class:`.Column` that
is associated with a lower-case-t :class:`.TableClause`; the
association should be ignored for the purposes of associating
the index with a :class:`.Table`.
fixes #3616
2015-12-23 22:59:44 -05:00
Mike Bayer 93b48e6aba - release date for 1.0.11 2015-12-22 20:50:38 -05:00
Mike Bayer 8c54b14b5c - An adjustment to the regular expression used to parse MySQL views,
such that we no longer assume the "ALGORITHM" keyword is present in
the reflected view source, as some users have reported this not being
present in some Amazon RDS environments.
fixes #3613
2015-12-22 12:04:45 -05:00
Mike Bayer 5c7ade2f42 - changelog for pullreq github:222 2015-12-22 11:56:02 -05:00
Mike Bayer e95c34481c Merge remote-tracking branch 'origin/pr/222' 2015-12-22 11:54:19 -05:00
Mike Bayer 0c8242b26e - varchar requires a length 2015-12-22 11:19:44 -05:00
Mike Bayer 4b708c4839 - add the test from ref #3614 as well for testing ref #3611 2015-12-21 21:42:45 -05:00
Mike Bayer 5e5b8a96a7 - just use *arg straight without "key" for pop 2015-12-17 11:47:14 -05:00
Mike Bayer 913858c949 - Further fixes to 🎫3605, pop method on :class:.MutableDict,
where the "default" argument was not included.
fixes #3605
2015-12-17 11:24:35 -05:00
Jeff Widman 30be49c157 Make docs listing of param order for event.listen match the code 2015-12-17 05:54:50 -08:00
jonathan vanasco 738d515b95 some spelling fixes 2015-12-16 11:12:07 -05:00
jonathan vanasco ce25ac172d Merge branch 'master' of bitbucket.org:zzzeek/sqlalchemy 2015-12-16 11:04:25 -05:00
Mike Bayer 03ee22f342 - remove errant pdb, references #3612 2015-12-15 22:08:47 -05:00
Mike Bayer a22b208506 - Fixed bug in baked loader system where the systemwide monkeypatch
for setting up baked lazy loaders would interfere with other
loader strategies that rely on lazy loading as a fallback, e.g.
joined and subquery eager loaders, leading to ``IndexError``
exceptions at mapper configuration time.
fixes #3612
2015-12-15 21:44:00 -05:00
Mike Bayer 8a24da6c10 - hyperlink default-related parameters
(cherry picked from commit 9f6f34bc8f)
2015-12-15 18:31:56 -05:00
Mike Bayer a8ec349198 - Fixed regression caused in 1.0.10 by the fix for 🎫3593 where
the check added for a polymorphic joinedload from a
poly_subclass->class->poly_baseclass connection would fail for the
scenario of class->poly_subclass->class.
fixes #3611
2015-12-15 14:00:50 -05:00
Mike Bayer c42725ed54 - add some more oracle skips 2015-12-14 20:22:04 -05:00
Mike Bayer 80bbf13959 - a few tweaks to allow "server_defaults" to be a little more linkable;
remove "undoc members" that was putting some random server_default
atributes from ColumnClause

(cherry picked from commit 270301890a)
2015-12-14 18:02:14 -05:00
Mike Bayer d0fc726988 - since we are mutating the statement in a loop, start with
the same cached starting statement each time.  no issue has been observed
with the former but it could perhaps have issues w/ versioning
or eager_defaults
2015-12-14 17:53:56 -05:00
Mike Bayer 26ed90ab22 - Fixed bug where :meth:.Session.bulk_update_mappings and related
would not bump a version id counter when in use.  The experience
here is still a little rough as the original version id is required
in the given dictionaries and there's not clean error reporting
on that yet.
fixes #3610
2015-12-14 17:39:50 -05:00
Mike Bayer 0e4c4d7efc - Fixed bug in :meth:.Update.return_defaults which would cause all
insert-default holding columns not otherwise included in the SET
clause (such as primary key cols) to get rendered into the RETURNING
even though this is an UPDATE.

- Major fixes to the :paramref:`.Mapper.eager_defaults` flag, this
flag would not be honored correctly in the case that multiple
UPDATE statements were to be emitted, either as part of a flush
or a bulk update operation.  Additionally, RETURNING
would be emitted unnecessarily within update statements.

fixes #3609
2015-12-14 17:30:21 -05:00
Hanno Schlichting 03ee4bbda6 Add new reserved words for MySQL 5.7. 2015-12-14 08:14:35 +01:00
Mike Bayer 7d96ad4d53 - Fixed bug where use of the :meth:.Query.select_from method would
cause a subsequent call to the :meth:`.Query.with_parent` method to
fail. fixes #3606
- add mark-as-fail test for #3607
2015-12-12 21:08:56 -05:00
Mike Bayer d67d04c70a 1.0.10
(cherry picked from commit 6b87e0b301)
2015-12-11 16:05:41 -05:00
Mike Bayer 5710a1e88b - Added support for the `dict.pop() and dict.popitem()` methods
to the :class:`.mutable.MutableDict` class.
fixes #3605
2015-12-11 11:21:46 -05:00
Mike Bayer 741b8af31b - convert ORM tutorial and basic_relationships to favor
back_populates while still maintaining great familiarity
w/ backref so as not to confuse people.  fixes #3390
2015-12-10 18:27:14 -05:00
Mike Bayer d533b8e922 - The ORM and Core tutorials, which have always been in doctest format,
are now exercised within the normal unit test suite in both Python
2 and Python 3.
- remove the old testdocs.py runner and replace with test/base/test_tutorials.py
- use pytest's unicode fixer so that we can test for unicode strings
in both py2k/3k
- use py3k format overall for prints, exceptions
- add other fixers to guarantee deterministic results
- add skips and ellipses to outputs that aren't worth matching
2015-12-10 17:09:47 -05:00
Mike Bayer fb443199c1 Merge remote-tracking branch 'origin/pr/220' 2015-12-10 14:23:44 -05:00
Mike Bayer b606e47ddc - refactor of adapt_like_to_iterable(), fixes #3457.
Includes removal of adapt_like_to_iterable() as well
as _set_iterable(), uses __slots__ for collectionadapter,
does much less duck typing of collections.
2015-12-09 19:15:12 -05:00
Mike Bayer e57bf79616 - Fixed issue within the :meth:.Insert.from_select construct whereby
the :class:`.Select` construct would have its ``._raw_columns``
collection mutated in-place when compiling the :class:`.Insert`
construct, when the target :class:`.Table` has Python-side defaults.
The :class:`.Select` construct would compile standalone with the
erroneous column present subsequent to compilation of the
:class:`.Insert`, and the the :class:`.Insert` statement itself would
fail on a second compile attempt due to duplicate bound parameters.
fixes #3603
2015-12-09 18:15:25 -05:00
Nils Philippsen 7e6f331233 fix some typos 2015-12-08 23:47:00 +01:00
Mike Bayer f4a1129e79 - fix changelog for #3602
- add version switch for backend fsp test

(cherry picked from commit 67b22cee3a)
2015-12-08 13:50:25 -05:00
Mike Bayer 7df4054b04 - make this DROP conditional, attempting to isolate why jenkins has
an issue with just one test
2015-12-08 10:40:45 -05:00
Mike Bayer 3f42743d6a - Fixed bug in MySQL reflection where the "fractional sections portion"
of the :class:`.mysql.DATETIME`, :class:`.mysql.TIMESTAMP` and
:class:`.mysql.TIME` types would be incorrectly placed into the
``timestamp`` attribute, which is unused by MySQL, instead of the
``fsp`` attribute.
fixes #3602
2015-12-07 17:24:09 -05:00
Mike Bayer d7eae8c95c - flake8 test_reflection and rework the type-based tests into
individual categories w/ modernized fixtures, assert attributes
within type objects.
2015-12-07 17:09:11 -05:00
Mike Bayer 8fa62d652b - write a real inline documentation section for from_self(),
building on the example of query.join().  Ideally all the methods
in Query would have this kind of thing.  fixes #3544
2015-12-07 12:36:36 -05:00
Mike Bayer 077f26af5f - and NLS_LANG.... 2015-12-05 17:17:40 -05:00
Mike Bayer 7f423e8756 - add ORACLE_HOME to passenv allowing oracle to work w/ tox 2.0 2015-12-05 16:56:53 -05:00
Mike Bayer 012f3852bf - fix loading.py merge_result for new _merge() argument 2015-12-04 17:31:47 -05:00
Mike Bayer 3ec9b9f6b6 - The :meth:.Session.merge method now tracks pending objects by
primary key before emitting an INSERT, and merges distinct objects with
duplicate primary keys together as they are encountered, which is
essentially semi-deterministic at best.   This behavior
matches what happens already with persistent objects.
fixes #3601
2015-12-04 11:52:16 -05:00
Mike Bayer 935bc34dc5 - Fixed issue where post_update on a many-to-one relationship would
fail to emit an UPDATE in the case where the attribute were set to
None and not previously loaded.
fixes #3599
2015-12-02 12:13:57 -05:00
Mike Bayer 9695faf329 - Fixed bug where CREATE TABLE with a no-column table, but a constraint
such as a CHECK constraint would render an erroneous comma in the
definition; this scenario can occur such as with a Postgresql
INHERITS table that has no columns of its own.
fixes #3598
2015-12-01 19:03:03 -05:00
Mike Bayer ab69467697 - Added the error "20006: Write to the server failed" to the list
of disconnect errors for the pymssql driver, as this has been observed
to render a connection unusable.
fixes #3585
2015-11-30 13:15:40 -05:00
Mike Bayer f4cb3f8cac - changelog for #3573, fixes #3573 2015-11-30 13:06:11 -05:00
Mike Bayer 9c2c247563 Merge remote-tracking branch 'origin/pr/216' 2015-11-30 13:02:39 -05:00
Mike Bayer c3fbfa8257 - changelog for pullreq github:215 2015-11-30 13:01:07 -05:00
Mike Bayer a09fc9740d Merge remote-tracking branch 'origin/pr/215' 2015-11-30 12:57:47 -05:00
Mike Bayer 954aafa064 Merge remote-tracking branch 'origin/pr/217' 2015-11-30 12:55:26 -05:00
Mike Bayer 38e043a475 Merge remote-tracking branch 'origin/pr/214' 2015-11-30 12:53:56 -05:00
Mike Bayer be24b3ea83 - restore 'declarative' classifier 2015-11-30 12:52:01 -05:00
Nils Philippsen ef85a0d189 py2k: accept unicode literals on :func:backref, too
Fixed bug where in Py2K a unicode literal would not be accepted as the
string name of a class or other argument within declarative using
:func:`.backref` on :func:`.relationship`.

amends commit e6f67f4805

backport to rel_1_0

(cherry picked from commit 58f73d2278)
(cherry picked from commit 33c3aded3a)
2015-11-30 12:49:44 -05:00
Mike Bayer d5fd26b836 Merge remote-tracking branch 'origin/pr/212' 2015-11-30 12:46:45 -05:00
Mike Bayer 2c5ba60269 - update changelog for all the py3.5/3.6 related prs at once
(cherry picked from commit 4bb6770ae8)
2015-11-30 12:41:10 -05:00
Mike Bayer a058233f55 Merge remote-tracking branch 'origin/pr/211' 2015-11-30 12:35:10 -05:00
Mike Bayer 03a3b5ffd3 - A descriptive ValueError is now raised in the event that SQL server
returns an invalid date or time format from a DATE or TIME
column, rather than failing with a NoneType error.  Pull request
courtesy Ed Avis.
pullreq github:206
2015-11-30 12:19:26 -05:00
Mike Bayer 8145100da4 - update changelog to accommodate pr github:218
(cherry picked from commit 6657a008d6)
2015-11-30 11:55:31 -05:00
Mike Bayer 2b39f09e73 Merge remote-tracking branch 'origin/pr/218' 2015-11-30 11:53:09 -05:00
Iuri de Silvio d9178320d6 Fix _assert_unorderable_types on py36.
The error message changed to:

`'<' not supported between instances of 'foo' and 'bar'`
2015-11-30 14:50:25 -02:00
Mike Bayer d59e951f46 - changelog for pr github:210
(cherry picked from commit 3a4b89c5a0)
2015-11-30 11:42:55 -05:00
Mike Bayer e45e4aa97d Merge remote-tracking branch 'origin/pr/210' 2015-11-30 11:40:44 -05:00
Mike Bayer 86e5419968 - make inserted_primary_key a link and be more clear what happens here 2015-11-30 11:25:07 -05:00
Mike Bayer 4fcd93afb8 - close the session 2015-11-29 21:50:50 -05:00
Mike Bayer b0308a7b3a - Fixed an issue in baked queries where the .get() method, used either
directly or within lazy loads, didn't consider the mapper's "get clause"
as part of the cache key, causing bound parameter mismatches if the
clause got re-generated.  This clause is cached by mappers
on the fly but in highly concurrent scenarios may be generated more
than once when first accessed.
fixes #3597
2015-11-29 11:42:55 -05:00
Mike Bayer c90f0a49f3 - Added support for parameter-ordered SET clauses in an UPDATE
statement.  This feature is available by passing the
:paramref:`~.sqlalchemy.sql.expression.update.preserve_parameter_order`
flag either to the core :class:`.Update` construct or alternatively
adding it to the :paramref:`.Query.update.update_args` dictionary at
the ORM-level, also passing the parameters themselves as a list of 2-tuples.
Thanks to Gorka Eguileor for implementation and tests.
adapted from pullreq github:200
2015-11-28 14:30:05 -05:00
Hugh Cole-Baker 0438065a20 Fix a typo in the disconnect handling code example 2015-11-28 15:21:11 +00:00
Mike Bayer 1202e140b9 - Fixed bug which is actually a regression that occurred between
versions 0.8.0 and 0.8.1, due 🎫`2714`.  The case where
joined eager loading needs to join out over a subclass-bound
relationship when "with_polymorphic" were also used would fail
to join from the correct entity.
fixes #3593
2015-11-25 15:29:04 -05:00
Mike Bayer 2a2be6a2ce - support declarativemappedtest with per-test setup 2015-11-25 15:15:35 -05:00
Mike Bayer 2743b674f5 - add an ignore for N806 2015-11-25 14:31:58 -05:00
Nils Philippsen 58f73d2278 py2k: accept unicode literals on :func:backref, too
Fixed bug where in Py2K a unicode literal would not be accepted as the
string name of a class or other argument within declarative using
:func:`.backref` on :func:`.relationship`.

amends commit e6f67f4805
2015-11-25 16:03:59 +01:00
Bas van den Heuvel 054b22c786 - Change "expr" to "entity" for example illustrating an event
that intercepts a query and adds entity-oriented criteria
2015-11-24 14:10:51 -05:00
Diana Clarke fd47fea6fb - Postgres: Do not prefix table with schema in: "FOR UPDATE of <table>"
For example, this query:

    SELECT s1.users.name FROM s1.users FOR UPDATE OF s1.users

should actually be:

    SELECT s1.users.name FROM s1.users FOR UPDATE OF users

fixes #3573
2015-11-24 13:58:50 -05:00
aisch 0921a6abbc fix postgresql exclude contraint to check when= against None rather than __bool__ eval 2015-11-23 10:22:50 -08:00
Mike Bayer f7943db2f3 - add py35 2015-11-22 16:04:04 -05:00
Mike Bayer f9679710f1 - set explicit encoding settings for default mysql driver 2015-11-21 17:01:25 -05:00
Mike Bayer 60c36ca841 - Fixed joinedload bug which would occur when a. the query includes
limit/offset criteria that forces a subquery b. the relationship
uses "secondary" c. the primaryjoin of the relationship refers to
a column that is either not part of the primary key, or is a PK
col in a joined-inheritance subclass table that is under a different
attribute name than the parent table's primary key column d. the
query defers the columns that are present in the primaryjoin, typically
via not being included in load_only(); the necessary column(s) would
not be present in the subquery and produce invalid SQL.
fixes #3592
2015-11-21 16:36:50 -05:00
Mike Bayer 068d37035a - don't create tables on compile-only tests 2015-11-21 16:20:25 -05:00
Mike Bayer ef9a4cb60b - try to get this to skip for oracle 2015-11-20 18:19:33 -05:00
Mike Bayer a6fe4dc0c8 - A rare case which occurs when a :meth:.Session.rollback fails in the
scope of a :meth:`.Session.flush` operation that's raising an
exception, as has been observed in some MySQL SAVEPOINT cases, prevents
the original  database exception from being observed when it was
emitted during  flush, but only on Py2K because Py2K does not support
exception  chaining; on Py3K the originating exception is chained.  As
a workaround, a warning is emitted in this specific case showing at
least the string message of the original database error before we
proceed to raise  the rollback-originating exception.
fixes #2696
2015-11-19 15:45:17 -05:00
Mike Bayer 1dc805dd4d - add documentation that describes, then proceeds to warn about
the many caveats and confusing effects of, the popular approach
of using contains_eager() to alter the natural result of a
related collection.  I'm not a fan of this technique as it changes
the semantics of a relationship in such a way that the rest of the
ORM isn't aware of and it also can be undone very easily; hence the
section needs as much text for warnings as for describing the
technique itself.   fixes #3563
2015-11-19 15:24:22 -05:00
Mike Bayer 9ed36c2eed - Fixed the `.python_type attribute of :class:.postgresql.INTERVAL`
to return ``datetime.timedelta`` in the same way as that of
:obj:`.types.Interval.python_type`, rather than raising
``NotImplementedError``.
fixes #3571

(cherry picked from commit 29d6f6e19b)
2015-11-19 15:11:37 -05:00
Mike Bayer c7f9aa2818 - rewrite the docs and add a test for the bake_queries=True
relationship flag; this flag *does* have an effect when the baked
lazy loader plugin has been invoked.  clarify the intent of this
flag as an "opt out" but only has an effect when the baked system
is loaded anyway.  fixes #3572
2015-11-19 14:23:08 -05:00
Mike Bayer 14498364f8 - Added support for reflecting the source of materialized views
to the Postgresql version of the :meth:`.Inspector.get_view_definition`
method.
fixes #3587
2015-11-18 09:06:33 -05:00
Jeff Widman 11e190ef07 Fix typo: wtihin --> within 2015-11-16 18:47:29 -08:00
Mike Bayer 0847097c29 - extend pullreq github:213 to also include DATETIMEOFFSET and TIME,
which also accept zero precision
- extend test case here to include a backend-agnostic suite
- changelog for MSSQL date fix
2015-11-14 12:38:45 -05:00
Mike Bayer ac9ded338f Merge remote-tracking branch 'origin/pr/213' into pr213 2015-11-14 11:39:58 -05:00
Jacobo de Vera 80ce23f6fd Pass precision value to mssql.DATETIME2 when it is 0
The simple check on the precision results in DATETIME2(0) generating a
DATETIME2 column, with default precision, which is 7.
2015-11-13 20:51:05 +01:00
Mike Bayer 37565d2ce2 - fix missing argument in TypeDecorator.copy(), fixes #3584, references #2919 2015-11-13 11:01:49 -05:00
Mike Bayer 3370cbde50 - correct the commit from ref #3582 to refer to the correct sub-element 2015-11-11 14:21:02 -05:00
Mike Bayer 33c378f768 - Fixed bug where the "single table inheritance" criteria would be
added onto the end of a query in some inappropriate situations, such
as when querying from an exists() of a single-inheritance subclass.

fixes #3582
2015-11-11 12:57:32 -05:00
Mike Bayer d51a36397e Merge branch 'jeffwidman/update-links-in-sqlalchemy-docs-that-poi-1446667164356' of https://bitbucket.org/jeffwidman/sqlalchemy 2015-11-10 13:00:03 -05:00
Mike Bayer 1dbd3a0706 Merge branch 'jeffwidman/fix-typo-foriegn-foreign-1446862160653' of https://bitbucket.org/jeffwidman/sqlalchemy-1 into typos 2015-11-10 12:56:01 -05:00
Sven Schliesing 887edc431a fix typo: Explcitly -> Explicitly 2015-11-10 08:25:27 +01:00
Mike Bayer 5d8bb1f4a6 - fix ambiguous documentation re: after_flush_postexec(), the
looping nature of it only occurs within the context of a commit.
2015-11-09 16:48:58 -05:00
Mike Bayer 2d54e3819f - fix broken link to loader behavior 2015-11-07 14:24:12 -05:00
Jeff Widman 8660883e1a Fix typo: foriegn --> foreign 2015-11-07 02:09:28 +00:00
Jeff Widman a2e83dbd2a Updated PostgreSQL links to point to "current" rather than hardcoded version 2015-11-05 23:34:27 +00:00
Jeff Widman 0d3ab3198a Update links in SQLAlchemy docs that point to postgres docs to use 'devel' rather than hardcoded version 2015-11-04 19:59:28 +00:00
pgjones 6ab1205580 Change generator termination from StopIteration to return.
From [PEP 479](https://www.python.org/dev/peps/pep-0479/) the correct way to
terminate a generator is to return (which implicitly raises StopIteration)
rather than raise StopIteration.

Without this change using sqlalchemy in python 3.5 or greater results in
these warnings
    PendingDeprecationWarning: generator '__iter__' raised StopIteration
which this commit should remove.
2015-10-30 20:20:58 +00:00
Mike Bayer 07a199d929 - cross-linking for pool recycle feature 2015-10-30 11:47:32 -04:00
Mike Bayer 382950b701 Merge branch 'pr204' 2015-10-29 14:38:34 -04:00
Mike Bayer e31211c578 - convert wrap_callable() to a general purpose update_wrapper-like
function; the caller still passes in the "wrapper"
- move tests for wrap_callable() to be generic util tests
- changelog for pullreq github:204
2015-10-29 14:28:00 -04:00
Jacob MacDonald e8a5ed9c1c Update usages of getargspec to compat version.
The places inspect.getargspec was being used were causing problems for
newer Python versions.
2015-10-29 12:09:15 -06:00
Mike Bayer 98c1dcc6bc - add a JSON warning for coerce_compared_value 2015-10-28 11:22:55 -04:00
Mike Bayer c2c4fc14d5 Merge remote-tracking branch 'origin/pr/196' into pr196 2015-10-22 17:27:44 -04:00
Mike Bayer 2daaacef04 - update the pool pessimistic invalidation recipe to refer to the
engine_connect event, allowing easy detection of disconnects
and full invalidation of the pool
2015-10-22 11:58:25 -04:00
Mike Bayer 8a4a1fd70a - release date for 1.0.9 2015-10-20 18:14:26 -04:00
Mike Bayer 13278d1108 - try to make this language more succinct and fix links
(cherry picked from commit 3ffe8569fb)
2015-10-20 18:13:16 -04:00
Mike Bayer 5bc5adb627 - use is_() here to more clearly show what's going wrong
on occasional pypy test runs
2015-10-19 18:48:58 -04:00
Mike Bayer 8e9a81a19e - adjust 4f54607923 where we still allow_multirow as long
as versioning isn't needed, fixes test_unitofworkv2->test_update_multi_missing_broken_multi_rowcount
2015-10-19 14:22:31 -04:00
Mike Bayer 1e0afd584c - Fixed regression in 1.0 where new feature of using "executemany"
for UPDATE statements in the ORM (e.g. :ref:`feature_updatemany`)
would break on Postgresql and other RETURNING backends
when using server-side version generation
schemes, as the server side value is retrieved via RETURNING which
is not supported with executemany.
fixes #3556
2015-10-19 12:17:37 -04:00
Martin J. Hsu c7d04beeac - wrap ColumnDefault empty arg callables like functools.wraps, setting __name__, __doc__, and __module__ 2015-10-15 10:46:33 +08:00
Mike Bayer 322f8f18f5 - exclude this from unpredictable gc 2015-10-11 12:44:29 -04:00
Mike Bayer affcfd1e52 - modernize some very old global-engine tests w/ bad teardowns 2015-10-11 12:26:45 -04:00
Mike Bayer e6779d8437 - repair flake8 issues 2015-10-11 12:08:53 -04:00
Mike Bayer 2a8a06e33a - repair laziness about setting time zone here, which is leaking
out depending on connection pool state
2015-10-11 12:00:39 -04:00
Mike Bayer 9d08c6abc2 - Added the :paramref:.AssociationProxy.info parameter to the
:class:`.AssociationProxy` constructor, to suit the
:attr:`.AssociationProxy.info` accessor that was added in
🎫`2971`.  This is possible because :class:`.AssociationProxy`
is constructed explicitly, unlike a hybrid which is constructed
implicitly via the decorator syntax.
fixes #3551
2015-10-09 18:01:43 -04:00
Mike Bayer 78a7bbdb3b Merge remote-tracking branch 'origin/pr/203' 2015-10-09 17:11:56 -04:00
Mike Bayer a47e863dc5 - this was supposed to be client-side SQL default not server side 2015-10-09 17:10:08 -04:00
Mike Bayer 2ef7c5e499 Merge remote-tracking branch 'origin/pr/205' 2015-10-09 17:07:52 -04:00
Mike Bayer 845500280d - open up autoincrement for columns that have a default; autoinc is usually
"auto" now so True can indicate the dialect would support this
2015-10-08 17:02:55 -04:00
Mike Bayer 956c26d077 Merge remote-tracking branch 'origin/pr/208' 2015-10-08 00:33:02 -04:00
Mike Bayer 21b5d353ce - for DB's w/o a real "autoincrement", reflection should be returning
"auto", doesn't matter if there's a default here
2015-10-07 23:41:24 -04:00
Peter Demin f8eb7c2858 Update base.py
Docstring typo keysowrds => keywords
2015-10-07 11:38:48 -04:00
Mike Bayer 414af7b612 - The system by which a :class:.Column considers itself to be an
"auto increment" column has been changed, such that autoincrement
is no longer implicitly enabled for a :class:`.Table` that has a
composite primary key.  In order to accommodate being able to enable
autoincrement for a composite PK member column while at the same time
maintaining SQLAlchemy's long standing behavior of enabling
implicit autoincrement for a single integer primary key, a third
state has been added to the :paramref:`.Column.autoincrement` parameter
``"auto"``, which is now the default. fixes #3216
- The MySQL dialect no longer generates an extra "KEY" directive when
generating CREATE TABLE DDL for a table using InnoDB with a
composite primary key with AUTO_INCREMENT on a column that isn't the
first column;  to overcome InnoDB's limitation here, the PRIMARY KEY
constraint is now generated with the AUTO_INCREMENT column placed
first in the list of columns.
2015-10-07 10:02:45 -04:00
Mike Bayer 4578ab54a5 - Fixed bug in Oracle dialect where reflection of tables and other
symbols with names quoted to force all-lower-case would not be
identified properly in reflection queries.  The :class:`.quoted_name`
construct is now applied to incoming symbol names that detect as
forced into all-lower-case within the "name normalize" process.
fixes #3548
2015-10-05 09:49:34 -04:00
Mike Bayer d84dea62de - add an additional note regarding select_from, fixes #3546 2015-10-02 11:23:50 -04:00
Mike Bayer ac08920284 - remove ambiguous use of the phrase "joined together by AND" as this
may be construed as the Python "and" keyword
- add notes to ORM tutorial for beginners that Python "and" keyword
is not to be used
fixes #3545
2015-10-01 09:38:22 -04:00
Mike Bayer 7393ee8d4f - bzzt, fix the base _post_configure_engine() call to not fail 2015-09-29 11:33:45 -04:00
Mike Bayer 5bb2536cc5 - limit the search for schemas to not include "temp", which is sort of an implicit schema
- repair the CREATE INDEX ddl for schemas
- update provisioning to include support for setting up ATTACH DATABASE up front
for the test_schema; enable "schemas" testing for SQLite
- changelog / migration notes for new SQLite schema support
- include the "schema" as the "remote_schema" when we reflect SQLite FKs
2015-09-28 17:48:55 -04:00
Mike Bayer e4d445c6f5 Merge remote-tracking branch 'origin/pr/198' into pr198 2015-09-28 15:40:39 -04:00
Eric Siegerman febe0c0faa Doc fix 2015-09-28 12:12:27 -04:00
Eric Siegerman 2e5e6ff96c Remplement Query.one() in terms of .one_or_none()
Thanks to Mike Bayer for suggesting a simpler refactoring.
2015-09-28 12:08:19 -04:00
Mike Bayer 1704eacf24 - fix bool test 2015-09-27 12:13:06 -04:00
Mike Bayer a8e1d33ae5 - break out critical aspects of test_query into their own tests
finally, test_resultset and test_insert_exec.   Update all
idioms within these.
2015-09-27 12:09:24 -04:00
Eric Siegerman 91255618dd Fix sqlalchemy.ext.baked.Result.one_or_none() exception message
Also add a couple of missing tests.
2015-09-24 15:25:15 -04:00
Mike Bayer 5b71858533 - replicate Query.one_or_none to BakedQuery
- changelog / version note finishing
2015-09-24 13:52:25 -04:00
Eric Siegerman a9b5fb3f49 Add Query.one_or_none() 2015-09-24 13:22:45 -04:00
Eric Siegerman 0854f82993 Add a lot more detail
(cherry picked from commit 5db5e18d3b)
2015-09-23 17:05:20 -04:00
Eric Siegerman f29be1e6f7 Add some markup
(cherry picked from commit 81eefe038e)
2015-09-23 17:05:14 -04:00
Eric Siegerman 1195155937 A few minor rewordings
(cherry picked from commit ea084bdc65)
2015-09-23 17:05:06 -04:00
Mike Bayer 47fcb1d0b6 - Fixed rare TypeError which could occur when stringifying certain
kinds of internal column loader options within internal logging.
fixes #3539
2015-09-23 16:40:16 -04:00
Mike Bayer 3dfcb10bef - The `legacy_schema_aliasing` flag, introduced in version 1.0.5
as part of 🎫`3424` to allow disabling of the MSSQL dialect's
attempts to create aliases for schema-qualified tables, now defaults
to False; the old behavior is now disabled unless explicitly turned on.
fixes #3434
2015-09-19 18:06:23 -04:00
Mike Bayer 80aeba3d5e - Added a new type-level modifier :meth:.TypeEngine.evaluates_none
which indicates to the ORM that a positive set of None should be
persisted as the value NULL, instead of omitting the column from
the INSERT statement.  This feature is used both as part of the
implementation for 🎫`3514` as well as a standalone feature
available on any type.  fixes #3250
- add new documentation section illustrating the "how to force null"
 use case of #3250
- alter our change from #3514 so that the class-level flag is now
called "should_evaluate_none"; so that "evaluates_none" is now
a generative method.
2015-09-19 16:27:51 -04:00
Mike Bayer 371f1a82c5 - The use of a :class:.postgresql.ARRAY object that refers
to a :class:`.types.Enum` or :class:`.postgresql.ENUM` subtype
will now emit the expected "CREATE TYPE" and "DROP TYPE" DDL when
the type is used within a "CREATE TABLE" or "DROP TABLE".
fixes #2729
2015-09-19 11:58:50 -04:00
Mike Bayer 53defccab7 - fixes for the ORM side test for #3531. 2015-09-17 10:18:57 -04:00
Mike Bayer 24a7241b5e - The :func:.type_coerce construct is now a fully fledged Core
expression element which is late-evaluated at compile time.  Previously,
the function was only a conversion function which would handle different
expression inputs by returning either a :class:`.Label` of a column-oriented
expression or a copy of a given :class:`.BindParameter` object,
which in particular prevented the operation from being logically
maintained when an ORM-level expression transformation would convert
a column to a bound parameter (e.g. for lazy loading).
fixes #3531
2015-09-16 18:46:53 -04:00
Mike Bayer 7eb34baf99 - fix incorrect example in inheritance docs 2015-09-15 11:17:13 -04:00
Mike Bayer fe41e39b9b - add new entry for sharing of Engine across process boundaries 2015-09-14 11:02:43 -04:00
Mike Bayer ad28e228e3 - call it deque, since you can really pop from either side 2015-09-10 10:28:42 -04:00
Mike Bayer 03797b7847 - add a new FAQ recipe for "walk all objects", replacing the need
to use mapper.cascade_iterator() for this purpose as it was not really
designed for that use case.  Add docs to cascade_iterator() pointing
to the recipe.  fixes #3498
2015-09-10 10:00:46 -04:00
Jason Myers db824b5353 Correcting the Hybrid Property Example
Fixes #3528

Signed-off-by: Jason Myers <jason@jasonamyers.com>
2015-09-10 08:23:54 -05:00
Brian Van Klaveren 4d53b31247 Support get_schema_names for SQLite
Should return "main" and the names of attached databases.
2015-09-09 14:23:27 -07:00
Brian Van Klaveren 8174e7236b Support get_schema_names for SQLite 2015-09-09 14:03:14 -07:00
Mike Bayer be548690c7 - profile update 2015-09-08 18:15:12 -04:00
Mike Bayer f5b13797a6 Merged in bsmithgall/sqlalchemy/event-doc-link-fix (pull request #60)
fix typo in session events docs
2015-09-08 18:10:51 -04:00
mike bayer 74781d8532 Merge pull request #197 from davidjb/master
Minor grammar fix for capitalisation in session docs
2015-09-08 18:09:06 -04:00
Mike Bayer 0997e843f2 - Internal calls to "bookkeeping" functions within
:meth:`.Session.bulk_save_objects` and related bulk methods have
been scaled back to the extent that this functionality is not
currently used, e.g. checks for column default values to be
fetched after an INSERT or UPDATE statement.
fixes #3526
2015-09-08 14:12:32 -04:00
Mike Bayer 68a6701c6d - Fixed bug in :meth:.Session.bulk_save_objects where a mapped
column that had some kind of "fetch on update" value and was not
locally present in the given object would cause an AttributeError
within the operation.
fixes #3525
2015-09-08 13:00:26 -04:00
bsmithgall 2fb3bb31ef fix typo in session events docs 2015-09-07 21:37:19 -04:00
Mike Bayer 176ac6ab09 - update moved link, fixes #3351 2015-09-03 16:42:43 -04:00
Mike Bayer 67a42103d9 - rewrite some profiles that went *down*! woop 2015-09-03 14:39:32 -04:00
Mike Bayer 7699bd733b - reduce some callcounts within the new events 2015-09-03 11:11:25 -04:00
Mike Bayer 606135dd98 Merge branch 'ticket_2677' 2015-09-02 17:55:26 -04:00
Mike Bayer 108c60f460 - The :class:.SessionEvents suite now includes events to allow
unambiguous tracking of all object lifecycle state transitions
in terms of the :class:`.Session` itself, e.g. pending,
transient,  persistent, detached.   The state of the object
within each event is also defined.
fixes #2677
- Added a new session lifecycle state :term:`deleted`.  This new state
represents an object that has been deleted from the :term:`persistent`
state and will move to the :term:`detached` state once the transaction
is committed.  This resolves the long-standing issue that objects
which were deleted existed in a gray area between persistent and
detached.   The :attr:`.InstanceState.persistent` accessor will
**no longer** report on a deleted object as persistent; the
:attr:`.InstanceState.deleted` accessor will instead be True for
these objects, until they become detached.
- The :paramref:`.Session.weak_identity_map` parameter is deprecated.
See the new recipe at :ref:`session_referencing_behavior` for
an event-based approach to maintaining strong identity map behavior.
references #3517
2015-09-02 17:55:15 -04:00
Mike Bayer 8be93c23ee - add new documentation that applies to all modern SQLA versions,
detailing ORM event recipes across the board.
2015-09-02 11:58:59 -04:00
Mike Bayer 6d0c0994e9 - add a note about DISTINCT in query w/ ORDER BY, references #3518 2015-08-31 13:13:04 -04:00
Mike Bayer c39ff9978d - Fixed regression in 1.0-released default-processor for multi-VALUES
insert statement, 🎫`3288`, where the column type for the
default-holding column would not be propagated to the compiled
statement in the case where the default was being used,
leading to bind-level type handlers not being invoked.
fixes #3520
2015-08-31 11:30:03 -04:00
David\ Beitey 3bd58fac7b Minor grammar fix for capitalisation in session docs 2015-08-28 13:57:54 +10:00
Mike Bayer 956907a4b1 - use consistent and descriptive language in all cases
where we refer to the "weak_identity_map" option, and add additional
exposition in the session documentation which refers to it.
fixes #3517
2015-08-27 23:38:14 -04:00
Mike Bayer ed535649d4 - The :class:.TypeDecorator type extender will now work in conjunction
with a :class:`.SchemaType` implementation, typically :class:`.Enum`
or :class:`.Boolean` with regards to ensuring that the per-table
events are propagated from the implementation type to the outer type.
These events are used
to ensure that the constraints or Postgresql types (e.g. ENUM)
are correctly created (and possibly dropped) along with the parent
table.
fixes #2919
2015-08-27 18:04:25 -04:00
Mike Bayer d459afa8db - reword and update documentation on passive_updates=False; as virtually
all DBs now support ON UPDATE CASCADE other than Oracle, there's no need
to try to reimplement more functionality here and users should be encouraged
to forego natural PKs unless their target platform supports them.
references #2666
2015-08-27 15:56:00 -04:00
Mike Bayer 410be197ef - add a postgresql-specific form of array_agg() that injects the
ARRAY type, references #3132
2015-08-27 11:22:05 -04:00
Mike Bayer e2209f7534 - consolidate "constraints.py" into the more general "ext.py",
for all assorted PG SQL extensions
2015-08-27 10:33:21 -04:00
Mike Bayer 5295a683f9 - add PG-specific aggregate_order_by(), references #3132 2015-08-27 10:32:21 -04:00
Mike Bayer 4d63b472f2 Merge branch 'ticket_3516' 2015-08-26 17:20:56 -04:00
Mike Bayer 7c4512cbeb - Added support for "set-aggregate" functions of the form
``<function> WITHIN GROUP (ORDER BY <criteria>)``, using the
method :class:`.FunctionElement.within_group`.  A series of common
set-aggregate functions with return types derived from the set have
been added. This includes functions like :class:`.percentile_cont`,
:class:`.dense_rank` and others.
fixes #1370
- make sure we use func.name for all _literal_as_binds in functions.py
so we get consistent naming behavior for parameters.
2015-08-26 17:19:27 -04:00
Mike Bayer cfae9c2eaf - Added support for the SQL-standard function :class:.array_agg,
which automatically returns an :class:`.Array` of the correct type
and supports index / slice operations.   As arrays are only
supported on Postgresql at the moment, only actually works on
Postgresql. fixes #3132
2015-08-26 15:15:55 -04:00
Mike Bayer 7024745a14 - build out a new base type for Array, as well as new any/all operators
- any/all work for Array as well as subqueries, accepted by MySQL
- Postgresql ARRAY now subclasses Array
- fixes #3516
2015-08-25 18:24:46 -04:00
Mike Bayer 0127ac668e - re-document and fully cross link all of configure_mappers(),
mapper_configured(), after_configured(), and before_configured().
2015-08-24 21:52:33 -04:00
Mike Bayer d57e5edbcd - Fixed two issues in the "history_meta" example where history tracking
could encounter empty history, and where a column keyed to an alternate
attribute name would fail to track properly.  Fixes courtesy
Alex Fraser.
2015-08-24 10:54:09 -04:00
Mike Bayer 03e47a8255 - repair the inspection hook in sqltypes to not be fooled
by mock and other __getattr__ impostors
2015-08-22 16:01:23 -04:00
Mike Bayer 8712ef2f81 - Added new checks for the common error case of passing mapped classes
or mapped instances into contexts where they are interpreted as
SQL bound parameters; a new exception is raised for this.
fixes #3321
2015-08-22 12:47:13 -04:00
Mike Bayer e0a8030048 - rework the "controlling DDL sequences" documentation to
refer mostly to the DDL object; this system is primarily useful
in that case, and not for built-in objects.  Reference that
the built-in case is not really viable right now. References #3442.
2015-08-21 16:36:15 -04:00
Thomas Grainger e4bfe2aa4b Link to maintained redshift dialect 2015-08-19 19:15:40 +01:00
Mike Bayer acda2e7d0b - some cleanups in compiler.py 2015-08-18 17:25:05 -04:00
Mike Bayer 871330c379 - forgot to implement py3k logic for JSON.NULL 2015-08-18 16:36:56 -04:00
Mike Bayer b653fedca5 - fix the postgresql_jsonb requirement to include the 9.4 requirement
- new test for json col['x']['y']['z'] seems to fail pre PG 9.4,
fails on comparisons for non-compatible data instead of not matching
- no need to call SpecPredicate(db) directly in exclusion functions,
by using Predicate.as_predicate() the spec strings can have version
comparisons
2015-08-18 13:30:21 -04:00
Mike Bayer 3f8f1f16bd - as the Concatenable mixin was changed to support calling down to
"super" instead of hardcoding to "self.type" for the default return
value, the base Comparator was returning other_comparator.type.   It's
not clear what the rationale for this was, though in theory the
base Comparator should possibly even throw an exception if the two
types aren't the same (or of the same affinity?) .
- mysql.SET was broken on this because the bitwise version adds "0"
to the value to force an integer within column_expression, we are doing type_coerces here
now in any case so that there is no type ambiguity for this
operation
2015-08-18 12:40:18 -04:00
Mike Bayer ba1e959e53 - document workaround type for ARRAY of ENUM, fixes #3467 2015-08-18 11:33:56 -04:00
Mike Bayer d14a4b480c - merge of ticket_3514 None-handling branch
- Fixes to the ORM and to the postgresql JSON type regarding the
``None`` constant in conjunction with the Postgresql :class:`.JSON` type.  When
the :paramref:`.JSON.none_as_null` flag is left at its default
value of ``False``, the ORM will now correctly insert the Json
"'null'" string into the column whenever the value on the ORM
object is set to the value ``None`` or when the value ``None``
is used with :meth:`.Session.bulk_insert_mappings`,
**including** if the column has a default or server default on it.  This
makes use of a new type-level flag "evaluates_none" which is implemented
by the JSON type based on the none_as_null flag. fixes #3514
- Added a new constant :attr:`.postgresql.JSON.NULL`, indicating
that the JSON NULL value should be used for a value
regardless of other settings. part of fixes #3514
2015-08-17 17:12:16 -04:00
Mike Bayer ceeb033054 - merge of ticket_3499 indexed access branch
- The "hashable" flag on special datatypes such as :class:`.postgresql.ARRAY`,
:class:`.postgresql.JSON` and :class:`.postgresql.HSTORE` is now
set to False, which allows these types to be fetchable in ORM
queries that include entities within the row.  fixes #3499
- The Postgresql :class:`.postgresql.ARRAY` type now supports multidimensional
indexed access, e.g. expressions such as ``somecol[5][6]`` without
any need for explicit casts or type coercions, provided
that the :paramref:`.postgresql.ARRAY.dimensions` parameter is set to the
desired number of dimensions. fixes #3487
- The return type for the :class:`.postgresql.JSON` and :class:`.postgresql.JSONB`
when using indexed access has been fixed to work like Postgresql itself,
and returns an expression that itself is of type :class:`.postgresql.JSON`
or :class:`.postgresql.JSONB`.  Previously, the accessor would return
:class:`.NullType` which disallowed subsequent JSON-like operators to be
used. part of fixes #3503
- The :class:`.postgresql.JSON`, :class:`.postgresql.JSONB` and
:class:`.postgresql.HSTORE` datatypes now allow full control over the
return type from an indexed textual access operation, either ``column[someindex].astext``
for a JSON type or ``column[someindex]`` for an HSTORE type,
via the :paramref:`.postgresql.JSON.astext_type` and
:paramref:`.postgresql.HSTORE.text_type` parameters. also part of fixes #3503
- The :attr:`.postgresql.JSON.Comparator.astext` modifier no longer
calls upon :meth:`.ColumnElement.cast` implicitly, as PG's JSON/JSONB
types allow cross-casting between each other as well.  Code that
makes use of :meth:`.ColumnElement.cast` on JSON indexed access,
e.g. ``col[someindex].cast(Integer)``, will need to be changed
to call :attr:`.postgresql.JSON.Comparator.astext` explicitly.  This is
part of the refactor in references #3503 for consistency in operator
use.
2015-08-17 17:07:10 -04:00
Mike Bayer 10cacef2c0 - correct this, need brackets 2015-08-15 13:54:59 -04:00
Mike Bayer e1129b2d3e - make these failure cases more specific to catch Oracle.
Would be nice to fix Oracle here
2015-08-15 13:53:38 -04:00
Mike Bayer b00b430e87 - add tests for InstanceEvents.init, InstanceEvents.init_failure
- ensure that kwargs can be modified in-place within InstanceEvents.init
and that these take effect for the __init__ method.
- improve documentation for these and related events, including
that kwargs can be modified in-place.
2015-08-14 15:34:01 -04:00
Donald Stufft 39517d1046 Tell Wheel to generate platform and interpreter specific wheels
By telling wheel that we have extension modules, even though we
have none, wheel will create a Wheel which is platform and
interpreter specific. This will ensure that the pure Python wheels
on PyPy do not trigger installs on CPython without the C speedups.
2015-08-13 14:57:53 -04:00
Mike Bayer 44420423de - we can again use setuptools.find_packages since we require setuptools
- clean up other things we aren't using anymore
2015-08-13 14:48:18 -04:00
Mike Bayer 88749550f6 - The behavior of the :func:.union construct and related constructs
such as :meth:`.Query.union` now handle the case where the embedded
SELECT statements need to be parenthesized due to the fact that they
include LIMIT, OFFSET and/or ORDER BY.   These queries **do not work
on SQLite**, and will fail on that backend as they did before, but
should now work on all other backends.
fixes #2528
2015-08-12 14:26:11 -04:00
Mike Bayer 5198b1de31 - Fixed 1.0 regression where the "noload" loader strategy would fail
to function for a many-to-one relationship.  The loader used an
API to place "None" into the dictionary which no longer actually
writes a value; this is a side effect of 🎫`3061`.
- remove InstanceState._initialize() totally, it's used nowhere
else and no longer does what it says it does
- fill in fowards-port version ids throughout the changes for 1.0.9
2015-08-11 13:05:17 -04:00
Mike Bayer 669a42c604 - pep8 test/orm/test_mapper 2015-08-11 12:48:38 -04:00
Mike Bayer a7d7941d3e - Fixed two issues regarding Sybase reflection, allowing tables
without primary keys to be reflected as well as ensured that
a SQL statement involved in foreign key detection is pre-fetched up
front to avoid driver issues upon nested queries.  Fixes here
courtesy Eugene Zapolsky; note that we cannot currently test
Sybase to locally verify these changes.
fixes #3508  fixes #3509
2015-08-10 10:07:17 -04:00
mike bayer e99dbe141d Merge pull request #192 from halfcrazy/patch-1
fix typo int->into
2015-08-09 10:22:41 -04:00
halfcrazy 51870ddaef fix typo int->into 2015-08-09 12:00:17 +08:00
mike bayer 838ce5bbad Merge pull request #191 from leorochael/leorochael-remove_dead_variable
Remove useless code
2015-08-06 17:44:33 -04:00
Leonardo Rochael Almeida 69fcabb335 Remove useless code
`to_unicode` variable was created but was not used.
2015-08-06 18:26:45 -03:00
Mike Bayer 292f5bec1c - add a note clarifying query.with_labels(), fixes #3506 2015-08-03 17:46:34 -04:00
Mike Bayer dd6110eed3 - Fixed issue where the SQL Server dialect would reflect a string-
or other variable-length column type with unbounded length
by assigning the token ``"max"`` to the
length attribute of the string.   While using the ``"max"`` token
explicitly is supported by the SQL Server dialect, it isn't part
of the normal contract of the base string types, and instead the
length should just be left as None.   The dialect now assigns the
length to None on reflection of the type so that the type behaves
normally in other contexts.
fixes #3504
2015-07-30 10:34:36 -04:00
Mike Bayer d8efa2257e - Fixed support for cx_Oracle version 5.2, which was tripping
up SQLAlchemy's version detection under Python 3 and inadvertently
not using the correct unicode mode for Python 3.  This would cause
issues such as bound variables mis-interpreted as NULL and rows
silently not being returned.
fixes #3491
2015-07-29 17:40:47 -04:00
Mike Bayer 2e52f87763 - fix typo in suffix_with() docs, fixes #3502 2015-07-29 16:54:02 -04:00
Mike Bayer 4f51fa947f - work to bridge between core/ORM tutorials regarding the text() construct 2015-07-26 16:36:23 -04:00
Mike Bayer 7d268d4bcb - remove "completely raw", whatever that is 2015-07-26 16:29:30 -04:00
Mike Bayer 2997d3910d - typo 2015-07-26 16:22:35 -04:00
Mike Bayer d73ffaafe6 - add an example of text.columns
- correct the scalar() example output
2015-07-26 16:09:25 -04:00
Mike Bayer 5ab9ab7940 - remove "distutils-only" mode, use setuptools only
- add first-class "pytest" runner to setup.py, fixes #3489
- remove references to setuptools Feature and mark that "--without-cextensions"
 is removed, fixes #3500
2015-07-24 18:52:25 -04:00
Mike Bayer 3180f15837 - Organize the tree for 1.1 2015-07-24 18:27:45 -04:00
jonathan vanasco 0a5dcdc2c4 Merge branch 'master' of bitbucket.org:zzzeek/sqlalchemy 2015-07-10 18:52:46 -04:00
jonathan vanasco a0612a4d34 updated sphinx tageting 2015-04-02 15:21:21 -04:00
jonathan vanasco 47e775be2b updates to scoping docs to make .session_factory appear public 2015-04-02 14:46:40 -04:00
jonathan vanasco 6de3d490a2 Merge branch 'master' of bitbucket.org:zzzeek/sqlalchemy 2015-04-02 13:30:26 -04:00
Roman Podoliaka a87b3c2101 Add 'native' autocommit support for mysql drivers
Sometimes it might be useful to have 'native' autocommit support
provided by a DB API driver rather than rely on SQLAlchemy autocommit
emulation.
2015-02-24 19:50:54 +02:00
jvanasco efca4af936 Merged zzzeek/sqlalchemy into master 2014-10-17 19:37:47 -04:00
597 changed files with 206564 additions and 91091 deletions
+27
View File
@@ -0,0 +1,27 @@
<!-- Provide a general summary of your proposed changes in the Title field above -->
### Description
<!-- Describe your changes in detail -->
### Checklist
<!-- go over following points. check them with an `x` if they do apply, (they turn into clickable checkboxes once the PR is submitted, so no need to do everything at once)
-->
This pull request is:
- [ ] A documentation / typographical error fix
- Good to go, no issue or tests are needed
- [ ] A short code fix
- please include the issue number, and create an issue if none exists, which
must include a complete example of the issue. one line code fixes without an
issue and demonstration will not be accepted.
- Please include: `Fixes: #<issue number>` in the commit message
- please include tests. one line code fixes without tests will not be accepted.
- [ ] A new feature implementation
- please include the issue number, and create an issue if none exists, which must
include a complete example of how the feature would look.
- Please include: `Fixes: #<issue number>` in the commit message
- please include tests.
**Have a nice day!**
+11
View File
@@ -19,3 +19,14 @@ coverage.xml
sqlnet.log
/mapping_setup.py
/test.py
/.cache/
/.mypy_cache
*.sw[o,p]
/test?.py
/test.py
/mapping_setup.py
*.rej
test/test_schema.db
*test_schema.db
.idea
/Pipfile*
+4
View File
@@ -0,0 +1,4 @@
[gerrit]
host=gerrit.sqlalchemy.org
project=sqlalchemy/sqlalchemy
defaultbranch=master
-3
View File
@@ -12,7 +12,4 @@ Major contributing authors include:
- Paul Johnston <paj@pajhome.org.uk>
- Jonathan Ellis <jbellis@gmail.com>
For a larger list of SQLAlchemy contributors over time, see:
http://www.sqlalchemy.org/trac/wiki/Contributors
+1 -1
View File
@@ -1,6 +1,6 @@
This is the MIT license: http://www.opensource.org/licenses/mit-license.php
Copyright (c) 2005-2015 the SQLAlchemy authors and contributors <see AUTHORS file>.
Copyright (c) 2005-2019 the SQLAlchemy authors and contributors <see AUTHORS file>.
SQLAlchemy is a trademark of Michael Bayer.
Permission is hereby granted, free of charge, to any person obtaining a copy of this
+2 -2
View File
@@ -1,7 +1,7 @@
# any kind of "*" pulls in __init__.pyc files,
# so all extensions are explicit.
recursive-include doc *.html *.css *.txt *.js *.jpg *.png *.py Makefile *.rst *.mako *.sty
recursive-include doc *.html *.css *.txt *.js *.png *.py Makefile *.rst *.sty
recursive-include examples *.py *.xml
recursive-include test *.py *.dat
@@ -9,5 +9,5 @@ recursive-include test *.py *.dat
# don't come in if --with-cextensions isn't specified.
recursive-include lib *.c *.txt
include README* AUTHORS LICENSE distribute_setup.py sa2to3.py ez_setup.py sqla_nose.py CHANGES* tox.ini
include README* AUTHORS LICENSE sqla_nose.py CHANGES* tox.ini
prune doc/build/output
+5 -57
View File
@@ -35,7 +35,6 @@ The file structure of a dialect is typically similar to the following::
sqlalchemy-<dialect>/
setup.py
setup.cfg
run_tests.py
sqlalchemy_<dialect>/
__init__.py
base.py
@@ -77,27 +76,20 @@ Key aspects of this file layout include:
[egg_info]
tag_build = dev
[pytest]
addopts= --tb native -v -r fxX
[tool:pytest]
addopts= --tb native -v -r fxX --maxfail=25 -p no:warnings
python_files=test/*test_*.py
[nosetests]
with-sqla_testing = true
where = test
cover-package = sqlalchemy_access
with-coverage = 1
cover-erase = 1
[sqla_testing]
requirement_cls=sqlalchemy_access.requirements:Requirements
profile_file=.profiles.txt
profile_file=test/profiles.txt
[db]
default=access+pyodbc://admin@access_test
sqlite=sqlite:///:memory:
Above, the ``[sqla_testing]`` section contains configuration used by
SQLAlchemy's test plugin. The ``[pytest]`` and ``[nosetests]`` sections
SQLAlchemy's test plugin. The ``[tool:pytest]`` section
include directives to help with these runners; in the case of
Nose, the directive ``with-sql_testing = true``, which indicates to Nose that
the SQLAlchemy nose plugin should be used. In the case of pytest, the
@@ -122,35 +114,6 @@ Key aspects of this file layout include:
of setuptools, using the ``registry.register()`` function in a way that
is similar to the ``entry_points`` directive we placed in our ``setup.py``.
* run_tests.py - This script is used when running the tests via Nose.
The purpose of the script is to plug in SQLAlchemy's nose plugin into
the Nose environment before the tests run.
The format of this file is similar to that of conftest.py; first,
the optional but helpful step of registering your third party plugin,
then the other is to import SQLAlchemy's nose runner and invoke it::
from sqlalchemy.dialects import registry
registry.register("access", "sqlalchemy_access.pyodbc", "AccessDialect_pyodbc")
registry.register("access.pyodbc", "sqlalchemy_access.pyodbc", "AccessDialect_pyodbc")
from sqlalchemy.testing import runner
# use this in setup.py 'test_suite':
# test_suite="run_tests.setup_py_test"
def setup_py_test():
runner.setup_py_test()
if __name__ == '__main__':
runner.main()
The call to ``runner.main()`` then runs the Nose front end, which installs
SQLAlchemy's testing plugins. Invoking our custom runner looks like the
following::
$ python run_tests.py -v
* requirements.py - The ``requirements.py`` file is where directives
regarding database and dialect capabilities are set up.
SQLAlchemy's tests are often annotated with decorators that mark
@@ -229,7 +192,7 @@ Going Forward
==============
The third-party dialect can be distributed like any other Python
module on Pypi. Links to prominent dialects can be featured within
module on PyPI. Links to prominent dialects can be featured within
SQLAlchemy's own documentation; contact the developers (see AUTHORS)
for help with this.
@@ -245,18 +208,3 @@ requirements file will receive new tests and changes. The dialect
maintainer would normally keep track of these changes and make
adjustments as needed.
Continuous Integration
======================
The most ideal scenario for ongoing dialect testing is continuous
integration, that is, an automated test runner that runs in response
to changes not just in the dialect itself but to new pushes to
SQLAlchemy as well.
The SQLAlchemy project features a Jenkins installation that runs tests
on Amazon EC2 instances. It is possible for third-party dialect
developers to provide the SQLAlchemy project either with AMIs or EC2
instance keys which feature test environments appropriate to the
dialect - SQLAlchemy's own Jenkins suite can invoke tests on these
environments. Contact the developers for further info.
+31 -23
View File
@@ -16,47 +16,47 @@ language.
Major SQLAlchemy features include:
* An industrial strength ORM, built
* An industrial strength ORM, built
from the core on the identity map, unit of work,
and data mapper patterns. These patterns
allow transparent persistence of objects
allow transparent persistence of objects
using a declarative configuration system.
Domain models
can be constructed and manipulated naturally,
and changes are synchronized with the
current transaction automatically.
* A relationally-oriented query system, exposing
the full range of SQL's capabilities
explicitly, including joins, subqueries,
correlation, and most everything else,
the full range of SQL's capabilities
explicitly, including joins, subqueries,
correlation, and most everything else,
in terms of the object model.
Writing queries with the ORM uses the same
techniques of relational composition you use
Writing queries with the ORM uses the same
techniques of relational composition you use
when writing SQL. While you can drop into
literal SQL at any time, it's virtually never
needed.
* A comprehensive and flexible system
* A comprehensive and flexible system
of eager loading for related collections and objects.
Collections are cached within a session,
and can be loaded on individual access, all
and can be loaded on individual access, all
at once using joins, or by query per collection
across the full result set.
* A Core SQL construction system and DBAPI
* A Core SQL construction system and DBAPI
interaction layer. The SQLAlchemy Core is
separate from the ORM and is a full database
abstraction layer in its own right, and includes
an extensible Python-based SQL expression
language, schema metadata, connection pooling,
an extensible Python-based SQL expression
language, schema metadata, connection pooling,
type coercion, and custom types.
* All primary and foreign key constraints are
* All primary and foreign key constraints are
assumed to be composite and natural. Surrogate
integer primary keys are of course still the
integer primary keys are of course still the
norm, but SQLAlchemy never assumes or hardcodes
to this model.
* Database introspection and generation. Database
schemas can be "reflected" in one step into
Python structures representing database metadata;
those same structures can then generate
those same structures can then generate
CREATE statements right back out - all within
the Core, independent of the ORM.
@@ -73,7 +73,7 @@ SQLAlchemy's philosophy:
that should be fully exposed. SQLAlchemy's
ORM provides an open-ended set of patterns
that allow a developer to construct a custom
mediation layer between a domain model and
mediation layer between a domain model and
a relational schema, turning the so-called
"object relational impedance" issue into
a distant memory.
@@ -82,18 +82,18 @@ SQLAlchemy's philosophy:
of both the object model as well as the relational
schema. SQLAlchemy only provides the means
to automate the execution of these decisions.
* With SQLAlchemy, there's no such thing as
"the ORM generated a bad query" - you
retain full control over the structure of
* With SQLAlchemy, there's no such thing as
"the ORM generated a bad query" - you
retain full control over the structure of
queries, including how joins are organized,
how subqueries and correlation is used, what
how subqueries and correlation is used, what
columns are requested. Everything SQLAlchemy
does is ultimately the result of a developer-
initiated decision.
* Don't use an ORM if the problem doesn't need one.
SQLAlchemy consists of a Core and separate ORM
component. The Core offers a full SQL expression
language that allows Pythonic construction
language that allows Pythonic construction
of SQL constructs that render directly to SQL
strings for a target database, returning
result sets that are essentially enhanced DBAPI
@@ -105,7 +105,7 @@ SQLAlchemy's philosophy:
the start and end of a series of operations.
* Never render a literal value in a SQL statement.
Bound parameters are used to the greatest degree
possible, allowing query optimizers to cache
possible, allowing query optimizers to cache
query plans effectively and making SQL injection
attacks a non-issue.
@@ -119,7 +119,7 @@ http://www.sqlalchemy.org/docs/
Installation / Requirements
---------------------------
Full documentation for installation is at
Full documentation for installation is at
`Installation <http://www.sqlalchemy.org/docs/intro.html#installation>`_.
Getting Help / Development / Bug reporting
@@ -127,6 +127,14 @@ Getting Help / Development / Bug reporting
Please refer to the `SQLAlchemy Community Guide <http://www.sqlalchemy.org/support.html>`_.
Code of Conduct
---------------
Above all, SQLAlchemy places great emphasis on polite, thoughtful, and
constructive communication between users and developers.
Please see our current Code of Conduct at
`Code of Conduct <http://www.sqlalchemy.org/codeofconduct.html>`_.
License
-------
+118 -247
View File
@@ -2,193 +2,146 @@
SQLALCHEMY UNIT TESTS
=====================
**NOTE:** SQLAlchemy as of 0.9.4 now standardizes on `pytest <http://pytest.org/>`_
for test running! However, the existing support for Nose **still remains**!
That is, you can now run the tests via pytest or nose. We hope to keep the
suite nose-compatible indefinitely however this might change at some point.
Updated for 1.1, 1.2
SQLAlchemy unit tests by default run using Python's built-in sqlite3
module. If running on a Python installation that doesn't include this
module, then pysqlite or compatible must be installed.
Basic Test Running
==================
Unit tests can be run with pytest or nose:
A test target exists within the setup.py script. For basic test runs::
py.test: http://pytest.org/
nose: https://pypi.python.org/pypi/nose/
The suite includes enhanced support when running with pytest.
SQLAlchemy implements plugins for both pytest and nose that must be
present when tests are run. In the case of pytest, this plugin is automatically
used when pytest is run against the SQLAlchemy source tree. However,
for Nose support, a special test runner script must be used.
python setup.py test
The test suite as also requires the mock library. While
mock is part of the Python standard library as of 3.3, previous versions
will need to have it installed, and is available at::
Running with Tox
================
https://pypi.python.org/pypi/mock
For more elaborate CI-style test running, the tox script provided will
run against various Python / database targets. For a basic run against
Python 2.7 using an in-memory SQLite database::
RUNNING TESTS VIA SETUP.PY
--------------------------
A plain vanilla run of all tests using sqlite can be run via setup.py, and
requires that pytest is installed::
tox -e py27-sqlite
$ python setup.py test
The tox runner contains a series of target combinations that can run
against various combinations of databases. The test suite can be
run against SQLite with "backend" tests also running against a PostgreSQL
database::
tox -e py36-sqlite-postgresql
Or to run just "backend" tests against a MySQL database::
tox -e py36-mysql-backendonly
Running against backends other than SQLite requires that a database of that
vendor be available at a specific URL. See "Setting Up Databases" below
for details.
The py.test Engine
==================
Both the tox runner and the setup.py runner are using py.test to invoke
the test suite. Within the realm of py.test, SQLAlchemy itself is adding
a large series of option and customizations to the py.test runner using
plugin points, to allow for SQLAlchemy's multiple database support,
database setup/teardown and connectivity, multi process support, as well as
lots of skip / database selection rules.
Running tests with py.test directly grants more immediate control over
database options and test selection.
A generic py.test run looks like::
py.test -n4
Above, the full test suite will run against SQLite, using four processes.
If the "-n" flag is not used, the pytest-xdist is skipped and the tests will
run linearly, which will take a pretty long time.
The py.test command line is more handy for running subsets of tests and to
quickly allow for custom database connections. Example::
py.test --dburi=postgresql+psycopg2://scott:tiger@localhost/test test/sql/test_query.py
Above will run the tests in the test/sql/test_query.py file (a pretty good
file for basic "does this database work at all?" to start with) against a
running PostgreSQL database at the given URL.
The py.test frontend can also run tests against multiple kinds of databases
at once - a large subset of tests are marked as "backend" tests, which will
be run against each available backend, and additionally lots of tests are targeted
at specific backends only, which only run if a matching backend is made available.
For example, to run the test suite against both PostgreSQL and MySQL at the same time::
py.test -n4 --db postgresql --db mysql
RUNNING ALL TESTS - PYTEST
--------------------------
To run all tests::
Setting Up Databases
====================
$ py.test
The test suite identifies several built-in database tags that run against
a pre-set URL. These can be seen using --dbs::
The pytest configuration in setup.cfg will point the runner at the
test/ directory, where it consumes a conftest.py file that gets everything
else up and running.
RUNNING ALL TESTS - NOSE
--------------------------
When using Nose, a bootstrap script is provided which sets up sys.path
as well as installs the nose plugin::
$ ./sqla_nose.py
Assuming all tests pass, this is a very unexciting output. To make it more
interesting::
$ ./sqla_nose.py -v
RUNNING INDIVIDUAL TESTS
---------------------------------
Any directory of test modules can be run at once by specifying the directory
path, and a specific file can be specified as well::
$ py.test test/dialect
$ py.test test/orm/test_mapper.py
When using nose, the setup.cfg currently sets "where" to "test/", so the
"test/" prefix is omitted::
$ ./sqla_nose.py dialect/
$ ./sqla_nose.py orm/test_mapper.py
With Nose, it is often more intuitive to specify tests as module paths::
$ ./sqla_nose.py test.orm.test_mapper
Nose can also specify a test class and optional method using this syntax::
$ ./sqla_nose.py test.orm.test_mapper:MapperTest.test_utils
With pytest, the -k flag is used to limit tests::
$ py.test test/orm/test_mapper.py -k "MapperTest and test_utils"
COMMAND LINE OPTIONS
--------------------
SQLAlchemy-specific options are added to both runners, which are viewable
within the help screen. With pytest, these options are easier to locate
as they are underneath the "sqlalchemy" grouping::
$ py.test --help
$ ./sqla_nose.py --help
The --help screen is a combination of common nose options and options which
the SQLAlchemy nose plugin adds. The most commonly SQLAlchemy-specific
options used are '--db' and '--dburi'.
Both pytest and nose support the same set of SQLAlchemy options, though
pytest features a bit more capability with them.
DATABASE TARGETS
----------------
Tests will target an in-memory SQLite database by default. To test against
another database, use the --dburi option with any standard SQLAlchemy URL::
--dburi=postgresql://user:password@localhost/test
If you'll be running the tests frequently, database aliases can save a lot of
typing. The --dbs option lists the built-in aliases and their matching URLs::
$ py.test --dbs
$ py.test --dbs=.
Available --db options (use --dburi to override)
mysql mysql://scott:tiger@127.0.0.1:3306/test
oracle oracle://scott:tiger@127.0.0.1:1521
postgresql postgresql://scott:tiger@127.0.0.1:5432/test
[...]
default sqlite:///:memory:
firebird firebird://sysdba:masterkey@localhost//Users/classic/foo.fdb
mssql mssql+pyodbc://scott:tiger@ms_2008
mssql_pymssql mssql+pymssql://scott:tiger@ms_2008
mysql mysql://scott:tiger@127.0.0.1:3306/test?charset=utf8
oracle oracle://scott:tiger@127.0.0.1:1521
oracle8 oracle://scott:tiger@127.0.0.1:1521/?use_ansi=0
pg8000 postgresql+pg8000://scott:tiger@127.0.0.1:5432/test
postgresql postgresql://scott:tiger@127.0.0.1:5432/test
postgresql_psycopg2cffi postgresql+psycopg2cffi://scott:tiger@127.0.0.1:5432/test
pymysql mysql+pymysql://scott:tiger@127.0.0.1:3306/test?charset=utf8
sqlite sqlite:///:memory:
sqlite_file sqlite:///querytest.db
To run tests against an aliased database::
What those mean is that if you have a database running that can be accessed
by the above URL, you can run the test suite against it using ``--db <name>``.
$ py.test --db postgresql
This list of database urls is present in the setup.cfg file. The list
can be modified/extended by adding a file ``test.cfg`` at the
top level of the SQLAlchemy source distribution which includes
additional entries::
The URLs are present in the ``setup.cfg`` file. You can make your own URLs by
creating a new file called ``test.cfg`` and adding your own ``[db]`` section::
# test.cfg file
[db]
postgresql=postgresql://myuser:mypass@localhost/mydb
my_postgresql=postgresql://username:pass@hostname/dbname
Your custom entries will override the defaults and you'll see them reflected
in the output of --dbs.
Above, we can now run the tests with ``my_postgresql``::
MULTIPLE DATABASE TARGETS
-------------------------
py.test --db my_postgresql
As of SQLAlchemy 0.9.4, the test runner supports **multiple databases at once**.
This doesn't mean that the entire test suite runs for each database, but
instead specific test suites may do so, while other tests may choose to
run on a specific target out of those available. For example, if the tests underneath
test/dialect/ are run, the majority of these tests are either specific to
a particular backend, or are marked as "multiple", meaning they will run repeatedly
for each database in use. If one runs the test suite as follows::
We can also override the existing names in our ``test.cfg`` file, so that we can run
with the tox runner also::
$ py.test test/dialect --db sqlite --db postgresql --db mysql
# test.cfg file
[db]
postgresql=postgresql://username:pass@hostname/dbname
The tests underneath test/dialect/test_suite.py will be tripled up, running
as appropriate for each target database, whereas dialect-specific tests
within test/dialect/mysql, test/dialect/postgresql/ test/dialect/test_sqlite.py
should run fully with no skips, as each suite has its target database available.
Now when we run ``tox -e py27-postgresql``, it will use our custom URL instead
of the fixed one in setup.cfg.
The multiple targets feature is available both under pytest and nose,
however when running nose, the "multiple runner" feature won't be available;
instead, the first database target will be used.
Database Configuration
======================
When running with multiple targets, tests that don't prefer a specific target
will be run against the first target specified. Putting sqlite first in
the list will lead to a much faster suite as the in-memory database is
extremely fast for setting up and tearing down tables.
DATABASE CONFIGURATION
----------------------
Use an empty database and a database user with general DBA privileges.
The test suite will be creating and dropping many tables and other DDL, and
preexisting tables will interfere with the tests.
The test runner will by default create and drop tables within the default
database that's in the database URL, *unless* the multiprocessing option
is in use via the py.test "-n" flag, which invokes pytest-xdist. The
multiprocessing option is **enabled by default** for both the tox runner
and the setup.py frontend. When multiprocessing is used, the SQLAlchemy
testing framework will create a new database for each process, and then
tear it down after the test run is complete. So it will be necessary
for the database user to have access to CREATE DATABASE in order for this
to work.
Several tests require alternate usernames or schemas to be present, which
are used to test dotted-name access scenarios. On some databases such
as Oracle or Sybase, these are usernames, and others such as Postgresql
as Oracle or Sybase, these are usernames, and others such as PostgreSQL
and MySQL they are schemas. The requirement applies to all backends
except SQLite and Firebird. The names are::
test_schema
test_schema_2 (only used on Postgresql)
test_schema_2 (only used on PostgreSQL)
Please refer to your vendor documentation for the proper syntax to create
these namespaces - the database user must have permission to create and drop
@@ -210,10 +163,14 @@ Additional steps specific to individual databases are as follows::
test=# create extension hstore;
CREATE EXTENSION
MYSQL: Default storage engine should be "MyISAM". Tests that require
"InnoDB" as the engine will specify this explicitly.
Full-text search configuration should be set to English, else
several tests of ``.match()`` will fail. This can be set (if it isn't so
already) with:
ORACLE: a user named "test_schema" is created.
ALTER DATABASE test SET default_text_search_config = 'pg_catalog.english'
ORACLE: a user named "test_schema" is created in addition to the default
user.
The primary database user needs to be able to create and drop tables,
synonyms, and constraints within the "test_schema" user. For this
@@ -223,31 +180,6 @@ Additional steps specific to individual databases are as follows::
grant dba to scott;
SYBASE: Similar to Oracle, "test_schema" is created as a user, and the
primary test user needs to have the "sa_role".
It's also recommended to turn on "trunc log on chkpt" and to use a
separate transaction log device - Sybase basically seizes up when
the transaction log is full otherwise.
A full series of setup assuming sa/master:
disk init name="translog", physname="/opt/sybase/data/translog.dat", size="10M"
create database sqlalchemy on default log on translog="10M"
sp_dboption sqlalchemy, "trunc log on chkpt", true
sp_addlogin scott, "tiger7"
sp_addlogin test_schema, "tiger7"
use sqlalchemy
sp_adduser scott
sp_adduser test_schema
grant all to scott
sp_role "grant", sa_role, scott
Sybase will still freeze for up to a minute when the log becomes
full. To manually dump the log::
dump tran sqlalchemy with truncate_only
MSSQL: Tests that involve multiple connections require Snapshot Isolation
ability implemented on the test database in order to prevent deadlocks that
will occur with record locking isolation. This feature is only available
@@ -258,16 +190,6 @@ Additional steps specific to individual databases are as follows::
ALTER DATABASE MyDatabase SET READ_COMMITTED_SNAPSHOT ON
MSSQL+zxJDBC: Trying to run the unit tests on Windows against SQL Server
requires using a test.cfg configuration file as the cmd.exe shell won't
properly pass the URL arguments into the nose test runner.
POSTGRESQL: Full-text search configuration should be set to English, else
several tests of ``.match()`` will fail. This can be set (if it isn't so
already) with:
ALTER DATABASE test SET default_text_search_config = 'pg_catalog.english'
CONFIGURING LOGGING
-------------------
@@ -275,66 +197,15 @@ SQLAlchemy logs its activity and debugging through Python's logging package.
Any log target can be directed to the console with command line options, such
as::
$ ./sqla_nose.py test.orm.unitofwork --log-info=sqlalchemy.orm.mapper \
$ ./py.test test/orm/test_unitofwork.py -s \
--log-debug=sqlalchemy.pool --log-info=sqlalchemy.engine
This would log mapper configuration, connection pool checkouts, and SQL
statement execution.
Above we add the py.test "-s" flag so that standard out is not suppressed.
BUILT-IN COVERAGE REPORTING
------------------------------
Coverage is tracked using the coverage plugins built for pytest or nose::
$ py.test test/sql/test_query --cov=sqlalchemy
$ ./sqla_nose.py test.sql.test_query --with-coverage
BIG COVERAGE TIP !!! There is an issue where existing .pyc files may
store the incorrect filepaths, which will break the coverage system. If
coverage numbers are coming out as low/zero, try deleting all .pyc files.
DEVELOPING AND TESTING NEW DIALECTS
-----------------------------------
See the file README.dialects.rst for detail on dialects.
TESTING WITH MULTIPLE PYTHON VERSIONS USING TOX
-----------------------------------------------
If you want to test across multiple versions of Python, you may find `tox
<http://tox.testrun.org/>`_ useful. SQLAlchemy includes a tox.ini file::
tox -e full
SQLAlchemy uses tox mostly for pre-fab testing configurations, to simplify
configuration of Jenkins jobs, and *not* for testing different Python
interpreters simultaneously. You can of course create whatever alternate
tox.ini file you want.
Environments include::
"full" - runs a full py.test
"coverage" - runs a py.test plus coverage, skipping memory/timing
intensive tests
"pep8" - runs flake8 against the codebase (useful with --diff to check
against a patch)
PARALLEL TESTING
----------------
Parallel testing is supported using the Pytest xdist plugin. Supported
databases currently include sqlite, postgresql, and mysql. The username
for the database should have CREATE DATABASE and DROP DATABASE privileges.
After installing pytest-xdist, testing is run adding the -n<num> option.
For example, to run against sqlite, mysql, postgresql with four processes::
tox -e -- -n 4 --db sqlite --db postgresql --db mysql
Each backend has a different scheme for setting up the database. Postgresql
still needs the "test_schema" and "test_schema_2" schemas present, as the
parallel databases are created using the base database as a "template".
+6 -6
View File
@@ -1,7 +1,7 @@
==============
=============
0.1 Changelog
==============
=============
.. changelog::
@@ -223,7 +223,7 @@
added 'version_id' keyword argument to mapper. this keyword should reference a
Column object with type Integer, preferably non-nullable, which will be used on
the mapped table to track version numbers. this number is incremented on each
save operation and is specifed in the UPDATE/DELETE conditions so that it
save operation and is specified in the UPDATE/DELETE conditions so that it
factors into the returned row count, which results in a ConcurrencyError if the
value received is not the expected count.
@@ -237,7 +237,7 @@
created for a class, qualified by the entity name. instances of those classes
will issue all of their load and save operations through their
entity_name-qualified mapper, and maintain separate a identity in the identity
map for an otherwise equilvalent object.
map for an otherwise equivalent object.
.. change::
:tags:
@@ -877,7 +877,7 @@
:tags:
:tickets:
began to implement newer logic in object properities. you can now say
began to implement newer logic in object properties. you can now say
myclass.attr.property, which will give you the PropertyLoader corresponding to that
attribute, i.e. myclass.mapper.props['attr']
@@ -943,7 +943,7 @@
:tickets:
fix to engine.process_defaults so it works correctly with a table that has
different column name/column keys (changset 982)
different column name/column keys (changeset 982)
.. change::
:tags:
+6 -6
View File
@@ -1,7 +1,7 @@
==============
=============
0.2 Changelog
==============
=============
.. changelog::
@@ -223,7 +223,7 @@
:tags:
:tickets:
modifcation to unitofwork to not maintain ordering within the
modification to unitofwork to not maintain ordering within the
"new" list or within the UOWTask "objects" list; instead, new objects
are tagged with an ordering identifier as they are registered as new
with the session, and the INSERT statements are then sorted within the
@@ -949,7 +949,7 @@
:tags:
:tickets:
fixes to session cascade behavior, entity_name propigation
fixes to session cascade behavior, entity_name propagation
.. change::
:tags:
@@ -1098,7 +1098,7 @@
overhaul to Schema to build upon MetaData object instead of an Engine.
Entire SQL/Schema system can be used with no Engines whatsoever, executed
solely by an explicit Connection object. the "bound" methodlogy exists via the
solely by an explicit Connection object. the "bound" methodology exists via the
BoundMetaData for schema objects. ProxyEngine is generally not needed
anymore and is replaced by DynamicMetaData.
@@ -1143,7 +1143,7 @@
:tickets:
backrefs create themselves against primary mapper of its originating
property, priamry/secondary join arguments can be specified to override.
property, primary/secondary join arguments can be specified to override.
helps their usage with polymorphic mappers
.. change::
+11 -11
View File
@@ -1,7 +1,7 @@
==============
=============
0.3 Changelog
==============
=============
.. changelog::
@@ -167,7 +167,7 @@
:tags: sql
:tickets: 667
foreign key specs can have any chararcter in their identifiers
foreign key specs can have any character in their identifiers
.. change::
:tags: sql
@@ -878,7 +878,7 @@
preliminary support for unicode table names, column names and
SQL statements added, for databases which can support them.
Works with sqlite and postgres so far. Mysql *mostly* works
Works with sqlite and postgres so far. MySQL *mostly* works
except the has_table() function does not work. Reflection
works too.
@@ -1167,7 +1167,7 @@
and the key will be shared. proper positional/named args translate
at compile time. for the old behavior of "aliasing" bind parameters
with conflicting names, specify "unique=True" - this option is
still used internally for all the auto-genererated (value-based)
still used internally for all the auto-generated (value-based)
bind parameters.
.. change::
@@ -1379,7 +1379,7 @@
:tickets:
some fixes to relationship calcs when using "viewonly=True" to pull
in other tables into the join condition which arent parent of the
in other tables into the join condition which aren't parent of the
relationship's parent/child mappings
.. change::
@@ -1508,7 +1508,7 @@
the value of "case_sensitive" defaults to True now, regardless of the
casing of the identifier, unless specifically set to False. this is
because the object might be label'ed as something else which does
contain mixed case, and propigating "case_sensitive=False" breaks that.
contain mixed case, and propagating "case_sensitive=False" breaks that.
Other fixes to quoting when using labels and "fake" column objects
.. change::
@@ -2622,7 +2622,7 @@
index=True/unique=False creates a plain Index,
index=True/unique=True on Column creates a unique Index. 'index'
and 'unique' keyword arguments to column are now boolean only; for
explcit names and groupings of indexes or unique constraints, use the
explicit names and groupings of indexes or unique constraints, use the
UniqueConstraint/Index constructs explicitly.
.. change::
@@ -2645,7 +2645,7 @@
:tickets:
fixed condition that occurred during reflection when a primary key
column was explciitly overridden, where the PrimaryKeyConstraint would
column was explicitly overridden, where the PrimaryKeyConstraint would
get both the reflected and the programmatic column doubled up
.. change::
@@ -2701,7 +2701,7 @@
changed "for_update" parameter to accept False/True/"nowait"
and "read", the latter two of which are interpreted only by
Oracle and Mysql
Oracle and MySQL
.. change::
:tags: construction, sql
@@ -2753,7 +2753,7 @@
:tickets:
a wide refactoring to "attribute loader" and "options" architectures.
ColumnProperty and PropertyLoader define their loading behaivor via switchable
ColumnProperty and PropertyLoader define their loading behavior via switchable
"strategies", and MapperOptions no longer use mapper/property copying
in order to function; they are instead propagated via QueryContext
and SelectionContext objects at query/instances time.
+8 -8
View File
@@ -1,7 +1,7 @@
==============
=============
0.4 Changelog
==============
=============
.. changelog::
@@ -266,7 +266,7 @@
:tickets: 1036
repaired single table inheritance such that you
can single-table inherit from a joined-table inherting
can single-table inherit from a joined-table inheriting
mapper without issue.
.. change::
@@ -674,7 +674,7 @@
whether or not it remains attached to its also-deleted
parent.
- delete-orphan casacde is properly detected on relations
- delete-orphan cascade is properly detected on relations
that are present on superclasses when using inheritance.
.. change::
@@ -2300,7 +2300,7 @@
MSSQL
- PyODBC no longer has a global "set nocount on".
- Fix non-identity integer PKs on autload
- Fix non-identity integer PKs on autoload
- Better support for convert_unicode
- Less strict date conversion for pyodbc/adodbapi
- Schema-qualified tables / autoload
@@ -2712,7 +2712,7 @@
:tickets:
Renamed the Dialect attribute 'preexecute_sequences' to
'preexecute_pk_sequences'. An attribute porxy is in place for
'preexecute_pk_sequences'. An attribute proxy is in place for
out-of-tree dialects using the old name.
.. change::
@@ -3415,7 +3415,7 @@
:tickets:
Hooks added throughout base/sql/defaults to optimize the calling of bind
aram/result processors so that method call overhead is minimized.
param/result processors so that method call overhead is minimized.
.. change::
:tags:
@@ -4080,7 +4080,7 @@
:tags: metadata
:tickets:
Added "explcit" create/drop/execute support for sequences (i.e. you can
Added "explicit" create/drop/execute support for sequences (i.e. you can
pass a "connectable" to each of those methods on Sequence).
.. change::
+12 -12
View File
@@ -1,7 +1,7 @@
==============
=============
0.5 Changelog
==============
=============
.. changelog::
@@ -599,7 +599,7 @@
Fixed Query being able to join() from individual columns of a
joined-table subclass entity, i.e. query(SubClass.foo,
SubcClass.bar).join(<anything>). In most cases, an error
SubClass.bar).join(<anything>). In most cases, an error
"Could not find a FROM clause to join from" would be
raised. In a few others, the result would be returned in terms
of the base class rather than the subclass - so applications
@@ -783,10 +783,10 @@
itself differently to some MapperExtensions.
The change also affects the internal attribute API, but not
the AttributeExtension interface nor any of the publically
the AttributeExtension interface nor any of the publicly
documented attribute functions.
- The unit of work no longer genererates a graph of "dependency"
- The unit of work no longer generates a graph of "dependency"
processors for the full graph of mappers during flush(), instead
creating such processors only for those mappers which represent
objects with pending changes. This saves a tremendous number
@@ -1172,7 +1172,7 @@
Query won't fail with weakref error when a non-mapper/class
instrumented descriptor is passed, raises
"Invalid column expession".
"Invalid column expression".
.. change::
:tags: orm
@@ -1443,7 +1443,7 @@
:tickets: 1237, 781
Added a new `relation()` keyword `back_populates`. This
allows configuation of backreferences using explicit
allows configuration of backreferences using explicit
relations. This is required when creating
bidirectional relations between a hierarchy of concrete
mappers and another class.
@@ -1461,7 +1461,7 @@
Query.from_self() as well as query.subquery() both disable
the rendering of eager joins inside the subquery produced.
The "disable all eager joins" feature is available publically
The "disable all eager joins" feature is available publicly
via a new query.enable_eagerloads() generative.
.. change::
@@ -1470,7 +1470,7 @@
Added a rudimental series of set operations to Query that
receive Query objects as arguments, including union(),
union_all(), intersect(), except_(), insertsect_all(),
union_all(), intersect(), except_(), intersect_all(),
except_all(). See the API documentation for
Query.union() for examples.
@@ -1525,7 +1525,7 @@
Using delete-orphan on a many-to-many relation is deprecated.
This produces misleading or erroneous results since SQLA does
not retrieve the full list of "parents" for m2m. To get delete-orphan
behavior with an m2m table, use an explcit association class
behavior with an m2m table, use an explicit association class
so that the individual association row is treated as a parent.
.. change::
@@ -2651,7 +2651,7 @@
Added more granularity to internal attribute access, such that
cascade and flush operations will not initialize unloaded
attributes and collections, leaving them intact for a
lazy-load later on. Backref events still initialize attrbutes
lazy-load later on. Backref events still initialize attributes
and collections for pending instances.
.. change::
@@ -3461,7 +3461,7 @@
:tickets:
Fixed query.join() when used in conjunction with a
columns-only clause and an SQL-expression ON clause in the
columns-only clause and a SQL-expression ON clause in the
join.
.. change::
+20 -20
View File
@@ -1,7 +1,7 @@
==============
=============
0.6 Changelog
==============
=============
.. changelog::
@@ -524,7 +524,7 @@
cleanup() were not explicitly closed, leaving garbage
collection to the task instead. This generally only
affects non-reference-counting backends like Jython
and Pypy. Thanks to Jaimy Azle for spotting
and PyPy. Thanks to Jaimy Azle for spotting
this.
.. change::
@@ -543,7 +543,7 @@
of the auto-generated sequence of a SERIAL column,
which currently only occurs if implicit_returning=False,
now accommodates if the table + column name is greater
than 63 characters using the same logic Postgresql uses.
than 63 characters using the same logic PostgreSQL uses.
.. change::
:tags: postgresql
@@ -1309,7 +1309,7 @@
@classproperty 's official name/location for usage
with declarative is sqlalchemy.ext.declarative.declared_attr.
Same thing, but moving there since it is more of a
"marker" that's specific to declararative,
"marker" that's specific to declarative,
not just an attribute technique.
.. change::
@@ -1390,7 +1390,7 @@
:tags: oracle
:tickets: 1878
The implicit_retunring argument to create_engine()
The implicit_returning argument to create_engine()
is now honored regardless of detected version of
Oracle. Previously, the flag would be forced
to False if server version info was < 10.
@@ -1465,7 +1465,7 @@
changed to StaleDataError, and descriptive
error messages have been revised to reflect
exactly what the issue is. Both names will
remain available for the forseeable future
remain available for the foreseeable future
for schemes that may be specifying
ConcurrentModificationError in an "except:"
clause.
@@ -1477,7 +1477,7 @@
Added a mutex to the identity map which mutexes
remove operations against iteration methods,
which now pre-buffer before returning an
iterable. This because asyncrhonous gc
iterable. This because asynchronous gc
can remove items via the gc thread at any time.
.. change::
@@ -2479,7 +2479,7 @@
:tags: sql
:tickets: 1571
Fixed "table" argument on constructor of ForeginKeyConstraint
Fixed "table" argument on constructor of ForeignKeyConstraint
.. change::
:tags: sql
@@ -2850,7 +2850,7 @@
:tags: postgresql
:tickets: 1071
Postgresql now reflects sequence names associated with
PostgreSQL now reflects sequence names associated with
SERIAL columns correctly, after the name of the sequence
has been changed. Thanks to Kumar McMillan for the patch.
@@ -2873,7 +2873,7 @@
:tags: postgresql
:tickets: 1769
Postgresql reflects the name of primary key constraints,
PostgreSQL reflects the name of primary key constraints,
if one exists.
.. change::
@@ -3462,7 +3462,7 @@
as well as the adaptation of the Python operator into
a SQL operator, based on the full left/right/operator
of the given expression. In particular
the date/time/interval system created for Postgresql
the date/time/interval system created for PostgreSQL
EXTRACT in has now been generalized into
the type system. The previous behavior which often
occurred of an expression "column + literal" forcing
@@ -3845,7 +3845,7 @@
:tickets:
For the full set of feature descriptions, see
http://www.sqlalchemy.org/trac/wiki/06Migration .
http://docs.sqlalchemy.org/en/latest/changelog/migration_06.html .
This document is a work in progress.
.. change::
@@ -4259,7 +4259,7 @@
returning() support is native to insert(), update(),
delete(). Implementations of varying levels of
functionality exist for Postgresql, Firebird, MSSQL and
functionality exist for PostgreSQL, Firebird, MSSQL and
Oracle. returning() can be called explicitly with column
expressions which are then returned in the resultset,
usually via fetchone() or first().
@@ -4280,7 +4280,7 @@
another will now be grouped with parenthesis - previously,
the first compound element in the list would not be grouped,
as SQLite doesn't like a statement to start with
parenthesis. However, Postgresql in particular has
parenthesis. However, PostgreSQL in particular has
precedence rules regarding INTERSECT, and it is
more consistent for parenthesis to be applied equally
to all sub-elements. So now, the workaround for SQLite
@@ -4586,7 +4586,7 @@
The "start" and "increment" attributes on Sequence now
generate "START WITH" and "INCREMENT BY" by default,
on Oracle and Postgresql. Firebird doesn't support
on Oracle and PostgreSQL. Firebird doesn't support
these keywords right now.
.. change::
@@ -5227,7 +5227,7 @@
:tickets:
The construction of types within dialects has been totally
overhauled. Dialects now define publically available types
overhauled. Dialects now define publicly available types
as UPPERCASE names exclusively, and internal implementation
types using underscore identifiers (i.e. are private).
The system by which types are expressed in SQL and DDL
@@ -5279,7 +5279,7 @@
optimized, resulting in varying speed improvements:
Unicode, PickleType, Interval, TypeDecorator, Binary.
Also the following dbapi-specific implementations have been improved:
Time, Date and DateTime on Sqlite, ARRAY on Postgresql,
Time, Date and DateTime on Sqlite, ARRAY on PostgreSQL,
Time on MySQL, Numeric(as_decimal=False) on MySQL, oursql and
pypostgresql, DateTime on cx_oracle and LOB-based types on cx_oracle.
@@ -5332,7 +5332,7 @@
PickleType now uses == for comparison of values when
mutable=True, unless the "comparator" argument with a
comparsion function is specified to the type. Objects
comparison function is specified to the type. Objects
being pickled will be compared based on identity (which
defeats the purpose of mutable=True) if __eq__() is not
overridden or a comparison function is not provided.
@@ -5368,7 +5368,7 @@
session, using autocommit=False, autoflush=True. Default
behavior of SQLSoup now requires the usual usage of commit()
and rollback(), which have been added to its interface. An
explcit Session or scoped_session can be passed to the
explicit Session or scoped_session can be passed to the
constructor, allowing these arguments to be overridden.
.. change::
+17 -17
View File
@@ -1,7 +1,7 @@
==============
=============
0.7 Changelog
==============
=============
.. changelog::
:version: 0.7.11
@@ -88,7 +88,7 @@
:tickets: 2676
:versions: 0.8.0
Added support for Postgresql's traditional SUBSTRING
Added support for PostgreSQL's traditional SUBSTRING
function syntax, renders as "SUBSTRING(x FROM y FOR z)"
when regular ``func.substring()`` is used.
Courtesy Gunnlaugur Þór Briem.
@@ -586,7 +586,7 @@
Fixed compiler bug whereby using a correlated
subquery within an ORDER BY would fail to render correctly
if the stament also used LIMIT/OFFSET, due to mis-rendering
if the statement also used LIMIT/OFFSET, due to mis-rendering
within the ROW_NUMBER() OVER clause. Fix courtesy
sayap
@@ -885,7 +885,7 @@
:tickets: 2445
Added new for_update/with_lockmode()
options for Postgresql: for_update="read"/
options for PostgreSQL: for_update="read"/
with_lockmode("read"),
for_update="read_nowait"/
with_lockmode("read_nowait").
@@ -1873,7 +1873,7 @@
The update() construct can now accommodate
multiple tables in the WHERE clause, which will
render an "UPDATE..FROM" construct, recognized by
Postgresql and MSSQL. When compiled on MySQL,
PostgreSQL and MSSQL. When compiled on MySQL,
will instead generate "UPDATE t1, t2, ..". MySQL
additionally can render against multiple tables in the
SET clause, if Column objects are used as keys
@@ -1968,7 +1968,7 @@
:tickets: 1679
a "has_schema" method has been implemented
on dialect, but only works on Postgresql so far.
on dialect, but only works on PostgreSQL so far.
Courtesy Manlio Perillo.
.. change::
@@ -2025,7 +2025,7 @@
:tags: postgresql, bug
:tickets: 2311
Postgresql dialect memoizes that an ENUM of a
PostgreSQL dialect memoizes that an ENUM of a
particular name was processed
during a create/drop sequence. This allows
a create/drop sequence to work without any
@@ -3220,7 +3220,7 @@
This section documents those changes from 0.7b4
to 0.7.0. For an overview of what's new in
SQLAlchemy 0.7, see
http://www.sqlalchemy.org/trac/wiki/07Migration
http://docs.sqlalchemy.org/en/latest/changelog/migration_07.html
.. change::
:tags: orm
@@ -3696,7 +3696,7 @@
:tickets: 2081
REAL has been added to the core types. Supported
by Postgresql, SQL Server, MySQL, SQLite. Note
by PostgreSQL, SQL Server, MySQL, SQLite. Note
that the SQL Server and MySQL versions, which
add extra arguments, are also still available
from those dialects.
@@ -3790,7 +3790,7 @@
:tags: general
:tickets:
Lots of fixes to unit tests when run under Pypy
Lots of fixes to unit tests when run under PyPy
(courtesy Alex Gaynor).
.. change::
@@ -4125,7 +4125,7 @@
Detailed descriptions of each change below are
described at:
http://www.sqlalchemy.org/trac/wiki/07Migration
http://docs.sqlalchemy.org/en/latest/changelog/migration_07.html
.. change::
:tags: general
@@ -4348,7 +4348,7 @@
:tickets: 1069
Query.distinct() now accepts column expressions
as \*args, interpreted by the Postgresql dialect
as \*args, interpreted by the PostgreSQL dialect
as DISTINCT ON (<expr>).
.. change::
@@ -4448,7 +4448,7 @@
:tickets: 1069
select.distinct() now accepts column expressions
as \*args, interpreted by the Postgresql dialect
as \*args, interpreted by the PostgreSQL dialect
as DISTINCT ON (<expr>). Note this was already
available via passing a list to the `distinct`
keyword argument to select().
@@ -4531,7 +4531,7 @@
"isolation_level" argument, sets transaction isolation
level for that connection only until returned to the
connection pool, for those backends which support it
(SQLite, Postgresql)
(SQLite, PostgreSQL)
.. change::
:tags: sql
@@ -4648,7 +4648,7 @@
of the auto-generated sequence of a SERIAL column,
which currently only occurs if implicit_returning=False,
now accommodates if the table + column name is greater
than 63 characters using the same logic Postgresql uses. (also in 0.6.7)
than 63 characters using the same logic PostgreSQL uses. (also in 0.6.7)
.. change::
:tags: postgresql
@@ -4668,7 +4668,7 @@
'unbounded'. This also occurs for the VARBINARY type..
This behavior makes these types more closely compatible
with Postgresql's VARCHAR type which is similarly unbounded
with PostgreSQL's VARCHAR type which is similarly unbounded
when no length is specified.
.. change::
+31 -43
View File
@@ -1,7 +1,7 @@
==============
=============
0.8 Changelog
==============
=============
.. changelog_imports::
@@ -93,7 +93,7 @@
:tickets: 3044
Fixed bug in INSERT..FROM SELECT construct where selecting from a
UNION would wrap the union in an anonymous (e.g. unlabled) subquery.
UNION would wrap the union in an anonymous (e.g. unlabeled) subquery.
.. change::
:tags: bug, postgresql
@@ -127,7 +127,6 @@
.. change::
:tags: bug, ext
:versions: 0.9.5, 1.0.0b1
:pullreq: bitbucket:24
:tickets: 3093, 3051
Fixed bug where :meth:`.MutableDict.setdefault` didn't return the
@@ -137,7 +136,6 @@
.. change::
:tags: bug, mysql
:versions: 0.9.5, 1.0.0b1
:pullreq: bitbucket:15
Added support for reflecting tables where an index includes
KEY_BLOCK_SIZE using an equal sign. Pull request courtesy
@@ -165,7 +163,6 @@
.. change::
:tags: bug, postgresql
:pullreq: bitbucket:13
:versions: 0.9.5, 1.0.0b1
Added a new "disconnect" message "connection has been closed unexpectedly".
@@ -197,7 +194,7 @@
:versions: 0.9.4
Fixed regression caused by release 0.8.5 / 0.9.3's compatibility
enhancements where index reflection on Postgresql versions specific
enhancements where index reflection on PostgreSQL versions specific
to only the 8.1, 8.2 series again
broke, surrounding the ever problematic int2vector type. While
int2vector supports array operations as of 8.1, apparently it only
@@ -252,7 +249,7 @@
Fixed bug in :func:`.tuple_` construct where the "type" of essentially
the first SQL expression would be applied as the "comparison type"
to a compared tuple value; this has the effect in some cases of an
inappropriate "type coersion" occurring, such as when a tuple that
inappropriate "type coercion" occurring, such as when a tuple that
has a mix of String and Binary values improperly coerces target
values to Binary even though that's not what they are on the left
side. :func:`.tuple_` now expects heterogeneous types within its
@@ -284,8 +281,8 @@
:tags: postgresql, bug
:versions: 0.9.3
Support has been improved for Postgresql reflection behavior on very old
(pre 8.1) versions of Postgresql, and potentially other PG engines
Support has been improved for PostgreSQL reflection behavior on very old
(pre 8.1) versions of PostgreSQL, and potentially other PG engines
such as Redshift (assuming Redshift reports the version as < 8.1).
The query for "indexes" as well as "primary keys" relies upon inspecting
a so-called "int2vector" datatype, which refuses to coerce to an array
@@ -311,7 +308,6 @@
:tags: bug, mysql
:versions: 0.9.3
:tickets: 2966
:pullreq: bitbucket:12
Added support for the ``PARTITION BY`` and ``PARTITIONS``
MySQL table keywords, specified as ``mysql_partition_by='value'`` and
@@ -339,7 +335,6 @@
.. change::
:tags: bug, sqlite
:pullreq: github:72
Restored a change that was missed in the backport of unique
constraint reflection to 0.8, where :class:`.UniqueConstraint`
@@ -351,10 +346,10 @@
:tickets: 2291
:versions: 0.9.3
Revised this very old issue where the Postgresql "get primary key"
Revised this very old issue where the PostgreSQL "get primary key"
reflection query were updated to take into account primary key constraints
that were renamed; the newer query fails on very old versions of
Postgresql such as version 7, so the old query is restored in those cases
PostgreSQL such as version 7, so the old query is restored in those cases
when server_version_info < (8, 0) is detected.
.. change::
@@ -392,7 +387,6 @@
.. change::
:tags: bug, mysql
:pullreq: github:61
:versions: 0.9.2
Some missing methods added to the cymysql dialect, including
@@ -401,7 +395,6 @@
.. change::
:tags: bug, py3k
:pullreq: github:63
Fixed Py3K bug where a missing import would cause "literal binary"
mode to fail to import "util.binary_type" when rendering a bound
@@ -411,7 +404,6 @@
.. change::
:tags: bug, orm
:versions: 0.9.2
:pullreq: github:58
Fixed error message when an iterator object is passed to
:func:`.class_mapper` or similar, where the error would fail to
@@ -444,7 +436,6 @@
.. change::
:tags: bug, mssql, pymssql
:versions: 0.9.0
:pullreq: github:51
Added "Net-Lib error during Connection reset by peer" message
to the list of messages checked for "disconnect" within the
@@ -571,7 +562,6 @@
.. change::
:tags: bug, mssql
:versions: 0.9.0
:pullreq: bitbucket:7
Fixed bug introduced in 0.8.0 where the ``DROP INDEX``
statement for an index in MSSQL would render incorrectly if the
@@ -798,8 +788,8 @@
:tickets: 2819
:versions: 0.9.0b1
Fixed bug where Postgresql version strings that had a prefix preceding
the words "Postgresql" or "EnterpriseDB" would not parse.
Fixed bug where PostgreSQL version strings that had a prefix preceding
the words "PostgreSQL" or "EnterpriseDB" would not parse.
Courtesy Scott Schaefer.
.. change::
@@ -834,10 +824,10 @@
Added a new flag ``system=True`` to :class:`.Column`, which marks
the column as a "system" column which is automatically made present
by the database (such as Postgresql ``oid`` or ``xmin``). The
by the database (such as PostgreSQL ``oid`` or ``xmin``). The
column will be omitted from the ``CREATE TABLE`` statement but will
otherwise be available for querying. In addition, the
:class:`.CreateColumn` construct can be appled to a custom
:class:`.CreateColumn` construct can be applied to a custom
compilation rule which allows skipping of columns, by producing
a rule that returns ``None``.
@@ -858,7 +848,7 @@
Fixed a potential issue in an ordered sequence implementation used
by the ORM to iterate mapper hierarchies; under the Jython interpreter
this implementation wasn't ordered, even though cPython and Pypy
this implementation wasn't ordered, even though cPython and PyPy
maintained ordering.
.. change::
@@ -942,7 +932,7 @@
form of a some expressions when referring to the ``.c`` collection
on a ``select()`` construct, but the ``str()`` form isn't available
since the element relies on dialect-specific compilation constructs,
notably the ``__getitem__()`` operator as used with a Postgresql
notably the ``__getitem__()`` operator as used with a PostgreSQL
``ARRAY`` element. The fix also adds a new exception class
:exc:`.UnsupportedCompilationError` which is raised in those cases
where a compiler is asked to compile something it doesn't know
@@ -1069,7 +1059,7 @@
:versions: 0.9.0b1
The behavior of :func:`.extract` has been simplified on the
Postgresql dialect to no longer inject a hardcoded ``::timestamp``
PostgreSQL dialect to no longer inject a hardcoded ``::timestamp``
or similar cast into the given expression, as this interfered
with types such as timezone-aware datetimes, but also
does not appear to be at all necessary with modern versions
@@ -1103,7 +1093,7 @@
:versions: 0.9.0b1
Fixed bug where the order of columns in a multi-column
Postgresql index would be reflected in the wrong order.
PostgreSQL index would be reflected in the wrong order.
Courtesy Roman Podolyaka.
.. change::
@@ -1167,7 +1157,7 @@
:tags: feature, postgresql
:versions: 0.9.0b1
Support for Postgresql 9.2 range types has been added.
Support for PostgreSQL 9.2 range types has been added.
Currently, no type translation is provided, so works
directly with strings or psycopg2 2.5 range extension types
at the moment. Patch courtesy Chris Withers.
@@ -1202,7 +1192,6 @@
.. change::
:tags: bug, engine
:pullreq: github:6
:versions: 0.9.0b1
Fixed bug where the ``reset_on_return`` argument to various :class:`.Pool`
@@ -1334,7 +1323,6 @@
.. change::
:tags: bug, postgresql
:pullreq: github:2
:tickets: 2735
Fixed the HSTORE type to correctly encode/decode for unicode.
@@ -1463,7 +1451,7 @@
:tags: bug, postgresql
:tickets: 2681
The operators for the Postgresql ARRAY type supports
The operators for the PostgreSQL ARRAY type supports
input types of sets, generators, etc. even when
a dimension is not specified, by turning the given
iterable into a collection unconditionally.
@@ -1872,7 +1860,7 @@
is now copied in all cases when :meth:`.Table.tometadata` happens,
and if ``inherit_schema=True``, the type will take on the new
schema name passed to the method. The ``schema`` is important
when used with the Postgresql backend, as the type results in
when used with the PostgreSQL backend, as the type results in
a ``CREATE TYPE`` statement.
.. change::
@@ -1945,7 +1933,7 @@
custom collections using an ``__instrumentation__`` datastructure
associated with the collection has been removed, as this was a complex
and untested feature which was also essentially redundant versus the
decorator approach. Other internal simplifcations to the
decorator approach. Other internal simplifications to the
orm.collections module have been made as well.
.. change::
@@ -2153,7 +2141,7 @@
The :class:`.Insert` construct now supports multi-valued inserts,
that is, an INSERT that renders like
"INSERT INTO table VALUES (...), (...), ...".
Supported by Postgresql, SQLite, and MySQL.
Supported by PostgreSQL, SQLite, and MySQL.
Big thanks to Idan Kamara for doing the legwork on this one.
.. seealso::
@@ -2272,7 +2260,7 @@
:tags: postgresql, feature
:tickets: 2606
:class:`.HSTORE` is now available in the Postgresql dialect.
:class:`.HSTORE` is now available in the PostgreSQL dialect.
Will also use psycopg2's extensions if available. Courtesy
Audrius Kažukauskas.
@@ -2440,7 +2428,7 @@
:tickets: 2589
The Beaker caching example has been converted
to use `dogpile.cache <http://dogpilecache.readthedocs.org/>`_.
to use `dogpile.cache <https://dogpilecache.readthedocs.io/>`_.
This is a new caching library written by the same
creator of Beaker's caching internals, and represents a
vastly improved, simplified, and modernized system of caching.
@@ -2677,7 +2665,7 @@
UPDATE..FROM syntax as allowed by the dialect
to satisfy the WHERE clause. MySQL's multi-table
update feature is also supported if columns
are specified by object in the "values" dicitionary.
are specified by object in the "values" dictionary.
PG's DELETE..USING is also not available
in Core yet.
@@ -3189,17 +3177,17 @@
to augment bind- and result- behavior at the
SQL level, as opposed to in the Python level.
Allows for schemes like transparent encryption/
decryption, usage of Postgis functions, etc.
decryption, usage of PostGIS functions, etc.
.. change::
:tags: feature, sql
:tickets:
The Core oeprator system now includes
The Core operator system now includes
the `getitem` operator, i.e. the bracket
operator in Python. This is used at first
to provide index and slice behavior to the
Postgresql ARRAY type, and also provides a hook
PostgreSQL ARRAY type, and also provides a hook
for end-user definition of custom __getitem__
schemes which can be applied at the type
level as well as within ORM-level custom
@@ -3237,7 +3225,7 @@
String types. When present, renders as
COLLATE <collation>. This to support the
COLLATE keyword now supported by several
databases including MySQL, SQLite, and Postgresql.
databases including MySQL, SQLite, and PostgreSQL.
.. change::
:tags: change, sql
@@ -3603,7 +3591,7 @@
:tags: postgresql, feature
:tickets: 2506
Added support for the Postgresql ONLY
Added support for the PostgreSQL ONLY
keyword, which can appear corresponding to a
table in a SELECT, UPDATE, or DELETE statement.
The phrase is established using with_hint().
@@ -3614,7 +3602,7 @@
:tickets:
The "ischema_names" dictionary of the
Postgresql dialect is "unofficially" customizable.
PostgreSQL dialect is "unofficially" customizable.
Meaning, new types such as PostGIS types can
be added into this dictionary, and the PG type
reflection code should be able to handle simple
+47 -75
View File
@@ -1,7 +1,6 @@
==============
=============
0.9 Changelog
==============
=============
.. changelog_imports::
@@ -11,9 +10,20 @@
.. include:: changelog_07.rst
:start-line: 5
.. changelog::
.. _unreleased_changelog::
:version: 0.9.11
.. change::
:tags: bug, oracle, py3k
:tickets: 3491
:versions: 1.0.9
Fixed support for cx_Oracle version 5.2, which was tripping
up SQLAlchemy's version detection under Python 3 and inadvertently
not using the correct unicode mode for Python 3. This would cause
issues such as bound variables mis-interpreted as NULL and rows
silently not being returned.
.. change::
:tags: bug, engine
:tickets: 3497
@@ -145,7 +155,6 @@
.. change::
:tags: bug, py3k, mysql
:tickets: 3333
:pullreq: github:158
:versions: 1.0.0b2
Fixed the :class:`.mysql.BIT` type on Py3K which was not using the
@@ -180,10 +189,9 @@
.. change::
:tags: feature, postgresql
:pullreq: bitbucket:45
:versions: 1.0.0b1
Added support for the ``CONCURRENTLY`` keyword with Postgresql
Added support for the ``CONCURRENTLY`` keyword with PostgreSQL
indexes, established using ``postgresql_concurrently``. Pull
request courtesy Iuri de Silvio.
@@ -193,7 +201,6 @@
.. change::
:tags: bug, ext, py3k
:pullreq: github:154
:versions: 1.0.0b1
Fixed bug where the association proxy list class would not interpret
@@ -202,7 +209,6 @@
.. change::
:tags: feature, sqlite
:pullreq: bitbucket:42
:versions: 1.0.0b1
Added support for partial indexes (e.g. with a WHERE clause) on
@@ -238,7 +244,6 @@
.. change::
:tags: bug, orm
:pullreq: github:147
:versions: 1.0.0b1
Fixed bug where TypeError raised when :meth:`.Query.join` called
@@ -301,7 +306,7 @@
:tickets: 2940
:versions: 1.0.0b1
Repaired support for Postgresql UUID types in conjunction with
Repaired support for PostgreSQL UUID types in conjunction with
the ARRAY type when using psycopg2. The psycopg2 dialect now
employs use of the psycopg2.extras.register_uuid() hook
so that UUID values are always passed to/from the DBAPI as
@@ -311,7 +316,6 @@
.. change::
:tags: bug, postgresql
:pullreq: github:145
:versions: 1.0.0b1
Added support for the :class:`postgresql.JSONB` datatype when
@@ -320,7 +324,7 @@
additionally, the newly added psycopg2 extension
``extras.register_default_jsonb`` is used to establish a JSON
deserializer passed to the dialect via the ``json_deserializer``
argument. Also repaired the Postgresql integration tests which
argument. Also repaired the PostgreSQL integration tests which
weren't actually round-tripping the JSONB type as opposed to the
JSON type. Pull request courtesy Mateusz Susik.
@@ -363,7 +367,7 @@
:versions: 1.0.0b1
:tickets: 3174
Fixed bug where Postgresql dialect would fail to render an
Fixed bug where PostgreSQL dialect would fail to render an
expression in an :class:`.Index` that did not correspond directly
to a table-bound column; typically when a :func:`.text` construct
was one of the expressions within the index; or could misinterpret the
@@ -387,7 +391,6 @@
.. change::
:tags: bug, sql
:versions: 1.0.0b1
:pullreq: bitbucket:41
Added the ``native_enum`` flag to the ``__repr__()`` output
of :class:`.Enum`, which is mostly important when using it with
@@ -402,7 +405,7 @@
:class:`.Query` before it fetched results, particularly when
row processors can't be formed, the cursor would stay open with
results pending and not actually be closed. This is typically only
an issue on an interpreter like Pypy where the cursor isn't
an issue on an interpreter like PyPy where the cursor isn't
immediately GC'ed, and can in some circumstances lead to transactions/
locks being open longer than is desirable.
@@ -463,7 +466,7 @@
:tags: bug, examples
:versions: 1.0.0b1
Fixed a bug in the examples/generic_assocaitions/discriminator_on_association.py
Fixed a bug in the examples/generic_associations/discriminator_on_association.py
example, where the subclasses of AddressAssociation were not being
mapped as "single table inheritance", leading to problems when trying
to use the mappings further.
@@ -705,7 +708,6 @@
.. change::
:tags: bug, ext
:versions: 1.0.0b1
:pullrequest: bitbucket:28
Fixed bug where :class:`.ext.mutable.MutableDict`
failed to implement the ``update()`` dictionary method, thus
@@ -714,7 +716,6 @@
.. change::
:tags: bug, ext
:versions: 1.0.0b1
:pullrequest: bitbucket:27
Fixed bug where a custom subclass of :class:`.ext.mutable.MutableDict`
would not show up in a "coerce" operation, and would instead
@@ -735,7 +736,6 @@
.. change::
:tags: feature, postgresql, pg8000
:versions: 1.0.0b1
:pullreq: github:125
Support is added for "sane multi row count" with the pg8000 driver,
which applies mostly to when using versioning with the ORM.
@@ -759,7 +759,7 @@
:versions: 1.0.0b1
:tickets: 3159
Fixed bug where Postgresql JSON type was not able to persist or
Fixed bug where PostgreSQL JSON type was not able to persist or
otherwise render a SQL NULL column value, rather than a JSON-encoded
``'null'``. To support this case, changes are as follows:
@@ -768,7 +768,7 @@
* A new parameter :paramref:`.JSON.none_as_null` is added, which
when True indicates that the Python ``None`` value should be
peristed as SQL NULL, rather than JSON-encoded ``'null'``.
persisted as SQL NULL, rather than JSON-encoded ``'null'``.
Retrival of NULL as None is also repaired for DBAPIs other than
psycopg2, namely pg8000.
@@ -806,7 +806,6 @@
:tags: bug, postgresql
:versions: 1.0.0b1
:tickets: 3141
:pullreq: github:124
Fixed bug in :class:`.postgresql.array` object where comparison
to a plain Python list would fail to use the correct array constructor.
@@ -880,7 +879,7 @@
then force all :class:`.Boolean` and :class:`.Enum` types to
require names as well, as these implicitly create a
constraint, even if the ultimate target backend were one that does
not require generation of the constraint such as Postgresql.
not require generation of the constraint such as PostgreSQL.
The mechanics of naming conventions for these particular
constraints has been reorganized such that the naming
determination is done at DDL compile time, rather than at
@@ -966,7 +965,6 @@
.. change::
:tags: feature, postgresql
:versions: 1.0.0b1
:pullreq: bitbucket:22
:tickets: 3078
Added kw argument ``postgresql_regconfig`` to the
@@ -977,14 +975,12 @@
.. change::
:tags: feature, postgresql
:versions: 1.0.0b1
:pullreq: github:101
Added support for Postgresql JSONB via :class:`.JSONB`. Pull request
Added support for PostgreSQL JSONB via :class:`.JSONB`. Pull request
courtesy Damian Dimmich.
.. change::
:tags: feature, mssql
:pullreq: github:98
:versions: 1.0.0b1
Enabled "multivalues insert" for SQL Server 2008. Pull request
@@ -1037,7 +1033,7 @@
Fixed bug when the declarative ``__abstract__`` flag was not being
distinguished for when it was actually the value ``False``.
The ``__abstract__`` flag needs to acutally evaluate to a True
The ``__abstract__`` flag needs to actually evaluate to a True
value at the level being tested.
.. changelog::
@@ -1092,7 +1088,7 @@
:tickets: 3002
:versions: 1.0.0b1
Added a new type :class:`.postgresql.OID` to the Postgresql dialect.
Added a new type :class:`.postgresql.OID` to the PostgreSQL dialect.
While "oid" is generally a private type within PG that is not exposed
in modern versions, there are some PG use cases such as large object
support where these types might be exposed, as well as within some
@@ -1113,7 +1109,6 @@
.. change::
:tags: feature, examples
:pullreq: bitbucket:21
:versions: 1.0.0b1
Added a new example illustrating materialized paths, using the
@@ -1121,10 +1116,9 @@
.. change::
:tags: bug, testsuite
:pullreq: github:95
:versions: 1.0.0b1
In public test suite, shanged to use of ``String(40)`` from
In public test suite, changed to use of ``String(40)`` from
less-supported ``Text`` in ``StringTest.test_literal_backslashes``.
Pullreq courtesy Jan.
@@ -1145,7 +1139,6 @@
.. change::
:tags: feature, postgresql
:versions: 1.0.0b1
:pullreq: github:88
Added support for AUTOCOMMIT isolation level when using the pg8000
DBAPI. Pull request courtesy Tony Locke.
@@ -1154,7 +1147,6 @@
:tags: bug, postgresql
:tickets: 3021
:versions: 1.0.0b1
:pullreq: github:87
The psycopg2 ``.closed`` accessor is now consulted when determining
if an exception is a "disconnect" error; ideally, this should remove
@@ -1174,7 +1166,7 @@
in some cases a scalar attribute set to None, may not be detected
as a net change in value, and therefore the UPDATE would not reset
what was on the previous row. This is due to some as-yet
unresovled side effects of the way attribute history works in terms
unresolved side effects of the way attribute history works in terms
of implicitly assuming None isn't really a "change" for a previously
un-set attribute. See also :ticket:`3061`.
@@ -1217,14 +1209,13 @@
.. change::
:tags: feature, postgresql
:tickets: 2785
:pullreq: bitbucket:18
:versions: 1.0.0b1
Added a new flag :paramref:`.ARRAY.zero_indexes` to the Postgresql
Added a new flag :paramref:`.ARRAY.zero_indexes` to the PostgreSQL
:class:`.ARRAY` type. When set to ``True``, a value of one will be
added to all array index values before passing to the database, allowing
better interoperability between Python style zero-based indexes and
Postgresql one-based indexes. Pull request courtesy Alexey Terentev.
PostgreSQL one-based indexes. Pull request courtesy Alexey Terentev.
.. change::
:tags: bug, engine
@@ -1309,7 +1300,6 @@
.. change::
:tags: bug, py3k, tests
:tickets: 2830
:pullreq: bitbucket:2830
:versions: 1.0.0b1
Corrected for some deprecation warnings involving the ``imp``
@@ -1362,7 +1352,7 @@
Added new flag :paramref:`.expression.between.symmetric`, when set to True
renders "BETWEEN SYMMETRIC". Also added a new negation operator
"notbetween_op", which now allows an expression like ``~col.between(x, y)``
to render as "col NOT BETWEEN x AND y", rather than a parentheiszed NOT
to render as "col NOT BETWEEN x AND y", rather than a parenthesized NOT
string.
.. changelog::
@@ -1380,7 +1370,7 @@
(except when version_id is used) to support the unusual edge case of
self-referential ON DELETE CASCADE; to accommodate this, the message
is now just a warning, not an exception, and the flag can be used
to indicate a mapping that expects self-refererntial cascaded
to indicate a mapping that expects self-referential cascaded
deletes of this nature. See also :ticket:`2403` for background on the
original change.
@@ -1496,7 +1486,6 @@
.. change::
:tags: bug, sql
:tickets: 2988
:pullreq: github:78
Fixed an 0.9 regression where a :class:`.Table` that failed to
reflect correctly wouldn't be removed from the parent
@@ -1575,13 +1564,12 @@
.. change::
:tags: feature, oracle
:tickets: 2911
:pullreq: github:74
Added a new engine option ``coerce_to_unicode=True`` to the
cx_Oracle dialect, which restores the cx_Oracle outputtypehandler
approach to Python unicode conversion under Python 2, which was
removed in 0.9.2 as a result of :ticket:`2911`. Some use cases would
prefer that unicode coersion is unconditional for all string values,
prefer that unicode coercion is unconditional for all string values,
despite performance concerns. Pull request courtesy
Christoph Zwerschke.
@@ -1620,7 +1608,7 @@
with pytest.
The test plugin system has also been enhanced to support running
tests against mutiple database URLs at once, by specifying the ``--db``
tests against multiple database URLs at once, by specifying the ``--db``
and/or ``--dburi`` flags multiple times. This does not run the entire test
suite for each database, but instead allows test cases that are specific
to certain backends make use of that backend as the test is run.
@@ -1796,7 +1784,6 @@
.. change::
:tags: sqlite, bug
:pullreq: github:65
Support has been added to SQLite type reflection to fully support
the "type affinity" contract specified at http://www.sqlite.org/datatype3.html.
@@ -1810,14 +1797,12 @@
.. change::
:tags: postgresql, feature
:pullreq: github:64
Added the :attr:`.TypeEngine.python_type` convenience accessor onto the
:class:`.postgresql.ARRAY` type. Pull request courtesy Alexey Terentev.
.. change::
:tags: examples, feature
:pullreq: github:41
Added optional "changed" column to the versioned rows example, as well
as support for when the versioned :class:`.Table` has an explicit
@@ -1841,7 +1826,7 @@
fully usable within declarative relationship configuration, as its
string classname would not be available in the registry of classnames
at mapper configuration time. The class now explicitly adds itself
to the class regsitry, and additionally both :class:`.AbstractConcreteBase`
to the class registry, and additionally both :class:`.AbstractConcreteBase`
as well as :class:`.ConcreteBase` set themselves up *before* mappers
are configured within the :func:`.configure_mappers` setup, using
the new :meth:`.MapperEvents.before_configured` event.
@@ -1857,7 +1842,6 @@
.. change::
:tags: bug, mysql, cymysql
:tickets: 2934
:pullreq: github:69
Fixed bug in cymysql dialect where a version string such as
``'33a-MariaDB'`` would fail to parse properly. Pull request
@@ -1870,7 +1854,7 @@
Fixed an 0.9 regression where ORM instance or mapper events applied
to a base class such as a declarative base with the propagate=True
flag would fail to apply to existing mapped classes which also
used inheritance due to an assertion. Addtionally, repaired an
used inheritance due to an assertion. Additionally, repaired an
attribute error which could occur during removal of such an event,
depending on how it was first assigned.
@@ -1886,7 +1870,6 @@
.. change::
:tags: bug, sql
:pullreq: github:67
Fixed regression in new "naming convention" feature where conventions
would fail if the referred table in a foreign key contained a schema
@@ -1946,7 +1929,7 @@
Added a new dialect-level argument ``postgresql_ignore_search_path``;
this argument is accepted by both the :class:`.Table` constructor
as well as by the :meth:`.MetaData.reflect` method. When in use
against Postgresql, a foreign-key referenced table which specifies
against PostgreSQL, a foreign-key referenced table which specifies
a remote schema name will retain that schema name even if the name
is present in the ``search_path``; the default behavior since 0.7.3
has been that schemas present in ``search_path`` would not be copied
@@ -2036,7 +2019,6 @@
:ref:`relationship_custom_operator`
.. change::
:tags: bug, sqlite
@@ -2177,7 +2159,6 @@
.. change::
:tags: bug, sql
:pullreq: bitbucket:11
A :class:`.UniqueConstraint` created inline with a :class:`.Table`
that has no columns within it will be skipped. Pullreq courtesy
@@ -2185,7 +2166,6 @@
.. change::
:tags: feature, mssql
:pullreq: bitbucket:11
Added an option ``mssql_clustered`` to the :class:`.UniqueConstraint`
and :class:`.PrimaryKeyConstraint` constructs; on SQL Server, this adds
@@ -2312,7 +2292,7 @@
:tags: feature, pool, engine
Added a new pool event :meth:`.PoolEvents.invalidate`. Called when
a DBAPI connection is to be marked as "invaldated" and discarded
a DBAPI connection is to be marked as "invalidated" and discarded
from the pool.
.. change::
@@ -2327,7 +2307,6 @@
.. change::
:tags: bug, py3k, cextensions
:pullreq: github:55
Fixed an issue where the C extensions in Py3K are using the wrong API
to specify the top-level module function, which breaks
@@ -2338,7 +2317,6 @@
.. change::
:tags: bug, schema
:pullreq: github:57
Restored :class:`sqlalchemy.schema.SchemaVisitor` to the ``.schema``
module. Pullreq courtesy Sean Dague.
@@ -2407,7 +2385,6 @@
.. change::
:tags: bug, orm
:pullreq: bitbucket:9
Fixed bug where using new :attr:`.Session.info` attribute would fail
if the ``.info`` argument were only passed to the :class:`.sessionmaker`
@@ -2487,9 +2464,8 @@
.. change::
:tags: feature, postgresql
:tickets: 2581
:pullreq: github:50
Support for Postgresql JSON has been added, using the new
Support for PostgreSQL JSON has been added, using the new
:class:`.JSON` type. Huge thanks to Nathan Rice for
implementing and testing this.
@@ -2537,9 +2513,8 @@
.. change::
:tags: feature, postgresql
:pullreq: bitbucket:8
Added support for Postgresql TSVECTOR via the
Added support for PostgreSQL TSVECTOR via the
:class:`.postgresql.TSVECTOR` type. Pull request courtesy
Noufal Ibrahim.
@@ -2598,7 +2573,6 @@
.. change::
:tags: bug, orm, collections, py3k
:pullreq: github:40
Added support for the Python 3 method ``list.clear()`` within
the ORM collection instrumentation system; pull request
@@ -2641,7 +2615,6 @@
.. change::
:tags: feature, sql
:pullreq: github:42
A new API for specifying the ``FOR UPDATE`` clause of a ``SELECT``
is added with the new :meth:`.GenerativeSelect.with_for_update` method.
@@ -2658,7 +2631,6 @@
.. change::
:tags: feature, orm
:pullreq: github:42
A new API for specifying the ``FOR UPDATE`` clause of a ``SELECT``
is added with the new :meth:`.Query.with_for_update` method,
@@ -2676,7 +2648,7 @@
The :func:`.create_engine` routine and the related
:func:`.make_url` function no longer considers the ``+`` sign
to be a space within the password field. The parsing has been
adjuted to match RFC 1738 exactly, in that both ``username``
adjusted to match RFC 1738 exactly, in that both ``username``
and ``password`` expect only ``:``, ``@``, and ``/`` to be
encoded.
@@ -2695,7 +2667,7 @@
adaptation which goes on has been made more robust, such that if a descriptor
returns another instrumented attribute, rather than a compound SQL
expression element, the operation will still proceed.
Addtionally, the "adapted" operator will retain its class; previously,
Additionally, the "adapted" operator will retain its class; previously,
a change in class from ``InstrumentedAttribute`` to ``QueryableAttribute``
(a superclass) would interact with Python's operator system such that
an expression like ``aliased(MyClass.x) > MyClass.x`` would reverse itself
@@ -2814,9 +2786,9 @@
:tags: feature, sql, postgresql, mysql
:tickets: 2183
The Postgresql and MySQL dialects now support reflection/inspection
of foreign key options, including ON UPDATE, ON DELETE. Postgresql
also reflects MATCH, DEFERRABLE, and INITIALLY. Coutesy ijl.
The PostgreSQL and MySQL dialects now support reflection/inspection
of foreign key options, including ON UPDATE, ON DELETE. PostgreSQL
also reflects MATCH, DEFERRABLE, and INITIALLY. Courtesy ijl.
.. change::
:tags: bug, mysql
@@ -2925,7 +2897,7 @@
Added support for rendering ``SMALLSERIAL`` when a :class:`.SmallInteger`
type is used on a primary key autoincrement column, based on server
version detection of Postgresql version 9.2 or greater.
version detection of PostgreSQL version 9.2 or greater.
.. change::
:tags: feature, mysql
@@ -3058,7 +3030,7 @@
to rely upon server generated version identifiers, using triggers
or other database-provided versioning features, or via an optional programmatic
value, by setting ``version_id_generator=False``.
When using a server-generated version identfier, the ORM will use RETURNING when
When using a server-generated version identifier, the ORM will use RETURNING when
available to immediately
load the new version value, else it will emit a second SELECT.
+978 -56
View File
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+950
View File
@@ -0,0 +1,950 @@
=============
1.3 Changelog
=============
.. changelog_imports::
.. include:: changelog_12.rst
:start-line: 5
.. include:: changelog_11.rst
:start-line: 5
.. changelog::
:version: 1.3.2
:include_notes_from: unreleased_13
.. changelog::
:version: 1.3.1
:released: March 9, 2019
.. change::
:tags: bug, mssql
:tickets: 4525
Fixed regression in SQL Server reflection due to :ticket:`4393` where the
removal of open-ended ``**kw`` from the :class:`.Float` datatype caused
reflection of this type to fail due to a "scale" argument being passed.
.. change::
:tags: bug, orm, ext
:tickets: 4522
Fixed regression where an association proxy linked to a synonym would no
longer work, both at instance level and at class level.
.. changelog::
:version: 1.3.0
:released: March 4, 2019
.. change::
:tags: feature, schema
:tickets: 4517
Added new parameters :paramref:`.Table.resolve_fks` and
:paramref:`.MetaData.reflect.resolve_fks` which when set to False will
disable the automatic reflection of related tables encountered in
:class:`.ForeignKey` objects, which can both reduce SQL overhead for omitted
tables as well as avoid tables that can't be reflected for database-specific
reasons. Two :class:`.Table` objects present in the same :class:`.MetaData`
collection can still refer to each other even if the reflection of the two
tables occurred separately.
.. change::
:tags: feature, orm
:tickets: 4316
The :meth:`.Query.get` method can now accept a dictionary of attribute keys
and values as a means of indicating the primary key value to load; is
particularly useful for composite primary keys. Pull request courtesy
Sanjana S.
.. change::
:tags: feature, orm
:tickets: 3133
A SQL expression can now be assigned to a primary key attribute for an ORM
flush in the same manner as ordinary attributes as described in
:ref:`flush_embedded_sql_expressions` where the expression will be evaulated
and then returned to the ORM using RETURNING, or in the case of pysqlite,
works using the cursor.lastrowid attribute.Requires either a database that
supports RETURNING (e.g. Postgresql, Oracle, SQL Server) or pysqlite.
.. change::
:tags: bug, sql
:tickets: 4509
The :class:`.Alias` class and related subclasses :class:`.CTE`,
:class:`.Lateral` and :class:`.TableSample` have been reworked so that it is
not possible for a user to construct the objects directly. These constructs
require that the standalone construction function or selectable-bound method
be used to instantiate new objects.
.. change::
:tags: feature, engine
:tickets: 4500
Revised the formatting for :class:`.StatementError` when stringified. Each
error detail is broken up over multiple newlines instead of spaced out on a
single line. Additionally, the SQL representation now stringifies the SQL
statement rather than using ``repr()``, so that newlines are rendered as is.
Pull request courtesy Nate Clark.
.. seealso::
:ref:`change_4500`
.. changelog::
:version: 1.3.0b3
:released: March 4, 2019
:released: February 8, 2019
.. change::
:tags: bug, ext
:tickets: 2642
Implemented a more comprehensive assignment operation (e.g. "bulk replace")
when using association proxy with sets or dictionaries. Fixes the problem
of redundant proxy objects being created to replace the old ones, which
leads to excessive events and SQL and in the case of unique constraints
will cause the flush to fail.
.. seealso::
:ref:`change_2642`
.. change::
:tags: bug, postgresql
:tickets: 4473
Fixed issue where using an uppercase name for an index type (e.g. GIST,
BTREE, etc. ) or an EXCLUDE constraint would treat it as an identifier to
be quoted, rather than rendering it as is. The new behavior converts these
types to lowercase and ensures they contain only valid SQL characters.
.. change::
:tags: bug, orm
:tickets: 4469
Improved the behavior of :func:`.orm.with_polymorphic` in conjunction with
loader options, in particular wildcard operations as well as
:func:`.orm.load_only`. The polymorphic object will be more accurately
targeted so that column-level options on the entity will correctly take
effect.The issue is a continuation of the same kinds of things fixed in
:ticket:`4468`.
.. change::
:tags: bug, sql
:tickets: 4481
Fully removed the behavior of strings passed directly as components of a
:func:`.select` or :class:`.Query` object being coerced to :func:`.text`
constructs automatically; the warning that has been emitted is now an
ArgumentError or in the case of order_by() / group_by() a CompileError.
This has emitted a warning since version 1.0 however its presence continues
to create concerns for the potential of mis-use of this behavior.
Note that public CVEs have been posted for order_by() / group_by() which
are resolved by this commit: CVE-2019-7164 CVE-2019-7548
.. seealso::
:ref:`change_4481`
.. change::
:tags: bug, sql
:tickets: 4467
Quoting is applied to :class:`.Function` names, those which are usually but
not necessarily generated from the :attr:`.sql.func` construct, at compile
time if they contain illegal characters, such as spaces or punctuation. The
names are as before treated as case insensitive however, meaning if the
names contain uppercase or mixed case characters, that alone does not
trigger quoting. The case insensitivity is currently maintained for
backwards compatibility.
.. change::
:tags: bug, sql
:tickets: 4481
Added "SQL phrase validation" to key DDL phrases that are accepted as plain
strings, including :paramref:`.ForeignKeyConstraint.on_delete`,
:paramref:`.ForeignKeyConstraint.on_update`,
:paramref:`.ExcludeConstraint.using`,
:paramref:`.ForeignKeyConstraint.initially`, for areas where a series of SQL
keywords only are expected.Any non-space characters that suggest the phrase
would need to be quoted will raise a :class:`.CompileError`. This change
is related to the series of changes committed as part of :ticket:`4481`.
.. change::
:tags: bug, orm, declarative
:tickets: 4470
Added some helper exceptions that invoke when a mapping based on
:class:`.AbstractConcreteBase`, :class:`.DeferredReflection`, or
:class:`.AutoMap` is used before the mapping is ready to be used, which
contain descriptive information on the class, rather than falling through
into other failure modes that are less informative.
.. change::
:tags: change, tests
:tickets: 4460
The test system has removed support for Nose, which is unmaintained for
several years and is producing warnings under Python 3. The test suite is
currently standardized on Pytest. Pull request courtesy Parth Shandilya.
.. changelog::
:version: 1.3.0b2
:released: March 4, 2019
:released: January 25, 2019
.. change::
:tags: bug, ext
:tickets: 4401
Fixed a regression in 1.3.0b1 caused by :ticket:`3423` where association
proxy objects that access an attribute that's only present on a polymorphic
subclass would raise an ``AttributeError`` even though the actual instance
being accessed was an instance of that subclass.
.. change::
:tags: bug, orm
:tickets: 1103
Fixed long-standing issue where duplicate collection members would cause a
backref to delete the association between the member and its parent object
when one of the duplicates were removed, as occurs as a side effect of
swapping two objects in one statement.
.. seealso::
:ref:`change_1103`
.. change::
:tags: bug, mssql
:tickets: 4442
The ``literal_processor`` for the :class:`.Unicode` and
:class:`.UnicodeText` datatypes now render an ``N`` character in front of
the literal string expression as required by SQL Server for Unicode string
values rendered in SQL expressions.
.. change::
:tags: feature, orm
:tickets: 4423
Implemented a new feature whereby the :class:`.AliasedClass` construct can
now be used as the target of a :func:`.relationship`. This allows the
concept of "non primary mappers" to no longer be necessary, as the
:class:`.AliasedClass` is much easier to configure and automatically inherits
all the relationships of the mapped class, as well as preserves the
ability for loader options to work normally.
.. seealso::
:ref:`change_4423`
.. change::
:tags: bug, orm
:tickets: 4373
Extended the fix first made as part of :ticket:`3287`, where a loader option
made against a subclass using a wildcard would extend itself to include
application of the wildcard to attributes on the super classes as well, to a
"bound" loader option as well, e.g. in an expression like
``Load(SomeSubClass).load_only('foo')``. Columns that are part of the
parent class of ``SomeSubClass`` will also be excluded in the same way as if
the unbound option ``load_only('foo')`` were used.
.. change::
:tags: bug, orm
:tickets: 4433
Improved error messages emitted by the ORM in the area of loader option
traversal. This includes early detection of mis-matched loader strategies
along with a clearer explanation why these strategies don't match.
.. change::
:tags: change, orm
:tickets: 4412
Added a new function :func:`.close_all_sessions` which takes
over the task of the :meth:`.Session.close_all` method, which
is now deprecated as this is confusing as a classmethod.
Pull request courtesy Augustin Trancart.
.. change::
:tags: feature, orm
:tickets: 4397
Added new :meth:`.MapperEvents.before_mapper_configured` event. This
event complements the other "configure" stage mapper events with a per
mapper event that receives each :class:`.Mapper` right before its
configure step, and additionally may be used to prevent or delay the
configuration of specific :class:`.Mapper` objects using a new
return value :attr:`.orm.interfaces.EXT_SKIP`. See the
documentation link for an example.
.. seealso::
:meth:`.MapperEvents.before_mapper_configured`
.. change::
:tags: bug, orm
The "remove" event for collections is now called before the item is removed
in the case of the ``collection.remove()`` method, as is consistent with the
behavior for most other forms of collection item removal (such as
``__delitem__``, replacement under ``__setitem__``). For ``pop()`` methods,
the remove event still fires after the operation.
.. change::
:tags: bug, orm declarative
:tickets: 4372
Added a ``__clause_element__()`` method to :class:`.ColumnProperty` which
can allow the usage of a not-fully-declared column or deferred attribute in
a declarative mapped class slightly more friendly when it's used in a
constraint or other column-oriented scenario within the class declaration,
though this still can't work in open-ended expressions; prefer to call the
:attr:`.ColumnProperty.expression` attribute if receiving ``TypeError``.
.. change::
:tags: bug, orm, engine
:tickets: 4464
Added accessors for execution options to Core and ORM, via
:meth:`.Query.get_execution_options`,
:meth:`.Connection.get_execution_options`,
:meth:`.Engine.get_execution_options`, and
:meth:`.Executable.get_execution_options`. PR courtesy Daniel Lister.
.. change::
:tags: bug, orm
:tickets: 4446
Fixed issue in association proxy due to :ticket:`3423` which caused the use
of custom :class:`.PropComparator` objects with hybrid attribites, such as
the one demonstrated in the ``dictlike-polymorphic`` example to not
function within an association proxy. The strictness that was added in
:ticket:`3423` has been relaxed, and additional logic to accomodate for
an association proxy that links to a custom hybrid have been added.
.. change::
:tags: change, general
:tickets: 4393
A large change throughout the library has ensured that all objects,
parameters, and behaviors which have been noted as deprecated or legacy now
emit ``DeprecationWarning`` warnings when invoked.As the Python 3
interpreter now defaults to displaying deprecation warnings, as well as that
modern test suites based on tools like tox and pytest tend to display
deprecation warnings, this change should make it easier to note what API
features are obsolete. A major rationale for this change is so that long-
deprecated features that nonetheless still see continue to see real world
use can finally be removed in the near future; the biggest example of this
are the :class:`.SessionExtension` and :class:`.MapperExtension` classes as
well as a handful of other pre-event extension hooks, which have been
deprecated since version 0.7 but still remain in the library. Another is
that several major longstanding behaviors are to be deprecated as well,
including the threadlocal engine strategy, the convert_unicode flag, and non
primary mappers.
.. seealso::
:ref:`change_4393_general`
.. change::
:tags: change, engine
:tickets: 4393
The "threadlocal" engine strategy which has been a legacy feature of
SQLAlchemy since around version 0.2 is now deprecated, along with the
:paramref:`.Pool.threadlocal` parameter of :class:`.Pool` which has no
effect in most modern use cases.
.. seealso::
:ref:`change_4393_threadlocal`
.. change::
:tags: change, sql
:tickets: 4393
The :paramref:`.create_engine.convert_unicode` and
:paramref:`.String.convert_unicode` parameters have been deprecated. These
parameters were built back when most Python DBAPIs had little to no support
for Python Unicode objects, and SQLAlchemy needed to take on the very
complex task of marshalling data and SQL strings between Unicode and
bytestrings throughout the system in a performant way. Thanks to Python 3,
DBAPIs were compelled to adapt to Unicode-aware APIs and today all DBAPIs
supported by SQLAlchemy support Unicode natively, including on Python 2,
allowing this long-lived and very complicated feature to finally be (mostly)
removed. There are still of course a few Python 2 edge cases where
SQLAlchemy has to deal with Unicode however these are handled automatically;
in modern use, there should be no need for end-user interaction with these
flags.
.. seealso::
:ref:`change_4393_convertunicode`
.. change::
:tags: bug, orm
:tickets: 3777
Implemented the ``.get_history()`` method, which also implies availability
of :attr:`.AttributeState.history`, for :func:`.synonym` attributes.
Previously, trying to access attribute history via a synonym would raise an
``AttributeError``.
.. change::
:tags: feature, engine
:tickets: 3689
Added public accessor :meth:`.QueuePool.timeout` that returns the configured
timeout for a :class:`.QueuePool` object. Pull request courtesy Irina Delamare.
.. change::
:tags: feature, sql
:tickets: 4386
Amended the :class:`.AnsiFunction` class, the base of common SQL
functions like ``CURRENT_TIMESTAMP``, to accept positional arguments
like a regular ad-hoc function. This to suit the case that many of
these functions on specific backends accept arguments such as
"fractional seconds" precision and such. If the function is created
with arguments, it renders the parenthesis and the arguments. If
no arguments are present, the compiler generates the non-parenthesized form.
.. changelog::
:version: 1.3.0b1
:released: March 4, 2019
:released: November 16, 2018
.. change::
:tags: bug, ext
:tickets: 3423
Reworked :class:`.AssociationProxy` to store state that's specific to a
parent class in a separate object, so that a single
:class:`.AssocationProxy` can serve for multiple parent classes, as is
intrinsic to inheritance, without any ambiguity in the state returned by it.
A new method :meth:`.AssociationProxy.for_class` is added to allow
inspection of class-specific state.
.. seealso::
:ref:`change_3423`
.. change::
:tags: bug, oracle
:tickets: 4369
Updated the parameters that can be sent to the cx_Oracle DBAPI to both allow
for all current parameters as well as for future parameters not added yet.
In addition, removed unused parameters that were deprecated in version 1.2,
and additionally we are now defaulting "threaded" to False.
.. seealso::
:ref:`change_4369`
.. change::
:tags: bug, oracle
:tickets: 4242
The Oracle dialect will no longer use the NCHAR/NCLOB datatypes
represent generic unicode strings or clob fields in conjunction with
:class:`.Unicode` and :class:`.UnicodeText` unless the flag
``use_nchar_for_unicode=True`` is passed to :func:`.create_engine` -
this includes CREATE TABLE behavior as well as ``setinputsizes()`` for
bound parameters. On the read side, automatic Unicode conversion under
Python 2 has been added to CHAR/VARCHAR/CLOB result rows, to match the
behavior of cx_Oracle under Python 3. In order to mitigate the performance
hit under Python 2, SQLAlchemy's very performant (when C extensions
are built) native Unicode handlers are used under Python 2.
.. seealso::
:ref:`change_4242`
.. change::
:tags: bug, orm
:tickets: 3844
Fixed issue regarding passive_deletes="all", where the foreign key
attribute of an object is maintained with its value even after the object
is removed from its parent collection. Previously, the unit of work would
set this to NULL even though passive_deletes indicated it should not be
modified.
.. seealso::
:ref:`change_3844`
.. change::
:tags: bug, ext
:tickets: 4268
The long-standing behavior of the association proxy collection maintaining
only a weak reference to the parent object is reverted; the proxy will now
maintain a strong reference to the parent for as long as the proxy
collection itself is also in memory, eliminating the "stale association
proxy" error. This change is being made on an experimental basis to see if
any use cases arise where it causes side effects.
.. seealso::
:ref:`change_4268`
.. change::
:tags: bug, sql
:tickets: 4302
Added "like" based operators as "comparison" operators, including
:meth:`.ColumnOperators.startswith` :meth:`.ColumnOperators.endswith`
:meth:`.ColumnOperators.ilike` :meth:`.ColumnOperators.notilike` among many
others, so that all of these operators can be the basis for an ORM
"primaryjoin" condition.
.. change::
:tags: feature, sqlite
:tickets: 3850
Added support for SQLite's json functionality via the new
SQLite implementation for :class:`.types.JSON`, :class:`.sqlite.JSON`.
The name used for the type is ``JSON``, following an example found at
SQLite's own documentation. Pull request courtesy Ilja Everilä.
.. seealso::
:ref:`change_3850`
.. change::
:tags: feature, engine
Added new "lifo" mode to :class:`.QueuePool`, typically enabled by setting
the flag :paramref:`.create_engine.pool_use_lifo` to True. "lifo" mode
means the same connection just checked in will be the first to be checked
out again, allowing excess connections to be cleaned up from the server
side during periods of the pool being only partially utilized. Pull request
courtesy Taem Park.
.. seealso::
:ref:`change_pr467`
.. change::
:tags: bug, orm
:tickets: 4359
Improved the behavior of a relationship-bound many-to-one object expression
such that the retrieval of column values on the related object are now
resilient against the object being detached from its parent
:class:`.Session`, even if the attribute has been expired. New features
within the :class:`.InstanceState` are used to memoize the last known value
of a particular column attribute before its expired, so that the expression
can still evaluate when the object is detached and expired at the same
time. Error conditions are also improved using modern attribute state
features to produce more specific messages as needed.
.. seealso::
:ref:`change_4359`
.. change::
:tags: feature, mysql
:tickets: 4219
Support added for the "WITH PARSER" syntax of CREATE FULLTEXT INDEX
in MySQL, using the ``mysql_with_parser`` keyword argument. Reflection
is also supported, which accommodates MySQL's special comment format
for reporting on this option as well. Additionally, the "FULLTEXT" and
"SPATIAL" index prefixes are now reflected back into the ``mysql_prefix``
index option.
.. change::
:tags: bug, orm, mysql, postgresql
:tickets: 4246
The ORM now doubles the "FOR UPDATE" clause within the subquery that
renders in conjunction with joined eager loading in some cases, as it has
been observed that MySQL does not lock the rows from a subquery. This
means the query renders with two FOR UPDATE clauses; note that on some
backends such as Oracle, FOR UPDATE clauses on subqueries are silently
ignored since they are unnecessary. Additionally, in the case of the "OF"
clause used primarily with PostgreSQL, the FOR UPDATE is rendered only on
the inner subquery when this is used so that the selectable can be targeted
to the table within the SELECT statement.
.. seealso::
:ref:`change_4246`
.. change::
:tags: feature, mssql
:tickets: 4158
Added ``fast_executemany=True`` parameter to the SQL Server pyodbc dialect,
which enables use of pyodbc's new performance feature of the same name
when using Microsoft ODBC drivers.
.. seealso::
:ref:`change_4158`
.. change::
:tags: bug, ext
:tickets: 4308
Fixed multiple issues regarding de-association of scalar objects with the
association proxy. ``del`` now works, and additionally a new flag
:paramref:`.AssociationProxy.cascade_scalar_deletes` is added, which when
set to True indicates that setting a scalar attribute to ``None`` or
deleting via ``del`` will also set the source association to ``None``.
.. seealso::
:ref:`change_4308`
.. change::
:tags: feature, ext
:tickets: 4318
Added new feature :meth:`.BakedQuery.to_query`, which allows for a
clean way of using one :class:`.BakedQuery` as a subquery inside of another
:class:`.BakedQuery` without needing to refer explicitly to a
:class:`.Session`.
.. change::
:tags: feature, sqlite
:tickets: 4360
Implemented the SQLite ``ON CONFLICT`` clause as understood at the DDL
level, e.g. for primary key, unique, and CHECK constraints as well as
specified on a :class:`.Column` to satisfy inline primary key and NOT NULL.
Pull request courtesy Denis Kataev.
.. seealso::
:ref:`change_4360`
.. change::
:tags: feature, postgresql
:tickets: 4237
Added rudimental support for reflection of PostgreSQL
partitioned tables, e.g. that relkind='p' is added to reflection
queries that return table information.
.. seealso::
:ref:`change_4237`
.. change::
:tags: feature, ext
:tickets: 4351
The :class:`.AssociationProxy` now has standard column comparison operations
such as :meth:`.ColumnOperators.like` and
:meth:`.ColumnOperators.startswith` available when the target attribute is a
plain column - the EXISTS expression that joins to the target table is
rendered as usual, but the column expression is then use within the WHERE
criteria of the EXISTS. Note that this alters the behavior of the
``.contains()`` method on the association proxy to make use of
:meth:`.ColumnOperators.contains` when used on a column-based attribute.
.. seealso::
:ref:`change_4351`
.. change::
:tags: feature, orm
Added new flag :paramref:`.Session.bulk_save_objects.preserve_order` to the
:meth:`.Session.bulk_save_objects` method, which defaults to True. When set
to False, the given mappings will be grouped into inserts and updates per
each object type, to allow for greater opportunities to batch common
operations together. Pull request courtesy Alessandro Cucci.
.. change::
:tags: bug, orm
:tickets: 4365
Refactored :meth:`.Query.join` to further clarify the individual components
of structuring the join. This refactor adds the ability for
:meth:`.Query.join` to determine the most appropriate "left" side of the
join when there is more than one element in the FROM list or the query is
against multiple entities. If more than one FROM/entity matches, an error
is raised that asks for an ON clause to be specified to resolve the
ambiguity. In particular this targets the regression we saw in
:ticket:`4363` but is also of general use. The codepaths within
:meth:`.Query.join` are now easier to follow and the error cases are
decided more specifically at an earlier point in the operation.
.. seealso::
:ref:`change_4365`
.. change::
:tags: bug, sql
:tickets: 3981
Fixed issue with :meth:`.TypeEngine.bind_expression` and
:meth:`.TypeEngine.column_expression` methods where these methods would not
work if the target type were part of a :class:`.Variant`, or other target
type of a :class:`.TypeDecorator`. Additionally, the SQL compiler now
calls upon the dialect-level implementation when it renders these methods
so that dialects can now provide for SQL-level processing for built-in
types.
.. seealso::
:ref:`change_3981`
.. change::
:tags: bug, orm
:tickets: 4304
Fixed long-standing issue in :class:`.Query` where a scalar subquery such
as produced by :meth:`.Query.exists`, :meth:`.Query.as_scalar` and other
derivations from :attr:`.Query.statement` would not correctly be adapted
when used in a new :class:`.Query` that required entity adaptation, such as
when the query were turned into a union, or a from_self(), etc. The change
removes the "no adaptation" annotation from the :func:`.select` object
produced by the :attr:`.Query.statement` accessor.
.. change::
:tags: bug, orm, declarative
:tickets: 4133
Fixed bug where declarative would not update the state of the
:class:`.Mapper` as far as what attributes were present, when additional
attributes were added or removed after the mapper attribute collections had
already been called and memoized. Addtionally, a ``NotImplementedError``
is now raised if a fully mapped attribute (e.g. column, relationship, etc.)
is deleted from a class that is currently mapped, since the mapper will not
function correctly if the attribute has been removed.
.. change::
:tags: bug, mssql
:tickets: 4362
Deprecated the use of :class:`.Sequence` with SQL Server in order to affect
the "start" and "increment" of the IDENTITY value, in favor of new
parameters ``mssql_identity_start`` and ``mssql_identity_increment`` which
set these parameters directly. :class:`.Sequence` will be used to generate
real ``CREATE SEQUENCE`` DDL with SQL Server in a future release.
.. seealso::
:ref:`change_4362`
.. change::
:tags: feature, mysql
Added support for the parameters in an ON DUPLICATE KEY UPDATE statement on
MySQL to be ordered, since parameter order in a MySQL UPDATE clause is
significant, in a similar manner as that described at
:ref:`updates_order_parameters`. Pull request courtesy Maxim Bublis.
.. seealso::
:ref:`change_mysql_ondupordering`
.. change::
:tags: feature, sql
:tickets: 4144
Added :class:`.Sequence` to the "string SQL" system that will render a
meaningful string expression (``"<next sequence value: my_sequence>"``)
when stringifying without a dialect a statement that includes a "sequence
nextvalue" expression, rather than raising a compilation error.
.. change::
:tags: bug, orm
:tickets: 4232
An informative exception is re-raised when a primary key value is not
sortable in Python during an ORM flush under Python 3, such as an ``Enum``
that has no ``__lt__()`` method; normally Python 3 raises a ``TypeError``
in this case. The flush process sorts persistent objects by primary key
in Python so the values must be sortable.
.. change::
:tags: orm, bug
:tickets: 3604
Removed the collection converter used by the :class:`.MappedCollection`
class. This converter was used only to assert that the incoming dictionary
keys matched that of their corresponding objects, and only during a bulk set
operation. The converter can interfere with a custom validator or
:meth:`.AttributeEvents.bulk_replace` listener that wants to convert
incoming values further. The ``TypeError`` which would be raised by this
converter when an incoming key didn't match the value is removed; incoming
values during a bulk assignment will be keyed to their value-generated key,
and not the key that's explicitly present in the dictionary.
Overall, @converter is superseded by the
:meth:`.AttributeEvents.bulk_replace` event handler added as part of
:ticket:`3896`.
.. change::
:tags: feature, sql
:tickets: 3989
Added new naming convention tokens ``column_0N_name``, ``column_0_N_name``,
etc., which will render the names / keys / labels for all columns referenced
by a particular constraint in a sequence. In order to accommodate for the
length of such a naming convention, the SQL compiler's auto-truncation
feature now applies itself to constraint names as well, which creates a
shortened, deterministically generated name for the constraint that will
apply to a target backend without going over the character limit of that
backend.
The change also repairs two other issues. One is that the ``column_0_key``
token wasn't available even though this token was documented, the other was
that the ``referred_column_0_name`` token would inadvertently render the
``.key`` and not the ``.name`` of the column if these two values were
different.
.. seealso::
:ref:`change_3989`
.. change::
:tags: feature, ext
:tickets: 4196
Added support for bulk :meth:`.Query.update` and :meth:`.Query.delete`
to the :class:`.ShardedQuery` class within the horizontal sharding
extension. This also adds an additional expansion hook to the
bulk update/delete methods :meth:`.Query._execute_crud`.
.. seealso::
:ref:`change_4196`
.. change::
:tags: feature, sql
:tickets: 4271
Added new logic to the "expanding IN" bound parameter feature whereby if
the given list is empty, a special "empty set" expression that is specific
to different backends is generated, thus allowing IN expressions to be
fully dynamic including empty IN expressions.
.. seealso::
:ref:`change_4271`
.. change::
:tags: feature, mysql
The "pre-ping" feature of the connection pool now uses
the ``ping()`` method of the DBAPI connection in the case of
mysqlclient, PyMySQL and mysql-connector-python. Pull request
courtesy Maxim Bublis.
.. seealso::
:ref:`change_mysql_ping`
.. change::
:tags: feature, orm
:tickets: 4340
The "selectin" loader strategy now omits the JOIN in the case of a simple
one-to-many load, where it instead relies loads only from the related
table, relying upon the foreign key columns of the related table in order
to match up to primary keys in the parent table. This optimization can be
disabled by setting the :paramref:`.relationship.omit_join` flag to False.
Many thanks to Jayson Reis for the efforts on this.
.. seealso::
:ref:`change_4340`
.. change::
:tags: bug, orm
:tickets: 4353
Added new behavior to the lazy load that takes place when the "old" value of
a many-to-one is retrieved, such that exceptions which would be raised due
to either ``lazy="raise"`` or a detached session error are skipped.
.. seealso::
:ref:`change_4353`
.. change::
:tags: feature, sql
The Python builtin ``dir()`` is now supported for a SQLAlchemy "properties"
object, such as that of a Core columns collection (e.g. ``.c``),
``mapper.attrs``, etc. Allows iPython autocompletion to work as well.
Pull request courtesy Uwe Korn.
.. change::
:tags: feature, orm
:tickets: 4257
Added ``.info`` dictionary to the :class:`.InstanceState` class, the object
that comes from calling :func:`.inspect` on a mapped object.
.. seealso::
:ref:`change_4257`
.. change::
:tags: feature, sql
:tickets: 3831
Added new feature :meth:`.FunctionElement.as_comparison` which allows a SQL
function to act as a binary comparison operation that can work within the
ORM.
.. seealso::
:ref:`change_3831`
.. change::
:tags: bug, orm
:tickets: 4354
A long-standing oversight in the ORM, the ``__delete__`` method for a many-
to-one relationship was non-functional, e.g. for an operation such as ``del
a.b``. This is now implemented and is equivalent to setting the attribute
to ``None``.
.. seealso::
:ref:`change_4354`
+8 -2
View File
@@ -7,12 +7,12 @@ SQLAlchemy changelogs and migration guides are now integrated
within the main documentation.
Current Migration Guide
------------------------
-----------------------
.. toctree::
:titlesonly:
migration_10
migration_13
Change logs
-----------
@@ -20,6 +20,9 @@ Change logs
.. toctree::
:titlesonly:
changelog_13
changelog_12
changelog_11
changelog_10
changelog_09
changelog_08
@@ -38,6 +41,9 @@ Older Migration Guides
.. toctree::
:titlesonly:
migration_12
migration_11
migration_10
migration_09
migration_08
migration_07
+5 -7
View File
@@ -412,7 +412,7 @@ flush before each query.
foo.bars.append(Bar(name='lala'))
for bar in foo.bars.filter(Bar.name=='lala'):
print bar
print(bar)
session.commit()
@@ -672,16 +672,14 @@ Nested Session Transactions with SAVEPOINT
Available at the Engine and ORM level. ORM docs so far:
http://www.sqlalchemy.org/docs/04/session.html#unitofwork_ma
naging
http://www.sqlalchemy.org/docs/04/session.html#unitofwork_managing
Two-Phase Commit Sessions
^^^^^^^^^^^^^^^^^^^^^^^^^
Available at the Engine and ORM level. ORM docs so far:
http://www.sqlalchemy.org/docs/04/session.html#unitofwork_ma
naging
http://www.sqlalchemy.org/docs/04/session.html#unitofwork_managing
Inheritance
-----------
@@ -737,8 +735,8 @@ New Operator System
SQL operators and more or less every SQL keyword there is
are now abstracted into the compiler layer. They now act
intelligently and are type/backend aware, see: http://www.sq
lalchemy.org/docs/04/sqlexpression.html#sql_operators
intelligently and are type/backend aware, see:
http://www.sqlalchemy.org/docs/04/sqlexpression.html#sql_operators
All ``type`` Keyword Arguments Renamed to ``type_``
---------------------------------------------------
+3 -3
View File
@@ -72,7 +72,7 @@ Object Relational Mapping
::
for row in session.query(User.name, func.count(Address.id).label('numaddresses')).join(Address).group_by(User.name):
print "name", row.name, "number", row.numaddresses
print("name", row.name, "number", row.numaddresses)
``Query`` has a ``statement`` accessor, as well as a
``subquery()`` method which allow ``Query`` to be used to
@@ -144,7 +144,7 @@ Object Relational Mapping
::
for col in table.c:
print col
print(col)
Work with a specific column:
@@ -606,7 +606,7 @@ Removed
from sqlalchemy.orm import aliased
address_alias = aliased(Address)
print session.query(User, address_alias).join((address_alias, User.addresses)).all()
print(session.query(User, address_alias).join((address_alias, User.addresses)).all())
* ``sqlalchemy.orm.Mapper``
+21 -21
View File
@@ -1,6 +1,6 @@
==============================
=============================
What's New in SQLAlchemy 0.6?
==============================
=============================
.. admonition:: About this Document
@@ -68,7 +68,7 @@ The URL format used by ``create_engine()`` has been enhanced
to handle any number of DBAPIs for a particular backend,
using a scheme that is inspired by that of JDBC. The
previous format still works, and will select a "default"
DBAPI implementation, such as the Postgresql URL below that
DBAPI implementation, such as the PostgreSQL URL below that
will use psycopg2:
::
@@ -180,7 +180,7 @@ But what happens if we say this?
::
>>> if column('foo') == 5:
... print "yes"
... print("yes")
...
In previous versions of SQLAlchemy, the returned
@@ -205,7 +205,7 @@ That means code such as the following:
::
if expression:
print "the expression is:", expression
print("the expression is:", expression)
Would not evaluate if ``expression`` was a binary clause.
Since the above pattern should never be used, the base
@@ -227,7 +227,7 @@ Code that wants to check for the presence of a
::
if expression is not None:
print "the expression is:", expression
print("the expression is:", expression)
Keep in mind, **this applies to Table and Column objects
too**.
@@ -306,7 +306,7 @@ A rule that was designed to help SQLite has been removed,
that of the first compound element within another compound
(such as, a ``union()`` inside of an ``except_()``) wouldn't
be parenthesized. This is inconsistent and produces the
wrong results on Postgresql, which has precedence rules
wrong results on PostgreSQL, which has precedence rules
regarding INTERSECTION, and its generally a surprise. When
using complex composites with SQLite, you now need to turn
the first element into a subquery (which is also compatible
@@ -415,7 +415,7 @@ expression object:
create = CreateTable(mytable)
# dumps the CREATE TABLE as a string
print create
print(create)
# executes the CREATE TABLE statement
engine.execute(create)
@@ -568,11 +568,11 @@ To use an inspector:
from sqlalchemy.engine.reflection import Inspector
insp = Inspector.from_engine(my_engine)
print insp.get_schema_names()
print(insp.get_schema_names())
the ``from_engine()`` method will in some cases provide a
backend-specific inspector with additional capabilities,
such as that of Postgresql which provides a
such as that of PostgreSQL which provides a
``get_table_oid()`` method:
::
@@ -581,14 +581,14 @@ such as that of Postgresql which provides a
my_engine = create_engine('postgresql://...')
pg_insp = Inspector.from_engine(my_engine)
print pg_insp.get_table_oid('my_table')
print(pg_insp.get_table_oid('my_table'))
RETURNING Support
=================
The ``insert()``, ``update()`` and ``delete()`` constructs
now support a ``returning()`` method, which corresponds to
the SQL RETURNING clause as supported by Postgresql, Oracle,
the SQL RETURNING clause as supported by PostgreSQL, Oracle,
MS-SQL, and Firebird. It is not supported for any other
backend at this time.
@@ -603,7 +603,7 @@ columns will be returned as a regular result set:
table.insert().values(data='some data').returning(table.c.id, table.c.timestamp)
)
row = result.first()
print "ID:", row['id'], "Timestamp:", row['timestamp']
print("ID:", row['id'], "Timestamp:", row['timestamp'])
The implementation of RETURNING across the four supported
backends varies wildly, in the case of Oracle requiring an
@@ -659,7 +659,7 @@ scenes to provide two goals:
Highlights of these changes include:
* The construction of types within dialects has been totally
overhauled. Dialects now define publically available types
overhauled. Dialects now define publicly available types
as UPPERCASE names exclusively, and internal
implementation types using underscore identifiers (i.e.
are private). The system by which types are expressed in
@@ -747,7 +747,7 @@ Note that the ``assert_unicode`` flag is now deprecated.
SQLAlchemy allows the DBAPI and backend database in use to
handle Unicode parameters when available, and does not add
operational overhead by checking the incoming type; modern
systems like sqlite and Postgresql will raise an encoding
systems like sqlite and PostgreSQL will raise an encoding
error on their end if invalid data is passed. In those
cases where SQLAlchemy does need to coerce a bind parameter
from Python Unicode to an encoded string, or when the
@@ -766,13 +766,13 @@ default, this type generates a ``VARCHAR`` using the size of
the largest label, and applies a CHECK constraint to the
table within the CREATE TABLE statement. When using MySQL,
the type by default uses MySQL's ENUM type, and when using
Postgresql the type will generate a user defined type using
PostgreSQL the type will generate a user defined type using
``CREATE TYPE <mytype> AS ENUM``. In order to create the
type using Postgresql, the ``name`` parameter must be
type using PostgreSQL, the ``name`` parameter must be
specified to the constructor. The type also accepts a
``native_enum=False`` option which will issue the
VARCHAR/CHECK strategy for all databases. Note that
Postgresql ENUM types currently don't work with pg8000 or
PostgreSQL ENUM types currently don't work with pg8000 or
zxjdbc.
Reflection Returns Dialect-Specific Types
@@ -921,7 +921,7 @@ A new kind of eager loading is added called "subquery"
loading. This is a load that emits a second SQL query
immediately after the first which loads full collections for
all the parents in the first query, joining upwards to the
parent using INNER JOIN. Subquery loading is used simlarly
parent using INNER JOIN. Subquery loading is used similarly
to the current joined-eager loading, using the
```subqueryload()```` and ````subqueryload_all()```` options
as well as the ````lazy='subquery'```` setting on
@@ -958,7 +958,7 @@ innerjoin=True on relation, joinedload
Joined-eagerly loaded scalars and collections can now be
instructed to use INNER JOIN instead of OUTER JOIN. On
Postgresql this is observed to provide a 300-600% speedup on
PostgreSQL this is observed to provide a 300-600% speedup on
some queries. Set this flag for any many-to-one which is
on a NOT NULLable foreign key, and similarly for any
collection where related items are guaranteed to exist.
@@ -1049,7 +1049,7 @@ Mutable Primary Keys with Joined Table Inheritance
A joined table inheritance config where the child table has
a PK that foreign keys to the parent PK can now be updated
on a CASCADE-capable database like Postgresql.
on a CASCADE-capable database like PostgreSQL.
``mapper()`` now has an option ``passive_updates=True``
which indicates this foreign key is updated automatically.
If on a non-cascading database like SQLite or MySQL/MyISAM,
+11 -11
View File
@@ -1,6 +1,6 @@
==============================
=============================
What's New in SQLAlchemy 0.7?
==============================
=============================
.. admonition:: About this Document
@@ -310,14 +310,14 @@ These are implemented as an extension to the ``asc()`` and
:ticket:`723`
select.distinct(), query.distinct() accepts \*args for Postgresql DISTINCT ON
select.distinct(), query.distinct() accepts \*args for PostgreSQL DISTINCT ON
-----------------------------------------------------------------------------
This was already available by passing a list of expressions
to the ``distinct`` keyword argument of ``select()``, the
``distinct()`` method of ``select()`` and ``Query`` now
accept positional arguments which are rendered as DISTINCT
ON when a Postgresql backend is used.
ON when a PostgreSQL backend is used.
`distinct() <http://www.sqlalchemy.org/docs/07/core/expressi
on_api.html#sqlalchemy.sql.expression.Select.distinct>`_
@@ -367,9 +367,9 @@ A "window function" provides to a statement information
about the result set as it's produced. This allows criteria
against various things like "row number", "rank" and so
forth. They are known to be supported at least by
Postgresql, SQL Server and Oracle, possibly others.
PostgreSQL, SQL Server and Oracle, possibly others.
The best introduction to window functions is on Postgresql's
The best introduction to window functions is on PostgreSQL's
site, where window functions have been supported since
version 8.4:
@@ -398,7 +398,7 @@ tutorial:
label('avg')
])
print s
print(s)
SQL:
@@ -425,7 +425,7 @@ The default isolation level is set using the
``isolation_level`` argument to ``create_engine()``.
Transaction isolation support is currently only supported by
the Postgresql and SQLite backends.
the PostgreSQL and SQLite backends.
`execution_options() <http://www.sqlalchemy.org/docs/07/core
/connections.html#sqlalchemy.engine.base.Connection.executio
@@ -483,7 +483,7 @@ C Extensions Build by Default
This is as of 0.7b4. The exts will build if cPython 2.xx
is detected. If the build fails, such as on a windows
install, that condition is caught and the non-C install
proceeds. The C exts won't build if Python 3 or Pypy is
proceeds. The C exts won't build if Python 3 or PyPy is
used.
Query.count() simplified, should work virtually always
@@ -749,7 +749,7 @@ MS-SQL - ``String``/``Unicode``/``VARCHAR``/``NVARCHAR``/``VARBINARY`` emit "max
On the MS-SQL backend, the String/Unicode types, and their
counterparts VARCHAR/ NVARCHAR, as well as VARBINARY
(:ticket:`1833`) emit "max" as the length when no length is
specified. This makes it more compatible with Postgresql's
specified. This makes it more compatible with PostgreSQL's
VARCHAR type which is similarly unbounded when no length
specified. SQL Server defaults the length on these types
to '1' when no length is specified.
@@ -997,7 +997,7 @@ same manner as that of 0.5 and 0.6:
::
print s.query(Parent).with_polymorphic([Child]).filter(Child.id > 7)
print(s.query(Parent).with_polymorphic([Child]).filter(Child.id > 7))
Which on both 0.6 and 0.7 renders:
+29 -27
View File
@@ -1,6 +1,6 @@
==============================
=============================
What's New in SQLAlchemy 0.8?
==============================
=============================
.. admonition:: About this Document
@@ -282,7 +282,7 @@ A walkthrough of some key capabilities follows::
<Mapper at 0x101521950; User>
>>> # an expression
>>> print b.expression
>>> print(b.expression)
"user".id = address.user_id
>>> # inspect works on instances
@@ -432,7 +432,7 @@ with a declarative base class::
@event.listens_for("load", Base, propagate=True)
def on_load(target, context):
print "New instance loaded:", target
print("New instance loaded:", target)
# on_load() will be applied to SomeClass
class SomeClass(Base):
@@ -526,8 +526,10 @@ the :class:`.Table` to which ``User`` is mapped.
:ticket:`2245`
.. _change_orm_2365:
Query.update() supports UPDATE..FROM
-------------------------------------
------------------------------------
The new UPDATE..FROM mechanics work in query.update().
Below, we emit an UPDATE against ``SomeEntity``, adding
@@ -576,9 +578,9 @@ that were not flushed in the current transaction.
:ticket:`2452`
Caching Example now uses dogpile.cache
---------------------------------------
--------------------------------------
The caching example now uses `dogpile.cache <http://dogpilecache.readthedocs.org/>`_.
The caching example now uses `dogpile.cache <https://dogpilecache.readthedocs.io/>`_.
Dogpile.cache is a rewrite of the caching portion
of Beaker, featuring vastly simpler and faster operation,
as well as support for distributed locking.
@@ -607,7 +609,7 @@ this change is needed as illustrated in the Beaker example::
:ticket:`2589`
New Core Features
==================
=================
Fully extensible, type-level operator support in Core
-----------------------------------------------------
@@ -622,7 +624,7 @@ now, the only way operators could be flexibly redefined was
in the ORM layer, using :func:`.column_property` given a
``comparator_factory`` argument. Third party libraries
like GeoAlchemy therefore were forced to be ORM-centric and
rely upon an array of hacks to apply new opertions as well
rely upon an array of hacks to apply new operations as well
as to get them to propagate correctly.
The new operator system in Core adds the one hook that's
@@ -665,12 +667,12 @@ The new type is usable like any other type:
)
stmt = select([data.c.x.log(data.c.y)]).where(data.c.x.log(2) < value)
print conn.execute(stmt).fetchall()
print(conn.execute(stmt).fetchall())
New features which have come from this immediately include
support for Postgresql's HSTORE type, as well as new
operations associated with Postgresql's ARRAY
support for PostgreSQL's HSTORE type, as well as new
operations associated with PostgreSQL's ARRAY
type. It also paves the way for existing types to acquire
lots more operators that are specific to those types, such
as more string, integer and date operators.
@@ -686,12 +688,12 @@ as more string, integer and date operators.
.. _feature_2623:
Multiple-VALUES support for Insert
-----------------------------------
----------------------------------
The :meth:`.Insert.values` method now supports a list of dictionaries,
which will render a multi-VALUES statement such as
``VALUES (<row1>), (<row2>), ...``. This is only relevant to backends which
support this syntax, including Postgresql, SQLite, and MySQL. It is
support this syntax, including PostgreSQL, SQLite, and MySQL. It is
not the same thing as the usual ``executemany()`` style of INSERT which
remains unchanged::
@@ -708,7 +710,7 @@ remains unchanged::
:ticket:`2623`
Type Expressions
-----------------
----------------
SQL expressions can now be associated with types. Historically,
:class:`.TypeEngine` has always allowed Python-side functions which
@@ -738,7 +740,7 @@ Above, the ``LowerString`` type defines a SQL expression that will be emitted
whenever the ``test_table.c.data`` column is rendered in the columns
clause of a SELECT statement::
>>> print select([test_table]).where(test_table.c.data == 'HI')
>>> print(select([test_table]).where(test_table.c.data == 'HI'))
SELECT lower(test_table.data) AS data
FROM test_table
WHERE test_table.data = lower(:data_1)
@@ -753,7 +755,7 @@ to embed PostGIS expressions inline in SQL based on type rules.
:ticket:`1534`
Core Inspection System
-----------------------
----------------------
The :func:`.inspect` function introduced in :ref:`feature_orminspection_08`
also applies to the core. Applied to an :class:`.Engine` it produces
@@ -764,7 +766,7 @@ an :class:`.Inspector` object::
engine = create_engine("postgresql://scott:tiger@localhost/test")
insp = inspect(engine)
print insp.get_table_names()
print(insp.get_table_names())
It can also be applied to any :class:`.ClauseElement`, which returns
the :class:`.ClauseElement` itself, such as :class:`.Table`, :class:`.Column`,
@@ -804,10 +806,10 @@ against a particular target selectable::
:meth:`.Select.correlate_except`
Postgresql HSTORE type
PostgreSQL HSTORE type
----------------------
Support for Postgresql's ``HSTORE`` type is now available as
Support for PostgreSQL's ``HSTORE`` type is now available as
:class:`.postgresql.HSTORE`. This type makes great usage
of the new operator system to provide a full range of operators
for HSTORE types, including index access, concatenation,
@@ -840,7 +842,7 @@ and containment methods such as
:ticket:`2606`
Enhanced Postgresql ARRAY type
Enhanced PostgreSQL ARRAY type
------------------------------
The :class:`.postgresql.ARRAY` type will accept an optional
@@ -939,7 +941,7 @@ Huge thanks to Nate Dub for the sprinting on this at Pycon 2012.
:ticket:`2363`
"COLLATE" supported across all dialects; in particular MySQL, Postgresql, SQLite
"COLLATE" supported across all dialects; in particular MySQL, PostgreSQL, SQLite
--------------------------------------------------------------------------------
The "collate" keyword, long accepted by the MySQL dialect, is now established
@@ -947,7 +949,7 @@ on all :class:`.String` types and will render on any backend, including
when features such as :meth:`.MetaData.create_all` and :func:`.cast` is used::
>>> stmt = select([cast(sometable.c.somechar, String(20, collation='utf8'))])
>>> print stmt
>>> print(stmt)
SELECT CAST(sometable.somechar AS VARCHAR(20) COLLATE "utf8") AS anon_1
FROM sometable
@@ -1079,7 +1081,7 @@ The new behavior allows the following test case to work::
from sqlalchemy import create_engine
from sqlalchemy.orm import Session
# note we're using Postgresql to ensure that referential integrity
# note we're using PostgreSQL to ensure that referential integrity
# is enforced, for demonstration purposes.
e = create_engine("postgresql://scott:tiger@localhost/test", echo=True)
@@ -1208,7 +1210,7 @@ Within a SELECT, the correlation takes effect as expected::
s2 = select([t1, t2]).where(t1.c.x == t2.c.y).where(t1.c.x == s)
print (s2)
print(s2)
SELECT t1.x, t2.y FROM t1, t2
WHERE t1.x = t2.y AND t1.x =
@@ -1231,7 +1233,7 @@ create_all() and drop_all() will now honor an empty list as such
The methods :meth:`.MetaData.create_all` and :meth:`.MetaData.drop_all`
will now accept a list of :class:`.Table` objects that is empty,
and will not emit any CREATE or DROP statements. Previously,
an empty list was interepreted the same as passing ``None``
an empty list was interpreted the same as passing ``None``
for a collection, and CREATE/DROP would be emitted for all
items unconditionally.
@@ -1241,7 +1243,7 @@ the previous behavior.
:ticket:`2664`
Repaired the Event Targeting of :class:`.InstrumentationEvents`
----------------------------------------------------------------
---------------------------------------------------------------
The :class:`.InstrumentationEvents` series of event targets have
documented that the events will only be fired off according to
+38 -32
View File
@@ -391,7 +391,7 @@ This is a small change demonstrated as follows::
# in 0.8, this would fail to load the unloaded state.
assert attributes.get_history(a1, 'data') == ((), ['a1',], ())
# load_history() is now equiavlent to get_history() with
# load_history() is now equivalent to get_history() with
# passive=PASSIVE_OFF ^ INIT_OK
assert inspect(a1).attrs.data.load_history() == ((), ['a1',], ())
@@ -522,7 +522,7 @@ The "password" portion of a ``create_engine()`` no longer considers the ``+`` si
For whatever reason, the Python function ``unquote_plus()`` was applied to the
"password" field of a URL, which is an incorrect application of the
encoding rules described in `RFC 1738 <http://www.ietf.org/rfc/rfc1738.txt>`_
in that it escaped spaces as plus signs. The stringiciation of a URL
in that it escaped spaces as plus signs. The stringification of a URL
now only encodes ":", "@", or "/" and nothing else, and is now applied to both the
``username`` and ``password`` fields (previously it only applied to the
password). On parsing, encoded characters are converted, but plus signs and
@@ -550,7 +550,7 @@ The precedence rules for COLLATE have been changed
Previously, an expression like the following::
print (column('x') == 'somevalue').collate("en_EN")
print((column('x') == 'somevalue').collate("en_EN"))
would produce an expression like this::
@@ -567,7 +567,7 @@ by that of most database documentation::
The potentially backwards incompatible change arises if the :meth:`.collate`
operator is being applied to the right-hand column, as follows::
print column('x') == literal('somevalue').collate("en_EN")
print(column('x') == literal('somevalue').collate("en_EN"))
In 0.8, this produces::
@@ -584,11 +584,11 @@ The :meth:`.ColumnOperators.collate` operator now works more appropriately withi
generated::
>>> # 0.8
>>> print column('x').collate('en_EN').desc()
>>> print(column('x').collate('en_EN').desc())
(x COLLATE en_EN) DESC
>>> # 0.9
>>> print column('x').collate('en_EN').desc()
>>> print(column('x').collate('en_EN').desc())
x COLLATE en_EN DESC
:ticket:`2879`
@@ -597,7 +597,7 @@ generated::
.. _migration_2878:
Postgresql CREATE TYPE <x> AS ENUM now applies quoting to values
PostgreSQL CREATE TYPE <x> AS ENUM now applies quoting to values
----------------------------------------------------------------
The :class:`.postgresql.ENUM` type will now apply escaping to single quote
@@ -606,7 +606,7 @@ signs within the enumerated values::
>>> from sqlalchemy.dialects import postgresql
>>> type = postgresql.ENUM('one', 'two', "three's", name="myenum")
>>> from sqlalchemy.dialects.postgresql import base
>>> print base.CreateEnumType(type).compile(dialect=postgresql.dialect())
>>> print(base.CreateEnumType(type).compile(dialect=postgresql.dialect()))
CREATE TYPE myenum AS ENUM ('one','two','three''s')
Existing workarounds which already escape single quote signs will need to be
@@ -879,7 +879,7 @@ New FOR UPDATE support on ``select()``, ``Query()``
An attempt is made to simplify the specification of the ``FOR UPDATE``
clause on ``SELECT`` statements made within Core and ORM, and support is added
for the ``FOR UPDATE OF`` SQL supported by Postgresql and Oracle.
for the ``FOR UPDATE OF`` SQL supported by PostgreSQL and Oracle.
Using the core :meth:`.GenerativeSelect.with_for_update`, options like ``FOR SHARE`` and
``NOWAIT`` can be specified individually, rather than linking to arbitrary
@@ -976,11 +976,11 @@ identifier, or alternatively fetch the version identifier
from each row at the same time the INSERT or UPDATE is emitted. When using a
server-generated version identifier, it is strongly
recommended that this feature be used only on a backend with strong RETURNING
support (Postgresql, SQL Server; Oracle also supports RETURNING but the cx_oracle
support (PostgreSQL, SQL Server; Oracle also supports RETURNING but the cx_oracle
driver has only limited support), else the additional SELECT statements will
add significant performance
overhead. The example provided at :ref:`server_side_version_counter` illustrates
the usage of the Postgresql ``xmin`` system column in order to integrate it with
the usage of the PostgreSQL ``xmin`` system column in order to integrate it with
the ORM's versioning feature.
.. seealso::
@@ -1033,10 +1033,10 @@ from a backref::
:ticket:`1535`
Postgresql JSON Type
PostgreSQL JSON Type
--------------------
The Postgresql dialect now features a :class:`.postgresql.JSON` type to
The PostgreSQL dialect now features a :class:`.postgresql.JSON` type to
complement the :class:`.postgresql.HSTORE` type.
.. seealso::
@@ -1085,7 +1085,7 @@ classes, including relationships, based on a reflected schema::
session.commit()
# collection-based relationships are by default named "<classname>_collection"
print (u1.address_collection)
print(u1.address_collection)
Beyond that, the :class:`.AutomapBase` class is a declarative base, and supports
all the features that declarative does. The "automapping" feature can be used
@@ -1095,7 +1095,7 @@ can be dropped in using callable functions.
It is hoped that the :class:`.AutomapBase` system provides a quick
and modernized solution to the problem that the very famous
`SQLSoup <https://sqlsoup.readthedocs.org/en/latest/>`_
`SQLSoup <https://sqlsoup.readthedocs.io/en/latest/>`_
also tries to solve, that of generating a quick and rudimentary object
model from an existing database on the fly. By addressing the issue strictly
at the mapper configuration level, and integrating fully with existing
@@ -1125,7 +1125,7 @@ as INNER JOINs could always be flattened)::
SELECT a.*, b.*, c.* FROM a LEFT OUTER JOIN (b JOIN c ON b.id = c.id) ON a.id
This was due to the fact that SQLite, even today, cannot parse a statement of the above format::
This was due to the fact that SQLite up until version **3.7.16** cannot parse a statement of the above format::
SQLite version 3.7.15.2 2013-01-09 11:53:05
Enter ".help" for instructions
@@ -1149,7 +1149,7 @@ but today it seems clear every database tested except SQLite now supports it
(Oracle 8, a very old database, doesn't support the JOIN keyword at all,
but SQLAlchemy has always had a simple rewriting scheme in place for Oracle's syntax).
To make matters worse, SQLAlchemy's usual workaround of applying a
SELECT often degrades performance on platforms like Postgresql and MySQL::
SELECT often degrades performance on platforms like PostgreSQL and MySQL::
SELECT a.*, anon_1.* FROM a LEFT OUTER JOIN (
SELECT b.id AS b_id, c.id AS c_id
@@ -1248,10 +1248,16 @@ with the above queries rewritten as::
JOIN item ON item.id = order_item_1.item_id AND item.type IN (?)
) AS anon_1 ON "order".id = anon_1.order_item_1_order_id
.. note::
As of SQLAlchemy 1.1, the workarounds present in this feature for SQLite
will automatically disable themselves when SQLite version **3.7.16**
or greater is detected, as SQLite has repaired support for right-nested joins.
The :meth:`.Join.alias`, :func:`.aliased` and :func:`.with_polymorphic` functions now
support a new argument, ``flat=True``, which is used to construct aliases of joined-table
entities without embedding into a SELECT. This flag is not on by default, to help with
backwards compatibility - but now a "polymorhpic" selectable can be joined as a target
backwards compatibility - but now a "polymorphic" selectable can be joined as a target
without any subqueries generated::
employee_alias = with_polymorphic(Person, [Engineer, Manager], flat=True)
@@ -1329,7 +1335,7 @@ immediately within the flush process.
In 0.9, as a result of the version id enhancements, ``eager_defaults`` can now
emit a RETURNING clause for these values, so on a backend with strong RETURNING
support in particular Postgresql, the ORM can fetch newly generated default
support in particular PostgreSQL, the ORM can fetch newly generated default
and SQL expression values inline with the INSERT or UPDATE. ``eager_defaults``,
when enabled, makes use of RETURNING automatically when the target backend
and :class:`.Table` supports "implicit returning".
@@ -1453,7 +1459,7 @@ The typing system now handles the task of rendering "literal bind" values
A new method is added to :class:`.TypeEngine` :meth:`.TypeEngine.literal_processor`
as well as :meth:`.TypeDecorator.process_literal_param` for :class:`.TypeDecorator`
which take on the task of rendering so-called "inline literal paramters" - parameters
which take on the task of rendering so-called "inline literal parameters" - parameters
that normally render as "bound" values, but are instead being rendered inline
into the SQL statement due to the compiler configuration. This feature is used
when generating DDL for constructs such as :class:`.CheckConstraint`, as well
@@ -1496,7 +1502,7 @@ insensitive names).
The :class:`.quoted_name` object is used internally as needed; however if
other keywords require fixed quoting preferences, the class is available
publically.
publicly.
:ticket:`2812`
@@ -1517,46 +1523,46 @@ Starting with a table such as this::
t1 = Table('t', MetaData(), Column('x', Boolean()), Column('y', Integer))
A select construct will now render the boolean column as a binary expression
on backends that don't feature ``true``/``false`` constant beahvior::
on backends that don't feature ``true``/``false`` constant behavior::
>>> from sqlalchemy import select, and_, false, true
>>> from sqlalchemy.dialects import mysql, postgresql
>>> print select([t1]).where(t1.c.x).compile(dialect=mysql.dialect())
>>> print(select([t1]).where(t1.c.x).compile(dialect=mysql.dialect()))
SELECT t.x, t.y FROM t WHERE t.x = 1
The :func:`.and_` and :func:`.or_` constructs will now exhibit quasi
"short circuit" behavior, that is truncating a rendered expression, when a
:func:`.true` or :func:`.false` constant is present::
>>> print select([t1]).where(and_(t1.c.y > 5, false())).compile(
... dialect=postgresql.dialect())
>>> print(select([t1]).where(and_(t1.c.y > 5, false())).compile(
... dialect=postgresql.dialect()))
SELECT t.x, t.y FROM t WHERE false
:func:`.true` can be used as the base to build up an expression::
>>> expr = true()
>>> expr = expr & (t1.c.y > 5)
>>> print select([t1]).where(expr)
>>> print(select([t1]).where(expr))
SELECT t.x, t.y FROM t WHERE t.y > :y_1
The boolean constants :func:`.true` and :func:`.false` themselves render as
``0 = 1`` and ``1 = 1`` for a backend with no boolean constants::
>>> print select([t1]).where(and_(t1.c.y > 5, false())).compile(
... dialect=mysql.dialect())
>>> print(select([t1]).where(and_(t1.c.y > 5, false())).compile(
... dialect=mysql.dialect()))
SELECT t.x, t.y FROM t WHERE 0 = 1
Interpretation of ``None``, while not particularly valid SQL, is at least
now consistent::
>>> print select([t1.c.x]).where(None)
>>> print(select([t1.c.x]).where(None))
SELECT t.x FROM t WHERE NULL
>>> print select([t1.c.x]).where(None).where(None)
>>> print(select([t1.c.x]).where(None).where(None))
SELECT t.x FROM t WHERE NULL AND NULL
>>> print select([t1.c.x]).where(and_(None, None))
>>> print(select([t1.c.x]).where(and_(None, None)))
SELECT t.x FROM t WHERE NULL AND NULL
:ticket:`2804`
@@ -1580,7 +1586,7 @@ E.g. an example like::
stmt = select([expr]).order_by(expr)
print stmt
print(stmt)
Prior to 0.9 would render as::
+60 -62
View File
@@ -1,6 +1,6 @@
==============================
=============================
What's New in SQLAlchemy 1.0?
==============================
=============================
.. admonition:: About this Document
@@ -41,7 +41,7 @@ to proceed at speeds that rival direct use of the Core.
:ticket:`3100`
New Performance Example Suite
------------------------------
-----------------------------
Inspired by the benchmarking done for the :ref:`bulk_operations` feature
as well as for the :ref:`faq_how_to_profile` section of the FAQ, a new
@@ -64,7 +64,7 @@ straightforward construction an invocation of :class:`.Query` objects
using caching, which upon successive calls features vastly reduced
Python function call overhead (over 75%). By specifying a
:class:`.Query` object as a series of lambdas which are only invoked
once, a query as a pre-compiled unit begins to be feasable::
once, a query as a pre-compiled unit begins to be feasible::
from sqlalchemy.ext import baked
from sqlalchemy import bindparam
@@ -94,7 +94,7 @@ once, a query as a pre-compiled unit begins to be feasable::
.. _feature_3150:
Improvements to declarative mixins, ``@declared_attr`` and related features
----------------------------------------------------------------------------
---------------------------------------------------------------------------
The declarative system in conjunction with :class:`.declared_attr` has been
overhauled to support new capabilities.
@@ -163,18 +163,16 @@ is affixed to the base class only, and just inherited from subclasses.
With :attr:`.declared_attr.cascading`, individual behaviors can be
applied::
class HasSomeAttribute(object):
class HasIdMixin(object):
@declared_attr.cascading
def some_id(cls):
def id(cls):
if has_inherited_table(cls):
return Column(ForeignKey('myclass.id'), primary_key=True)
else:
return Column(Integer, primary_key=True)
return Column('id', Integer, primary_key=True)
class MyClass(HasSomeAttribute, Base):
""
class MyClass(HasIdMixin, Base):
__tablename__ = 'myclass'
# ...
class MySubClass(MyClass):
@@ -324,7 +322,7 @@ object totally smokes both namedtuple and KeyedTuple::
.. _feature_slots:
Significant Improvements in Structural Memory Use
--------------------------------------------------
-------------------------------------------------
Structural memory use has been improved via much more significant use
of ``__slots__`` for many internal objects. This optimization is
@@ -355,7 +353,7 @@ well as weakrefs, within a basic import of "nova.db.sqlalchemy.models"::
.. _feature_updatemany:
UPDATE statements are now batched with executemany() in a flush
----------------------------------------------------------------
---------------------------------------------------------------
UPDATE statements can now be batched within an ORM flush
into more performant executemany() call, similarly to how INSERT
@@ -420,7 +418,7 @@ of inheritance-oriented scenarios, including:
.. _bug_3227:
Session.get_bind() will receive the Mapper in all relevant Query cases
-----------------------------------------------------------------------
----------------------------------------------------------------------
A series of issues were repaired where the :meth:`.Session.get_bind`
would not receive the primary :class:`.Mapper` of the :class:`.Query`,
@@ -479,7 +477,7 @@ of object that one would retrieve from the :attr:`.Mapper.all_orm_descriptors`
collection. This includes :class:`.hybrid_property` and :func:`.association_proxy`.
However, as these objects are class-bound descriptors, they must be accessed
**separately** from the class to which they are attached in order to get
at the attribute. Below this is illustared using the
at the attribute. Below this is illustrated using the
:attr:`.Mapper.all_orm_descriptors` namespace::
class SomeObject(Base):
@@ -503,7 +501,7 @@ as remaining ORM constructs such as :func:`.orm.synonym`.
.. _bug_3188:
ColumnProperty constructs work a lot better with aliases, order_by
-------------------------------------------------------------------
------------------------------------------------------------------
A variety of issues regarding :func:`.column_property` have been fixed,
most specifically with regards to the :func:`.aliased` construct as well
@@ -530,7 +528,7 @@ Given a mapping like the following::
A simple scenario that included "A.b" twice would fail to render
correctly::
print sess.query(A, a1).order_by(a1.b)
print(sess.query(A, a1).order_by(a1.b))
This would order by the wrong column::
@@ -585,7 +583,7 @@ New Features and Improvements - Core
.. _feature_3034:
Select/Query LIMIT / OFFSET may be specified as an arbitrary SQL expression
----------------------------------------------------------------------------
---------------------------------------------------------------------------
The :meth:`.Select.limit` and :meth:`.Select.offset` methods now accept
any SQL expression, in addition to integer values, as arguments. The ORM
@@ -634,7 +632,7 @@ does not support ALTER, in the case that during a DROP, the given tables have
an unresolvable cycle; in this case a warning is emitted, and the tables
are dropped with **no** ordering, which is usually fine on SQLite unless
constraints are enabled. To resolve the warning and proceed with at least
a partial ordering on a SQLite database, particuarly one where constraints
a partial ordering on a SQLite database, particularly one where constraints
are enabled, re-apply "use_alter" flags to those
:class:`.ForeignKey` and :class:`.ForeignKeyConstraint` objects which should
be explicitly omitted from the sort.
@@ -828,7 +826,7 @@ the :class:`.Constraint` is constructed::
.. _feature_insert_from_select_defaults:
INSERT FROM SELECT now includes Python and SQL-expression defaults
-------------------------------------------------------------------
------------------------------------------------------------------
:meth:`.Insert.from_select` now includes Python and SQL-expression defaults if
otherwise unspecified; the limitation where non-server column defaults
@@ -845,7 +843,7 @@ expressions are rendered as constants into the SELECT statement::
Column('y', Integer, default=func.somefunction()))
stmt = select([t.c.x])
print t.insert().from_select(['x'], stmt)
print(t.insert().from_select(['x'], stmt))
Will render::
@@ -898,12 +896,12 @@ UniqueConstraint is now part of the Table reflection process
A :class:`.Table` object populated using ``autoload=True`` will now
include :class:`.UniqueConstraint` constructs as well as
:class:`.Index` constructs. This logic has a few caveats for
Postgresql and Mysql:
PostgreSQL and MySQL:
Postgresql
PostgreSQL
^^^^^^^^^^
Postgresql has the behavior such that when a UNIQUE constraint is
PostgreSQL has the behavior such that when a UNIQUE constraint is
created, it implicitly creates a UNIQUE INDEX corresponding to that
constraint as well. The :meth:`.Inspector.get_indexes` and the
:meth:`.Inspector.get_unique_constraints` methods will continue to
@@ -1073,7 +1071,7 @@ it emits SQL resembling::
(None,)
Note above, there is a comparison ``WHERE ? = address.user_id`` where the
bound value ``?`` is receving ``None``, or ``NULL`` in SQL. **This will
bound value ``?`` is receiving ``None``, or ``NULL`` in SQL. **This will
always return False in SQL**. The comparison here would in theory
generate SQL as follows::
@@ -1356,11 +1354,11 @@ joined loader options can still be used::
.. _bug_3233:
Changes and fixes in handling of duplicate join targets
--------------------------------------------------------
-------------------------------------------------------
Changes here encompass bugs where an unexpected and inconsistent
behavior would occur in some scenarios when joining to an entity
twice, or to multple single-table entities against the same table,
twice, or to multiple single-table entities against the same table,
without using a relationship-based ON clause, as well as when joining
multiple times to the same target relationship.
@@ -1384,7 +1382,7 @@ Starting with a mapping as::
A query that joins to ``A.bs`` twice::
print s.query(A).join(A.bs).join(A.bs)
print(s.query(A).join(A.bs).join(A.bs))
Will render::
@@ -1407,7 +1405,7 @@ larger path will now emit a warning::
The bigger change involves when joining to an entity without using a
relationship-bound path. If we join to ``B`` twice::
print s.query(A).join(B, B.a_id == A.id).join(B, B.a_id == A.id)
print(s.query(A).join(B, B.a_id == A.id).join(B, B.a_id == A.id))
In 0.9, this would render as follows::
@@ -1467,9 +1465,9 @@ a mapping as follows::
s = Session()
print s.query(ASub1).join(B, ASub1.b).join(ASub2, B.a)
print(s.query(ASub1).join(B, ASub1.b).join(ASub2, B.a))
print s.query(ASub1).join(B, ASub1.b).join(ASub2, ASub2.id == B.a_id)
print(s.query(ASub1).join(B, ASub1.b).join(ASub2, ASub2.id == B.a_id))
The two queries at the bottom are equivalent, and should both render
the identical SQL::
@@ -1499,7 +1497,7 @@ as all the subclasses normally refer to the same table::
asub2_alias = aliased(ASub2)
print s.query(ASub1).join(B, ASub1.b).join(asub2_alias, B.a.of_type(asub2_alias))
print(s.query(ASub1).join(B, ASub1.b).join(asub2_alias, B.a.of_type(asub2_alias)))
:ticket:`3233`
:ticket:`3367`
@@ -1663,7 +1661,7 @@ joined eager loading is now dropped in this case::
LIMIT :param_1
In the case that the LEFT OUTER JOIN returns more than one row, the ORM
has always emitted a warning here and ignored addtional results for
has always emitted a warning here and ignored additional results for
``uselist=False``, so the results in that error situation should not change.
:ticket:`3249`
@@ -1962,7 +1960,7 @@ The output does what we say, but again it warns us::
The above behavior applies to all those places where we might want to refer
to a so-called "label reference"; ORDER BY and GROUP BY, but also within an
OVER clause as well as a DISTINCT ON clause that refers to columns (e.g. the
Postgresql syntax).
PostgreSQL syntax).
We can still specify any arbitrary expression for ORDER BY or others using
:func:`.text`::
@@ -1980,8 +1978,8 @@ be qualified with :func:`.text` or similar.
.. _bug_3288:
Python-side defaults invoked for each row invidually when using a multivalued insert
------------------------------------------------------------------------------------
Python-side defaults invoked for each row individually when using a multivalued insert
--------------------------------------------------------------------------------------
Support for Python-side column defaults when using the multi-valued
version of :meth:`.Insert.values` were essentially not implemented, and
@@ -2091,7 +2089,7 @@ rows (e.g. only the first row of many).
A similar change is also applied to an INSERT..VALUES
with multiple parameter sets; implicit RETURNING will no longer emit
for this statement either. As both of these constructs deal
with varible numbers of rows, the
with variable numbers of rows, the
:attr:`.ResultProxy.inserted_primary_key` accessor does not
apply. Previously, there was a documentation note that one
may prefer ``inline=True`` with INSERT..FROM SELECT as some databases
@@ -2157,7 +2155,7 @@ state.
.. _feature_3084:
MetaData.sorted_tables accessor is "deterministic"
-----------------------------------------------------
--------------------------------------------------
The sorting of tables resulting from the :attr:`.MetaData.sorted_tables`
accessor is "deterministic"; the ordering should be the same in all cases
@@ -2211,7 +2209,7 @@ reflection from temp tables as well, which is :ticket:`3203`.
:ticket:`3204`
Dialect Improvements and Changes - Postgresql
Dialect Improvements and Changes - PostgreSQL
=============================================
.. _change_3319:
@@ -2219,7 +2217,7 @@ Dialect Improvements and Changes - Postgresql
Overhaul of ENUM type create/drop rules
---------------------------------------
The rules for Postgresql :class:`.postgresql.ENUM` have been made more strict
The rules for PostgreSQL :class:`.postgresql.ENUM` have been made more strict
with regards to creating and dropping of the TYPE.
An :class:`.postgresql.ENUM` that is created **without** being explicitly
@@ -2234,7 +2232,7 @@ corresponding to :meth:`.Table.create` and :meth:`.Table.drop`::
table.drop(engine) # will emit DROP TABLE and DROP TYPE - new for 1.0
This means that if a second table also has an enum named 'myenum', the
above DROP operation will now fail. In order to accomodate the use case
above DROP operation will now fail. In order to accommodate the use case
of a common shared enumerated type, the behavior of a metadata-associated
enumeration has been enhanced.
@@ -2265,8 +2263,8 @@ flag::
:ticket:`3319`
New Postgresql Table options
-----------------------------
New PostgreSQL Table options
----------------------------
Added support for PG table options TABLESPACE, ON COMMIT,
WITH(OUT) OIDS, and INHERITS, when rendering DDL via
@@ -2280,11 +2278,11 @@ the :class:`.Table` construct.
.. _feature_get_enums:
New get_enums() method with Postgresql Dialect
New get_enums() method with PostgreSQL Dialect
----------------------------------------------
The :func:`.inspect` method returns a :class:`.PGInspector` object in the
case of Postgresql, which includes a new :meth:`.PGInspector.get_enums`
case of PostgreSQL, which includes a new :meth:`.PGInspector.get_enums`
method that returns information on all available ``ENUM`` types::
from sqlalchemy import inspect, create_engine
@@ -2299,23 +2297,23 @@ method that returns information on all available ``ENUM`` types::
.. _feature_2891:
Postgresql Dialect reflects Materialized Views, Foreign Tables
PostgreSQL Dialect reflects Materialized Views, Foreign Tables
--------------------------------------------------------------
Changes are as follows:
* the :class:`Table` construct with ``autoload=True`` will now match a name
that exists in the database as a materialized view or foriegn table.
that exists in the database as a materialized view or foreign table.
* :meth:`.Inspector.get_view_names` will return plain and materialized view
names.
* :meth:`.Inspector.get_table_names` does **not** change for Postgresql, it
* :meth:`.Inspector.get_table_names` does **not** change for PostgreSQL, it
continues to return only the names of plain tables.
* A new method :meth:`.PGInspector.get_foreign_table_names` is added which
will return the names of tables that are specifically marked as "foreign"
in the Postgresql schema tables.
in the PostgreSQL schema tables.
The change to reflection involves adding ``'m'`` and ``'f'`` to the list
of qualifiers we use when querying ``pg_class.relkind``, but this change
@@ -2326,7 +2324,7 @@ running 0.9 in production.
.. _change_3264:
Postgresql ``has_table()`` now works for temporary tables
PostgreSQL ``has_table()`` now works for temporary tables
---------------------------------------------------------
This is a simple fix such that "has table" for temporary tables now works,
@@ -2350,7 +2348,7 @@ so that code like the following may proceed::
user_tmp.create(conn, checkfirst=True)
The very unlikely case that this behavior will cause a non-failing application
to behave differently, is because Postgresql allows a non-temporary table
to behave differently, is because PostgreSQL allows a non-temporary table
to silently overwrite a temporary table. So code like the following will
now act completely differently, no longer creating the real table following
the temporary table::
@@ -2384,11 +2382,11 @@ the temporary table::
.. _feature_gh134:
Postgresql FILTER keyword
PostgreSQL FILTER keyword
-------------------------
The SQL standard FILTER keyword for aggregate functions is now supported
by Postgresql as of 9.4. SQLAlchemy allows this using
by PostgreSQL as of 9.4. SQLAlchemy allows this using
:meth:`.FunctionElement.filter`::
func.count(1).filter(True)
@@ -2400,20 +2398,20 @@ by Postgresql as of 9.4. SQLAlchemy allows this using
:class:`.FunctionFilter`
PG8000 dialect supports client side encoding
---------------------------------------------
--------------------------------------------
The :paramref:`.create_engine.encoding` parameter is now honored
by the pg8000 dialect, using on connect handler which
emits ``SET CLIENT_ENCODING`` matching the selected encoding.
PG8000 native JSONB support
--------------------------------------
---------------------------
Support for PG8000 versions greater than 1.10.1 has been added, where
JSONB is supported natively.
Support for psycopg2cffi Dialect on Pypy
Support for psycopg2cffi Dialect on PyPy
----------------------------------------
Support for the pypy psycopg2cffi dialect is added.
@@ -2423,12 +2421,12 @@ Support for the pypy psycopg2cffi dialect is added.
:mod:`sqlalchemy.dialects.postgresql.psycopg2cffi`
Dialect Improvements and Changes - MySQL
=============================================
========================================
.. _change_3155:
MySQL TIMESTAMP Type now renders NULL / NOT NULL in all cases
--------------------------------------------------------------
-------------------------------------------------------------
The MySQL dialect has always worked around MySQL's implicit NOT NULL
default associated with TIMESTAMP columns by emitting NULL for
@@ -2451,7 +2449,7 @@ columns.
.. _change_3283:
MySQL SET Type Overhauled to support empty sets, unicode, blank value handling
-------------------------------------------------------------------------------
------------------------------------------------------------------------------
The :class:`.mysql.SET` type historically not included a system of handling
blank sets and empty values separately; as different drivers had different
@@ -2584,7 +2582,7 @@ and is generally in decent working order, if someone wants to pick up
on polishing it.
Dialect Improvements and Changes - SQLite
=============================================
=========================================
SQLite named and unnamed UNIQUE and FOREIGN KEY constraints will inspect and reflect
-------------------------------------------------------------------------------------
@@ -2634,7 +2632,7 @@ to control the behavior completely, based on deprecation guidelines from
Microsoft. See :ref:`mssql_large_type_deprecation` for details.
Dialect Improvements and Changes - Oracle
=============================================
=========================================
.. _change_3220:
@@ -2655,7 +2653,7 @@ CTE support has been fixed up for Oracle, and there is also a new feature
:ticket:`3220`
New Oracle Keywords for DDL
-----------------------------
---------------------------
Keywords such as COMPRESS, ON COMMIT, BITMAP:
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
+9
View File
@@ -0,0 +1,9 @@
.. change::
:tags: bug, mysql
:tickets: 4065
:versions: 1.2.0b3, 1.1.14
mysqlclient as of 1.3.11 changed the exception
class for a particular disconnect situation from
InterfaceError to InternalError; the disconnection
detection logic now accommodates this.
+11
View File
@@ -0,0 +1,11 @@
Individual per-changelog files go here
in .rst format, which are pulled in by
changelog (version 0.4.0 or higher) to
be rendered into the changelog_xx.rst file.
At release time, the files here are removed and written
directly into the changelog.
Rationale is so that multiple changes being merged
into gerrit don't produce conflicts. Note that
gerrit does not support custom merge handlers unlike
git itself.
+12
View File
@@ -0,0 +1,12 @@
Individual per-changelog files go here
in .rst format, which are pulled in by
changelog (version 0.4.0 or higher) to
be rendered into the changelog_xx.rst file.
At release time, the files here are removed and written
directly into the changelog.
Rationale is so that multiple changes being merged
into gerrit don't produce conflicts. Note that
gerrit does not support custom merge handlers unlike
git itself.
+11
View File
@@ -0,0 +1,11 @@
.. change::
:tags: bug, engine
:tickets: 4406
Comparing two objects of :class:`.URL` using ``__eq__()`` did not take port
number into consideration, two objects differing only by port number were
considered equal. Port comparison is now added in ``__eq__()`` method of
:class:`.URL`, objects differing by port number are now not equal.
Additionally, ``__ne__()`` was not implemented for :class:`.URL` which
caused unexpected result when ``!=`` was used in Python2, since there are no
implied relationships among the comparison operators in Python2.
+8
View File
@@ -0,0 +1,8 @@
.. change::
:tags: bug, oracle
:tickets: 4506
Added support for reflection of the :class:`.NCHAR` datatype to the Oracle
dialect, and added :class:`.NCHAR` to the list of types exported by the
Oracle dialect.
+13
View File
@@ -0,0 +1,13 @@
.. change::
:tags: bug, orm
:tickets: 4507
Fixed a regression in 1.2 due to the introduction of baked queries for
relationship lazy loaders, where a race condition is created during the
generation of the "lazy clause" which occurs within a memoized attribute. If
two threads initialize the memoized attribute concurrently, the baked query
could be generated with bind parameter keys that are then replaced with new
keys by the next run, leading to a lazy load query that specifies the
related criteria as ``None``. The fix establishes that the parameter names
are fixed before the new clause and parameter objects are generated, so that
the names are the same every time.
+7
View File
@@ -0,0 +1,7 @@
.. change::
:tags: bug, examples
:tickets: 4528
Fixed bug in large_resultsets example case where a re-named "id" variable
due to code reformatting caused the test to fail. Pull request courtesy
Matt Schuchhardt.
+8
View File
@@ -0,0 +1,8 @@
.. change::
:tags: bug, mssql
:tickets: 4536
:versions: 1.3.1
A commit() is emitted after an isolation level change to SNAPSHOT, as both
pyodbc and pymssql open an implicit transaction which blocks subsequent SQL
from being emitted in the current transaction.
+12
View File
@@ -0,0 +1,12 @@
Individual per-changelog files go here
in .rst format, which are pulled in by
changelog (version 0.4.0 or higher) to
be rendered into the changelog_xx.rst file.
At release time, the files here are removed and written
directly into the changelog.
Rationale is so that multiple changes being merged
into gerrit don't produce conflicts. Note that
gerrit does not support custom merge handlers unlike
git itself.
+13
View File
@@ -0,0 +1,13 @@
.. change::
:tags: bug, orm
:tickets: 4537
Fixed bug where use of :func:`.with_polymorphic` or other aliased construct
would not properly adapt when the aliased target were used as the
:meth:`.Select.correlate_except` target of a subquery used inside of a
:func:`.column_property`. This required a fix to the clause adaption
mechanics to properly handle a selectable that shows up in the "correlate
except" list, in a similar manner as which occurs for selectables that show
up in the "correlate" list. This is ultimately a fairly fundamental bug
that has lasted for a long time but it is hard to come across it.
+10
View File
@@ -0,0 +1,10 @@
.. change::
:tags: bug, postgresql
:tickets: 4550
Modified the :paramref:`.Select.with_for_update.of` parameter so that if a
join or other composed selectable is passed, the individual :class:`.Table`
objects will be filtered from it, allowing one to pass a join() object to
the parameter, as occurs normally when using joined table inheritance with
the ORM. Pull request courtesy Raymond Lu.
+12
View File
@@ -0,0 +1,12 @@
Individual per-changelog files go here
in .rst format, which are pulled in by
changelog (version 0.4.0 or higher) to
be rendered into the changelog_xx.rst file.
At release time, the files here are removed and written
directly into the changelog.
Rationale is so that multiple changes being merged
into gerrit don't produce conflicts. Note that
gerrit does not support custom merge handlers unlike
git itself.
+21 -57
View File
@@ -13,25 +13,6 @@
import sys
import os
import traceback
def force_install_reqs():
import logging
log = logging.getLogger("pip")
handler = logging.StreamHandler(sys.stderr)
handler.setFormatter(logging.Formatter("[pip] %(message)s"))
log.addHandler(handler)
log.setLevel(logging.INFO)
log.info("READTHEDOCS is set, force-installing requirements.txt")
from pip.commands import install
req = os.path.join(os.path.dirname(__file__), "requirements.txt")
cmd = install.InstallCommand()
options, args = cmd.parse_args(["-v", "-U", "-r", req])
cmd.run(options, args)
# If extensions (or modules to document with autodoc) are in another directory,
# add these directories to sys.path here. If the directory is relative to the
@@ -42,34 +23,20 @@ sys.path.insert(0, os.path.abspath('.'))
import sqlalchemy
# attempt to force pip to definitely get the latest
# versions of libraries, see
# https://github.com/rtfd/readthedocs.org/issues/1293
rtd = os.environ.get('READTHEDOCS', None) == 'True'
if rtd:
try:
force_install_reqs()
except:
traceback.print_exc()
# -- General configuration -----------------------------------------------------
# If your documentation needs a minimal Sphinx version, state it here.
#needs_sphinx = '1.0'
needs_sphinx = '1.6.0'
# Add any Sphinx extension module names here, as strings. They can be extensions
# coming with Sphinx (named 'sphinx.ext.*') or your custom ones.
extensions = [
'sphinx.ext.autodoc',
'sphinx.ext.intersphinx',
'zzzeeksphinx',
'changelog',
'sphinx_paramlinks',
#'corrections'
'zzzeeksphinx',
'changelog',
'sphinx_paramlinks',
]
# Add any paths that contain templates here, relative to this directory.
@@ -96,13 +63,17 @@ changelog_inner_tag_sort = ["feature", "changed", "removed", "bug", "moved"]
changelog_render_ticket = "http://www.sqlalchemy.org/trac/ticket/%s"
changelog_render_pullreq = {
"bitbucket": "https://bitbucket.org/zzzeek/sqlalchemy/pull-request/%s",
"default": "https://bitbucket.org/zzzeek/sqlalchemy/pull-request/%s",
"github": "https://github.com/zzzeek/sqlalchemy/pull/%s",
"default": "https://github.com/sqlalchemy/sqlalchemy/pull/%s",
"github": "https://github.com/sqlalchemy/sqlalchemy/pull/%s",
}
changelog_render_changeset = "http://www.sqlalchemy.org/trac/changeset/%s"
exclude_patterns = [
'build',
'**/unreleased*/*',
]
autodocmods_convert_modname = {
"sqlalchemy.sql.sqltypes": "sqlalchemy.types",
"sqlalchemy.sql.type_api": "sqlalchemy.types",
@@ -129,18 +100,18 @@ master_doc = 'contents'
# General information about the project.
project = u'SQLAlchemy'
copyright = u'2007-2015, the SQLAlchemy authors and contributors'
copyright = u'2007-2019, the SQLAlchemy authors and contributors'
# The version info for the project you're documenting, acts as replacement for
# |version| and |release|, also used in various other places throughout the
# built documents.
#
# The short X.Y version.
version = "1.0"
version = "1.3"
# The full version, including alpha/beta/rc tags.
release = "1.0.8"
release = "1.3.1"
release_date = "July 22, 2015"
release_date = "March 9, 2019"
site_base = os.environ.get("RTD_SITE_BASE", "http://www.sqlalchemy.org")
site_adapter_template = "docs_adapter.mako"
@@ -148,7 +119,7 @@ site_adapter_py = "docs_adapter.py"
# arbitrary number recognized by builders.py, incrementing this
# will force a rebuild
build_number = 3
build_number = "3"
# The language for content autogenerated by Sphinx. Refer to documentation
# for a list of supported languages.
@@ -160,10 +131,6 @@ build_number = 3
# Else, today_fmt is used as the format for a strftime call.
#today_fmt = '%B %d, %Y'
# List of patterns, relative to source directory, that match files and
# directories to ignore when looking for source files.
exclude_patterns = ['build']
# The reST default role (used for this markup: `text`) to use for all documents.
#default_role = None
@@ -241,7 +208,9 @@ html_last_updated_fmt = '%m/%d/%Y %H:%M:%S'
# Additional templates that should be rendered to pages, maps page names to
# template names.
#html_additional_pages = {}
html_additional_pages = {
"notfound": "notfound.html"
}
# If false, no module index is generated.
html_domain_indices = False
@@ -290,8 +259,8 @@ htmlhelp_basename = 'SQLAlchemydoc'
# Grouping the document tree into LaTeX files. List of tuples
# (source start file, target name, title, author, documentclass [howto/manual]).
latex_documents = [
('contents', 'sqlalchemy_%s.tex' % release.replace('.', '_'), ur'SQLAlchemy Documentation',
ur'Mike Bayer', 'manual'),
('contents', 'sqlalchemy_%s.tex' % release.replace('.', '_'), 'SQLAlchemy Documentation',
'Mike Bayer', 'manual'),
]
# The name of an image file (relative to this directory) to place at the top of
@@ -372,9 +341,4 @@ epub_copyright = u'2007-2015, SQLAlchemy authors'
# Allow duplicate toc entries.
#epub_tocdup = True
intersphinx_mapping = {
'alembic': ('http://alembic.readthedocs.org/en/latest/', None),
'psycopg2': ('http://pythonhosted.org/psycopg2', None),
}
+1
View File
@@ -15,6 +15,7 @@ documentation, see :ref:`index_toplevel`.
core/index
dialects/index
faq/index
errors
changelog/index
Indices and tables
+1 -1
View File
@@ -6,7 +6,7 @@ Appendix: Copyright
This is the MIT license: `<http://www.opensource.org/licenses/mit-license.php>`_
Copyright (c) 2005-2015 Michael Bayer and contributors.
Copyright (c) 2005-2019 Michael Bayer and contributors.
SQLAlchemy is a trademark of Michael Bayer.
Permission is hereby granted, free of charge, to any person obtaining a copy of this
+2 -2
View File
@@ -1,6 +1,6 @@
=================
===============
Core API Basics
=================
===============
.. toctree::
:maxdepth: 2
+85 -14
View File
@@ -1,8 +1,8 @@
.. _connections_toplevel:
=====================================
====================================
Working with Engines and Connections
=====================================
====================================
.. module:: sqlalchemy.engine
@@ -48,7 +48,7 @@ way is first procure a connection resource, which you get via the
connection = engine.connect()
result = connection.execute("select username from users")
for row in result:
print "username:", row['username']
print("username:", row['username'])
connection.close()
The connection is an instance of :class:`.Connection`,
@@ -76,7 +76,7 @@ The above procedure can be performed in a shorthand way by using the
result = engine.execute("select username from users")
for row in result:
print "username:", row['username']
print("username:", row['username'])
Where above, the :meth:`~.Engine.execute` method acquires a new
:class:`.Connection` on its own, executes the statement with that object,
@@ -148,7 +148,7 @@ is available as well::
.. _connections_nested_transactions:
Nesting of Transaction Blocks
------------------------------
-----------------------------
The :class:`.Transaction` object also handles "nested"
behavior by keeping track of the outermost begin/commit pair. In this example,
@@ -241,7 +241,7 @@ it so that a SELECT statement will issue a COMMIT::
.. _dbengine_implicit:
Connectionless Execution, Implicit Execution
=============================================
============================================
Recall from the first section we mentioned executing with and without explicit
usage of :class:`.Connection`. "Connectionless" execution
@@ -251,7 +251,7 @@ of :class:`.Engine`::
result = engine.execute("select username from users")
for row in result:
print "username:", row['username']
print("username:", row['username'])
In addition to "connectionless" execution, it is also possible
to use the :meth:`~.Executable.execute` method of
@@ -368,6 +368,69 @@ the SQL statement. When the :class:`.ResultProxy` is closed, the underlying
:class:`.Connection` is closed for us, resulting in the
DBAPI connection being returned to the pool with transactional resources removed.
.. _schema_translating:
Translation of Schema Names
===========================
To support multi-tenancy applications that distribute common sets of tables
into multiple schemas, the
:paramref:`.Connection.execution_options.schema_translate_map`
execution option may be used to repurpose a set of :class:`.Table` objects
to render under different schema names without any changes.
Given a table::
user_table = Table(
'user', metadata,
Column('id', Integer, primary_key=True),
Column('name', String(50))
)
The "schema" of this :class:`.Table` as defined by the
:paramref:`.Table.schema` attribute is ``None``. The
:paramref:`.Connection.execution_options.schema_translate_map` can specify
that all :class:`.Table` objects with a schema of ``None`` would instead
render the schema as ``user_schema_one``::
connection = engine.connect().execution_options(
schema_translate_map={None: "user_schema_one"})
result = connection.execute(user_table.select())
The above code will invoke SQL on the database of the form::
SELECT user_schema_one.user.id, user_schema_one.user.name FROM
user_schema.user
That is, the schema name is substituted with our translated name. The
map can specify any number of target->destination schemas::
connection = engine.connect().execution_options(
schema_translate_map={
None: "user_schema_one", # no schema name -> "user_schema_one"
"special": "special_schema", # schema="special" becomes "special_schema"
"public": None # Table objects with schema="public" will render with no schema
})
The :paramref:`.Connection.execution_options.schema_translate_map` parameter
affects all DDL and SQL constructs generated from the SQL expression language,
as derived from the :class:`.Table` or :class:`.Sequence` objects.
It does **not** impact literal string SQL used via the :func:`.expression.text`
construct nor via plain strings passed to :meth:`.Connection.execute`.
The feature takes effect **only** in those cases where the name of the
schema is derived directly from that of a :class:`.Table` or :class:`.Sequence`;
it does not impact methods where a string schema name is passed directly.
By this pattern, it takes effect within the "can create" / "can drop" checks
performed by methods such as :meth:`.MetaData.create_all` or
:meth:`.MetaData.drop_all` are called, and it takes effect when
using table reflection given a :class:`.Table` object. However it does
**not** affect the operations present on the :class:`.Inspector` object,
as the schema name is passed to these methods explicitly.
.. versionadded:: 1.1
.. _engine_disposal:
Engine Disposal
@@ -447,18 +510,24 @@ with the current thread, such that all parts of the
application can participate in that transaction implicitly without the need to
explicitly reference a :class:`.Connection`.
.. note::
.. deprecated:: 1.3
The "threadlocal" feature is generally discouraged. It's
designed for a particular pattern of usage which is generally
considered as a legacy pattern. It has **no impact** on the "thread safety"
of SQLAlchemy components
or one's application. It also should not be used when using an ORM
The "threadlocal" engine strategy is deprecated, and will be removed
in a future release.
This strategy is designed for a particular pattern of usage which is
generally considered as a legacy pattern. It has **no impact** on the
"thread safety" of SQLAlchemy components or one's application. It also
should not be used when using an ORM
:class:`~sqlalchemy.orm.session.Session` object, as the
:class:`~sqlalchemy.orm.session.Session` itself represents an ongoing
transaction and itself handles the job of maintaining connection and
transactional resources.
.. seealso::
:ref:`change_4393_threadlocal`
Enabling ``threadlocal`` is achieved as follows::
db = create_engine('mysql://localhost/test', strategy='threadlocal')
@@ -645,7 +714,6 @@ the need for separate installation. Use the ``register()`` function as follows
The above will respond to ``create_engine("mysql+foodialect://")`` and load the
``MyMySQLDialect`` class from the ``myapp.dialect`` module.
.. versionadded:: 0.8
Connection / Engine API
=======================
@@ -656,6 +724,9 @@ Connection / Engine API
.. autoclass:: Connectable
:members:
.. autoclass:: CreateEnginePlugin
:members:
.. autoclass:: Engine
:members:
+65 -32
View File
@@ -3,9 +3,9 @@
.. module:: sqlalchemy.schema
=================================
================================
Defining Constraints and Indexes
=================================
================================
This section will discuss SQL :term:`constraints` and indexes. In SQLAlchemy
the key classes include :class:`.ForeignKeyConstraint` and :class:`.Index`.
@@ -145,7 +145,7 @@ most forms of ALTER. Given a schema like::
)
When we call upon :meth:`.MetaData.create_all` on a backend such as the
Postgresql backend, the cycle between these two tables is resolved and the
PostgreSQL backend, the cycle between these two tables is resolved and the
constraints are created separately:
.. sourcecode:: pycon+sql
@@ -300,9 +300,8 @@ arguments. The value is any string which will be output after the appropriate
)
)
Note that these clauses are not supported on SQLite, and require ``InnoDB``
tables when used with MySQL. They may also not be supported on other
databases.
Note that these clauses require ``InnoDB`` tables when used with MySQL.
They may also not be supported on other databases.
UNIQUE Constraint
@@ -391,7 +390,7 @@ option of being configured directly::
:class:`.PrimaryKeyConstraint` - detailed API documentation.
Setting up Constraints when using the Declarative ORM Extension
----------------------------------------------------------------
---------------------------------------------------------------
The :class:`.Table` is the SQLAlchemy Core construct that allows one to define
table metadata, which among other things can be used by the SQLAlchemy ORM
@@ -415,7 +414,7 @@ produced inline with the table definition, the database usually has a system
in place in which names are automatically assigned to these constraints, if
a name is not otherwise specified. When an existing database table is altered
in a database using a command such as ``ALTER TABLE``, this command typically
needs to specify expicit names for new constraints as well as be able to
needs to specify explicit names for new constraints as well as be able to
specify the name of an existing constraint that is to be dropped or modified.
Constraints can be named explicitly using the :paramref:`.Constraint.name` parameter,
@@ -426,7 +425,7 @@ parameters which create :class:`.UniqueConstraint` and :class:`.Index` objects
without an explicit name being specified.
The use case of alteration of existing tables and constraints can be handled
by schema migration tools such as `Alembic <http://http://alembic.readthedocs.org/>`_.
by schema migration tools such as `Alembic <https://alembic.sqlalchemy.org/>`_.
However, neither Alembic nor SQLAlchemy currently create names for constraint
objects where the name is otherwise unspecified, leading to the case where
being able to alter existing constraints means that one must reverse-engineer
@@ -507,14 +506,53 @@ object that is created using the :paramref:`.Column.index` parameter::
>>> DEFAULT_NAMING_CONVENTION
immutabledict({'ix': 'ix_%(column_0_label)s'})
The tokens available include ``%(table_name)s``,
``%(referred_table_name)s``, ``%(column_0_name)s``, ``%(column_0_label)s``,
``%(column_0_key)s``, ``%(referred_column_0_name)s``, and ``%(constraint_name)s``;
the documentation for :paramref:`.MetaData.naming_convention` describes each
individually. New tokens can also be added, by specifying an additional
token and a callable within the naming_convention dictionary. For example,
if we wanted to name our foreign key constraints using a GUID scheme,
we could do that as follows::
The tokens available include ``%(table_name)s``, ``%(referred_table_name)s``,
``%(column_0_name)s``, ``%(column_0_label)s``, ``%(column_0_key)s``,
``%(referred_column_0_name)s``, and ``%(constraint_name)s``, as well as
multiple-column versions of each including ``%(column_0N_name)s``,
``%(column_0_N_name)s``, ``%(referred_column_0_N_name)s`` which render all
column names separated with or without an underscore. The documentation for
:paramref:`.MetaData.naming_convention` has further detail on each of these
conventions.
When a generated name, particularly those that use the multiple-column tokens,
is too long for the identifier length limit of the target database
(for example, PostgreSQL has a limit of 63 characters), the name will be
deterministically truncated using a 4-character suffix based on the md5
hash of the long name. For example, the naming convention below will
generate very long names given the column names in use::
metadata = MetaData(naming_convention={
"uq": "uq_%(table_name)s_%(column_0_N_name)s"
})
long_names = Table(
'long_names', metadata,
Column('information_channel_code', Integer, key='a'),
Column('billing_convention_name', Integer, key='b'),
Column('product_identifier', Integer, key='c'),
UniqueConstraint('a', 'b', 'c')
)
On the PostgreSQL dialect, names longer than 63 characters will be truncated
as in the following example::
CREATE TABLE long_names (
information_channel_code INTEGER,
billing_convention_name INTEGER,
product_identifier INTEGER,
CONSTRAINT uq_long_names_information_channel_code_billing_conventi_a79e
UNIQUE (information_channel_code, billing_convention_name, product_identifier)
)
The above suffix ``a79e`` is based on the md5 hash of the long name and will
generate the same value every time to produce consistent names for a given
schema.
New tokens can also be added, by specifying an additional token
and a callable within the naming_convention dictionary. For example, if we
wanted to name our foreign key constraints using a GUID scheme, we could do
that as follows::
import uuid
@@ -561,14 +599,17 @@ name as follows::
:paramref:`.MetaData.naming_convention` - for additional usage details
as well as a listing of all available naming components.
:ref:`alembic:tutorial_constraint_names` - in the Alembic documentation.
`The Importance of Naming Constraints <https://alembic.sqlalchemy.org/en/latest/naming.html>`_ - in the Alembic documentation.
.. versionadded:: 0.9.2 Added the :paramref:`.MetaData.naming_convention` argument.
.. versionadded:: 1.3.0 added multi-column naming tokens such as ``%(column_0_N_name)s``.
Generated names that go beyond the character limit for the target database will be
deterministically truncated.
.. _naming_check_constraints:
Naming CHECK Constraints
~~~~~~~~~~~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~~~~~~~~~
The :class:`.CheckConstraint` object is configured against an arbitrary
SQL expression, which can have any number of columns present, and additionally
@@ -640,7 +681,7 @@ structure of the expression will determine which column is noted as
.. _naming_schematypes:
Configuring Naming for Boolean, Enum, and other schema types
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The :class:`.SchemaType` class refers to type objects such as :class:`.Boolean`
and :class:`.Enum` which generate a CHECK constraint accompanying the type.
@@ -671,7 +712,7 @@ The above table will produce the constraint name ``ck_foo_flag_bool``::
)
The :class:`.SchemaType` classes use special internal symbols so that
the naming convention is only determined at DDL compile time. On Postgresql,
the naming convention is only determined at DDL compile time. On PostgreSQL,
there's a native BOOLEAN type, so the CHECK constraint of :class:`.Boolean`
is not needed; we are safe to set up a :class:`.Boolean` type without a
name, even though a naming convention is in place for check constraints.
@@ -725,7 +766,6 @@ Constraints API
:members:
:inherited-members:
.. autoclass:: PrimaryKeyConstraint
:members:
:inherited-members:
@@ -814,10 +854,6 @@ identify columns::
Index('idx_col34', 'col3', 'col4', unique=True)
)
.. versionadded:: 0.7
Support of "inline" definition inside the :class:`.Table`
for :class:`.Index`\ .
The :class:`~sqlalchemy.schema.Index` object also supports its own ``create()`` method:
.. sourcecode:: python+sql
@@ -829,7 +865,7 @@ The :class:`~sqlalchemy.schema.Index` object also supports its own ``create()``
.. _schema_indexes_functional:
Functional Indexes
~~~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~~~
:class:`.Index` supports SQL and function expressions, as supported by the
target backend. To create an index against a column using a descending
@@ -839,16 +875,13 @@ value, the :meth:`.ColumnElement.desc` modifier may be used::
Index('someindex', mytable.c.somecol.desc())
Or with a backend that supports functional indexes such as Postgresql,
Or with a backend that supports functional indexes such as PostgreSQL,
a "case insensitive" index can be created using the ``lower()`` function::
from sqlalchemy import func, Index
Index('someindex', func.lower(mytable.c.somecol))
.. versionadded:: 0.8 :class:`.Index` supports SQL expressions and functions
as well as plain columns.
Index API
---------
+128 -44
View File
@@ -3,13 +3,13 @@
.. _types_custom:
Custom Types
------------
============
A variety of methods exist to redefine the behavior of existing types
as well as to provide new ones.
Overriding Type Compilation
~~~~~~~~~~~~~~~~~~~~~~~~~~~
---------------------------
A frequent need is to force the "string" version of a type, that is
the one rendered in a CREATE TABLE statement or other SQL function
@@ -38,7 +38,7 @@ See the section :ref:`type_compilation_extension`, a subsection of
.. _types_typedecorator:
Augmenting Existing Types
~~~~~~~~~~~~~~~~~~~~~~~~~
-------------------------
The :class:`.TypeDecorator` allows the creation of custom types which
add bind-parameter and result-processing behavior to an existing
@@ -59,7 +59,8 @@ to and from the database is required.
TypeDecorator Recipes
~~~~~~~~~~~~~~~~~~~~~
---------------------
A few key :class:`.TypeDecorator` recipes follow.
.. _coerce_to_unicode:
@@ -123,7 +124,7 @@ Backend-agnostic GUID Type
^^^^^^^^^^^^^^^^^^^^^^^^^^
Receives and returns Python uuid() objects. Uses the PG UUID type
when using Postgresql, CHAR(32) on other backends, storing them
when using PostgreSQL, CHAR(32) on other backends, storing them
in stringified hex format. Can be modified to store
binary in CHAR(16) if desired::
@@ -134,7 +135,7 @@ binary in CHAR(16) if desired::
class GUID(TypeDecorator):
"""Platform-independent GUID type.
Uses Postgresql's UUID type, otherwise uses
Uses PostgreSQL's UUID type, otherwise uses
CHAR(32), storing as stringified hex values.
"""
@@ -153,19 +154,21 @@ binary in CHAR(16) if desired::
return str(value)
else:
if not isinstance(value, uuid.UUID):
return "%.32x" % uuid.UUID(value)
return "%.32x" % uuid.UUID(value).int
else:
# hexstring
return "%.32x" % value
return "%.32x" % value.int
def process_result_value(self, value, dialect):
if value is None:
return value
else:
return uuid.UUID(value)
if not isinstance(value, uuid.UUID):
value = uuid.UUID(value)
return value
Marshal JSON Strings
^^^^^^^^^^^^^^^^^^^^^
^^^^^^^^^^^^^^^^^^^^
This type uses ``simplejson`` to marshal Python data structures
to/from JSON. Can be modified to use Python's builtin json encoder::
@@ -195,19 +198,95 @@ to/from JSON. Can be modified to use Python's builtin json encoder::
value = json.loads(value)
return value
Note that the ORM by default will not detect "mutability" on such a type -
Adding Mutability
~~~~~~~~~~~~~~~~~
The ORM by default will not detect "mutability" on such a type as above -
meaning, in-place changes to values will not be detected and will not be
flushed. Without further steps, you instead would need to replace the existing
value with a new one on each parent object to detect changes. Note that
there's nothing wrong with this, as many applications may not require that the
values are ever mutated once created. For those which do have this requirement,
support for mutability is best applied using the ``sqlalchemy.ext.mutable``
extension - see the example in :ref:`mutable_toplevel`.
flushed. Without further steps, you instead would need to replace the existing
value with a new one on each parent object to detect changes::
obj.json_value["key"] = "value" # will *not* be detected by the ORM
obj.json_value = {"key": "value"} # *will* be detected by the ORM
The above limitation may be
fine, as many applications may not require that the values are ever mutated
once created. For those which do have this requirement, support for mutability
is best applied using the ``sqlalchemy.ext.mutable`` extension. For a
dictionary-oriented JSON structure, we can apply this as::
json_type = MutableDict.as_mutable(JSONEncodedDict)
class MyClass(Base):
# ...
json_data = Column(json_type)
.. seealso::
:ref:`mutable_toplevel`
Dealing with Comparison Operations
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The default behavior of :class:`.TypeDecorator` is to coerce the "right hand side"
of any expression into the same type. For a type like JSON, this means that
any operator used must make sense in terms of JSON. For some cases,
users may wish for the type to behave like JSON in some circumstances, and
as plain text in others. One example is if one wanted to handle the
LIKE operator for the JSON type. LIKE makes no sense against a JSON structure,
but it does make sense against the underlying textual representation. To
get at this with a type like ``JSONEncodedDict``, we need to
**coerce** the column to a textual form using :func:`.cast` or
:func:`.type_coerce` before attempting to use this operator::
from sqlalchemy import type_coerce, String
stmt = select([my_table]).where(
type_coerce(my_table.c.json_data, String).like('%foo%'))
:class:`.TypeDecorator` provides a built-in system for working up type
translations like these based on operators. If we wanted to frequently use the
LIKE operator with our JSON object interpreted as a string, we can build it
into the type by overriding the :meth:`.TypeDecorator.coerce_compared_value`
method::
from sqlalchemy.sql import operators
from sqlalchemy import String
class JSONEncodedDict(TypeDecorator):
impl = VARCHAR
def coerce_compared_value(self, op, value):
if op in (operators.like_op, operators.notlike_op):
return String()
else:
return self
def process_bind_param(self, value, dialect):
if value is not None:
value = json.dumps(value)
return value
def process_result_value(self, value, dialect):
if value is not None:
value = json.loads(value)
return value
Above is just one approach to handling an operator like "LIKE". Other
applications may wish to raise ``NotImplementedError`` for operators that
have no meaning with a JSON object such as "LIKE", rather than automatically
coercing to text.
.. _replacing_processors:
Replacing the Bind/Result Processing of Existing Types
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
------------------------------------------------------
Most augmentation of type behavior at the bind/result level
is achieved using :class:`.TypeDecorator`. For the rare scenario
@@ -245,13 +324,13 @@ cursor directly::
return None
return process
def adapt(self, impltype):
def adapt(self, impltype, **kw):
return MySpecialTime(self.special_argument)
.. _types_sql_value_processing:
Applying SQL-level Bind/Result Processing
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-----------------------------------------
As seen in the sections :ref:`types_typedecorator` and :ref:`replacing_processors`,
SQLAlchemy allows Python functions to be invoked both when parameters are sent
@@ -261,7 +340,7 @@ possible to define SQL-level transformations as well. The rationale here is whe
only the relational database contains a particular series of functions that are necessary
to coerce incoming and outgoing data between an application and persistence format.
Examples include using database-defined encryption/decryption functions, as well
as stored procedures that handle geographic data. The Postgis extension to Postgresql
as stored procedures that handle geographic data. The PostGIS extension to PostgreSQL
includes an extensive array of SQL functions that are necessary for coercing
data into particular formats.
@@ -271,7 +350,7 @@ can include implementations of
when defined to return a non-``None`` value should return a :class:`.ColumnElement`
expression to be injected into the SQL statement, either surrounding
bound parameters or a column expression. For example, to build a ``Geometry``
type which will apply the Postgis function ``ST_GeomFromText`` to all outgoing
type which will apply the PostGIS function ``ST_GeomFromText`` to all outgoing
values and the function ``ST_AsText`` to all incoming data, we can create
our own subclass of :class:`.UserDefinedType` which provides these methods
in conjunction with :data:`~.sqlalchemy.sql.expression.func`::
@@ -297,8 +376,8 @@ and use it in a :func:`.select` construct::
Column('geom_data', Geometry)
)
print select([geometry]).where(
geometry.c.geom_data == 'LINESTRING(189412 252431,189631 259122)')
print(select([geometry]).where(
geometry.c.geom_data == 'LINESTRING(189412 252431,189631 259122)'))
The resulting SQL embeds both functions as appropriate. ``ST_AsText``
is applied to the columns clause so that the return value is run through
@@ -315,7 +394,7 @@ with the labeling of the wrapped expression. Such as, if we rendered
a :func:`.select` against a :func:`.label` of our expression, the string
label is moved to the outside of the wrapped expression::
print select([geometry.c.geom_data.label('my_data')])
print(select([geometry.c.geom_data.label('my_data')]))
Output::
@@ -324,7 +403,7 @@ Output::
For an example of subclassing a built in type directly, we subclass
:class:`.postgresql.BYTEA` to provide a ``PGPString``, which will make use of the
Postgresql ``pgcrypto`` extension to encrpyt/decrypt values
PostgreSQL ``pgcrypto`` extension to encrypt/decrypt values
transparently::
from sqlalchemy import create_engine, String, select, func, \
@@ -361,10 +440,10 @@ transparently::
conn.execute(message.insert(), username="some user",
message="this is my message")
print conn.scalar(
print(conn.scalar(
select([message.c.message]).\
where(message.c.username == "some user")
)
))
The ``pgp_sym_encrypt`` and ``pgp_sym_decrypt`` functions are applied
to the INSERT and SELECT statements::
@@ -380,17 +459,14 @@ to the INSERT and SELECT statements::
{'pgp_sym_decrypt_1': 'this is my passphrase', 'username_1': 'some user'}
.. versionadded:: 0.8 Added the :meth:`.TypeEngine.bind_expression` and
:meth:`.TypeEngine.column_expression` methods.
.. seealso::
See also:
:ref:`examples_postgis`
:ref:`examples_postgis`
.. _types_operators:
Redefining and Creating New Operators
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-------------------------------------
SQLAlchemy Core defines a fixed set of expression operators available to all column expressions.
Some of these operations have the effect of overloading Python's built in operators;
@@ -425,7 +501,7 @@ associated with the :class:`.Integer` type.
Usage::
>>> sometable = Table("sometable", metadata, Column("data", MyInt))
>>> print sometable.c.data + 5
>>> print(sometable.c.data + 5)
sometable.data goofy :data_1
The implementation for :meth:`.ColumnOperators.__add__` is consulted
@@ -436,6 +512,15 @@ expression object produces a new SQL expression construct. Above, we
could just as well have said ``self.expr.op("goofy")(other)`` instead
of ``self.op("goofy")(other)``.
When using :meth:`.Operators.op` for comparison operations that return a
boolean result, the :paramref:`.Operators.op.is_comparison` flag should be
set to ``True``::
class MyInt(Integer):
class comparator_factory(Integer.Comparator):
def is_frobnozzled(self, other):
return self.op("--is_frobnozzled->", is_comparison=True)(other)
New methods added to a :class:`.TypeEngine.Comparator` are exposed on an
owning SQL expression
using a ``__getattr__`` scheme, which exposes methods added to
@@ -452,13 +537,12 @@ to integers::
Using the above type::
>>> print sometable.c.data.log(5)
>>> print(sometable.c.data.log(5))
log(:log_1, :log_2)
Unary operations
are also possible. For example, to add an implementation of the
Postgresql factorial operator, we combine the :class:`.UnaryExpression` construct
PostgreSQL factorial operator, we combine the :class:`.UnaryExpression` construct
along with a :class:`.custom_op` to produce the factorial expression::
from sqlalchemy import Integer
@@ -475,19 +559,19 @@ along with a :class:`.custom_op` to produce the factorial expression::
Using the above type::
>>> from sqlalchemy.sql import column
>>> print column('x', MyInteger).factorial()
>>> print(column('x', MyInteger).factorial())
x !
See also:
.. seealso::
:attr:`.TypeEngine.comparator_factory`
:meth:`.Operators.op`
:attr:`.TypeEngine.comparator_factory`
.. versionadded:: 0.8 The expression system was enhanced to support
customization of operators on a per-type level.
Creating New Types
~~~~~~~~~~~~~~~~~~
------------------
The :class:`.UserDefinedType` class is provided as a simple base class
for defining entirely new database types. Use this to represent native
+142 -134
View File
@@ -20,11 +20,120 @@ required, SQLAlchemy offers two techniques which can be used to add any DDL
based on any condition, either accompanying the standard generation of tables
or by itself.
Custom DDL
----------
Custom DDL phrases are most easily achieved using the
:class:`~sqlalchemy.schema.DDL` construct. This construct works like all the
other DDL elements except it accepts a string which is the text to be emitted:
.. sourcecode:: python+sql
event.listen(
metadata,
"after_create",
DDL("ALTER TABLE users ADD CONSTRAINT "
"cst_user_name_length "
" CHECK (length(user_name) >= 8)")
)
A more comprehensive method of creating libraries of DDL constructs is to use
custom compilation - see :ref:`sqlalchemy.ext.compiler_toplevel` for
details.
.. _schema_ddl_sequences:
Controlling DDL Sequences
-------------------------
The :class:`~.schema.DDL` construct introduced previously also has the
ability to be invoked conditionally based on inspection of the
database. This feature is available using the :meth:`.DDLElement.execute_if`
method. For example, if we wanted to create a trigger but only on
the PostgreSQL backend, we could invoke this as::
mytable = Table(
'mytable', metadata,
Column('id', Integer, primary_key=True),
Column('data', String(50))
)
trigger = DDL(
"CREATE TRIGGER dt_ins BEFORE INSERT ON mytable "
"FOR EACH ROW BEGIN SET NEW.data='ins'; END"
)
event.listen(
mytable,
'after_create',
trigger.execute_if(dialect='postgresql')
)
The :paramref:`.DDLElement.execute_if.dialect` keyword also accepts a tuple
of string dialect names::
event.listen(
mytable,
"after_create",
trigger.execute_if(dialect=('postgresql', 'mysql'))
)
event.listen(
mytable,
"before_drop",
trigger.execute_if(dialect=('postgresql', 'mysql'))
)
The :meth:`.DDLElement.execute_if` method can also work against a callable
function that will receive the database connection in use. In the
example below, we use this to conditionally create a CHECK constraint,
first looking within the PostgreSQL catalogs to see if it exists:
.. sourcecode:: python+sql
def should_create(ddl, target, connection, **kw):
row = connection.execute(
"select conname from pg_constraint where conname='%s'" %
ddl.element.name).scalar()
return not bool(row)
def should_drop(ddl, target, connection, **kw):
return not should_create(ddl, target, connection, **kw)
event.listen(
users,
"after_create",
DDL(
"ALTER TABLE users ADD CONSTRAINT "
"cst_user_name_length CHECK (length(user_name) >= 8)"
).execute_if(callable_=should_create)
)
event.listen(
users,
"before_drop",
DDL(
"ALTER TABLE users DROP CONSTRAINT cst_user_name_length"
).execute_if(callable_=should_drop)
)
{sql}users.create(engine)
CREATE TABLE users (
user_id SERIAL NOT NULL,
user_name VARCHAR(40) NOT NULL,
PRIMARY KEY (user_id)
)
select conname from pg_constraint where conname='cst_user_name_length'
ALTER TABLE users ADD CONSTRAINT cst_user_name_length CHECK (length(user_name) >= 8){stop}
{sql}users.drop(engine)
select conname from pg_constraint where conname='cst_user_name_length'
ALTER TABLE users DROP CONSTRAINT cst_user_name_length
DROP TABLE users{stop}
Using the built-in DDLElement Classes
-------------------------------------
The ``sqlalchemy.schema`` package contains SQL expression constructs that
provide DDL expressions. For example, to produce a ``CREATE TABLE`` statement:
@@ -42,127 +151,39 @@ provide DDL expressions. For example, to produce a ``CREATE TABLE`` statement:
){stop}
Above, the :class:`~sqlalchemy.schema.CreateTable` construct works like any
other expression construct (such as ``select()``, ``table.insert()``, etc.). A
full reference of available constructs is in :ref:`schema_api_ddl`.
other expression construct (such as ``select()``, ``table.insert()``, etc.).
All of SQLAlchemy's DDL oriented constructs are subclasses of
the :class:`.DDLElement` base class; this is the base of all the
objects corresponding to CREATE and DROP as well as ALTER,
not only in SQLAlchemy but in Alembic Migrations as well.
A full reference of available constructs is in :ref:`schema_api_ddl`.
The DDL constructs all extend a common base class which provides the
capability to be associated with an individual
:class:`~sqlalchemy.schema.Table` or :class:`~sqlalchemy.schema.MetaData`
object, to be invoked upon create/drop events. Consider the example of a table
which contains a CHECK constraint:
User-defined DDL constructs may also be created as subclasses of
:class:`.DDLElement` itself. The documentation in
:ref:`sqlalchemy.ext.compiler_toplevel` has several examples of this.
.. sourcecode:: python+sql
The event-driven DDL system described in the previous section
:ref:`schema_ddl_sequences` is available with other :class:`.DDLElement`
objects as well. However, when dealing with the built-in constructs
such as :class:`.CreateIndex`, :class:`.CreateSequence`, etc, the event
system is of **limited** use, as methods like :meth:`.Table.create` and
:meth:`.MetaData.create_all` will invoke these constructs unconditionally.
In a future SQLAlchemy release, the DDL event system including conditional
execution will taken into account for built-in constructs that currently
invoke in all cases.
users = Table('users', metadata,
Column('user_id', Integer, primary_key=True),
Column('user_name', String(40), nullable=False),
CheckConstraint('length(user_name) >= 8',name="cst_user_name_length")
)
{sql}users.create(engine)
CREATE TABLE users (
user_id SERIAL NOT NULL,
user_name VARCHAR(40) NOT NULL,
PRIMARY KEY (user_id),
CONSTRAINT cst_user_name_length CHECK (length(user_name) >= 8)
){stop}
The above table contains a column "user_name" which is subject to a CHECK
constraint that validates that the length of the string is at least eight
characters. When a ``create()`` is issued for this table, DDL for the
:class:`~sqlalchemy.schema.CheckConstraint` will also be issued inline within
the table definition.
The :class:`~sqlalchemy.schema.CheckConstraint` construct can also be
constructed externally and associated with the
:class:`~sqlalchemy.schema.Table` afterwards::
constraint = CheckConstraint('length(user_name) >= 8',name="cst_user_name_length")
users.append_constraint(constraint)
So far, the effect is the same. However, if we create DDL elements
corresponding to the creation and removal of this constraint, and associate
them with the :class:`.Table` as events, these new events
will take over the job of issuing DDL for the constraint. Additionally, the
constraint will be added via ALTER:
.. sourcecode:: python+sql
from sqlalchemy import event
event.listen(
users,
"after_create",
AddConstraint(constraint)
)
event.listen(
users,
"before_drop",
DropConstraint(constraint)
)
{sql}users.create(engine)
CREATE TABLE users (
user_id SERIAL NOT NULL,
user_name VARCHAR(40) NOT NULL,
PRIMARY KEY (user_id)
)
ALTER TABLE users ADD CONSTRAINT cst_user_name_length CHECK (length(user_name) >= 8){stop}
{sql}users.drop(engine)
ALTER TABLE users DROP CONSTRAINT cst_user_name_length
DROP TABLE users{stop}
The real usefulness of the above becomes clearer once we illustrate the
:meth:`.DDLElement.execute_if` method. This method returns a modified form of
the DDL callable which will filter on criteria before responding to a
received event. It accepts a parameter ``dialect``, which is the string
name of a dialect or a tuple of such, which will limit the execution of the
item to just those dialects. It also accepts a ``callable_`` parameter which
may reference a Python callable which will be invoked upon event reception,
returning ``True`` or ``False`` indicating if the event should proceed.
If our :class:`~sqlalchemy.schema.CheckConstraint` was only supported by
Postgresql and not other databases, we could limit its usage to just that dialect::
event.listen(
users,
'after_create',
AddConstraint(constraint).execute_if(dialect='postgresql')
)
event.listen(
users,
'before_drop',
DropConstraint(constraint).execute_if(dialect='postgresql')
)
Or to any set of dialects::
event.listen(
users,
"after_create",
AddConstraint(constraint).execute_if(dialect=('postgresql', 'mysql'))
)
event.listen(
users,
"before_drop",
DropConstraint(constraint).execute_if(dialect=('postgresql', 'mysql'))
)
When using a callable, the callable is passed the ddl element, the
:class:`.Table` or :class:`.MetaData`
object whose "create" or "drop" event is in progress, and the
:class:`.Connection` object being used for the
operation, as well as additional information as keyword arguments. The
callable can perform checks, such as whether or not a given item already
exists. Below we define ``should_create()`` and ``should_drop()`` callables
that check for the presence of our named constraint:
We can illustrate an event-driven
example with the :class:`.AddConstraint` and :class:`.DropConstraint`
constructs, as the event-driven system will work for CHECK and UNIQUE
constraints, using these as we did in our previous example of
:meth:`.DDLElement.execute_if`:
.. sourcecode:: python+sql
def should_create(ddl, target, connection, **kw):
row = connection.execute("select conname from pg_constraint where conname='%s'" % ddl.element.name).scalar()
row = connection.execute(
"select conname from pg_constraint where conname='%s'" %
ddl.element.name).scalar()
return not bool(row)
def should_drop(ddl, target, connection, **kw):
@@ -194,26 +215,12 @@ that check for the presence of our named constraint:
ALTER TABLE users DROP CONSTRAINT cst_user_name_length
DROP TABLE users{stop}
Custom DDL
----------
Custom DDL phrases are most easily achieved using the
:class:`~sqlalchemy.schema.DDL` construct. This construct works like all the
other DDL elements except it accepts a string which is the text to be emitted:
.. sourcecode:: python+sql
event.listen(
metadata,
"after_create",
DDL("ALTER TABLE users ADD CONSTRAINT "
"cst_user_name_length "
" CHECK (length(user_name) >= 8)")
)
A more comprehensive method of creating libraries of DDL constructs is to use
custom compilation - see :ref:`sqlalchemy.ext.compiler_toplevel` for
details.
While the above example is against the built-in :class:`.AddConstraint`
and :class:`.DropConstraint` objects, the main usefulness of DDL events
for now remains focused on the use of the :class:`.DDL` construct itself,
as well as with user-defined subclasses of :class:`.DDLElement` that aren't
already part of the :meth:`.MetaData.create_all`, :meth:`.Table.create`,
and corresponding "drop" processes.
.. _schema_api_ddl:
@@ -233,6 +240,7 @@ DDL Expression Constructs API
:members:
:undoc-members:
.. autoclass:: _CreateDropBase
.. autoclass:: CreateTable
:members:
+298 -160
View File
@@ -5,7 +5,7 @@
.. _metadata_defaults:
Column Insert/Update Defaults
==============================
=============================
SQLAlchemy provides a very rich featureset regarding column level events which
take place during INSERT and UPDATE statements. Options include:
@@ -45,7 +45,7 @@ defaults)::
Python-Executed Functions
-------------------------
The ``default`` and ``onupdate`` keyword arguments also accept Python
The :paramref:`.Column.default` and :paramref:`.Column.onupdate` keyword arguments also accept Python
functions. These functions are invoked at the time of insert or update if no
other value for that column is supplied, and the value returned is used for
the column's value. Below illustrates a crude "sequence" that assigns an
@@ -67,12 +67,12 @@ built-in capabilities of the database should normally be used, which may
include sequence objects or other autoincrementing capabilities. For primary
key columns, SQLAlchemy will in most cases use these capabilities
automatically. See the API documentation for
:class:`~sqlalchemy.schema.Column` including the ``autoincrement`` flag, as
:class:`~sqlalchemy.schema.Column` including the :paramref:`.Column.autoincrement` flag, as
well as the section on :class:`~sqlalchemy.schema.Sequence` later in this
chapter for background on standard primary key generation techniques.
To illustrate onupdate, we assign the Python ``datetime`` function ``now`` to
the ``onupdate`` attribute::
the :paramref:`.Column.onupdate` attribute::
import datetime
@@ -90,44 +90,64 @@ as the function itself without calling it (i.e. there are no parenthesis
following) - SQLAlchemy will execute the function at the time the statement
executes.
.. _context_default_functions:
Context-Sensitive Default Functions
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
The Python functions used by ``default`` and ``onupdate`` may also make use of
the current statement's context in order to determine a value. The `context`
of a statement is an internal SQLAlchemy object which contains all information
about the statement being executed, including its source expression, the
parameters associated with it and the cursor. The typical use case for this
context with regards to default generation is to have access to the other
values being inserted or updated on the row. To access the context, provide a
function that accepts a single ``context`` argument::
The Python functions used by :paramref:`.Column.default` and
:paramref:`.Column.onupdate` may also make use of the current statement's
context in order to determine a value. The `context` of a statement is an
internal SQLAlchemy object which contains all information about the statement
being executed, including its source expression, the parameters associated with
it and the cursor. The typical use case for this context with regards to
default generation is to have access to the other values being inserted or
updated on the row. To access the context, provide a function that accepts a
single ``context`` argument::
def mydefault(context):
return context.current_parameters['counter'] + 12
return context.get_current_parameters()['counter'] + 12
t = Table('mytable', meta,
Column('counter', Integer),
Column('counter_plus_twelve', Integer, default=mydefault, onupdate=mydefault)
)
Above we illustrate a default function which will execute for all INSERT and
UPDATE statements where a value for ``counter_plus_twelve`` was otherwise not
provided, and the value will be that of whatever value is present in the
execution for the ``counter`` column, plus the number 12.
The above default generation function is applied so that it will execute for
all INSERT and UPDATE statements where a value for ``counter_plus_twelve`` was
otherwise not provided, and the value will be that of whatever value is present
in the execution for the ``counter`` column, plus the number 12.
While the context object passed to the default function has many attributes,
the ``current_parameters`` member is a special member provided only during the
execution of a default function for the purposes of deriving defaults from its
existing values. For a single statement that is executing many sets of bind
parameters, the user-defined function is called for each set of parameters,
and ``current_parameters`` will be provided with each individual parameter set
for each execution.
For a single statement that is being executed using "executemany" style, e.g.
with multiple parameter sets passed to :meth:`.Connection.execute`, the user-
defined function is called once for each set of parameters. For the use case of
a multi-valued :class:`.Insert` construct (e.g. with more than one VALUES
clause set up via the :meth:`.Insert.values` method), the user-defined function
is also called once for each set of parameters.
SQL Expressions
---------------
When the function is invoked, the special method
:meth:`.DefaultExecutionContext.get_current_parameters` is available from
the context object (an subclass of :class:`.DefaultExecutionContext`). This
method returns a dictionary of column-key to values that represents the
full set of values for the INSERT or UPDATE statement. In the case of a
multi-valued INSERT construct, the subset of parameters that corresponds to
the individual VALUES clause is isolated from the full parameter dictionary
and returned alone.
The "default" and "onupdate" keywords may also be passed SQL expressions,
including select statements or direct function calls::
.. versionadded:: 1.2
Added :meth:`.DefaultExecutionContext.get_current_parameters` method,
which improves upon the still-present
:attr:`.DefaultExecutionContext.current_parameters` attribute
by offering the service of organizing multiple VALUES clauses
into individual parameter dictionaries.
Client-Invoked SQL Expressions
------------------------------
The :paramref:`.Column.default` and :paramref:`.Column.onupdate` keywords may
also be passed SQL expressions, which are in most cases rendered inline within the
INSERT or UPDATE statement::
t = Table("mytable", meta,
Column('id', Integer, primary_key=True),
@@ -136,7 +156,7 @@ including select statements or direct function calls::
Column('create_date', DateTime, default=func.now()),
# define 'key' to pull its default from the 'keyvalues' table
Column('key', String(20), default=keyvalues.select(keyvalues.c.type='type1', limit=1)),
Column('key', String(20), default=select([keyvalues.c.key]).where(keyvalues.c.type='type1')),
# define 'last_modified' to use the current_timestamp SQL function on update
Column('last_modified', DateTime, onupdate=func.utc_timestamp())
@@ -147,141 +167,130 @@ Above, the ``create_date`` column will be populated with the result of the
or ``CURRENT_TIMESTAMP`` in most cases) during an INSERT statement, and the
``key`` column with the result of a SELECT subquery from another table. The
``last_modified`` column will be populated with the value of
``UTC_TIMESTAMP()``, a function specific to MySQL, when an UPDATE statement is
the SQL ``UTC_TIMESTAMP()`` MySQL function when an UPDATE statement is
emitted for this table.
Note that when using ``func`` functions, unlike when using Python `datetime`
functions we *do* call the function, i.e. with parenthesis "()" - this is
because what we want in this case is the return value of the function, which
is the SQL expression construct that will be rendered into the INSERT or
UPDATE statement.
.. note::
The above SQL functions are usually executed "inline" with the INSERT or
UPDATE statement being executed, meaning, a single statement is executed which
embeds the given expressions or subqueries within the VALUES or SET clause of
the statement. Although in some cases, the function is "pre-executed" in a
SELECT statement of its own beforehand. This happens when all of the following
is true:
When using SQL functions with the :attr:`.func` construct, we "call" the
named function, e.g. with parenthesis as in ``func.now()``. This differs
from when we specify a Python callable as a default such as
``datetime.datetime``, where we pass the function itself, but we don't
invoke it ourselves. In the case of a SQL function, invoking
``func.now()`` returns the SQL expression object that will render the
"NOW" function into the SQL being emitted.
* the column is a primary key column
* the database dialect does not support a usable ``cursor.lastrowid`` accessor
(or equivalent); this currently includes PostgreSQL, Oracle, and Firebird, as
well as some MySQL dialects.
* the dialect does not support the "RETURNING" clause or similar, or the
``implicit_returning`` flag is set to ``False`` for the dialect. Dialects
which support RETURNING currently include Postgresql, Oracle, Firebird, and
MS-SQL.
* the statement is a single execution, i.e. only supplies one set of
parameters and doesn't use "executemany" behavior
* the ``inline=True`` flag is not set on the
:class:`~sqlalchemy.sql.expression.Insert()` or
:class:`~sqlalchemy.sql.expression.Update()` construct, and the statement has
not defined an explicit `returning()` clause.
Default and update SQL expressions specified by :paramref:`.Column.default` and
:paramref:`.Column.onupdate` are invoked explicitly by SQLAlchemy when an
INSERT or UPDATE statement occurs, typically rendered inline within the DML
statement except in certain cases listed below. This is different than a
"server side" default, which is part of the table's DDL definition, e.g. as
part of the "CREATE TABLE" statement, which are likely more common. For
server side defaults, see the next section :ref:`server_defaults`.
Whether or not the default generation clause "pre-executes" is not something
that normally needs to be considered, unless it is being addressed for
performance reasons.
When a SQL expression indicated by :paramref:`.Column.default` is used with
primary key columns, there are some cases where SQLAlchemy must "pre-execute"
the default generation SQL function, meaning it is invoked in a separate SELECT
statement, and the resulting value is passed as a parameter to the INSERT.
This only occurs for primary key columns for an INSERT statement that is being
asked to return this primary key value, where RETURNING or ``cursor.lastrowid``
may not be used. An :class:`.Insert` construct that specifies the
:paramref:`~.expression.insert.inline` flag will always render default expressions
inline.
When the statement is executed with a single set of parameters (that is, it is
not an "executemany" style execution), the returned
:class:`~sqlalchemy.engine.ResultProxy` will contain a collection
accessible via ``result.postfetch_cols()`` which contains a list of all
:class:`~sqlalchemy.engine.ResultProxy` will contain a collection accessible
via :meth:`.ResultProxy.postfetch_cols` which contains a list of all
:class:`~sqlalchemy.schema.Column` objects which had an inline-executed
default. Similarly, all parameters which were bound to the statement,
including all Python and SQL expressions which were pre-executed, are present
in the ``last_inserted_params()`` or ``last_updated_params()`` collections on
:class:`~sqlalchemy.engine.ResultProxy`. The ``inserted_primary_key``
collection contains a list of primary key values for the row inserted (a list
so that single-column and composite-column primary keys are represented in the
same format).
default. Similarly, all parameters which were bound to the statement, including
all Python and SQL expressions which were pre-executed, are present in the
:meth:`.ResultProxy.last_inserted_params` or
:meth:`.ResultProxy.last_updated_params` collections on
:class:`~sqlalchemy.engine.ResultProxy`. The
:attr:`.ResultProxy.inserted_primary_key` collection contains a list of primary
key values for the row inserted (a list so that single-column and composite-
column primary keys are represented in the same format).
Server Side Defaults
--------------------
.. _server_defaults:
A variant on the SQL expression default is the ``server_default``, which gets
placed in the CREATE TABLE statement during a ``create()`` operation:
Server-invoked DDL-Explicit Default Expressions
-----------------------------------------------
A variant on the SQL expression default is the :paramref:`.Column.server_default`, which gets
placed in the CREATE TABLE statement during a :meth:`.Table.create` operation:
.. sourcecode:: python+sql
t = Table('test', meta,
Column('abc', String(20), server_default='abc'),
Column('created_at', DateTime, server_default=text("sysdate"))
Column('created_at', DateTime, server_default=func.sysdate()),
Column('index_value', Integer, server_default=text("0"))
)
A create call for the above table will produce::
CREATE TABLE test (
abc varchar(20) default 'abc',
created_at datetime default sysdate
created_at datetime default sysdate,
index_value integer default 0
)
The behavior of ``server_default`` is similar to that of a regular SQL
default; if it's placed on a primary key column for a database which doesn't
have a way to "postfetch" the ID, and the statement is not "inlined", the SQL
expression is pre-executed; otherwise, SQLAlchemy lets the default fire off on
the database side normally.
The above example illustrates the two typical use cases for :paramref:`.Column.server_default`,
that of the SQL function (SYSDATE in the above example) as well as a server-side constant
value (the integer "0" in the above example). It is advisable to use the
:func:`.text` construct for any literal SQL values as opposed to passing the
raw value, as SQLAlchemy does not typically perform any quoting or escaping on
these values.
Like client-generated expressions, :paramref:`.Column.server_default` can accommodate
SQL expressions in general, however it is expected that these will usually be simple
functions and expressions, and not the more complex cases like an embedded SELECT.
.. _triggered_columns:
Triggered Columns
------------------
Marking Implicitly Generated Values, timestamps, and Triggered Columns
----------------------------------------------------------------------
Columns with values set by a database trigger or other external process may be
called out using :class:`.FetchedValue` as a marker::
Columns which generate a new value on INSERT or UPDATE based on other
server-side database mechanisms, such as database-specific auto-generating
behaviors such as seen with TIMESTAMP columns on some platforms, as well as
custom triggers that invoke upon INSERT or UPDATE to generate a new value,
may be called out using :class:`.FetchedValue` as a marker::
t = Table('test', meta,
Column('abc', String(20), server_default=FetchedValue()),
Column('id', Integer, primary_key=True),
Column('abc', TIMESTAMP, server_default=FetchedValue()),
Column('def', String(20), server_onupdate=FetchedValue())
)
.. versionchanged:: 0.8.0b2,0.7.10
The ``for_update`` argument on :class:`.FetchedValue` is set automatically
when specified as the ``server_onupdate`` argument. If using an older version,
specify the onupdate above as ``server_onupdate=FetchedValue(for_update=True)``.
The :class:`.FetchedValue` indicator does not affect the rendered DDL for the
CREATE TABLE. Instead, it marks the column as one that will have a new value
populated by the database during the process of an INSERT or UPDATE statement,
and for supporting databases may be used to indicate that the column should be
part of a RETURNING or OUTPUT clause for the statement. Tools such as the
SQLAlchemy ORM then make use of this marker in order to know how to get at the
value of the column after such an operation. In particular, the
:meth:`.ValuesBase.return_defaults` method can be used with an :class:`.Insert`
or :class:`.Update` construct to indicate that these values should be
returned.
These markers do not emit a "default" clause when the table is created,
however they do set the same internal flags as a static ``server_default``
clause, providing hints to higher-level tools that a "post-fetch" of these
rows should be performed after an insert or update.
For details on using :class:`.FetchedValue` with the ORM, see
:ref:`orm_server_defaults`.
.. note::
.. seealso::
It's generally not appropriate to use :class:`.FetchedValue` in
conjunction with a primary key column, particularly when using the
ORM or any other scenario where the :attr:`.ResultProxy.inserted_primary_key`
attribute is required. This is becaue the "post-fetch" operation requires
that the primary key value already be available, so that the
row can be selected on its primary key.
For a server-generated primary key value, all databases provide special
accessors or other techniques in order to acquire the "last inserted
primary key" column of a table. These mechanisms aren't affected by the presence
of :class:`.FetchedValue`. For special situations where triggers are
used to generate primary key values, and the database in use does not
support the ``RETURNING`` clause, it may be necessary to forego the usage
of the trigger and instead apply the SQL expression or function as a
"pre execute" expression::
t = Table('test', meta,
Column('abc', MyType, default=func.generate_new_value(), primary_key=True)
)
Where above, when :meth:`.Table.insert` is used,
the ``func.generate_new_value()`` expression will be pre-executed
in the context of a scalar ``SELECT`` statement, and the new value will
be applied to the subsequent ``INSERT``, while at the same time being
made available to the :attr:`.ResultProxy.inserted_primary_key`
attribute.
:ref:`orm_server_defaults`
Defining Sequences
-------------------
------------------
SQLAlchemy represents database sequences using the
:class:`~sqlalchemy.schema.Sequence` object, which is considered to be a
special case of "column default". It only has an effect on databases which
have explicit support for sequences, which currently includes Postgresql,
have explicit support for sequences, which currently includes PostgreSQL,
Oracle, and Firebird. The :class:`~sqlalchemy.schema.Sequence` object is
otherwise ignored.
@@ -291,7 +300,10 @@ configured to fire off during UPDATE operations if desired. It is most
commonly used in conjunction with a single integer primary key column::
table = Table("cartitems", meta,
Column("cart_id", Integer, Sequence('cart_id_seq'), primary_key=True),
Column(
"cart_id",
Integer,
Sequence('cart_id_seq', metadata=meta), primary_key=True),
Column("description", String(40)),
Column("createdate", DateTime())
)
@@ -299,45 +311,148 @@ commonly used in conjunction with a single integer primary key column::
Where above, the table "cartitems" is associated with a sequence named
"cart_id_seq". When INSERT statements take place for "cartitems", and no value
is passed for the "cart_id" column, the "cart_id_seq" sequence will be used to
generate a value.
generate a value. Typically, the sequence function is embedded in the
INSERT statement, which is combined with RETURNING so that the newly generated
value can be returned to the Python code::
When the :class:`~sqlalchemy.schema.Sequence` is associated with a table,
CREATE and DROP statements issued for that table will also issue CREATE/DROP
for the sequence object as well, thus "bundling" the sequence object with its
parent table.
INSERT INTO cartitems (cart_id, description, createdate)
VALUES (next_val(cart_id_seq), 'some description', '2015-10-15 12:00:15')
RETURNING cart_id
The :class:`~sqlalchemy.schema.Sequence` object also implements special
functionality to accommodate Postgresql's SERIAL datatype. The SERIAL type in
PG automatically generates a sequence that is used implicitly during inserts.
This means that if a :class:`~sqlalchemy.schema.Table` object defines a
:class:`~sqlalchemy.schema.Sequence` on its primary key column so that it
works with Oracle and Firebird, the :class:`~sqlalchemy.schema.Sequence` would
get in the way of the "implicit" sequence that PG would normally use. For this
use case, add the flag ``optional=True`` to the
:class:`~sqlalchemy.schema.Sequence` object - this indicates that the
:class:`~sqlalchemy.schema.Sequence` should only be used if the database
provides no other option for generating primary key identifiers.
When the :class:`~sqlalchemy.schema.Sequence` is associated with a
:class:`.Column` as its **Python-side** default generator, the
:class:`.Sequence` will also be subject to "CREATE SEQUENCE" and "DROP
SEQUENCE" DDL when similar DDL is emitted for the owning :class:`.Table`.
This is a limited scope convenience feature that does not accommodate for
inheritance of other aspects of the :class:`.MetaData`, such as the default
schema. Therefore, it is best practice that for a :class:`.Sequence` which
is local to a certain :class:`.Column` / :class:`.Table`, that it be
explicitly associated with the :class:`.MetaData` using the
:paramref:`.Sequence.metadata` parameter. See the section
:ref:`sequence_metadata` for more background on this.
The :class:`~sqlalchemy.schema.Sequence` object also has the ability to be
executed standalone like a SQL expression, which has the effect of calling its
"next value" function::
Associating a Sequence on a SERIAL column
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
seq = Sequence('some_sequence')
nextid = connection.execute(seq)
PostgreSQL's SERIAL datatype is an auto-incrementing type that implies
the implicit creation of a PostgreSQL sequence when CREATE TABLE is emitted.
If a :class:`.Column` specifies an explicit :class:`.Sequence` object
which also specifies a true value for the :paramref:`.Sequence.optional`
boolean flag, the :class:`.Sequence` will not take effect under PostgreSQL,
and the SERIAL datatype will proceed normally. Instead, the :class:`.Sequence`
will only take effect when used against other sequence-supporting
databases, currently Oracle and Firebird.
Executing a Sequence Standalone
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
A SEQUENCE is a first class schema object in SQL and can be used to generate
values independently in the database. If you have a :class:`.Sequence`
object, it can be invoked with its "next value" instruction by
passing it directly to a SQL execution method::
with my_engine.connect() as conn:
seq = Sequence('some_sequence')
nextid = conn.execute(seq)
In order to embed the "next value" function of a :class:`.Sequence`
inside of a SQL statement like a SELECT or INSERT, use the :meth:`.Sequence.next_value`
method, which will render at statement compilation time a SQL function that is
appropriate for the target backend::
>>> my_seq = Sequence('some_sequence')
>>> stmt = select([my_seq.next_value()])
>>> print stmt.compile(dialect=postgresql.dialect())
SELECT nextval('some_sequence') AS next_value_1
.. _sequence_metadata:
Associating a Sequence with the MetaData
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
For many years, the SQLAlchemy documentation referred to the
example of associating a :class:`.Sequence` with a table as follows::
table = Table("cartitems", meta,
Column("cart_id", Integer, Sequence('cart_id_seq'),
primary_key=True),
Column("description", String(40)),
Column("createdate", DateTime())
)
While the above is a prominent idiomatic pattern, it is recommended that
the :class:`.Sequence` in most cases be explicitly associated with the
:class:`.MetaData`, using the :paramref:`.Sequence.metadata` parameter::
table = Table("cartitems", meta,
Column(
"cart_id",
Integer,
Sequence('cart_id_seq', metadata=meta), primary_key=True),
Column("description", String(40)),
Column("createdate", DateTime())
)
The :class:`.Sequence` object is a first class
schema construct that can exist independently of any table in a database, and
can also be shared among tables. Therefore SQLAlchemy does not implicitly
modify the :class:`.Sequence` when it is associated with a :class:`.Column`
object as either the Python-side or server-side default generator. While the
CREATE SEQUENCE / DROP SEQUENCE DDL is emitted for a :class:`.Sequence`
defined as a Python side generator at the same time the table itself is subject
to CREATE or DROP, this is a convenience feature that does not imply that the
:class:`.Sequence` is fully associated with the :class:`.MetaData` object.
Explicitly associating the :class:`.Sequence` with :class:`.MetaData`
allows for the following behaviors:
* The :class:`.Sequence` will inherit the :paramref:`.MetaData.schema`
parameter specified to the target :class:`.MetaData`, which
affects the production of CREATE / DROP DDL, if any.
* The :meth:`.Sequence.create` and :meth:`.Sequence.drop` methods
automatically use the engine bound to the :class:`.MetaData`
object, if any.
* The :meth:`.MetaData.create_all` and :meth:`.MetaData.drop_all`
methods will emit CREATE / DROP for this :class:`.Sequence`,
even if the :class:`.Sequence` is not associated with any
:class:`.Table` / :class:`.Column` that's a member of this
:class:`.MetaData`.
Since the vast majority of cases that deal with :class:`.Sequence` expect
that :class:`.Sequence` to be fully "owned" by the associated :class:`.Table`
and that options like default schema are propagated, setting the
:paramref:`.Sequence.metadata` parameter should be considered a best practice.
Associating a Sequence as the Server Side Default
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
When we associate a :class:`.Sequence` with a :class:`.Column` as above,
this association is an **in-Python only** association. The CREATE TABLE
that would be generated for our :class:`.Table` would not refer to this
sequence. If we want the sequence to be used as a server-side default,
meaning it takes place even if we emit INSERT commands to the table from
the SQL commandline, we can use the :paramref:`.Column.server_default`
parameter in conjunction with the value-generation function of the
sequence, available from the :meth:`.Sequence.next_value` method::
.. note:: The following technique is known to work only with the PostgreSQL
database. It does not work with Oracle.
cart_id_seq = Sequence('cart_id_seq')
The preceding sections illustrate how to associate a :class:`.Sequence` with a
:class:`.Column` as the **Python side default generator**::
Column(
"cart_id", Integer, Sequence('cart_id_seq', metadata=meta),
primary_key=True)
In the above case, the :class:`.Sequence` will automatically be subject
to CREATE SEQUENCE / DROP SEQUENCE DDL when the related :class:`.Table`
is subject to CREATE / DROP. However, the sequence will **not** be present
as the server-side default for the column when CREATE TABLE is emitted.
If we want the sequence to be used as a server-side default,
meaning it takes place even if we emit INSERT commands to the table from
the SQL command line, we can use the :paramref:`.Column.server_default`
parameter in conjunction with the value-generation function of the
sequence, available from the :meth:`.Sequence.next_value` method. Below
we illustrate the same :class:`.Sequence` being associated with the
:class:`.Column` both as the Python-side default generator as well as
the server-side default generator::
cart_id_seq = Sequence('cart_id_seq', metadata=meta)
table = Table("cartitems", meta,
Column(
"cart_id", Integer, cart_id_seq,
@@ -346,7 +461,20 @@ sequence, available from the :meth:`.Sequence.next_value` method::
Column("createdate", DateTime())
)
The above metadata will generate a CREATE TABLE statement on Postgresql as::
or with the ORM::
class CartItem(Base):
__tablename__ = 'cartitems'
cart_id_seq = Sequence('cart_id_seq', metadata=Base.metadata)
cart_id = Column(
Integer, cart_id_seq,
server_default=cart_id_seq.next_value(), primary_key=True)
description = Column(String(40))
createdate = Column(DateTime)
When the "CREATE TABLE" statement is emitted, on PostgreSQL it would be
emitted as::
CREATE TABLE cartitems (
cart_id INTEGER DEFAULT nextval('cart_id_seq') NOT NULL,
@@ -355,15 +483,25 @@ The above metadata will generate a CREATE TABLE statement on Postgresql as::
PRIMARY KEY (cart_id)
)
We place the :class:`.Sequence` also as a Python-side default above, that
is, it is mentioned twice in the :class:`.Column` definition. Depending
on the backend in use, this may not be strictly necessary, for example
on the Postgresql backend the Core will use ``RETURNING`` to access the
newly generated primary key value in any case. However, for the best
compatibility, :class:`.Sequence` was originally intended to be a Python-side
directive first and foremost so it's probably a good idea to specify it
in this way as well.
Placement of the :class:`.Sequence` in both the Python-side and server-side
default generation contexts ensures that the "primary key fetch" logic
works in all cases. Typically, sequence-enabled databases also support
RETURNING for INSERT statements, which is used automatically by SQLAlchemy
when emitting this statement. However if RETURNING is not used for a particular
insert, then SQLAlchemy would prefer to "pre-execute" the sequence outside
of the INSERT statement itself, which only works if the sequence is
included as the Python-side default generator function.
The example also associates the :class:`.Sequence` with the enclosing
:class:`.MetaData` directly, which again ensures that the :class:`.Sequence`
is fully associated with the parameters of the :class:`.MetaData` collection
including the default schema, if any.
.. seealso::
:ref:`postgresql_sequences` - in the PostgreSQL dialect documentation
:ref:`oracle_returning` - in the Oracle dialect documentation
Default Objects API
-------------------
+29 -18
View File
@@ -42,7 +42,7 @@ applications.
.. _supported_dbapis:
Supported Databases
====================
===================
SQLAlchemy includes many :class:`.Dialect` implementations for various
backends. Dialects for the most common databases are included with SQLAlchemy; a handful
@@ -71,14 +71,26 @@ the database using all lowercase letters. If not specified, a "default" DBAPI
will be imported if available - this default is typically the most widely
known driver available for that backend.
Examples for common connection styles follow below. For a full index of
detailed information on all included dialects as well as links to third-party dialects, see
:ref:`dialect_toplevel`.
As the URL is like any other URL, special characters such as those that
may be used in the password need to be URL encoded. Below is an example
of a URL that includes the password ``"kx%jj5/g"``::
Postgresql
postgresql+pg8000://dbuser:kx%25jj5%2Fg@pghost10/appdb
The encoding for the above password can be generated using ``urllib``::
>>> import urllib.parse
>>> urllib.parse.quote_plus("kx%jj5/g")
'kx%25jj5%2Fg'
Examples for common connection styles follow below. For a full index of
detailed information on all included dialects as well as links to third-party
dialects, see :ref:`dialect_toplevel`.
PostgreSQL
----------
The Postgresql dialect uses psycopg2 as the default DBAPI. pg8000 is
The PostgreSQL dialect uses psycopg2 as the default DBAPI. pg8000 is
also available as a pure-Python substitute::
# default
@@ -90,7 +102,7 @@ also available as a pure-Python substitute::
# pg8000
engine = create_engine('postgresql+pg8000://scott:tiger@localhost/mydatabase')
More notes on connecting to Postgresql at :ref:`postgresql_toplevel`.
More notes on connecting to PostgreSQL at :ref:`postgresql_toplevel`.
MySQL
-----
@@ -101,14 +113,11 @@ MySQL DBAPIs available, including MySQL-connector-python and OurSQL::
# default
engine = create_engine('mysql://scott:tiger@localhost/foo')
# mysql-python
# mysqlclient (a maintained fork of MySQL-Python)
engine = create_engine('mysql+mysqldb://scott:tiger@localhost/foo')
# MySQL-connector-python
engine = create_engine('mysql+mysqlconnector://scott:tiger@localhost/foo')
# OurSQL
engine = create_engine('mysql+oursql://scott:tiger@localhost/foo')
# PyMySQL
engine = create_engine('mysql+pymysql://scott:tiger@localhost/foo')
More notes on connecting to MySQL at :ref:`mysql_toplevel`.
@@ -153,11 +162,13 @@ For a relative file path, this requires three slashes::
And for an absolute file path, the three slashes are followed by the absolute path::
#Unix/Mac - 4 initial slashes in total
# Unix/Mac - 4 initial slashes in total
engine = create_engine('sqlite:////absolute/path/to/foo.db')
#Windows
# Windows
engine = create_engine('sqlite:///C:\\path\\to\\foo.db')
#Windows alternative using raw string
# Windows alternative using raw string
engine = create_engine(r'sqlite:///C:\path\to\foo.db')
To use a SQLite ``:memory:`` database, specify an empty URL::
@@ -212,7 +223,7 @@ For more information on connection pooling, see :ref:`pooling_toplevel`.
.. _custom_dbapi_args:
Custom DBAPI connect() arguments
=================================
================================
Custom arguments used when issuing the ``connect()`` call to the underlying
DBAPI may be issued in three distinct ways. String-based arguments can be
@@ -246,7 +257,7 @@ argument, which specifies a callable that returns a DBAPI connection:
.. _dbengine_logging:
Configuring Logging
====================
===================
Python's standard `logging
<http://docs.python.org/library/logging.html>`_ module is used to
+8 -12
View File
@@ -6,17 +6,13 @@ Events
SQLAlchemy includes an event API which publishes a wide variety of hooks into
the internals of both SQLAlchemy Core and ORM.
.. versionadded:: 0.7
The system supersedes the previous system of "extension", "proxy",
and "listener" classes.
Event Registration
------------------
Subscribing to an event occurs through a single API point, the :func:`.listen` function,
or alternatively the :func:`.listens_for` decorator. These functions
accept a user-defined listening function, a string identifier which identifies the event to be
intercepted, and a target. Additional positional and keyword arguments to these
or alternatively the :func:`.listens_for` decorator. These functions accept a
target, a string identifier which identifies the event to be intercepted, and
a user-defined listening function. Additional positional and keyword arguments to these
two functions may be supported by
specific types of events, which may specify alternate interfaces for the given event function, or provide
instructions regarding secondary event targets based on the given target.
@@ -30,7 +26,7 @@ and that a user-defined listener function should receive two positional argument
from sqlalchemy.pool import Pool
def my_on_connect(dbapi_con, connection_record):
print "New DBAPI connection:", dbapi_con
print("New DBAPI connection:", dbapi_con)
listen(Pool, 'connect', my_on_connect)
@@ -41,7 +37,7 @@ To listen with the :func:`.listens_for` decorator looks like::
@listens_for(Pool, "connect")
def my_on_connect(dbapi_con, connection_record):
print "New DBAPI connection:", dbapi_con
print("New DBAPI connection:", dbapi_con)
Named Argument Styles
---------------------
@@ -117,7 +113,7 @@ and objects::
listen(my_engine, 'connect', my_on_connect)
Modifiers
----------
---------
Some listeners allow modifiers to be passed to :func:`.listen`. These
modifiers sometimes provide alternate calling signatures for
@@ -129,14 +125,14 @@ this value can be supported::
def validate_phone(target, value, oldvalue, initiator):
"""Strip non-numeric characters from a phone number"""
return re.sub(r'(?![0-9])', '', value)
return re.sub(r'\D', '', value)
# setup listener on UserContact.phone attribute, instructing
# it to use the return value
listen(UserContact.phone, 'set', validate_phone, retval=True)
Event Reference
----------------
---------------
Both SQLAlchemy Core and SQLAlchemy ORM feature a wide variety of event hooks:
+4 -8
View File
@@ -1,7 +1,7 @@
.. _core_event_toplevel:
Core Events
============
===========
This section describes the event interfaces provided in
SQLAlchemy Core.
@@ -11,18 +11,14 @@ ORM events are described in :ref:`orm_event_toplevel`.
.. autoclass:: sqlalchemy.event.base.Events
:members:
.. versionadded:: 0.7
The event system supersedes the previous system of "extension", "listener",
and "proxy" classes.
Connection Pool Events
-----------------------
----------------------
.. autoclass:: sqlalchemy.events.PoolEvents
:members:
SQL Execution and Connection Events
------------------------------------
-----------------------------------
.. autoclass:: sqlalchemy.events.ConnectionEvents
:members:
@@ -31,7 +27,7 @@ SQL Execution and Connection Events
:members:
Schema Events
-----------------------
-------------
.. autoclass:: sqlalchemy.events.DDLEvents
:members:
+2
View File
@@ -1,3 +1,5 @@
.. _core_exceptions_toplevel:
Core Exceptions
===============
+1 -1
View File
@@ -1,7 +1,7 @@
.. _dep_interfaces_core_toplevel:
Deprecated Event Interfaces
============================
===========================
.. module:: sqlalchemy.interfaces
+30 -20
View File
@@ -33,7 +33,7 @@ The remaining positional arguments are mostly
Column('user_id', Integer, primary_key=True),
Column('user_name', String(16), nullable=False),
Column('email_address', String(60)),
Column('password', String(20), nullable=False)
Column('nickname', String(50), nullable=False)
)
Above, a table called ``user`` is described, which contains four columns. The
@@ -45,7 +45,7 @@ Note also that each column describes its datatype using objects corresponding
to genericized types, such as :class:`~sqlalchemy.types.Integer` and
:class:`~sqlalchemy.types.String`. SQLAlchemy features dozens of types of
varying levels of specificity as well as the ability to create custom types.
Documentation on the type system can be found at :ref:`types`.
Documentation on the type system can be found at :ref:`types_toplevel`.
Accessing Tables and Columns
----------------------------
@@ -58,7 +58,7 @@ dependency (that is, each table is preceded by all tables which it
references)::
>>> for t in metadata.sorted_tables:
... print t.name
... print(t.name)
user
user_preference
invoice
@@ -93,15 +93,15 @@ table include::
# iterate through all columns
for c in employees.c:
print c
print(c)
# get the table's primary key columns
for primary_key in employees.primary_key:
print primary_key
print(primary_key)
# get the table's foreign key objects:
for fkey in employees.foreign_keys:
print fkey
print(fkey)
# access the table's MetaData:
employees.metadata
@@ -154,7 +154,7 @@ will issue the CREATE statements:
Column('user_id', Integer, primary_key=True),
Column('user_name', String(16), nullable=False),
Column('email_address', String(60), key='email'),
Column('password', String(20), nullable=False)
Column('nickname', String(50), nullable=False)
)
user_prefs = Table('user_prefs', metadata,
@@ -170,7 +170,7 @@ will issue the CREATE statements:
user_id INTEGER NOT NULL PRIMARY KEY,
user_name VARCHAR(16) NOT NULL,
email_address VARCHAR(60),
password VARCHAR(20) NOT NULL
nickname VARCHAR(50) NOT NULL
)
PRAGMA table_info(user_prefs){}
CREATE TABLE user_prefs(
@@ -243,20 +243,18 @@ database schemas in relation to application code using schema migration tools.
There are two major migration tools available for SQLAlchemy:
* `Alembic <http://alembic.readthedocs.org>`_ - Written by the author of SQLAlchemy,
* `Alembic <https://alembic.sqlalchemy.org>`_ - Written by the author of SQLAlchemy,
Alembic features a highly customizable environment and a minimalistic usage pattern,
supporting such features as transactional DDL, automatic generation of "candidate"
migrations, an "offline" mode which generates SQL scripts, and support for branch
resolution.
* `SQLAlchemy-Migrate <http://code.google.com/p/sqlalchemy-migrate/>`_ - The original
migration tool for SQLAlchemy, SQLAlchemy-Migrate is widely used and continues
under active development. SQLAlchemy-Migrate includes features such as
SQL script generation, ORM class generation, ORM model comparison, and extensive
support for SQLite migrations.
* `SQLAlchemy-Migrate <https://github.com/openstack/sqlalchemy-migrate>`_ - The original
migration tool for SQLAlchemy, SQLAlchemy-Migrate is still used by projects
such as Openstack, however is being superseded by Alembic.
Specifying the Schema Name
---------------------------
--------------------------
Some databases support the concept of multiple schemas. A
:class:`~sqlalchemy.schema.Table` can reference this by specifying the
@@ -303,29 +301,41 @@ described in the individual documentation sections for each dialect.
Column, Table, MetaData API
---------------------------
.. attribute:: sqlalchemy.schema.BLANK_SCHEMA
Symbol indicating that a :class:`.Table` or :class:`.Sequence`
should have 'None' for its schema, even if the parent
:class:`.MetaData` has specified a schema.
.. seealso::
:paramref:`.MetaData.schema`
:paramref:`.Table.schema`
:paramref:`.Sequence.schema`
.. versionadded:: 1.0.14
.. autoclass:: Column
:members:
:inherited-members:
:undoc-members:
.. autoclass:: MetaData
:members:
:undoc-members:
.. autoclass:: SchemaItem
:members:
:undoc-members:
.. autoclass:: Table
:members:
:inherited-members:
:undoc-members:
.. autoclass:: ThreadLocalMetaData
:members:
:undoc-members:
+179 -125
View File
@@ -102,7 +102,7 @@ a last resort for when a DBAPI has some form of ``connect``
that is not at all supported by SQLAlchemy.
Constructing a Pool
------------------------
-------------------
To use a :class:`.Pool` by itself, the ``creator`` function is
the only argument that's required and is passed first, followed
@@ -161,6 +161,8 @@ Connection pools support an event interface that allows hooks to execute
upon first connect, upon each new connection, and upon checkout and
checkin of connections. See :class:`.PoolEvents` for details.
.. _pool_disconnects:
Dealing with Disconnects
------------------------
@@ -170,19 +172,140 @@ its entire set of connections, setting the previously pooled connections as
when the database server has been restarted, and all previously established connections
are no longer functional. There are two approaches to this.
Disconnect Handling - Optimistic
.. _pool_disconnects_pessimistic:
Disconnect Handling - Pessimistic
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The most common approach is to let SQLAlchemy handle disconnects as they
occur, at which point the pool is refreshed. This assumes the :class:`.Pool`
is used in conjunction with a :class:`.Engine`. The :class:`.Engine` has
logic which can detect disconnection events and refresh the pool automatically.
The pessimistic approach refers to emitting a test statement on the SQL
connection at the start of each connection pool checkout, to test
that the database connection is still viable. Typically, this
is a simple statement like "SELECT 1", but may also make use of some
DBAPI-specific method to test the connection for liveness.
The approach adds a small bit of overhead to the connection checkout process,
however is otherwise the most simple and reliable approach to completely
eliminating database errors due to stale pooled connections. The calling
application does not need to be concerned about organizing operations
to be able to recover from stale connections checked out from the pool.
It is critical to note that the pre-ping approach **does not accommodate for
connections dropped in the middle of transactions or other SQL operations**.
If the database becomes unavailable while a transaction is in progress, the
transaction will be lost and the database error will be raised. While
the :class:`.Connection` object will detect a "disconnect" situation and
recycle the connection as well as invalidate the rest of the connection pool
when this condition occurs,
the individual operation where the exception was raised will be lost, and it's
up to the application to either abandon
the operation, or retry the whole transaction again.
Pessimistic testing of connections upon checkout is achievable by
using the :paramref:`.Pool.pre_ping` argument, available from :func:`.create_engine`
via the :paramref:`.create_engine.pool_pre_ping` argument::
engine = create_engine("mysql+pymysql://user:pw@host/db", pool_pre_ping=True)
The "pre ping" feature will normally emit SQL equivalent to "SELECT 1" each time a
connection is checked out from the pool; if an error is raised that is detected
as a "disconnect" situation, the connection will be immediately recycled, and
all other pooled connections older than the current time are invalidated, so
that the next time they are checked out, they will also be recycled before use.
If the database is still not available when "pre ping" runs, then the initial
connect will fail and the error for failure to connect will be propagated
normally. In the uncommon situation that the database is available for
connections, but is not able to respond to a "ping", the "pre_ping" will try up
to three times before giving up, propagating the database error last received.
.. note::
the "SELECT 1" emitted by "pre-ping" is invoked within the scope
of the connection pool / dialect, using a very short codepath for minimal
Python latency. As such, this statement is **not logged in the SQL
echo output**, and will not show up in SQLAlchemy's engine logging.
.. versionadded:: 1.2 Added "pre-ping" capability to the :class:`.Pool`
class.
Custom / Legacy Pessimistic Ping
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Before :paramref:`.create_engine.pool_pre_ping` was added, the "pre-ping"
approach historically has been performed manually using
the :meth:`.ConnectionEvents.engine_connect` engine event.
The most common recipe for this is below, for reference
purposes in case an application is already using such a recipe, or special
behaviors are needed::
from sqlalchemy import exc
from sqlalchemy import event
from sqlalchemy import select
some_engine = create_engine(...)
@event.listens_for(some_engine, "engine_connect")
def ping_connection(connection, branch):
if branch:
# "branch" refers to a sub-connection of a connection,
# we don't want to bother pinging on these.
return
# turn off "close with result". This flag is only used with
# "connectionless" execution, otherwise will be False in any case
save_should_close_with_result = connection.should_close_with_result
connection.should_close_with_result = False
try:
# run a SELECT 1. use a core select() so that
# the SELECT of a scalar value without a table is
# appropriately formatted for the backend
connection.scalar(select([1]))
except exc.DBAPIError as err:
# catch SQLAlchemy's DBAPIError, which is a wrapper
# for the DBAPI's exception. It includes a .connection_invalidated
# attribute which specifies if this connection is a "disconnect"
# condition, which is based on inspection of the original exception
# by the dialect in use.
if err.connection_invalidated:
# run the same SELECT again - the connection will re-validate
# itself and establish a new connection. The disconnect detection
# here also causes the whole connection pool to be invalidated
# so that all stale connections are discarded.
connection.scalar(select([1]))
else:
raise
finally:
# restore "close with result"
connection.should_close_with_result = save_should_close_with_result
The above recipe has the advantage that we are making use of SQLAlchemy's
facilities for detecting those DBAPI exceptions that are known to indicate
a "disconnect" situation, as well as the :class:`.Engine` object's ability
to correctly invalidate the current connection pool when this condition
occurs and allowing the current :class:`.Connection` to re-validate onto
a new DBAPI connection.
Disconnect Handling - Optimistic
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
When pessimistic handling is not employed, as well as when the database is
shutdown and/or restarted in the middle of a connection's period of use within
a transaction, the other approach to dealing with stale / closed connections is
to let SQLAlchemy handle disconnects as they occur, at which point all
connections in the pool are invalidated, meaning they are assumed to be
stale and will be refreshed upon next checkout. This behavior assumes the
:class:`.Pool` is used in conjunction with a :class:`.Engine`.
The :class:`.Engine` has logic which can detect
disconnection events and refresh the pool automatically.
When the :class:`.Connection` attempts to use a DBAPI connection, and an
exception is raised that corresponds to a "disconnect" event, the connection
is invalidated. The :class:`.Connection` then calls the :meth:`.Pool.recreate`
method, effectively invalidating all connections not currently checked out so
that they are replaced with new ones upon next checkout::
that they are replaced with new ones upon next checkout. This flow is
illustrated by the code example below::
from sqlalchemy import create_engine, exc
e = create_engine(...)
@@ -195,22 +318,26 @@ that they are replaced with new ones upon next checkout::
except exc.DBAPIError, e:
# an exception is raised, Connection is invalidated.
if e.connection_invalidated:
print "Connection was invalidated!"
print("Connection was invalidated!")
# after the invalidate event, a new connection
# starts with a new Pool
c = e.connect()
c.execute("SELECT * FROM table")
The above example illustrates that no special intervention is needed, the pool
continues normally after a disconnection event is detected. However, an exception is
raised. In a typical web application using an ORM Session, the above condition would
The above example illustrates that no special intervention is needed to
refresh the pool, which continues normally after a disconnection event is
detected. However, one database exception is raised, per each connection
that is in use while the database unavailability event occurred.
In a typical web application using an ORM Session, the above condition would
correspond to a single request failing with a 500 error, then the web application
continuing normally beyond that. Hence the approach is "optimistic" in that frequent
database restarts are not anticipated.
.. _pool_setting_recycle:
Setting Pool Recycle
~~~~~~~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~~~~~
An additional setting that can augment the "optimistic" approach is to set the
pool recycle parameter. This parameter prevents the pool from using a particular
@@ -226,65 +353,6 @@ upon next checkout. Note that the invalidation **only** occurs during checkout
any connections that are held in a checked out state. ``pool_recycle`` is a function
of the :class:`.Pool` itself, independent of whether or not an :class:`.Engine` is in use.
.. _pool_disconnects_pessimistic:
Disconnect Handling - Pessimistic
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
At the expense of some extra SQL emitted for each connection checked out from the pool,
a "ping" operation established by a checkout event handler
can detect an invalid connection before it is used::
from sqlalchemy import exc
from sqlalchemy import event
from sqlalchemy.pool import Pool
@event.listens_for(Pool, "checkout")
def ping_connection(dbapi_connection, connection_record, connection_proxy):
cursor = dbapi_connection.cursor()
try:
cursor.execute("SELECT 1")
except:
# optional - dispose the whole pool
# instead of invalidating one at a time
# connection_proxy._pool.dispose()
# raise DisconnectionError - pool will try
# connecting again up to three times before raising.
raise exc.DisconnectionError()
cursor.close()
Above, the :class:`.Pool` object specifically catches :class:`~sqlalchemy.exc.DisconnectionError` and attempts
to create a new DBAPI connection, up to three times, before giving up and then raising
:class:`~sqlalchemy.exc.InvalidRequestError`, failing the connection. This recipe will ensure
that a new :class:`.Connection` will succeed even if connections
in the pool have gone stale, provided that the database server is actually running. The expense
is that of an additional execution performed per checkout. When using the ORM :class:`.Session`,
there is one connection checkout per transaction, so the expense is fairly low. The ping approach
above also works with straight connection pool usage, that is, even if no :class:`.Engine` were
involved.
The event handler can be tested using a script like the following, restarting the database
server at the point at which the script pauses for input::
from sqlalchemy import create_engine
e = create_engine("mysql://scott:tiger@localhost/test", echo_pool=True)
c1 = e.connect()
c2 = e.connect()
c3 = e.connect()
c1.close()
c2.close()
c3.close()
# pool size is now three.
print "Restart the server"
raw_input()
for i in xrange(10):
c = e.connect()
print c.execute("select 1").fetchall()
c.close()
.. _pool_connection_invalidation:
@@ -328,6 +396,41 @@ a DBAPI connection might be invalidated include:
All invalidations which occur will invoke the :meth:`.PoolEvents.invalidate`
event.
.. _pool_use_lifo:
Using FIFO vs. LIFO
-------------------
The :class:`.QueuePool` class features a flag called
:paramref:`.QueuePool.use_lifo`, which can also be accessed from
:func:`.create_engine` via the flag :paramref:`.create_engine.pool_use_lifo`.
Setting this flag to ``True`` causes the pool's "queue" behavior to instead be
that of a "stack", e.g. the last connection to be returned to the pool is the
first one to be used on the next request. In contrast to the pool's long-
standing behavior of first-in-first-out, which produces a round-robin effect of
using each connection in the pool in series, lifo mode allows excess
connections to remain idle in the pool, allowing server-side timeout schemes to
close these connections out. The difference between FIFO and LIFO is
basically whether or not its desirable for the pool to keep a full set of
connections ready to go even during idle periods::
engine = create_engine(
"postgreql://", pool_use_lifo=True, pool_pre_ping=True)
Above, we also make use of the :paramref:`.create_engine.pool_pre_ping` flag
so that connections which are closed from the server side are gracefully
handled by the connection pool and replaced with a new connection.
Note that the flag only applies to :class:`.QueuePool` use.
.. versionadded:: 1.3
.. seealso::
:ref:`pool_disconnects`
Using Connection Pools with Multiprocessing
-------------------------------------------
@@ -347,12 +450,12 @@ connections from the pool so that it makes all new ones. Below is
a simple version using ``multiprocessing.Process``, but this idea
should be adapted to the style of forking in use::
eng = create_engine("...")
engine = create_engine("...")
def run_in_process():
eng.dispose()
engine.dispose()
with eng.connect() as conn:
with engine.connect() as conn:
conn.execute("...")
p = Process(target=run_in_process)
@@ -365,7 +468,7 @@ This is a little more magical but probably more foolproof::
from sqlalchemy import exc
import os
eng = create_engine("...")
engine = create_engine("...")
@event.listens_for(engine, "connect")
def connect(dbapi_connection, connection_record):
@@ -390,7 +493,7 @@ coercing the pool to recycle the connection record to make a new connection.
API Documentation - Available Pool Implementations
---------------------------------------------------
--------------------------------------------------
.. autoclass:: sqlalchemy.pool.Pool
@@ -426,52 +529,3 @@ API Documentation - Available Pool Implementations
.. autoclass:: _ConnectionRecord
:members:
Pooling Plain DB-API Connections
--------------------------------
Any :pep:`249` DB-API module can be "proxied" through the connection
pool transparently. Usage of the DB-API is exactly as before, except
the ``connect()`` method will consult the pool. Below we illustrate
this with ``psycopg2``::
import sqlalchemy.pool as pool
import psycopg2 as psycopg
psycopg = pool.manage(psycopg)
# then connect normally
connection = psycopg.connect(database='test', username='scott',
password='tiger')
This produces a :class:`_DBProxy` object which supports the same
``connect()`` function as the original DB-API module. Upon
connection, a connection proxy object is returned, which delegates its
calls to a real DB-API connection object. This connection object is
stored persistently within a connection pool (an instance of
:class:`.Pool`) that corresponds to the exact connection arguments sent
to the ``connect()`` function.
The connection proxy supports all of the methods on the original
connection object, most of which are proxied via ``__getattr__()``.
The ``close()`` method will return the connection to the pool, and the
``cursor()`` method will return a proxied cursor object. Both the
connection proxy and the cursor proxy will also return the underlying
connection to the pool after they have both been garbage collected,
which is detected via weakref callbacks (``__del__`` is not used).
Additionally, when connections are returned to the pool, a
``rollback()`` is issued on the connection unconditionally. This is
to release any locks still held by the connection that may have
resulted from normal activity.
By default, the ``connect()`` method will return the same connection
that is already checked out in the current thread. This allows a
particular connection to be used in a given thread without needing to
pass it around between functions. To disable this behavior, specify
``use_threadlocal=False`` to the ``manage()`` function.
.. autofunction:: sqlalchemy.pool.manage
.. autofunction:: sqlalchemy.pool.clear_managers
+5 -5
View File
@@ -55,7 +55,7 @@ hasn't already been loaded; once loaded, new calls to
reflection queries.
Overriding Reflected Columns
-----------------------------
----------------------------
Individual columns can be overridden with explicit values when reflecting
tables; this is handy for specifying custom datatypes, constraints such as
@@ -67,7 +67,7 @@ primary keys that may not be configured within the database, etc.::
... autoload=True)
Reflecting Views
-----------------
----------------
The reflection system can also reflect views. Basic usage is the same as that
of a table::
@@ -125,7 +125,7 @@ database is also available. This is known as the "Inspector"::
from sqlalchemy.engine import reflection
engine = create_engine('...')
insp = reflection.Inspector.from_engine(engine)
print insp.get_table_names()
print(insp.get_table_names())
.. autoclass:: sqlalchemy.engine.reflection.Inspector
:members:
@@ -156,8 +156,8 @@ different format than what was specified in SQLAlchemy. The :class:`.Table`
objects returned from reflection cannot be always relied upon to produce the identical
DDL as the original Python-defined :class:`.Table` objects. Areas where
this occurs includes server defaults, column-associated sequences and various
idosyncrasies regarding constraints and datatypes. Server side defaults may
be returned with cast directives (typically Postgresql will include a ``::<type>``
idiosyncrasies regarding constraints and datatypes. Server side defaults may
be returned with cast directives (typically PostgreSQL will include a ``::<type>``
cast) or different quoting patterns than originally specified.
Another category of limitation includes schema structures for which reflection
+17
View File
@@ -23,6 +23,8 @@ elements are themselves :class:`.ColumnElement` subclasses).
.. autofunction:: join
.. autofunction:: lateral
.. autofunction:: outerjoin
.. autofunction:: select
@@ -31,6 +33,8 @@ elements are themselves :class:`.ColumnElement` subclasses).
.. autofunction:: sqlalchemy.sql.expression.table
.. autofunction:: tablesample
.. autofunction:: union
.. autofunction:: union_all
@@ -57,6 +61,9 @@ elements are themselves :class:`.ColumnElement` subclasses).
:members:
:inherited-members:
.. autoclass:: HasCTE
:members:
.. autoclass:: HasPrefixes
:members:
@@ -67,6 +74,10 @@ elements are themselves :class:`.ColumnElement` subclasses).
:members:
:inherited-members:
.. autoclass:: Lateral
:members:
:inherited-members:
.. autoclass:: ScalarSelect
:members:
@@ -79,10 +90,16 @@ elements are themselves :class:`.ColumnElement` subclasses).
.. autoclass:: SelectBase
:members:
:inherited-members:
.. autoclass:: TableClause
:members:
:inherited-members:
.. autoclass:: TableSample
:members:
:inherited-members:
.. autoclass:: TextAsFrom
:members:
:inherited-members:
+26 -5
View File
@@ -3,14 +3,23 @@ Column Elements and Expressions
.. module:: sqlalchemy.sql.expression
The most fundamental part of the SQL expression API are the "column elements",
which allow for basic SQL expression support. The core of all SQL expression
constructs is the :class:`.ClauseElement`, which is the base for several
sub-branches. The :class:`.ColumnElement` class is the fundamental unit
used to construct any kind of typed SQL expression.
The expression API consists of a series of classes that each represent a
specific lexical element within a SQL string. Composed together
into a larger structure, they form a statement construct that may
be *compiled* into a string representation that can be passed to a database.
The classes are organized into a
hierarchy that begins at the basemost ClauseElement class. Key subclasses
include ColumnElement, which represents the role of any column-based expression
in a SQL statement, such as in the columns clause, WHERE clause, and ORDER BY
clause, and FromClause, which represents the role of a token that is placed in
the FROM clause of a SELECT statement.
.. autofunction:: all_
.. autofunction:: and_
.. autofunction:: any_
.. autofunction:: asc
.. autofunction:: between
@@ -65,6 +74,8 @@ used to construct any kind of typed SQL expression.
.. autofunction:: type_coerce
.. autofunction:: within_group
.. autoclass:: BinaryExpression
:members:
@@ -129,9 +140,15 @@ used to construct any kind of typed SQL expression.
.. autoclass:: Tuple
:members:
.. autoclass:: WithinGroup
:members:
.. autoclass:: sqlalchemy.sql.elements.True_
:members:
.. autoclass:: TypeCoerce
:members:
.. autoclass:: sqlalchemy.sql.operators.custom_op
:members:
@@ -141,6 +158,10 @@ used to construct any kind of typed SQL expression.
.. autoclass:: sqlalchemy.sql.elements.quoted_name
.. attribute:: quote
whether the string should be unconditionally quoted
.. autoclass:: UnaryExpression
:members:
+459 -164
View File
File diff suppressed because it is too large Load Diff
+4 -2
View File
@@ -3,7 +3,7 @@
.. _types_api:
Base Type API
--------------
-------------
.. autoclass:: TypeEngine
:members:
@@ -11,9 +11,11 @@ Base Type API
.. autoclass:: Concatenable
:members:
:inherited-members:
.. autoclass:: Indexable
:members:
.. autoclass:: NullType
+19 -9
View File
@@ -18,7 +18,6 @@ the database driver returns an incorrect type.
... Column('login', String(32))
... )
SQLAlchemy will use the ``Integer`` and ``String(32)`` type
information when issuing a ``CREATE TABLE`` statement and will use it
again when reading back rows ``SELECTed`` from the database.
@@ -35,8 +34,8 @@ Generic types specify a column that can read, write and store a
particular type of Python data. SQLAlchemy will choose the best
database column type available on the target database when issuing a
``CREATE TABLE`` statement. For complete control over which column
type is emitted in ``CREATE TABLE``, such as ``VARCHAR`` see `SQL
Standard Types`_ and the other sections of this chapter.
type is emitted in ``CREATE TABLE``, such as ``VARCHAR`` see
:ref:`types_sqlstandard` and the other sections of this chapter.
.. autoclass:: BigInteger
:members:
@@ -98,12 +97,19 @@ Standard Types`_ and the other sections of this chapter.
.. _types_sqlstandard:
SQL Standard Types
------------------
SQL Standard and Multiple Vendor Types
--------------------------------------
The SQL standard types always create database column types of the same
name when ``CREATE TABLE`` is issued. Some types may not be supported
on all databases.
This category of types refers to types that are either part of the
SQL standard, or are potentially found within a subset of database backends.
Unlike the "generic" types, the SQL standard/multi-vendor types have **no**
guarantee of working on all backends, and will only work on those backends
that explicitly support them by name. That is, the type will always emit
its exact name in DDL with ``CREATE TABLE`` is issued.
.. autoclass:: ARRAY
:members:
.. autoclass:: BIGINT
@@ -137,6 +143,9 @@ on all databases.
.. autoclass:: INT
.. autoclass:: JSON
:members:
.. autoclass:: sqlalchemy.types.INTEGER
@@ -163,6 +172,7 @@ on all databases.
.. autoclass:: TIMESTAMP
:members:
.. autoclass:: VARBINARY
@@ -213,7 +223,7 @@ implemented for that backend::
)
Where above, the INTEGER and VARCHAR types are ultimately from
sqlalchemy.types, and INET is specific to the Postgresql dialect.
sqlalchemy.types, and INET is specific to the PostgreSQL dialect.
Some dialect level types have the same name as the SQL standard type,
but also provide additional arguments. For example, MySQL implements
+15 -47
View File
@@ -16,12 +16,12 @@ Included Dialects
:maxdepth: 1
:glob:
firebird
mssql
mysql
oracle
postgresql
mysql
sqlite
oracle
mssql
firebird
sybase
.. _external_toplevel:
@@ -29,52 +29,20 @@ Included Dialects
External Dialects
-----------------
.. versionchanged:: 0.8
As of SQLAlchemy 0.8, several dialects have been moved to external
projects, and dialects for new databases will also be published
as external projects. The rationale here is to keep the base
SQLAlchemy install and test suite from growing inordinately large.
Currently maintained external dialect projects for SQLAlchemy include:
The "classic" dialects such as SQLite, MySQL, Postgresql, Oracle,
SQL Server, and Firebird will remain in the Core for the time being.
.. versionchanged:: 1.0
The Drizzle dialect has been moved into the third party system.
Current external dialect projects for SQLAlchemy include:
Production Ready
^^^^^^^^^^^^^^^^
* `ibm_db_sa <http://code.google.com/p/ibm-db/wiki/README>`_ - driver for IBM DB2 and Informix,
developed jointly by IBM and SQLAlchemy developers.
* `redshift-sqlalchemy <https://pypi.python.org/pypi/redshift-sqlalchemy>`_ - driver for Amazon Redshift, adapts
the existing Postgresql/psycopg2 driver.
* `ibm_db_sa <http://code.google.com/p/ibm-db/wiki/README>`_ - driver for IBM DB2 and Informix.
* `PyHive <https://github.com/dropbox/PyHive#sqlalchemy>`_ - driver for `Apache Hive <https://hive.apache.org/>`_ and `Presto <https://prestodb.github.io/>`_.
* `sqlalchemy-redshift <https://pypi.python.org/pypi/sqlalchemy-redshift>`_ - driver for Amazon Redshift, adapts
the existing PostgreSQL/psycopg2 driver.
* `sqlalchemy-drill <https://github.com/JohnOmernik/sqlalchemy-drill>`_ - driver for Apache Drill.
* `sqlalchemy-hana <https://github.com/SAP/sqlalchemy-hana>`_ - driver for SAP Hana.
* `sqlalchemy_exasol <https://github.com/blue-yonder/sqlalchemy_exasol>`_ - driver for EXASolution.
* `sqlalchemy-sqlany <https://github.com/sqlanywhere/sqlalchemy-sqlany>`_ - driver for SAP Sybase SQL
Anywhere, developed by SAP.
* `sqlalchemy-monetdb <https://github.com/gijzelaerr/sqlalchemy-monetdb>`_ - driver for MonetDB.
Experimental / Incomplete
^^^^^^^^^^^^^^^^^^^^^^^^^^
Dialects that are in an incomplete state or are considered somewhat experimental.
* `CALCHIPAN <https://bitbucket.org/zzzeek/calchipan/>`_ - Adapts `Pandas <http://pandas.pydata.org/>`_ dataframes to SQLAlchemy.
* `sqlalchemy-cubrid <https://bitbucket.org/zzzeek/sqlalchemy-cubrid>`_ - driver for the CUBRID database.
Attic
^^^^^
Dialects in the "attic" are those that were contributed for SQLAlchemy long ago
but have received little attention or demand since then, and are now moved out to
their own repositories in at best a semi-working state.
Community members interested in these dialects should feel free to pick up on
their current codebase and fork off into working libraries.
* `sqlalchemy-access <https://bitbucket.org/zzzeek/sqlalchemy-access>`_ - driver for Microsoft Access.
* `sqlalchemy-drizzle <https://bitbucket.org/zzzeek/sqlalchemy-drizzle>`_ - driver for the Drizzle MySQL variant.
* `sqlalchemy-informixdb <https://bitbucket.org/zzzeek/sqlalchemy-informixdb>`_ - driver for the informixdb DBAPI.
* `sqlalchemy-maxdb <https://bitbucket.org/zzzeek/sqlalchemy-maxdb>`_ - driver for the MaxDB database
* `snowflake-sqlalchemy <https://github.com/snowflakedb/snowflake-sqlalchemy>`_ - driver for `Snowflake <https://www.snowflake.net/>`_.
* `sqlalchemy-tds <https://github.com/m32/sqlalchemy-tds>`_ - driver for MS-SQL,
on top of `python-tds <https://github.com/denisenkom/pytds>`_.
* `crate <https://github.com/crate/crate-python>`_ - driver for `CrateDB <https://crate.io/>`_.
+28 -20
View File
@@ -6,7 +6,7 @@ Microsoft SQL Server
.. automodule:: sqlalchemy.dialects.mssql.base
SQL Server Data Types
-----------------------
---------------------
As with all SQLAlchemy dialects, all UPPERCASE types that are known to be
valid with SQL server are importable from the top level dialect, whether
@@ -26,75 +26,83 @@ construction arguments, are as follows:
.. autoclass:: BIT
:members: __init__
.. autoclass:: CHAR
:members: __init__
.. autoclass:: DATETIME2
:members: __init__
.. autoclass:: DATETIMEOFFSET
:members: __init__
.. autoclass:: IMAGE
:members: __init__
.. autoclass:: MONEY
:members: __init__
.. autoclass:: NCHAR
:members: __init__
.. autoclass:: NTEXT
:members: __init__
.. autoclass:: NVARCHAR
:members: __init__
.. autoclass:: REAL
:members: __init__
.. autoclass:: ROWVERSION
:members: __init__
.. autoclass:: SMALLDATETIME
:members: __init__
.. autoclass:: SMALLMONEY
:members: __init__
.. autoclass:: SQL_VARIANT
:members: __init__
.. autoclass:: TEXT
:members: __init__
.. autoclass:: TIME
:members: __init__
.. autoclass:: TIMESTAMP
:members: __init__
.. autoclass:: TINYINT
:members: __init__
.. autoclass:: UNIQUEIDENTIFIER
:members: __init__
.. autoclass:: VARCHAR
:members: __init__
.. autoclass:: XML
:members: __init__
PyODBC
@@ -110,7 +118,7 @@ pymssql
.. automodule:: sqlalchemy.dialects.mssql.pymssql
zxjdbc
--------------
------
.. automodule:: sqlalchemy.dialects.mssql.zxjdbc
+21 -10
View File
@@ -6,7 +6,7 @@ MySQL
.. automodule:: sqlalchemy.dialects.mysql.base
MySQL Data Types
------------------
----------------
As with all SQLAlchemy dialects, all UPPERCASE types that are known to be
valid with MySQL are importable from the top level dialect::
@@ -74,6 +74,8 @@ construction arguments, are as follows:
.. autoclass:: INTEGER
:members: __init__
.. autoclass:: JSON
:members:
.. autoclass:: LONGBLOB
:members: __init__
@@ -154,34 +156,43 @@ construction arguments, are as follows:
.. autoclass:: YEAR
:members: __init__
MySQL DML Constructs
-------------------------
MySQL-Python
--------------------
.. autofunction:: sqlalchemy.dialects.mysql.dml.insert
.. autoclass:: sqlalchemy.dialects.mysql.dml.Insert
:members:
mysqlclient (fork of MySQL-Python)
----------------------------------
.. automodule:: sqlalchemy.dialects.mysql.mysqldb
pymysql
-------------
PyMySQL
-------
.. automodule:: sqlalchemy.dialects.mysql.pymysql
MySQL-Connector
----------------------
---------------
.. automodule:: sqlalchemy.dialects.mysql.mysqlconnector
cymysql
------------
-------
.. automodule:: sqlalchemy.dialects.mysql.cymysql
OurSQL
--------------
------
.. automodule:: sqlalchemy.dialects.mysql.oursql
Google App Engine
-----------------------
-----------------
.. automodule:: sqlalchemy.dialects.mysql.gaerdbms
@@ -191,6 +202,6 @@ pyodbc
.. automodule:: sqlalchemy.dialects.mysql.pyodbc
zxjdbc
--------------
------
.. automodule:: sqlalchemy.dialects.mysql.zxjdbc
+7 -4
View File
@@ -6,7 +6,7 @@ Oracle
.. automodule:: sqlalchemy.dialects.oracle.base
Oracle Data Types
-------------------
-----------------
As with all SQLAlchemy dialects, all UPPERCASE types that are known to be
valid with Oracle are importable from the top level dialect, whether
@@ -14,10 +14,13 @@ they originate from :mod:`sqlalchemy.types` or from the local dialect::
from sqlalchemy.dialects.oracle import \
BFILE, BLOB, CHAR, CLOB, DATE, \
DOUBLE_PRECISION, FLOAT, INTERVAL, LONG, NCLOB, \
DOUBLE_PRECISION, FLOAT, INTERVAL, LONG, NCLOB, NCHAR, \
NUMBER, NVARCHAR, NVARCHAR2, RAW, TIMESTAMP, VARCHAR, \
VARCHAR2
.. versionadded:: 1.2.19 Added :class:`.NCHAR` to the list of datatypes
exported by the Oracle dialect.
Types which are specific to Oracle, or have Oracle-specific
construction arguments, are as follows:
@@ -54,11 +57,11 @@ construction arguments, are as follows:
cx_Oracle
----------
---------
.. automodule:: sqlalchemy.dialects.oracle.cx_oracle
zxjdbc
-------
------
.. automodule:: sqlalchemy.dialects.oracle.zxjdbc
+39 -30
View File
@@ -6,16 +6,16 @@ PostgreSQL
.. automodule:: sqlalchemy.dialects.postgresql.base
PostgreSQL Data Types
------------------------
---------------------
As with all SQLAlchemy dialects, all UPPERCASE types that are known to be
valid with Postgresql are importable from the top level dialect, whether
valid with PostgreSQL are importable from the top level dialect, whether
they originate from :mod:`sqlalchemy.types` or from the local dialect::
from sqlalchemy.dialects.postgresql import \
ARRAY, BIGINT, BIT, BOOLEAN, BYTEA, CHAR, CIDR, DATE, \
DOUBLE_PRECISION, ENUM, FLOAT, HSTORE, INET, INTEGER, \
INTERVAL, JSON, JSONB, MACADDR, NUMERIC, OID, REAL, SMALLINT, TEXT, \
INTERVAL, JSON, JSONB, MACADDR, MONEY, NUMERIC, OID, REAL, SMALLINT, TEXT, \
TIME, TIMESTAMP, UUID, VARCHAR, INT4RANGE, INT8RANGE, NUMRANGE, \
DATERANGE, TSRANGE, TSTZRANGE, TSVECTOR
@@ -24,26 +24,25 @@ construction arguments, are as follows:
.. currentmodule:: sqlalchemy.dialects.postgresql
.. autoclass:: aggregate_order_by
.. autoclass:: array
.. autoclass:: ARRAY
:members: __init__, Comparator
.. autofunction:: array_agg
.. autoclass:: Any
.. autofunction:: Any
.. autoclass:: All
.. autofunction:: All
.. autoclass:: BIT
:members: __init__
.. autoclass:: BYTEA
:members: __init__
.. autoclass:: CIDR
:members: __init__
.. autoclass:: DOUBLE_PRECISION
@@ -63,8 +62,6 @@ construction arguments, are as follows:
.. autoclass:: INET
:members: __init__
.. autoclass:: INTERVAL
:members: __init__
@@ -75,20 +72,18 @@ construction arguments, are as follows:
.. autoclass:: JSONB
:members:
.. autoclass:: JSONElement
:members:
.. autoclass:: MACADDR
:members: __init__
.. autoclass:: MONEY
.. autoclass:: OID
:members: __init__
.. autoclass:: REAL
:members: __init__
.. autoclass:: REGCLASS
.. autoclass:: TSVECTOR
:members: __init__
.. autoclass:: UUID
:members: __init__
@@ -126,19 +121,19 @@ mixin:
.. warning::
The range type DDL support should work with any Postgres DBAPI
The range type DDL support should work with any PostgreSQL DBAPI
driver, however the data types returned may vary. If you are using
``psycopg2``, it's recommended to upgrade to version 2.5 or later
before using these column types.
When instantiating models that use these column types, you should pass
whatever data type is expected by the DBAPI driver you're using for
the column type. For :mod:`psycopg2` these are
:class:`~psycopg2.extras.NumericRange`,
:class:`~psycopg2.extras.DateRange`,
:class:`~psycopg2.extras.DateTimeRange` and
:class:`~psycopg2.extras.DateTimeTZRange` or the class you've
registered with :func:`~psycopg2.extras.register_range`.
the column type. For ``psycopg2`` these are
``psycopg2.extras.NumericRange``,
``psycopg2.extras.DateRange``,
``psycopg2.extras.DateTimeRange`` and
``psycopg2.extras.DateTimeTZRange`` or the class you've
registered with ``psycopg2.extras.register_range``.
For example:
@@ -162,7 +157,7 @@ For example:
PostgreSQL Constraint Types
---------------------------
SQLAlchemy supports Postgresql EXCLUDE constraints via the
SQLAlchemy supports PostgreSQL EXCLUDE constraints via the
:class:`ExcludeConstraint` class:
.. autoclass:: ExcludeConstraint
@@ -183,29 +178,43 @@ For example::
ExcludeConstraint(('room', '='), ('during', '&&')),
)
PostgreSQL DML Constructs
-------------------------
.. autofunction:: sqlalchemy.dialects.postgresql.dml.insert
.. autoclass:: sqlalchemy.dialects.postgresql.dml.Insert
:members:
psycopg2
--------------
--------
.. automodule:: sqlalchemy.dialects.postgresql.psycopg2
pg8000
--------------
------
.. automodule:: sqlalchemy.dialects.postgresql.pg8000
psycopg2cffi
--------------
------------
.. automodule:: sqlalchemy.dialects.postgresql.psycopg2cffi
py-postgresql
--------------------
-------------
.. automodule:: sqlalchemy.dialects.postgresql.pypostgresql
.. _dialect-postgresql-pygresql:
pygresql
--------
.. automodule:: sqlalchemy.dialects.postgresql.pygresql
zxjdbc
--------------
------
.. automodule:: sqlalchemy.dialects.postgresql.zxjdbc
+4 -2
View File
@@ -6,7 +6,7 @@ SQLite
.. automodule:: sqlalchemy.dialects.sqlite.base
SQLite Data Types
------------------------
-----------------
As with all SQLAlchemy dialects, all UPPERCASE types that are known to be
valid with SQLite are importable from the top level dialect, whether
@@ -14,7 +14,7 @@ they originate from :mod:`sqlalchemy.types` or from the local dialect::
from sqlalchemy.dialects.sqlite import \
BLOB, BOOLEAN, CHAR, DATE, DATETIME, DECIMAL, FLOAT, \
INTEGER, NUMERIC, SMALLINT, TEXT, TIME, TIMESTAMP, \
INTEGER, NUMERIC, JSON, SMALLINT, TEXT, TIME, TIMESTAMP, \
VARCHAR
.. module:: sqlalchemy.dialects.sqlite
@@ -23,6 +23,8 @@ they originate from :mod:`sqlalchemy.types` or from the local dialect::
.. autoclass:: DATE
.. autoclass:: JSON
.. autoclass:: TIME
Pysqlite
+3 -3
View File
@@ -6,17 +6,17 @@ Sybase
.. automodule:: sqlalchemy.dialects.sybase.base
python-sybase
-------------------
-------------
.. automodule:: sqlalchemy.dialects.sybase.pysybase
pyodbc
------------
------
.. automodule:: sqlalchemy.dialects.sybase.pyodbc
mxodbc
------------
------
.. automodule:: sqlalchemy.dialects.sybase.mxodbc
+550
View File
@@ -0,0 +1,550 @@
:orphan:
.. _errors:
==============
Error Messages
==============
This section lists descriptions and background for common error messages
and warnings raised or emitted by SQLAlchemy.
SQLAlchemy normally raises errors within the context of a SQLAlchemy-specific
exception class. For details on these classes, see
:ref:`core_exceptions_toplevel` and :ref:`orm_exceptions_toplevel`.
SQLAlchemy errors can roughly be separated into two categories, the
**programming-time error** and the **runtime error**. Programming-time
errors are raised as a result of functions or methods being called with
incorrect arguments, or from other configuration-oriented methods such as
mapper configurations that can't be resolved. The programming-time error is
typically immediate and deterministic. The runtime error on the other hand
represents a failure that occurs as a program runs in response to some
condition that occurs arbitrarily, such as database connections being
exhausted or some data-related issue occurring. Runtime errors are more
likely to be seen in the logs of a running application as the program
encounters these states in response to load and data being encountered.
Since runtime errors are not as easy to reproduce and often occur in response
to some arbitrary condition as the program runs, they are more difficult to
debug and also affect programs that have already been put into production.
Within this section, the goal is to try to provide background on some of the
most common runtime errors as well as programming time errors.
Connections and Transactions
============================
.. _error_3o7r:
QueuePool limit of size <x> overflow <y> reached, connection timed out, timeout <z>
-----------------------------------------------------------------------------------
This is possibly the most common runtime error experienced, as it directly
involves the work load of the application surpassing a configured limit, one
which typically applies to nearly all SQLAlchemy applications.
The following points summarize what this error means, beginning with the
most fundamental points that most SQLAlchemy users should already be
familiar with.
* **The SQLAlchemy Engine object uses a pool of connections by default** - What
this means is that when one makes use of a SQL database connection resource
of an :class:`.Engine` object, and then :term:`releases` that resource,
the database connection itself remains connected to the database and
is returned to an internal queue where it can be used again. Even though
the code may appear to be ending its conversation with the database, in many
cases the application will still maintain a fixed number of database connections
that persist until the application ends or the pool is explicitly disposed.
* Because of the pool, when an application makes use of a SQL database
connection, most typically from either making use of :meth:`.Engine.connect`
or when making queries using an ORM :class:`.Session`, this activity
does not necessarily establish a new connection to the database at the
moment the connection object is acquired; it instead consults the
connection pool for a connection, which will often retrieve an existing
connection from the pool to be re-used. If no connections are available,
the pool will create a new database connection, but only if the
pool has not surpassed a configured capacity.
* The default pool used in most cases is called :class:`.QueuePool`. When
you ask this pool to give you a connection and none are available, it
will create a new connection **if the total number of connections in play
are less than a configured value**. This value is equal to the
**pool size plus the max overflow**. That means if you have configured
your engine as::
engine = create_engine("mysql://u:p@host/db", pool_size=10, max_overflow=20)
The above :class:`.Engine` will allow **at most 30 connections** to be in
play at any time, not including connections that were detached from the
engine or invalidated. If a request for a new connection arrives and
30 connections are already in use by other parts of the application,
the connection pool will block for a fixed period of time,
before timing out and raising this error message.
In order to allow for a higher number of connections be in use at once,
the pool can be adjusted using the
:paramref:`.create_engine.pool_size` and :paramref:`.create_engine.max_overflow`
parameters as passed to the :func:`.create_engine` function. The timeout
to wait for a connection to be available is configured using the
:paramref:`.create_engine.pool_timeout` parameter.
* The pool can be configured to have unlimited overflow by setting
:paramref:`.create_engine.max_overflow` to the value "-1". With this setting,
the pool will still maintain a fixed pool of connections, however it will
never block upon a new connection being requested; it will instead unconditionally
make a new connection if none are available.
However, when running in this way, if the application has an issue where it
is using up all available connectivity resources, it will eventually hit the
configured limit of available connections on the database itself, which will
again return an error. More seriously, when the application exhausts the
database of connections, it usually will have caused a great
amount of resources to be used up before failing, and can also interfere
with other applications and database status mechanisms that rely upon being
able to connect to the database.
Given the above, the connection pool can be looked at as a **safety valve
for connection use**, providing a critical layer of protection against
a rogue application causing the entire database to become unavailable
to all other applications. When receiving this error message, it is vastly
preferable to repair the issue using up too many connections and/or
configure the limits appropriately, rather than allowing for unlimited
overflow which does not actually solve the underlying issue.
What causes an application to use up all the connections that it has available?
* **The application is fielding too many concurrent requests to do work based
on the configured value for the pool** - This is the most straightforward
cause. If you have
an application that runs in a thread pool that allows for 30 concurrent
threads, with one connection in use per thread, if your pool is not configured
to allow at least 30 connections checked out at once, you will get this
error once your application receives enough concurrent requests. Solution
is to raise the limits on the pool or lower the number of concurrent threads.
* **The application is not returning connections to the pool** - This is the
next most common reason, which is that the application is making use of the
connection pool, but the program is failing to :term:`release` these
connections and is instead leaving them open. The connection pool as well
as the ORM :class:`.Session` do have logic such that when the session and/or
connection object is garbage collected, it results in the underlying
connection resources being released, however this behavior cannot be relied
upon to release resources in a timely manner.
A common reason this can occur is that the application uses ORM sessions and
does not call :meth:`.Session.close` upon them one the work involving that
session is complete. Solution is to make sure ORM sessions if using the ORM,
or engine-bound :class:`.Connection` objects if using Core, are explicitly
closed at the end of the work being done, either via the appropriate
``.close()`` method, or by using one of the available context managers (e.g.
"with:" statement) to properly release the resource.
* **The application is attempting to run long-running transactions** - A
database transaction is a very expensive resource, and should **never be
left idle waiting for some event to occur**. If an application is waiting
for a user to push a button, or a result to come off of a long running job
queue, or is holding a persistent connection open to a browser, **don't
keep a database transaction open for the whole time**. As the application
needs to work with the database and interact with an event, open a short-lived
transaction at that point and then close it.
* **The application is deadlocking** - Also a common cause of this error and
more difficult to grasp, if an application is not able to complete its use
of a connection either due to an application-side or database-side deadlock,
the application can use up all the available connections which then leads to
additional requests receiving this error. Reasons for deadlocks include:
* Using an implicit async system such as gevent or eventlet without
properly monkeypatching all socket libraries and drivers, or which
has bugs in not fully covering for all monkeypatched driver methods,
or less commonly when the async system is being used against CPU-bound
workloads and greenlets making use of database resources are simply waiting
too long to attend to them. Neither implicit nor explicit async
programming frameworks are typically
necessary or appropriate for the vast majority of relational database
operations; if an application must use an async system for some area
of functionality, it's best that database-oriented business methods
run within traditional threads that pass messages to the async part
of the application.
* A database side deadlock, e.g. rows are mutually deadlocked
* Threading errors, such as mutexes in a mutual deadlock, or calling
upon an already locked mutex in the same thread
Keep in mind an alternative to using pooling is to turn off pooling entirely.
See the section :ref:`pool_switching` for background on this. However, note
that when this error message is occurring, it is **always** due to a bigger
problem in the application itself; the pool just helps to reveal the problem
sooner.
.. seealso::
:ref:`pooling_toplevel`
:ref:`connections_toplevel`
.. _error_dbapi:
DBAPI Errors
============
The Python database API, or DBAPI, is a specification for database drivers
which can be located at `Pep-249 <https://www.python.org/dev/peps/pep-0249/>`_.
This API specifies a set of exception classes that accommodate the full range
of failure modes of the database.
SQLAlchemy does not generate these exceptions directly. Instead, they are
intercepted from the database driver and wrapped by the SQLAlchemy-provided
exception :class:`.DBAPIError`, however the messaging within the exception is
**generated by the driver, not SQLAlchemy**.
.. _error_rvf5:
InterfaceError
--------------
Exception raised for errors that are related to the database interface rather
than the database itself.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
The ``InterfaceError`` is sometimes raised by drivers in the context
of the database connection being dropped, or not being able to connect
to the database. For tips on how to deal with this, see the section
:ref:`pool_disconnects`.
.. _error_4xp6:
DatabaseError
--------------
Exception raised for errors that are related to the database itself, and not
the interface or data being passed.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
.. _error_9h9h:
DataError
---------
Exception raised for errors that are due to problems with the processed data
like division by zero, numeric value out of range, etc.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
.. _error_e3q8:
OperationalError
-----------------
Exception raised for errors that are related to the database's operation and
not necessarily under the control of the programmer, e.g. an unexpected
disconnect occurs, the data source name is not found, a transaction could not
be processed, a memory allocation error occurred during processing, etc.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
The ``OperationalError`` is the most common (but not the only) error class used
by drivers in the context of the database connection being dropped, or not
being able to connect to the database. For tips on how to deal with this, see
the section :ref:`pool_disconnects`.
.. _error_gkpj:
IntegrityError
--------------
Exception raised when the relational integrity of the database is affected,
e.g. a foreign key check fails.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
.. _error_2j85:
InternalError
-------------
Exception raised when the database encounters an internal error, e.g. the
cursor is not valid anymore, the transaction is out of sync, etc.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
The ``InternalError`` is sometimes raised by drivers in the context
of the database connection being dropped, or not being able to connect
to the database. For tips on how to deal with this, see the section
:ref:`pool_disconnects`.
.. _error_f405:
ProgrammingError
----------------
Exception raised for programming errors, e.g. table not found or already
exists, syntax error in the SQL statement, wrong number of parameters
specified, etc.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
The ``ProgrammingError`` is sometimes raised by drivers in the context
of the database connection being dropped, or not being able to connect
to the database. For tips on how to deal with this, see the section
:ref:`pool_disconnects`.
.. _error_tw8g:
NotSupportedError
------------------
Exception raised in case a method or database API was used which is not
supported by the database, e.g. requesting a .rollback() on a connection that
does not support transaction or has transactions turned off.
This error is a :ref:`DBAPI Error <error_dbapi>` and originates from
the database driver (DBAPI), not SQLAlchemy itself.
SQL Expression Language
=======================
TypeError: <operator> not supported between instances of 'ColumnProperty' and <something>
-----------------------------------------------------------------------------------------
This often occurs when attempting to use a :func:`.column_property` or
:func:`.deferred` object in the context of a SQL expression, usually within
declarative such as::
class Bar(Base):
__tablename__ = 'bar'
id = Column(Integer, primary_key=True)
cprop = deferred(Column(Integer))
__table_args__ = (
CheckConstraint(cprop > 5),
)
Above, the ``cprop`` attribute is used inline before it has been mapped,
however this ``cprop`` attribute is not a :class:`.Column`,
it's a :class:`.ColumnProperty`, which is an interim object and therefore
does not have the full functionality of either the :class:`.Column` object
or the :class:`.InstrmentedAttribute` object that will be mapped onto the
``Bar`` class once the declarative process is complete.
While the :class:`.ColumnProperty` does have a ``__clause_element__()`` method,
which allows it to work in some column-oriented contexts, it can't work in an
open-ended comparison context as illustrated above, since it has no Python
``__eq__()`` method that would allow it to interpret the comparison to the
number "5" as a SQL expression and not a regular Python comparison.
The solution is to access the :class:`.Column` directly using the
:attr:`.ColumnProperty.expression` attribute::
class Bar(Base):
__tablename__ = 'bar'
id = Column(Integer, primary_key=True)
cprop = deferred(Column(Integer))
__table_args__ = (
CheckConstraint(cprop.expression > 5),
)
.. _error_2afi:
This Compiled object is not bound to any Engine or Connection
-------------------------------------------------------------
This error refers to the concept of "bound metadata", described at
:ref:`dbengine_implicit`. The issue occurs when one invokes the
:meth:`.Executable.execute` method directly off of a Core expression object
that is not associated with any :class:`.Engine`::
metadata = MetaData()
table = Table('t', metadata, Column('q', Integer))
stmt = select([table])
result = stmt.execute() # <--- raises
What the logic is expecting is that the :class:`.MetaData` object has
been **bound** to a :class:`.Engine`::
engine = create_engine("mysql+pymysql://user:pass@host/db")
metadata = MetaData(bind=engine)
Where above, any statement that derives from a :class:`.Table` which
in turn derives from that :class:`.MetaData` will implicitly make use of
the given :class:`.Engine` in order to invoke the statement.
Note that the concept of bound metadata is a **legacy pattern** and in most
cases is **highly discouraged**. The best way to invoke the statement is
to pass it to the :meth:`.Connection.execute` method of a :class:`.Connection`::
with engine.connect() as conn:
result = conn.execute(stmt)
When using the ORM, a similar facility is available via the :class:`.Session`::
result = session.exxecute(stmt)
.. seealso::
:ref:`dbengine_implicit`
.. _error_cd3x:
A value is required for bind parameter <x> (in parameter group <y>)
-------------------------------------------------------------------
This error occurs when a statement makes use of :func:`.bindparam` either
implicitly or explicitly and does not provide a value when the statement
is executed::
stmt = select([table.c.column]).where(table.c.id == bindparam('my_param'))
result = conn.execute(stmt)
Above, no value has been provided for the parameter "my_param". The correct
approach is to provide a value::
result = conn.execute(stmt, my_param=12)
When the message takes the form "a value is required for bind parameter <x>
in parameter group <y>", the message is referring to the "executemany" style
of execution. In this case, the statement is typically an INSERT, UPDATE,
or DELETE and a list of parameters is being passed. In this format, the
statement may be generated dynamically to include parameter positions for
every parameter given in the argument list, where it will use the
**first set of parameters** to determine what these should be.
For example, the statement below is calculated based on the first parameter
set to require the parameters, "a", "b", and "c" - these names determine
the final string format of the statement which will be used for each
set of parameters in the list. As the second entry does not contain "b",
this error is generated::
m = MetaData()
t = Table(
't', m,
Column('a', Integer),
Column('b', Integer),
Column('c', Integer)
)
e.execute(
t.insert(), [
{"a": 1, "b": 2, "c": 3},
{"a": 2, "c": 4},
{"a": 3, "b": 4, "c": 5},
]
)
sqlalchemy.exc.StatementError: (sqlalchemy.exc.InvalidRequestError)
A value is required for bind parameter 'b', in parameter group 1
[SQL: u'INSERT INTO t (a, b, c) VALUES (?, ?, ?)']
[parameters: [{'a': 1, 'c': 3, 'b': 2}, {'a': 2, 'c': 4}, {'a': 3, 'c': 5, 'b': 4}]]
Since "b" is required, pass it as ``None`` so that the INSERT may proceed::
e.execute(
t.insert(), [
{"a": 1, "b": 2, "c": 3},
{"a": 2, "b": None, "c": 4},
{"a": 3, "b": 4, "c": 5},
]
)
.. seealso::
:ref:`coretutorial_bind_param`
:ref:`execute_multiple`
Object Relational Mapping
=========================
.. _error_bhk3:
Parent instance <x> is not bound to a Session; (lazy load/deferred load/refresh/etc.) operation cannot proceed
--------------------------------------------------------------------------------------------------------------
This is likely the most common error message when dealing with the ORM, and it
occurs as a result of the nature of a technique the ORM makes wide use of known
as :term:`lazy loading`. Lazy loading is a common object-relational pattern
whereby an object that's persisted by the ORM maintains a proxy to the database
itself, such that when various attributes upon the object are accessed, their
value may be retrieved from the database *lazily*. The advantage to this
approach is that objects can be retrieved from the database without having
to load all of their attributes or related data at once, and instead only that
data which is requested can be delivered at that time. The major disadvantage
is basically a mirror image of the advantage, which is that if lots of objects
are being loaded which are known to require a certain set of data in all cases,
it is wasteful to load that additional data piecemeal.
Another caveat of lazy loading beyond the usual efficiency concerns is that
in order for lazy loading to proceed, the object has to **remain associated
with a Session** in order to be able to retrieve its state. This error message
means that an object has become de-associated with its :class:`.Session` and
is being asked to lazy load data from the database.
The most common reason that objects become detached from their :class:`.Session`
is that the session itself was closed, typically via the :meth:`.Session.close`
method. The objects will then live on to be accessed further, very often
within web applications where they are delivered to a server-side templating
engine and are asked for further attributes which they cannot load.
Mitigation of this error is via two general techniques:
* **Don't close the session prematurely** - Often, applications will close
out a transaction before passing off related objects to some other system
which then fails due to this error. Sometimes the transaction doesn't need
to be closed so soon; an example is the web application closes out
the transaction before the view is rendered. This is often done in the name
of "correctness", but may be seen as a mis-application of "encapsulation",
as this term refers to code organization, not actual actions. The template that
uses an ORM object is making use of the `proxy pattern <https://en.wikipedia.org/wiki/Proxy_pattern>`_
which keeps database logic encapsulated from the caller. If the
:class:`.Session` can be held open until the lifespan of the objects are done,
this is the best approach.
* **Load everything that's needed up front** - It is very often impossible to
keep the transaction open, especially in more complex applications that need
to pass objects off to other systems that can't run in the same context
even though they're in the same process. In this case, the application
should try to make appropriate use of :term:`eager loading` to ensure
that objects have what they need up front. As an additional measure,
special directives like the :func:`.raiseload` option can ensure that
systems don't call upon lazy loading when its not expected.
.. seealso::
:ref:`loading_toplevel` - detailed documentation on eager loading and other
relationship-oriented loading techniques
Core Exception Classes
======================
See :ref:`core_exceptions_toplevel` for Core exception classes.
ORM Exception Classes
======================
See :ref:`orm_exceptions_toplevel` for ORM exception classes.
+189 -15
View File
@@ -22,7 +22,7 @@ refers to a :class:`.QueuePool` as a source of connectivity.
For more detail, see :ref:`engines_toplevel` and :ref:`pooling_toplevel`.
How do I pass custom connect arguments to my database API?
-----------------------------------------------------------
----------------------------------------------------------
The :func:`.create_engine` call accepts additional arguments either
directly via the ``connect_args`` keyword argument::
@@ -42,28 +42,121 @@ in the query string of the URL::
"MySQL Server has gone away"
----------------------------
There are two major causes for this error:
The primary cause of this error is that the MySQL connection has timed out
and has been closed by the server. The MySQL server closes connections
which have been idle a period of time which defaults to eight hours.
To accommodate this, the immediate setting is to enable the
:paramref:`.create_engine.pool_recycle` setting, which will ensure that a
connection which is older than a set amount of seconds will be discarded
and replaced with a new connection when it is next checked out.
1. The MySQL client closes connections which have been idle for a set period
of time, defaulting to eight hours. This can be avoided by using the ``pool_recycle``
setting with :func:`.create_engine`, described at :ref:`mysql_connection_timeouts`.
For the more general case of accommodating database restarts and other
temporary loss of connectivity due to network issues, connections that
are in the pool may be recycled in response to more generalized disconnect
detection techniques. The section :ref:`pool_disconnects` provides
background on both "pessimistic" (e.g. pre-ping) and "optimistic"
(e.g. graceful recovery) techniques. Modern SQLAlchemy tends to favor
the "pessimistic" approach.
.. seealso::
:ref:`pool_disconnects`
.. _mysql_sync_errors:
"Commands out of sync; you can't run this command now" / "This result object does not return rows. It has been closed automatically"
------------------------------------------------------------------------------------------------------------------------------------
The MySQL drivers have a fairly wide class of failure modes whereby the state of
the connection to the server is in an invalid state. Typically, when the connection
is used again, one of these two error messages will occur. The reason is because
the state of the server has been changed to one in which the client library
does not expect, such that when the client library emits a new statement
on the connection, the server does not respond as expected.
In SQLAlchemy, because database connections are pooled, the issue of the messaging
being out of sync on a connection becomes more important, since when an operation
fails, if the connection itself is in an unusable state, if it goes back into the
connection pool, it will malfunction when checked out again. The mitigation
for this issue is that the connection is **invalidated** when such a failure
mode occurs so that the underlying database connection to MySQL is discarded.
This invalidation occurs automatically for many known failure modes and can
also be called explicitly via the :meth:`.Connection.invalidate` method.
There is also a second class of failure modes within this category where a context manager
such as ``with session.begin_nested():`` wants to "roll back" the transaction
when an error occurs; however within some failure modes of the connection, the
rollback itself (which can also be a RELEASE SAVEPOINT operation) also
fails, causing misleading stack traces.
Originally, the cause of this error used to be fairly simple, it meant that
a multithreaded program was invoking commands on a single connection from more
than one thread. This applied to the original "MySQLdb" native-C driver that was
pretty much the only driver in use. However, with the introduction of pure Python
drivers like PyMySQL and MySQL-connector-Python, as well as increased use of
tools such as gevent/eventlet, multiprocessing (often with Celery), and others,
there is a whole series of factors that has been known to cause this problem, some of
which have been improved across SQLAlchemy versions but others which are unavoidable:
* **Sharing a connection among threads** - This is the original reason these kinds
of errors occurred. A program used the same connection in two or more threads at
the same time, meaning multiple sets of messages got mixed up on the connection,
putting the server-side session into a state that the client no longer knows how
to interpret. However, other causes are usually more likely today.
* **Sharing the filehandle for the connection among processes** - This usually occurs
when a program uses ``os.fork()`` to spawn a new process, and a TCP connection
that is present in th parent process gets shared into one or more child processes.
As multiple processes are now emitting messages to essentially the same filehandle,
the server receives interleaved messages and breaks the state of the connection.
This scenario can occur very easily if a program uses Python's "multiprocessing"
module and makes use of an :class:`.Engine` that was created in the parent
process. It's common that "multiprocessing" is in use when using tools like
Celery. The correct approach should be either that a new :class:`.Engine`
is produced when a child process first starts, discarding any :class:`.Engine`
that came down from the parent process; or, the :class:`.Engine` that's inherited
from the parent process can have it's internal pool of connections disposed by
calling :meth:`.Engine.dispose`.
* **Greenlet Monkeypatching w/ Exits** - When using a library like gevent or eventlet
that monkeypatches the Python networking API, libraries like PyMySQL are now
working in an asynchronous mode of operation, even though they are not developed
explicitly against this model. A common issue is that a greenthread is interrupted,
often due to timeout logic in the application. This results in the ``GreenletExit``
exception being raised, and the pure-Python MySQL driver is interrupted from
its work, which may have been that it was receiving a response from the server
or preparing to otherwise reset the state of the connection. When the exception
cuts all that work short, the conversation between client and server is now
out of sync and subsequent usage of the connection may fail. SQLAlchemy
as of version 1.1.0 knows how to guard against this, as if a database operation
is interrupted by a so-called "exit exception", which includes ``GreenletExit``
and any other subclass of Python ``BaseException`` that is not also a subclass
of ``Exception``, the connection is invalidated.
* **Rollbacks / SAVEPOINT releases failing** - Some classes of error cause
the connection to be unusable within the context of a transaction, as well
as when operating in a "SAVEPOINT" block. In these cases, the failure
on the connection has rendered any SAVEPOINT as no longer existing, yet
when SQLAlchemy, or the application, attempts to "roll back" this savepoint,
the "RELEASE SAVEPOINT" operation fails, typically with a message like
"savepoint does not exist". In this case, under Python 3 there will be
a chain of exceptions output, where the ultimate "cause" of the error
will be displayed as well. Under Python 2, there are no "chained" exceptions,
however recent versions of SQLAlchemy will attempt to emit a warning
illustrating the original failure cause, while still throwing the
immediate error which is the failure of the ROLLBACK.
2. Usage of the MySQLdb :term:`DBAPI`, or a similar DBAPI, in a non-threadsafe manner, or in an otherwise
inappropriate way. The MySQLdb connection object is not threadsafe - this expands
out to any SQLAlchemy system that links to a single connection, which includes the ORM
:class:`.Session`. For background
on how :class:`.Session` should be used in a multithreaded environment,
see :ref:`session_faq_threadsafe`.
Why does SQLAlchemy issue so many ROLLBACKs?
---------------------------------------------
--------------------------------------------
SQLAlchemy currently assumes DBAPI connections are in "non-autocommit" mode -
this is the default behavior of the Python database API, meaning it
must be assumed that a transaction is always in progress. The
connection pool issues ``connection.rollback()`` when a connection is returned.
This is so that any transactional resources remaining on the connection are
released. On a database like Postgresql or MSSQL where table resources are
released. On a database like PostgreSQL or MSSQL where table resources are
aggressively locked, this is critical so that rows and tables don't remain
locked within connections that are no longer in use. An application can
otherwise hang. It's not just for locks, however, and is equally critical on
@@ -74,7 +167,7 @@ isolation. For background on why you might see stale data even on MySQL, see
http://dev.mysql.com/doc/refman/5.1/en/innodb-transaction-model.html
I'm on MyISAM - how do I turn it off?
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The behavior of the connection pool's connection return behavior can be
configured using ``reset_on_return``::
@@ -85,7 +178,7 @@ configured using ``reset_on_return``::
engine = create_engine('mysql://scott:tiger@localhost/myisam_database', pool=QueuePool(reset_on_return=False))
I'm on SQL Server - how do I turn those ROLLBACKs into COMMITs?
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
``reset_on_return`` accepts the values ``commit``, ``rollback`` in addition
to ``True``, ``False``, and ``None``. Setting to ``commit`` will cause
@@ -136,3 +229,84 @@ when :meth:`.Connection.close` is called::
conn.detach() # detaches the DBAPI connection from the connection pool
conn.connection.<go nuts>
conn.close() # connection is closed for real, the pool replaces it with a new connection
How do I use engines / connections / sessions with Python multiprocessing, or os.fork()?
----------------------------------------------------------------------------------------
The key goal with multiple python processes is to prevent any database connections
from being shared across processes. Depending on specifics of the driver and OS,
the issues that arise here range from non-working connections to socket connections that
are used by multiple processes concurrently, leading to broken messaging (the latter
case is typically the most common).
The SQLAlchemy :class:`.Engine` object refers to a connection pool of existing
database connections. So when this object is replicated to a child process,
the goal is to ensure that no database connections are carried over. There
are three general approaches to this:
1. Disable pooling using :class:`.NullPool`. This is the most simplistic,
one shot system that prevents the :class:`.Engine` from using any connection
more than once.
2. Call :meth:`.Engine.dispose` on any given :class:`.Engine` as soon one is
within the new process. In Python multiprocessing, constructs such as
``multiprocessing.Pool`` include "initializer" hooks which are a place
that this can be performed; otherwise at the top of where ``os.fork()``
or where the ``Process`` object begins the child fork, a single call
to :meth:`.Engine.dispose` will ensure any remaining connections are flushed.
3. An event handler can be applied to the connection pool that tests for connections
being shared across process boundaries, and invalidates them. This looks like
the following::
import os
import warnings
from sqlalchemy import event
from sqlalchemy import exc
def add_engine_pidguard(engine):
"""Add multiprocessing guards.
Forces a connection to be reconnected if it is detected
as having been shared to a sub-process.
"""
@event.listens_for(engine, "connect")
def connect(dbapi_connection, connection_record):
connection_record.info['pid'] = os.getpid()
@event.listens_for(engine, "checkout")
def checkout(dbapi_connection, connection_record, connection_proxy):
pid = os.getpid()
if connection_record.info['pid'] != pid:
# substitute log.debug() or similar here as desired
warnings.warn(
"Parent process %(orig)s forked (%(newproc)s) with an open "
"database connection, "
"which is being discarded and recreated." %
{"newproc": pid, "orig": connection_record.info['pid']})
connection_record.connection = connection_proxy.connection = None
raise exc.DisconnectionError(
"Connection record belongs to pid %s, "
"attempting to check out in pid %s" %
(connection_record.info['pid'], pid)
)
These events are applied to an :class:`.Engine` as soon as its created::
engine = create_engine("...")
add_engine_pidguard(engine)
The above strategies will accommodate the case of an :class:`.Engine`
being shared among processes. However, for the case of a transaction-active
:class:`.Session` or :class:`.Connection` being shared, there's no automatic
fix for this; an application needs to ensure a new child process only
initiate new :class:`.Connection` objects and transactions, as well as ORM
:class:`.Session` objects. For a :class:`.Session` object, technically
this is only needed if the session is currently transaction-bound, however
the scope of a single :class:`.Session` is in any case intended to be
kept within a single call stack in any case (e.g. not a global object, not
shared between processes or threads).
+2 -2
View File
@@ -1,8 +1,8 @@
.. _faq_toplevel:
============================
==========================
Frequently Asked Questions
============================
==========================
The Frequently Asked Questions section is a growing collection of commonly
observed questions to well-known issues.
+10 -10
View File
@@ -1,6 +1,6 @@
==================
=================
MetaData / Schema
==================
=================
.. contents::
:local:
@@ -56,7 +56,7 @@ A more comprehensive option is to use schema migration tools, such as Alembic
or SQLAlchemy-Migrate; see :ref:`schema_migrations` for discussion on this.
How can I sort Table objects in order of their dependency?
===========================================================================
==========================================================
This is available via the :attr:`.MetaData.sorted_tables` function::
@@ -64,35 +64,35 @@ This is available via the :attr:`.MetaData.sorted_tables` function::
# ... add Table objects to metadata
ti = metadata.sorted_tables:
for t in ti:
print t
print(t)
How can I get the CREATE TABLE/ DROP TABLE output as a string?
===========================================================================
==============================================================
Modern SQLAlchemy has clause constructs which represent DDL operations. These
can be rendered to strings like any other SQL expression::
from sqlalchemy.schema import CreateTable
print CreateTable(mytable)
print(CreateTable(mytable))
To get the string specific to a certain engine::
print CreateTable(mytable).compile(engine)
print(CreateTable(mytable).compile(engine))
There's also a special form of :class:`.Engine` that can let you dump an entire
metadata creation sequence, using this recipe::
def dump(sql, *multiparams, **params):
print sql.compile(dialect=engine.dialect)
print(sql.compile(dialect=engine.dialect))
engine = create_engine('postgresql://', strategy='mock', executor=dump)
metadata.create_all(engine, checkfirst=False)
The `Alembic <https://bitbucket.org/zzzeek/alembic>`_ tool also supports
The `Alembic <https://alembic.sqlalchemy.org>`_ tool also supports
an "offline" SQL generation mode that renders database migrations as SQL scripts.
How can I subclass Table/Column to provide certain behaviors/configurations?
=============================================================================
============================================================================
:class:`.Table` and :class:`.Column` are not good targets for direct subclassing.
However, there are simple ways to get on-construction behaviors using creation
+10 -7
View File
@@ -1,5 +1,5 @@
ORM Configuration
==================
=================
.. contents::
:local:
@@ -72,7 +72,7 @@ columns::
How do I configure a Column that is a Python reserved word or similar?
----------------------------------------------------------------------------
----------------------------------------------------------------------
Column-based attributes can be given any name desired in the mapping. See
:ref:`mapper_column_distinct_names`.
@@ -89,7 +89,8 @@ To get at the :class:`.Mapper` for a particular mapped class, call the
mapper = inspect(MyClass)
From there, all information about the class can be acquired using such methods as:
From there, all information about the class can be accessed through properties
such as:
* :attr:`.Mapper.attrs` - a namespace of all mapped attributes. The attributes
themselves are instances of :class:`.MapperProperty`, which contain additional
@@ -293,7 +294,7 @@ the two queries may not see the same results:
ORDER BY anon_1.users_id
Depending on database specifics, there is
a chance we may get the a result like the following for the two queries::
a chance we may get a result like the following for the two queries::
-- query #1
+--------+
@@ -325,9 +326,11 @@ The primary key is a good choice for this::
session.query(User).options(subqueryload(User.addresses)).order_by(User.id).first()
Note that :func:`.joinedload` does not suffer from the same problem because
only one query is ever issued, so the load query cannot be different from the
main query.
Note that the :func:`.joinedload` eager loader strategy does not suffer from
the same problem because only one query is ever issued, so the load query
cannot be different from the main query. Similarly, the :func:`.selectinload`
eager loader strategy also does not have this issue as it links its collection
loads directly to primary key values just loaded.
.. seealso::
+51 -28
View File
@@ -13,11 +13,11 @@ Performance
How can I profile a SQLAlchemy powered application?
---------------------------------------------------
Looking for performance issues typically involves two stratgies. One
Looking for performance issues typically involves two strategies. One
is query profiling, and the other is code profiling.
Query Profiling
^^^^^^^^^^^^^^^^
^^^^^^^^^^^^^^^
Sometimes just plain SQL logging (enabled via python's logging module
or via the ``echo=True`` argument on :func:`.create_engine`) can give an
@@ -104,7 +104,7 @@ Below is a simple recipe which works profiling into a context manager::
ps.print_stats()
# uncomment this to see who's calling what
# ps.print_callers()
print s.getvalue()
print(s.getvalue())
To profile a section of code::
@@ -154,7 +154,7 @@ analysis of the query plan is warranted, using a system such as EXPLAIN,
SHOW PLAN, etc. as is provided by the database backend.
Result Fetching Slowness - Core
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
If on the other hand you see many thousands of calls related to fetching rows,
or very long calls to ``fetchall()``, it may
@@ -223,7 +223,7 @@ that could indicate that everything is fast except for the actual network connec
and too much time is spent with data moving over the network.
Result Fetching Slowness - ORM
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
To detect slowness in ORM fetching of rows (which is the most common area
of performance concern), calls like ``populate_state()`` and ``_instance()`` will
@@ -258,7 +258,7 @@ Common strategies to mitigate this include:
* Use result caching - see :ref:`examples_caching` for an in-depth example
of this.
* Consider a faster interpreter like that of Pypy.
* Consider a faster interpreter like that of PyPy.
The output of a profile can be a little daunting but after some
practice they are very easy to read.
@@ -269,7 +269,7 @@ practice they are very easy to read.
with bundled profiling capabilities.
I'm inserting 400,000 rows with the ORM and it's really slow!
--------------------------------------------------------------
-------------------------------------------------------------
The SQLAlchemy ORM uses the :term:`unit of work` pattern when synchronizing
changes to the database. This pattern goes far beyond simple "inserts"
@@ -298,6 +298,12 @@ SQL generation and execution system that the ORM builds on top of
is part of the :doc:`Core <core/tutorial>`. Using this system directly, we can produce an INSERT that
is competitive with using the raw database API directly.
.. note::
When using the psycopg2 dialect, consider making use of the
:ref:`batch execution helpers <psycopg2_batch_mode>` feature of psycopg2,
now supported directly by the SQLAlchemy psycopg2 dialect.
Alternatively, the SQLAlchemy ORM offers the :ref:`bulk_operations`
suite of methods, which provide hooks into subsections of the unit of
work process in order to emit Core-level INSERT and UPDATE constructs with
@@ -307,20 +313,21 @@ The example below illustrates time-based tests for several different
methods of inserting rows, going from the most automated to the least.
With cPython 2.7, runtimes observed::
classics-MacBook-Pro:sqlalchemy classic$ python test.py
SQLAlchemy ORM: Total time for 100000 records 12.0471920967 secs
SQLAlchemy ORM pk given: Total time for 100000 records 7.06283402443 secs
SQLAlchemy ORM bulk_save_objects(): Total time for 100000 records 0.856323003769 secs
SQLAlchemy Core: Total time for 100000 records 0.485800027847 secs
sqlite3: Total time for 100000 records 0.487842082977 sec
SQLAlchemy ORM: Total time for 100000 records 6.89754080772 secs
SQLAlchemy ORM pk given: Total time for 100000 records 4.09481811523 secs
SQLAlchemy ORM bulk_save_objects(): Total time for 100000 records 1.65821218491 secs
SQLAlchemy ORM bulk_insert_mappings(): Total time for 100000 records 0.466513156891 secs
SQLAlchemy Core: Total time for 100000 records 0.21024107933 secs
sqlite3: Total time for 100000 records 0.137335062027 sec
We can reduce the time by a factor of three using recent versions of `Pypy <http://pypy.org/>`_::
We can reduce the time by a factor of nearly three using recent versions of `PyPy <http://pypy.org/>`_::
classics-MacBook-Pro:sqlalchemy classic$ /usr/local/src/pypy-2.1-beta2-osx64/bin/pypy test.py
SQLAlchemy ORM: Total time for 100000 records 5.88369488716 secs
SQLAlchemy ORM pk given: Total time for 100000 records 3.52294301987 secs
SQLAlchemy Core: Total time for 100000 records 0.613556146622 secs
sqlite3: Total time for 100000 records 0.442467927933 sec
SQLAlchemy ORM: Total time for 100000 records 2.39429616928 secs
SQLAlchemy ORM pk given: Total time for 100000 records 1.51412987709 secs
SQLAlchemy ORM bulk_save_objects(): Total time for 100000 records 0.568987131119 secs
SQLAlchemy ORM bulk_insert_mappings(): Total time for 100000 records 0.320806980133 secs
SQLAlchemy Core: Total time for 100000 records 0.206904888153 secs
sqlite3: Total time for 100000 records 0.165791988373 sec
Script::
@@ -370,7 +377,7 @@ Script::
init_sqlalchemy()
t0 = time.time()
for i in xrange(n):
customer = Customer(id=i+1, name="NAME " + str(i))
customer = Customer(id=i + 1, name="NAME " + str(i))
DBSession.add(customer)
if i % 1000 == 0:
DBSession.flush()
@@ -380,17 +387,14 @@ Script::
" records " + str(time.time() - t0) + " secs")
def test_sqlalchemy_orm_bulk_insert(n=100000):
def test_sqlalchemy_orm_bulk_save_objects(n=100000):
init_sqlalchemy()
t0 = time.time()
n1 = n
while n1 > 0:
n1 = n1 - 10000
DBSession.bulk_insert_mappings(
Customer,
for chunk in range(0, n, 10000):
DBSession.bulk_save_objects(
[
dict(name="NAME " + str(i))
for i in xrange(min(10000, n1))
Customer(name="NAME " + str(i))
for i in xrange(chunk, min(chunk + 10000, n))
]
)
DBSession.commit()
@@ -399,6 +403,23 @@ Script::
" records " + str(time.time() - t0) + " secs")
def test_sqlalchemy_orm_bulk_insert(n=100000):
init_sqlalchemy()
t0 = time.time()
for chunk in range(0, n, 10000):
DBSession.bulk_insert_mappings(
Customer,
[
dict(name="NAME " + str(i))
for i in xrange(chunk, min(chunk + 10000, n))
]
)
DBSession.commit()
print(
"SQLAlchemy ORM bulk_insert_mappings(): Total time for " + str(n) +
" records " + str(time.time() - t0) + " secs")
def test_sqlalchemy_core(n=100000):
init_sqlalchemy()
t0 = time.time()
@@ -437,7 +458,9 @@ Script::
if __name__ == '__main__':
test_sqlalchemy_orm(100000)
test_sqlalchemy_orm_pk_given(100000)
test_sqlalchemy_orm_bulk_save_objects(100000)
test_sqlalchemy_orm_bulk_insert(100000)
test_sqlalchemy_core(100000)
test_sqlite3(100000)
+107 -8
View File
@@ -1,5 +1,5 @@
Sessions / Queries
===================
==================
.. contents::
:local:
@@ -135,7 +135,7 @@ For a detailed discussion on how to organize usage of the :class:`.Session`,
please see :ref:`session_faq_whentocreate`.
But why does flush() insist on issuing a ROLLBACK?
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
It would be great if :meth:`.Session.flush` could partially complete and then not roll
back, however this is beyond its current capabilities since its internal
@@ -268,7 +268,7 @@ The joins generated by joined eager loading are only used to fully load related
collections, and are designed to have no impact on the primary results of the query.
Since they are anonymously aliased, they cannot be referenced directly.
For detail on this beahvior, see :doc:`orm/loading`.
For detail on this behavior, see :ref:`zen_of_eager_loading`.
Query has no ``__len__()``, why not?
------------------------------------
@@ -282,11 +282,11 @@ one::
class Iterates(object):
def __len__(self):
print "LEN!"
print("LEN!")
return 5
def __iter__(self):
print "ITER!"
print("ITER!")
return iter([1, 2, 3, 4, 5])
list(Iterates())
@@ -297,7 +297,7 @@ output::
LEN!
How Do I use Textual SQL with ORM Queries?
-------------------------------------------
------------------------------------------
See:
@@ -316,12 +316,12 @@ why isn't my ``__init__()`` called when I load objects?
See :ref:`mapping_constructors` for a description of this behavior.
how do I use ON DELETE CASCADE with SA's ORM?
----------------------------------------------
---------------------------------------------
SQLAlchemy will always issue UPDATE or DELETE statements for dependent
rows which are currently loaded in the :class:`.Session`. For rows which
are not loaded, it will by default issue SELECT statements to load
those rows and udpate/delete those as well; in other words it assumes
those rows and update/delete those as well; in other words it assumes
there is no ON DELETE CASCADE configured.
To configure SQLAlchemy to cooperate with ON DELETE CASCADE, see
:ref:`passive_deletes`.
@@ -417,6 +417,77 @@ The recipe `ExpireRelationshipOnFKChange <http://www.sqlalchemy.org/trac/wiki/Us
in order to coordinate the setting of foreign key attributes with many-to-one
relationships.
.. _faq_walk_objects:
How do I walk all objects that are related to a given object?
-------------------------------------------------------------
An object that has other objects related to it will correspond to the
:func:`.relationship` constructs set up between mappers. This code fragment will
iterate all the objects, correcting for cycles as well::
from sqlalchemy import inspect
def walk(obj):
deque = [obj]
seen = set()
while deque:
obj = deque.pop(0)
if obj in seen:
continue
else:
seen.add(obj)
yield obj
insp = inspect(obj)
for relationship in insp.mapper.relationships:
related = getattr(obj, relationship.key)
if relationship.uselist:
deque.extend(related)
elif related is not None:
deque.append(related)
The function can be demonstrated as follows::
Base = declarative_base()
class A(Base):
__tablename__ = 'a'
id = Column(Integer, primary_key=True)
bs = relationship("B", backref="a")
class B(Base):
__tablename__ = 'b'
id = Column(Integer, primary_key=True)
a_id = Column(ForeignKey('a.id'))
c_id = Column(ForeignKey('c.id'))
c = relationship("C", backref="bs")
class C(Base):
__tablename__ = 'c'
id = Column(Integer, primary_key=True)
a1 = A(bs=[B(), B(c=C())])
for obj in walk(a1):
print(obj)
Output::
<__main__.A object at 0x10303b190>
<__main__.B object at 0x103025210>
<__main__.B object at 0x10303b0d0>
<__main__.C object at 0x103025490>
Is there a way to automagically have only unique keywords (or other kinds of objects) without doing a query for the keyword and getting a reference to the row containing that keyword?
---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
@@ -426,4 +497,32 @@ Which is somewhat inconvenient.
This `UniqueObject <http://www.sqlalchemy.org/trac/wiki/UsageRecipes/UniqueObject>`_ recipe was created to address this issue.
.. _faq_post_update_update:
Why does post_update emit UPDATE in addition to the first UPDATE?
-----------------------------------------------------------------
The post_update feature, documented at :ref:`post_update`, involves that an
UPDATE statement is emitted in response to changes to a particular
relationship-bound foreign key, in addition to the INSERT/UPDATE/DELETE that
would normally be emitted for the target row. While the primary purpose of this
UPDATE statement is that it pairs up with an INSERT or DELETE of that row, so
that it can post-set or pre-unset a foreign key reference in order to break a
cycle with a mutually dependent foreign key, it currently is also bundled as a
second UPDATE that emits when the target row itself is subject to an UPDATE.
In this case, the UPDATE emitted by post_update is *usually* unnecessary
and will often appear wasteful.
However, some research into trying to remove this "UPDATE / UPDATE" behavior
reveals that major changes to the unit of work process would need to occur not
just throughout the post_update implementation, but also in areas that aren't
related to post_update for this to work, in that the order of operations would
need to be reversed on the non-post_update side in some cases, which in turn
can impact other cases, such as correctly handling an UPDATE of a referenced
primary key value (see :ticket:`1063` for a proof of concept).
The answer is that "post_update" is used to break a cycle between two
mutually dependent foreign keys, and to have this cycle breaking be limited
to just INSERT/DELETE of the target table implies that the ordering of UPDATE
statements elsewhere would need to be liberalized, leading to breakage
in other edge cases.
+79 -34
View File
@@ -1,5 +1,5 @@
SQL Expressions
=================
===============
.. contents::
:local:
@@ -88,53 +88,98 @@ producing output like::
WHERE mytable.x > my_fancy_formatting(5)
Why does ``.col.in_([])`` Produce ``col != col``? Why not ``1=0``?
-------------------------------------------------------------------
.. _faq_sql_expression_op_parenthesis:
A little introduction to the issue. The IN operator in SQL, given a list of
elements to compare against a column, generally does not accept an empty list,
that is while it is valid to say::
I'm using op() to generate a custom operator and my parenthesis are not coming out correctly
---------------------------------------------------------------------------------------------
column IN (1, 2, 3)
The :meth:`.Operators.op` method allows one to create a custom database operator
otherwise not known by SQLAlchemy::
it's not valid to say::
>>> print(column('q').op('->')(column('p')))
q -> p
column IN ()
However, when using it on the right side of a compound expression, it doesn't
generate parenthesis as we expect::
SQLAlchemy's :meth:`.Operators.in_` operator, when given an empty list, produces this
expression::
>>> print((column('q1') + column('q2')).op('->')(column('p')))
q1 + q2 -> p
column != column
Where above, we probably want ``(q1 + q2) -> p``.
As of version 0.6, it also produces a warning stating that a less efficient
comparison operation will be rendered. This expression is the only one that is
both database agnostic and produces correct results.
The solution to this case is to set the precedence of the operator, using
the :paramref:`.Operators.op.precedence` parameter, to a high
number, where 100 is the maximum value, and the highest number used by any
SQLAlchemy operator is currently 15::
For example, the naive approach of "just evaluate to false, by comparing 1=0
or 1!=1", does not handle nulls properly. An expression like::
>>> print((column('q1') + column('q2')).op('->', precedence=100)(column('p')))
(q1 + q2) -> p
NOT column != column
We can also usually force parenthesization around a binary expression (e.g.
an expression that has left/right operands and an operator) using the
:meth:`.ColumnElement.self_group` method::
will not return a row when "column" is null, but an expression which does not
take the column into account::
>>> print((column('q1') + column('q2')).self_group().op('->')(column('p')))
(q1 + q2) -> p
NOT 1=0
Why are the parentheses rules like this?
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
will.
A lot of databases barf when there are excessive parenthesis or when
parenthesis are in unusual places they doesn't expect, so SQLAlchemy does not
generate parenthesis based on groupings, it uses operator precedence and if the
operator is known to be associative, so that parenthesis are generated
minimally. Otherwise, an expression like::
Closer to the mark is the following CASE expression::
column('a') & column('b') & column('c') & column('d')
CASE WHEN column IS NOT NULL THEN 1=0 ELSE NULL END
would produce::
We don't use this expression due to its verbosity, and its also not
typically accepted by Oracle within a WHERE clause - depending
on how you phrase it, you'll either get "ORA-00905: missing keyword" or
"ORA-00920: invalid relational operator". It's also still less efficient than
just rendering SQL without the clause altogether (or not issuing the SQL at
all, if the statement is just a simple search).
(((a AND b) AND c) AND d)
The best approach therefore is to avoid the usage of IN given an argument list
of zero length. Instead, don't emit the Query in the first place, if no rows
should be returned. The warning is best promoted to a full error condition
using the Python warnings filter (see http://docs.python.org/library/warnings.html).
which is fine but would probably annoy people (and be reported as a bug). In
other cases, it leads to things that are more likely to confuse databases or at
the very least readability, such as::
column('q', ARRAY(Integer, dimensions=2))[5][6]
would produce::
((q[5])[6])
There are also some edge cases where we get things like ``"(x) = 7"`` and databases
really don't like that either. So parenthesization doesn't naively
parenthesize, it uses operator precedence and associativity to determine
groupings.
For :meth:`.Operators.op`, the value of precedence defaults to zero.
What if we defaulted the value of :paramref:`.Operators.op.precedence` to 100,
e.g. the highest? Then this expression makes more parenthesis, but is
otherwise OK, that is, these two are equivalent::
>>> print (column('q') - column('y')).op('+', precedence=100)(column('z'))
(q - y) + z
>>> print (column('q') - column('y')).op('+')(column('z'))
q - y + z
but these two are not::
>>> print column('q') - column('y').op('+', precedence=100)(column('z'))
q - y + z
>>> print column('q') - column('y').op('+')(column('z'))
q - (y + z)
For now, it's not clear that as long as we are doing parenthesization based on
operator precedence and associativity, if there is really a way to parenthesize
automatically for a generic operator with no precedence given that is going to
work in all cases, because sometimes you want a custom op to have a lower
precedence than the other operators and sometimes you want it to be higher.
It is possible that maybe if the "binary" expression above forced the use of
the ``self_group()`` method when ``op()`` is called, making the assumption that
a compound expression on the left side can always be parenthesized harmlessly.
Perhaps this change can be made at some point, however for the time being
keeping the parenthesization rules more internally consistent seems to be
the safer approach.
+31 -13
View File
@@ -60,7 +60,7 @@ Glossary
``__delete__()`` methods. The :class:`.InstrumentedAttribute`
will generate a SQL expression when used at the class level::
>>> print MyClass.data == 5
>>> print(MyClass.data == 5)
data = :data_1
and at the instance level, keeps track of changes to values,
@@ -103,7 +103,7 @@ Glossary
Instrumentation refers to the process of augmenting the functionality
and attribute set of a particular class. Ideally, the
behavior of the class should remain close to a regular
class, except that additional behviors and features are
class, except that additional behaviors and features are
made available. The SQLAlchemy :term:`mapping` process,
among other things, adds database-enabled :term:`descriptors`
to a mapped
@@ -129,6 +129,7 @@ Glossary
lazy load
lazy loads
lazy loaded
lazy loading
In object relational mapping, a "lazy load" refers to an
attribute that does not contain its database-side value
@@ -245,7 +246,7 @@ Glossary
transactional resources", to indicate more explicitly that
what we are actually "releasing" is any transactional
state which as accumulated upon the connection. In most
situations, the proces of selecting from tables, emitting
situations, the process of selecting from tables, emitting
updates, etc. acquires :term:`isolated` state upon
that connection as well as potential row or table locks.
This state is all local to a particular transaction
@@ -359,7 +360,7 @@ Glossary
comprises the WHERE clause of the ``SELECT``.
FROM clause
The portion of the ``SELECT`` statement which incicates the initial
The portion of the ``SELECT`` statement which indicates the initial
source of rows.
A simple ``SELECT`` will feature one or more table names in its
@@ -513,7 +514,7 @@ Glossary
http://en.wikipedia.org/wiki/Atomicity_(database_systems)
consistency
Consistency is one of the compoments of the :term:`ACID` model,
Consistency is one of the components of the :term:`ACID` model,
and ensures that any transaction will
bring the database from one valid state to another. Any data
written to the database must be valid according to all defined
@@ -573,7 +574,7 @@ Glossary
were created, as well as a way to get at server-generated
default values in an atomic way.
An example of RETURNING, idiomatic to Postgresql, looks like::
An example of RETURNING, idiomatic to PostgreSQL, looks like::
INSERT INTO user_account (name) VALUES ('new name') RETURNING id, timestamp
@@ -584,14 +585,14 @@ Glossary
or SQL expressions can be placed into RETURNING, not just default-value columns).
The backends that currently support
RETURNING or a similar construct are Postgresql, SQL Server, Oracle,
and Firebird. The Postgresql and Firebird implementations are generally
RETURNING or a similar construct are PostgreSQL, SQL Server, Oracle,
and Firebird. The PostgreSQL and Firebird implementations are generally
full featured, whereas the implementations of SQL Server and Oracle
have caveats. On SQL Server, the clause is known as "OUTPUT INSERTED"
for INSERT and UPDATE statements and "OUTPUT DELETED" for DELETE statements;
the key caveat is that triggers are not supported in conjunction with this
keyword. On Oracle, it is known as "RETURNING...INTO", and requires that the
value be placed into an OUT paramter, meaning not only is the syntax awkward,
value be placed into an OUT parameter, meaning not only is the syntax awkward,
but it can also only be used for one row at a time.
SQLAlchemy's :meth:`.UpdateBase.returning` system provides a layer of abstraction
@@ -937,6 +938,8 @@ Glossary
http://en.wikipedia.org/wiki/Candidate_key
https://www.databasestar.com/database-keys/
primary key
primary key constraint
@@ -1019,7 +1022,7 @@ Glossary
http://en.wikipedia.org/wiki/Unique_key#Defining_unique_keys
transient
This describes one of the four major object states which
This describes one of the major object states which
an object can have within a :term:`session`; a transient object
is a new object that doesn't have any database identity
and has not been associated with a session yet. When the
@@ -1031,7 +1034,7 @@ Glossary
:ref:`session_object_states`
pending
This describes one of the four major object states which
This describes one of the major object states which
an object can have within a :term:`session`; a pending object
is a new object that doesn't have any database identity,
but has been recently associated with a session. When
@@ -1042,8 +1045,23 @@ Glossary
:ref:`session_object_states`
deleted
This describes one of the major object states which
an object can have within a :term:`session`; a deleted object
is an object that was formerly persistent and has had a
DELETE statement emitted to the database within a flush
to delete its row. The object will move to the :term:`detached`
state once the session's transaction is committed; alternatively,
if the session's transaction is rolled back, the DELETE is
reverted and the object moves back to the :term:`persistent`
state.
.. seealso::
:ref:`session_object_states`
persistent
This describes one of the four major object states which
This describes one of the major object states which
an object can have within a :term:`session`; a persistent object
is an object that has a database identity (i.e. a primary key)
and is currently associated with a session. Any object
@@ -1058,7 +1076,7 @@ Glossary
:ref:`session_object_states`
detached
This describes one of the four major object states which
This describes one of the major object states which
an object can have within a :term:`session`; a detached object
is an object that has a database identity (i.e. a primary key)
but is not associated with any session. An object that
+11 -3
View File
@@ -14,8 +14,9 @@ A high level view and getting set up.
:doc:`Overview <intro>` |
:ref:`Installation Guide <installation>` |
:doc:`Frequently Asked Questions <faq/index>` |
:doc:`Migration from 0.9 <changelog/migration_10>` |
:doc:`Migration from 1.2 <changelog/migration_13>` |
:doc:`Glossary <glossary>` |
:doc:`Error Messages <errors>` |
:doc:`Changelog catalog <changelog/index>`
SQLAlchemy ORM
@@ -38,7 +39,8 @@ of Python objects, proceed first to the tutorial.
:doc:`Association Proxy <orm/extensions/associationproxy>` |
:doc:`Hybrid Attributes <orm/extensions/hybrid>` |
:doc:`Automap <orm/extensions/automap>` |
:doc:`Mutable Scalars <orm/extensions/mutable>`
:doc:`Mutable Scalars <orm/extensions/mutable>` |
:doc:`Indexable <orm/extensions/indexable>`
* **ORM Usage:**
:doc:`Session Usage and Guidelines <orm/session>` |
@@ -96,5 +98,11 @@ Dialect Documentation
The **dialect** is the system SQLAlchemy uses to communicate with various types of DBAPIs and databases.
This section describes notes, options, and usage patterns regarding individual dialects.
:doc:`Index of all Dialects <dialects/index>`
:doc:`PostgreSQL <dialects/postgresql>` |
:doc:`MySQL <dialects/mysql>` |
:doc:`SQLite <dialects/sqlite>` |
:doc:`Oracle <dialects/oracle>` |
:doc:`Microsoft SQL Server <dialects/mssql>`
:doc:`More Dialects ... <dialects/index>`
+31 -58
View File
@@ -9,7 +9,7 @@ The SQLAlchemy SQL Toolkit and Object Relational Mapper
is a comprehensive set of tools for working with
databases and Python. It has several distinct areas of
functionality which can be used individually or combined
together. Its major components are illustrated in below,
together. Its major components are illustrated below,
with component dependencies organized into layers:
.. image:: sqla_arch_small.png
@@ -70,45 +70,44 @@ Supported Platforms
SQLAlchemy has been tested against the following platforms:
* cPython since version 2.6, through the 2.xx series
* cPython version 3, throughout all 3.xx series
* `Pypy <http://pypy.org/>`_ 2.1 or greater
* cPython 2.7
* cPython 3.4 and higher
* `PyPy <http://pypy.org/>`_ 2.1 or greater
.. versionchanged:: 0.9
Python 2.6 is now the minimum Python version supported.
.. versionchanged:: 1.2
Python 2.7 is now the minimum Python version supported.
Platforms that don't currently have support include Jython, IronPython.
.. versionchanged:: 1.3
Within the Python 3 series, 3.4 is now the minimum Python 3 version supported.
Platforms that don't currently have support include Jython and IronPython.
Jython has been supported in the past and may be supported in future
releases as well, depending on the state of Jython itself.
Supported Installation Methods
-------------------------------
SQLAlchemy supports installation using standard Python "distutils" or
"setuptools" methodologies. An overview of potential setups is as follows:
SQLAlchemy installation is via standard Python methodologies that are
based on `setuptools <http://pypi.python.org/pypi/setuptools/>`_, either
by referring to ``setup.py`` directly or by using
`pip <http://pypi.python.org/pypi/pip/>`_ or other setuptools-compatible
approaches.
* **Plain Python Distutils** - SQLAlchemy can be installed with a clean
Python install using the services provided via `Python Distutils <http://docs.python.org/distutils/>`_,
using the ``setup.py`` script. The C extensions as well as Python 3 builds are supported.
* **Setuptools or Distribute** - When using `setuptools <http://pypi.python.org/pypi/setuptools/>`_,
SQLAlchemy can be installed via ``setup.py`` or ``easy_install``, and the C
extensions are supported.
* **pip** - `pip <http://pypi.python.org/pypi/pip/>`_ is an installer that
rides on top of ``setuptools`` or ``distribute``, replacing the usage
of ``easy_install``. It is often preferred for its simpler mode of usage.
.. versionchanged:: 1.1 setuptools is now required by the setup.py file;
plain distutils installs are no longer supported.
Install via pip
---------------
When ``pip`` is available, the distribution can be
downloaded from Pypi and installed in one step::
downloaded from PyPI and installed in one step::
pip install SQLAlchemy
This command will download the latest **released** version of SQLAlchemy from the `Python
Cheese Shop <http://pypi.python.org/pypi/SQLAlchemy>`_ and install it to your system.
In order to install the latest **prerelease** version, such as ``1.0.0b1``,
In order to install the latest **prerelease** version, such as ``1.3.0b1``,
pip requires that the ``--pre`` flag be used::
pip install --pre SQLAlchemy
@@ -124,6 +123,8 @@ Otherwise, you can install from the distribution using the ``setup.py`` script::
python setup.py install
.. _c_extensions:
Installing the C Extensions
----------------------------------
@@ -131,14 +132,10 @@ SQLAlchemy includes C extensions which provide an extra speed boost for
dealing with result sets. The extensions are supported on both the 2.xx
and 3.xx series of cPython.
.. versionchanged:: 0.9.0
The C extensions now compile on Python 3 as well as Python 2.
``setup.py`` will automatically build the extensions if an appropriate platform is
detected. If the build of the C extensions fails, due to missing compiler or
other issue, the setup process will output a warning message, and re-run the
build without the C extensions, upon completion reporting final status.
detected. If the build of the C extensions fails due to a missing compiler or
other issue, the setup process will output a warning message and re-run the
build without the C extensions upon completion, reporting final status.
To run the build/install without even attempting to compile the C extensions,
the ``DISABLE_SQLALCHEMY_CEXT`` environment variable may be specified. The
@@ -146,36 +143,12 @@ use case for this is either for special testing circumstances, or in the rare
case of compatibility/build issues not overcome by the usual "rebuild"
mechanism::
# *** only in SQLAlchemy 0.9.4 / 0.8.6 or greater ***
export DISABLE_SQLALCHEMY_CEXT=1; python setup.py install
.. versionadded:: 0.9.4,0.8.6 Support for disabling the build of
C extensions using the ``DISABLE_SQLALCHEMY_CEXT`` environment variable
has been added. This allows control of C extension building whether or not
setuptools is available, and additionally works around the fact that
setuptools will possibly be **removing support** for command-line switches
such as ``--without-extensions`` in a future release.
.. versionchanged:: 1.1 The legacy ``--without-cextensions`` flag has been
removed from the installer as it relies on deprecated features of
setuptools.
For versions of SQLAlchemy prior to 0.9.4 or 0.8.6, the
``--without-cextensions`` option may be used to disable the attempt to build
C extensions, provided setupools is in use, and provided the ``Feature``
construct is supported by the installed version of setuptools::
python setup.py --without-cextensions install
Or with pip::
pip install --global-option='--without-cextensions' SQLAlchemy
Installing on Python 3
----------------------------------
SQLAlchemy runs directly on Python 2 or Python 3, and can be installed in
either environment without any adjustments or code conversion.
.. versionchanged:: 0.9.0 Python 3 is now supported in place with no 2to3 step
required.
Installing a Database API
@@ -189,7 +162,7 @@ the available DBAPIs for each database, including external links.
Checking the Installed SQLAlchemy Version
------------------------------------------
This documentation covers SQLAlchemy version 1.0. If you're working on a
This documentation covers SQLAlchemy version 1.3. If you're working on a
system that already has SQLAlchemy installed, check the version from your
Python prompt like this:
@@ -197,11 +170,11 @@ Python prompt like this:
>>> import sqlalchemy
>>> sqlalchemy.__version__ # doctest: +SKIP
1.0.0
1.3.0
.. _migration:
0.9 to 1.0 Migration
1.2 to 1.3 Migration
=====================
Notes on what's changed from 0.9 to 1.0 is available here at :doc:`changelog/migration_10`.
Notes on what's changed from 1.2 to 1.3 is available here at :doc:`changelog/migration_13`.
+5 -5
View File
@@ -71,7 +71,7 @@ is ``None``::
>>> a1 = Address()
>>> u1.addresses
[]
>>> print a1.user
>>> print(a1.user)
None
However, once the ``Address`` is appended to the ``u1.addresses`` collection,
@@ -105,7 +105,7 @@ exactly the same as if the above two relationships were created individually
using :paramref:`~.relationship.back_populates` on each.
Backref Arguments
~~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~~
We've established that the :paramref:`~.relationship.backref` keyword is merely a shortcut for building
two individual :func:`.relationship` constructs that refer to each other. Part of
@@ -144,10 +144,10 @@ as if we limited the list of ``Address`` objects to those which start with "tony
We can observe, by inspecting the resulting property, that both sides
of the relationship have this join condition applied::
>>> print User.addresses.property.primaryjoin
>>> print(User.addresses.property.primaryjoin)
"user".id = address.user_id AND address.email LIKE :email_1 || '%%'
>>>
>>> print Address.user.property.primaryjoin
>>> print(Address.user.property.primaryjoin)
"user".id = address.user_id AND address.email LIKE :email_1 || '%%'
>>>
@@ -187,7 +187,7 @@ it into a form that is interpreted by the receiving :func:`.relationship` as add
arguments to be applied to the new relationship it creates.
One Way Backrefs
~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~
An unusual case is that of the "one way backref". This is where the
"back-populating" behavior of the backref is only desirable in one
+148 -38
View File
@@ -1,21 +1,21 @@
.. _relationship_patterns:
Basic Relationship Patterns
----------------------------
---------------------------
A quick walkthrough of the basic relational patterns.
The imports used for each of the following sections is as follows::
from sqlalchemy import Table, Column, Integer, ForeignKey
from sqlalchemy.orm import relationship, backref
from sqlalchemy.orm import relationship
from sqlalchemy.ext.declarative import declarative_base
Base = declarative_base()
One To Many
~~~~~~~~~~~~
~~~~~~~~~~~
A one to many relationship places a foreign key on the child table referencing
the parent. :func:`.relationship` is then specified on the parent, as referencing
@@ -32,22 +32,34 @@ a collection of items represented by the child::
parent_id = Column(Integer, ForeignKey('parent.id'))
To establish a bidirectional relationship in one-to-many, where the "reverse"
side is a many to one, specify the :paramref:`~.relationship.backref` option::
side is a many to one, specify an additional :func:`.relationship` and connect
the two using the :paramref:`.relationship.back_populates` parameter::
class Parent(Base):
__tablename__ = 'parent'
id = Column(Integer, primary_key=True)
children = relationship("Child", back_populates="parent")
class Child(Base):
__tablename__ = 'child'
id = Column(Integer, primary_key=True)
parent_id = Column(Integer, ForeignKey('parent.id'))
parent = relationship("Parent", back_populates="children")
``Child`` will get a ``parent`` attribute with many-to-one semantics.
Alternatively, the :paramref:`~.relationship.backref` option may be used
on a single :func:`.relationship` instead of using
:paramref:`~.relationship.back_populates`::
class Parent(Base):
__tablename__ = 'parent'
id = Column(Integer, primary_key=True)
children = relationship("Child", backref="parent")
class Child(Base):
__tablename__ = 'child'
id = Column(Integer, primary_key=True)
parent_id = Column(Integer, ForeignKey('parent.id'))
``Child`` will get a ``parent`` attribute with many-to-one semantics.
Many To One
~~~~~~~~~~~~
~~~~~~~~~~~
Many to one places a foreign key in the parent table referencing the child.
:func:`.relationship` is declared on the parent, where a new scalar-holding
@@ -63,9 +75,23 @@ attribute will be created::
__tablename__ = 'child'
id = Column(Integer, primary_key=True)
Bidirectional behavior is achieved by setting
:paramref:`~.relationship.backref` to the value ``"parents"``, which
will place a one-to-many collection on the ``Child`` class::
Bidirectional behavior is achieved by adding a second :func:`.relationship`
and applying the :paramref:`.relationship.back_populates` parameter
in both directions::
class Parent(Base):
__tablename__ = 'parent'
id = Column(Integer, primary_key=True)
child_id = Column(Integer, ForeignKey('child.id'))
child = relationship("Child", back_populates="parents")
class Child(Base):
__tablename__ = 'child'
id = Column(Integer, primary_key=True)
parents = relationship("Parent", back_populates="child")
Alternatively, the :paramref:`~.relationship.backref` parameter
may be applied to a single :func:`.relationship`, such as ``Parent.child``::
class Parent(Base):
__tablename__ = 'parent'
@@ -76,7 +102,7 @@ will place a one-to-many collection on the ``Child`` class::
.. _relationships_one_to_one:
One To One
~~~~~~~~~~~
~~~~~~~~~~
One To One is essentially a bidirectional relationship with a scalar
attribute on both sides. To achieve this, the :paramref:`~.relationship.uselist` flag indicates
@@ -86,15 +112,32 @@ of the relationship. To convert one-to-many into one-to-one::
class Parent(Base):
__tablename__ = 'parent'
id = Column(Integer, primary_key=True)
child = relationship("Child", uselist=False, backref="parent")
child = relationship("Child", uselist=False, back_populates="parent")
class Child(Base):
__tablename__ = 'child'
id = Column(Integer, primary_key=True)
parent_id = Column(Integer, ForeignKey('parent.id'))
parent = relationship("Parent", back_populates="child")
Or to turn a one-to-many backref into one-to-one, use the :func:`.backref` function
to provide arguments for the reverse side::
Or for many-to-one::
class Parent(Base):
__tablename__ = 'parent'
id = Column(Integer, primary_key=True)
child_id = Column(Integer, ForeignKey('child.id'))
child = relationship("Child", back_populates="parent")
class Child(Base):
__tablename__ = 'child'
id = Column(Integer, primary_key=True)
parent = relationship("Parent", back_populates="child", uselist=False)
As always, the :paramref:`.relationship.backref` and :func:`.backref` functions
may be used in lieu of the :paramref:`.relationship.back_populates` approach;
to specify ``uselist`` on a backref, use the :func:`.backref` function::
from sqlalchemy.orm import backref
class Parent(Base):
__tablename__ = 'parent'
@@ -102,14 +145,11 @@ to provide arguments for the reverse side::
child_id = Column(Integer, ForeignKey('child.id'))
child = relationship("Child", backref=backref("parent", uselist=False))
class Child(Base):
__tablename__ = 'child'
id = Column(Integer, primary_key=True)
.. _relationships_many_to_many:
Many To Many
~~~~~~~~~~~~~
~~~~~~~~~~~~
Many to Many adds an association table between two classes. The association
table is indicated by the :paramref:`~.relationship.secondary` argument to
@@ -133,7 +173,32 @@ directives can locate the remote tables with which to link::
id = Column(Integer, primary_key=True)
For a bidirectional relationship, both sides of the relationship contain a
collection. The :paramref:`~.relationship.backref` keyword will automatically use
collection. Specify using :paramref:`.relationship.back_populates`, and
for each :func:`.relationship` specify the common association table::
association_table = Table('association', Base.metadata,
Column('left_id', Integer, ForeignKey('left.id')),
Column('right_id', Integer, ForeignKey('right.id'))
)
class Parent(Base):
__tablename__ = 'left'
id = Column(Integer, primary_key=True)
children = relationship(
"Child",
secondary=association_table,
back_populates="parents")
class Child(Base):
__tablename__ = 'right'
id = Column(Integer, primary_key=True)
parents = relationship(
"Parent",
secondary=association_table,
back_populates="children")
When using the :paramref:`~.relationship.backref` parameter instead of
:paramref:`.relationship.back_populates`, the backref will automatically use
the same :paramref:`~.relationship.secondary` argument for the reverse relationship::
association_table = Table('association', Base.metadata,
@@ -206,7 +271,7 @@ There are several possibilities here:
suppose it's called ``Child.parents``, SQLAlchemy by default will load in
the ``Child.parents`` collection to locate all ``Parent`` objects, and remove
each row from the "secondary" table which establishes this link. Note that
this relationship does not need to be bidrectional; SQLAlchemy is strictly
this relationship does not need to be bidirectional; SQLAlchemy is strictly
looking at every :func:`.relationship` associated with the ``Child`` object
being deleted.
* A higher performing option here is to use ON DELETE CASCADE directives
@@ -259,23 +324,26 @@ is stored along with each association between ``Parent`` and
__tablename__ = 'right'
id = Column(Integer, primary_key=True)
The bidirectional version adds backrefs to both relationships::
As always, the bidirectional version makes use of :paramref:`.relationship.back_populates`
or :paramref:`.relationship.backref`::
class Association(Base):
__tablename__ = 'association'
left_id = Column(Integer, ForeignKey('left.id'), primary_key=True)
right_id = Column(Integer, ForeignKey('right.id'), primary_key=True)
extra_data = Column(String(50))
child = relationship("Child", backref="parent_assocs")
child = relationship("Child", back_populates="parents")
parent = relationship("Parent", back_populates="children")
class Parent(Base):
__tablename__ = 'left'
id = Column(Integer, primary_key=True)
children = relationship("Association", backref="parent")
children = relationship("Association", back_populates="parent")
class Child(Base):
__tablename__ = 'right'
id = Column(Integer, primary_key=True)
parents = relationship("Association", back_populates="child")
Working with the association pattern in its direct form requires that child
objects are associated with an association instance before being appended to
@@ -291,8 +359,8 @@ association object::
# iterate through child objects via association, including association
# attributes
for assoc in p.children:
print assoc.extra_data
print assoc.child
print(assoc.extra_data)
print(assoc.child)
To enhance the association object pattern such that direct
access to the ``Association`` object is optional, SQLAlchemy
@@ -301,13 +369,55 @@ extension allows the configuration of attributes which will
access two "hops" with a single access, one "hop" to the
associated object, and a second to a target attribute.
.. note::
.. warning::
When using the association object pattern, it is advisable that the
association-mapped table not be used as the
:paramref:`~.relationship.secondary` argument on a
:func:`.relationship` elsewhere, unless that :func:`.relationship`
contains the option :paramref:`~.relationship.viewonly` set to
``True``. SQLAlchemy otherwise may attempt to emit redundant INSERT
and DELETE statements on the same table, if similar state is
detected on the related attribute as well as the associated object.
The association object pattern **does not coordinate changes with a
separate relationship that maps the association table as "secondary"**.
Below, changes made to ``Parent.children`` will not be coordinated
with changes made to ``Parent.child_associations`` or
``Child.parent_associations`` in Python; while all of these relationships will continue
to function normally by themselves, changes on one will not show up in another
until the :class:`.Session` is expired, which normally occurs automatically
after :meth:`.Session.commit`::
class Association(Base):
__tablename__ = 'association'
left_id = Column(Integer, ForeignKey('left.id'), primary_key=True)
right_id = Column(Integer, ForeignKey('right.id'), primary_key=True)
extra_data = Column(String(50))
child = relationship("Child", backref="parent_associations")
parent = relationship("Parent", backref="child_associations")
class Parent(Base):
__tablename__ = 'left'
id = Column(Integer, primary_key=True)
children = relationship("Child", secondary="association")
class Child(Base):
__tablename__ = 'right'
id = Column(Integer, primary_key=True)
Additionally, just as changes to one relationship aren't reflected in the
others automatically, writing the same data to both relationships will cause
conflicting INSERT or DELETE statements as well, such as below where we
establish the same relationship between a ``Parent`` and ``Child`` object
twice::
p1 = Parent()
c1 = Child()
p1.children.append(c1)
# redundant, will cause a duplicate INSERT on Association
p1.parent_associations.append(Association(child=c1))
It's fine to use a mapping like the above if you know what
you're doing, though it may be a good idea to apply the ``viewonly=True`` parameter
to the "secondary" relationship to avoid the issue of redundant changes
being logged. However, to get a foolproof pattern that allows a simple
two-object ``Parent->Child`` relationship while still using the association
object pattern, use the association proxy extension
as documented at :ref:`associationproxy_toplevel`.
+3 -3
View File
@@ -17,7 +17,7 @@ the :ref:`cascade_delete` and :ref:`cascade_delete_orphan` options;
these settings are appropriate for related objects which only exist as
long as they are attached to their parent, and are otherwise deleted.
Cascade behavior is configured using the by changing the
Cascade behavior is configured using the
:paramref:`~.relationship.cascade` option on
:func:`~sqlalchemy.orm.relationship`::
@@ -131,7 +131,7 @@ delete
The ``delete`` cascade indicates that when a "parent" object
is marked for deletion, its related "child" objects should also be marked
for deletion. If for example we we have a relationship ``User.addresses``
for deletion. If for example we have a relationship ``User.addresses``
with ``delete`` cascade configured::
class User(Base):
@@ -341,7 +341,7 @@ easily described through demonstration; it means that, given a mapping such as t
})
If an ``Order`` is already in the session, and is assigned to the ``order``
attribute of an ``Item``, the backref appends the ``Order`` to the ``items``
attribute of an ``Item``, the backref appends the ``Item`` to the ``items``
collection of that ``Order``, resulting in the ``save-update`` cascade taking
place::
+46 -12
View File
@@ -16,7 +16,7 @@ and techniques.
.. currentmodule:: sqlalchemy.orm
Working with Large Collections
===============================
==============================
The default behavior of :func:`.relationship` is to fully load
the collection of items in, as according to the loading strategy of the
@@ -31,7 +31,7 @@ loading of child items both at load time as well as deletion time.
.. _dynamic_relationship:
Dynamic Relationship Loaders
-----------------------------
----------------------------
A key feature to enable management of a large collection is the so-called "dynamic"
relationship. This is an optional form of :func:`~sqlalchemy.orm.relationship` which
@@ -91,8 +91,10 @@ Note that eager/lazy loading options cannot be used in conjunction dynamic relat
relationships. Newer versions of SQLAlchemy emit warnings or exceptions
in these cases.
Setting Noload
---------------
.. _collections_noload_raiseload:
Setting Noload, RaiseLoad
-------------------------
A "noload" relationship never loads from the database, even when
accessed. It is configured using ``lazy='noload'``::
@@ -105,12 +107,40 @@ accessed. It is configured using ``lazy='noload'``::
Above, the ``children`` collection is fully writeable, and changes to it will
be persisted to the database as well as locally available for reading at the
time they are added. However when instances of ``MyClass`` are freshly loaded
from the database, the ``children`` collection stays empty.
from the database, the ``children`` collection stays empty. The noload
strategy is also available on a query option basis using the
:func:`.orm.noload` loader option.
Alternatively, a "raise"-loaded relationship will raise an
:exc:`~sqlalchemy.exc.InvalidRequestError` where the attribute would normally
emit a lazy load::
class MyClass(Base):
__tablename__ = 'some_table'
children = relationship(MyOtherClass, lazy='raise')
Above, attribute access on the ``children`` collection will raise an exception
if it was not previously eagerloaded. This includes read access but for
collections will also affect write access, as collections can't be mutated
without first loading them. The rationale for this is to ensure that an
application is not emitting any unexpected lazy loads within a certain context.
Rather than having to read through SQL logs to determine that all necessary
attributes were eager loaded, the "raise" strategy will cause unloaded
attributes to raise immediately if accessed. The raise strategy is
also available on a query option basis using the :func:`.orm.raiseload`
loader option.
.. versionadded:: 1.1 added the "raise" loader strategy.
.. seealso::
:ref:`prevent_lazy_with_raiseload`
.. _passive_deletes:
Using Passive Deletes
----------------------
---------------------
Use :paramref:`~.relationship.passive_deletes` to disable child object loading on a DELETE
operation, in conjunction with "ON DELETE (CASCADE|SET NULL)" on your database
@@ -150,6 +180,10 @@ instances of ``MyOtherClass`` which are not loaded, SQLAlchemy assumes that
"ON DELETE CASCADE" rules will ensure that those rows are deleted by the
database.
.. seealso::
:paramref:`.orm.mapper.passive_deletes` - similar feature on :func:`.mapper`
.. currentmodule:: sqlalchemy.orm.collections
.. _custom_collections:
@@ -168,7 +202,7 @@ this collection is a ``list``::
parent = Parent()
parent.children.append(Child())
print parent.children[0]
print(parent.children[0])
Collections are not limited to lists. Sets, mutable sequences and almost any
other Python object that can act as a container can be used in place of the
@@ -188,7 +222,7 @@ default list, by specifying the :paramref:`~.relationship.collection_class` opti
assert child in parent.children
Dictionary Collections
-----------------------
----------------------
A little extra detail is needed when using a dictionary as a collection.
This because objects are always loaded from the database as lists, and a key-generation
@@ -316,10 +350,10 @@ for examples.
.. autofunction:: mapped_collection
Custom Collection Implementations
==================================
=================================
You can use your own types for collections as well. In simple cases,
inherting from ``list`` or ``set``, adding custom behavior, is all that's needed.
inheriting from ``list`` or ``set``, adding custom behavior, is all that's needed.
In other cases, special decorators are needed to tell SQLAlchemy more detail
about how the collection operates.
@@ -420,7 +454,7 @@ collections. Use them when your class doesn't quite meet the regular interface
for its container type, or when you otherwise would like to use a different method to
get the job done.
.. sourcecode:: python+sql
.. sourcecode:: python
from sqlalchemy.orm.collections import collection
@@ -565,7 +599,7 @@ The ORM uses this approach for built-ins, quietly substituting a trivial
subclass when a ``list``, ``set`` or ``dict`` is used directly.
Collection Internals
=====================
====================
Various internal methods.
+86 -31
View File
@@ -3,22 +3,12 @@
.. _mapper_composite:
Composite Column Types
=======================
======================
Sets of columns can be associated with a single user-defined datatype. The ORM
provides a single attribute which represents the group of columns using the
class you provide.
.. versionchanged:: 0.7
Composites have been simplified such that
they no longer "conceal" the underlying column based attributes. Additionally,
in-place mutation is no longer automatic; see the section below on
enabling mutability to support tracking of in-place changes.
.. versionchanged:: 0.9
Composites will return their object-form, rather than as individual columns,
when used in a column-oriented :class:`.Query` construct. See :ref:`migration_2824`.
A simple example represents pairs of columns as a ``Point`` object.
``Point`` represents such a pair as ``.x`` and ``.y``::
@@ -48,7 +38,7 @@ the object as a list or tuple, in order of its column-based attributes. It
also should supply adequate ``__eq__()`` and ``__ne__()`` methods which test
the equality of two instances.
We will create a mapping to a table ``vertice``, which represents two points
We will create a mapping to a table ``vertices``, which represents two points
as ``x1/y1`` and ``x2/y2``. These are created normally as :class:`.Column`
objects. Then, the :func:`.composite` function is used to assign new
attributes that will represent sets of columns via the ``Point`` class::
@@ -60,7 +50,7 @@ attributes that will represent sets of columns via the ``Point`` class::
Base = declarative_base()
class Vertex(Base):
__tablename__ = 'vertice'
__tablename__ = 'vertices'
id = Column(Integer, primary_key=True)
x1 = Column(Integer)
@@ -74,9 +64,9 @@ attributes that will represent sets of columns via the ``Point`` class::
A classical mapping above would define each :func:`.composite`
against the existing table::
mapper(Vertex, vertice_table, properties={
'start':composite(Point, vertice_table.c.x1, vertice_table.c.y1),
'end':composite(Point, vertice_table.c.x2, vertice_table.c.y2),
mapper(Vertex, vertices_table, properties={
'start':composite(Point, vertices_table.c.x1, vertices_table.c.y1),
'end':composite(Point, vertices_table.c.x2, vertices_table.c.y2),
})
We can now persist and use ``Vertex`` instances, as well as query for them,
@@ -87,17 +77,17 @@ using the ``.start`` and ``.end`` attributes against ad-hoc ``Point`` instances:
>>> v = Vertex(start=Point(3, 4), end=Point(5, 6))
>>> session.add(v)
>>> q = session.query(Vertex).filter(Vertex.start == Point(3, 4))
{sql}>>> print q.first().start
{sql}>>> print(q.first().start)
BEGIN (implicit)
INSERT INTO vertice (x1, y1, x2, y2) VALUES (?, ?, ?, ?)
INSERT INTO vertices (x1, y1, x2, y2) VALUES (?, ?, ?, ?)
(3, 4, 5, 6)
SELECT vertice.id AS vertice_id,
vertice.x1 AS vertice_x1,
vertice.y1 AS vertice_y1,
vertice.x2 AS vertice_x2,
vertice.y2 AS vertice_y2
FROM vertice
WHERE vertice.x1 = ? AND vertice.y1 = ?
SELECT vertices.id AS vertices_id,
vertices.x1 AS vertices_x1,
vertices.y1 AS vertices_y1,
vertices.x2 AS vertices_x2,
vertices.y2 AS vertices_y2
FROM vertices
WHERE vertices.x1 = ? AND vertices.y1 = ?
LIMIT ? OFFSET ?
(3, 4, 1, 0)
{stop}Point(x=3, y=4)
@@ -115,11 +105,6 @@ via the usage of the :class:`.MutableComposite` mixin, which uses events
to associate each user-defined composite object with all parent associations.
Please see the example in :ref:`mutable_composites`.
.. versionchanged:: 0.7
In-place changes to an existing composite value are no longer
tracked automatically; the functionality is superseded by the
:class:`.MutableComposite` class.
.. _composite_operations:
Redefining Comparison Operations for Composites
@@ -145,7 +130,7 @@ the same expression that the base "greater than" does::
other.__composite_values__())])
class Vertex(Base):
___tablename__ = 'vertice'
___tablename__ = 'vertices'
id = Column(Integer, primary_key=True)
x1 = Column(Integer)
@@ -158,3 +143,73 @@ the same expression that the base "greater than" does::
end = composite(Point, x2, y2,
comparator_factory=PointComparator)
Nesting Composites
-------------------
Composite objects can be defined to work in simple nested schemes, by
redefining behaviors within the composite class to work as desired, then
mapping the composite class to the full length of individual columns normally.
Typically, it is convenient to define separate constructors for user-defined
use and generate-from-row use. Below we reorganize the ``Vertex`` class to
itself be a composite object, which is then mapped to a class ``HasVertex``::
from sqlalchemy.orm import composite
class Point(object):
def __init__(self, x, y):
self.x = x
self.y = y
def __composite_values__(self):
return self.x, self.y
def __repr__(self):
return "Point(x=%r, y=%r)" % (self.x, self.y)
def __eq__(self, other):
return isinstance(other, Point) and \
other.x == self.x and \
other.y == self.y
def __ne__(self, other):
return not self.__eq__(other)
class Vertex(object):
def __init__(self, start, end):
self.start = start
self.end = end
@classmethod
def _generate(self, x1, y1, x2, y2):
"""generate a Vertex from a row"""
return Vertex(
Point(x1, y1),
Point(x2, y2)
)
def __composite_values__(self):
return \
self.start.__composite_values__() + \
self.end.__composite_values__()
class HasVertex(Base):
__tablename__ = 'has_vertex'
id = Column(Integer, primary_key=True)
x1 = Column(Integer)
y1 = Column(Integer)
x2 = Column(Integer)
y2 = Column(Integer)
vertex = composite(Vertex._generate, x1, y1, x2, y2)
We can then use the above mapping as::
hv = HasVertex(vertex=Vertex(Point(1, 2), Point(3, 4)))
s.add(hv)
s.commit()
hv = s.query(HasVertex).filter(
HasVertex.vertex == Vertex(Point(1, 2), Point(3, 4))).first()
print(hv.vertex.start)
print(hv.vertex.end)
+18 -14
View File
@@ -3,7 +3,7 @@
.. _mapping_constructors:
Constructors and Object Initialization
=======================================
======================================
Mapping imposes no restrictions or requirements on the constructor
(``__init__``) method for the class. You are free to require any arguments for
@@ -18,10 +18,13 @@ then quietly restoring attributes directly on the instance rather than calling
``__init__``.
If you need to do some setup on database-loaded instances before they're ready
to use, you can use the ``@reconstructor`` decorator to tag a method as the
ORM counterpart to ``__init__``. SQLAlchemy will call this method with no
arguments every time it loads or reconstructs one of your instances. This is
useful for recreating transient properties that are normally assigned in your
to use, there is an event hook known as :meth:`.InstanceEvents.load` which
can achieve this; it is also available via a class-specific decorator called
:func:`.orm.reconstructor`. When using :func:`.orm.reconstructor`,
the mapper will invoke the decorated method with no
arguments every time it loads or reconstructs an instance of the
class. This is
useful for recreating transient properties that are normally assigned in
``__init__``::
from sqlalchemy import orm
@@ -36,21 +39,22 @@ useful for recreating transient properties that are normally assigned in your
def init_on_load(self):
self.stuff = []
When ``obj = MyMappedClass()`` is executed, Python calls the ``__init__``
method as normal and the ``data`` argument is required. When instances are
Above, when ``obj = MyMappedClass()`` is executed, the ``__init__`` constructor
is invoked normally and the ``data`` argument is required. When instances are
loaded during a :class:`~sqlalchemy.orm.query.Query` operation as in
``query(MyMappedClass).one()``, ``init_on_load`` is called.
Any method may be tagged as the :func:`~sqlalchemy.orm.reconstructor`, even
the ``__init__`` method. SQLAlchemy will call the reconstructor method with no
arguments. Scalar (non-collection) database-mapped attributes of the instance
will be available for use within the function. Eagerly-loaded collections are
generally not yet available and will usually only contain the first element.
Any method may be tagged as the :func:`.orm.reconstructor`, even
the ``__init__`` method itself. It is invoked after all immediate
column-level attributes are loaded as well as after eagerly-loaded scalar
relationships. Eagerly loaded collections may be only partially populated
or not populated at all, depending on the kind of eager loading used.
ORM state changes made to objects at this stage will not be recorded for the
next flush() operation, so the activity within a reconstructor should be
next flush operation, so the activity within a reconstructor should be
conservative.
:func:`~sqlalchemy.orm.reconstructor` is a shortcut into a larger system
:func:`.orm.reconstructor` is a shortcut into a larger system
of "instance level" events, which can be subscribed to using the
event API - see :class:`.InstanceEvents` for the full API description
of these events.
+4 -4
View File
@@ -1,7 +1,7 @@
.. _unitofwork_contextual:
Contextual/Thread-local Sessions
=================================
================================
Recall from the section :ref:`session_faq_whentocreate`, the concept of
"session scopes" was introduced, with an emphasis on web applications
@@ -96,9 +96,9 @@ underlying :class:`.Session` being maintained by the registry::
# equivalent to:
#
# session = Session()
# print session.query(MyClass).all()
# print(session.query(MyClass).all())
#
print Session.query(MyClass).all()
print(Session.query(MyClass).all())
The above code accomplishes the same task as that of acquiring the current
:class:`.Session` by calling upon the registry, then using that :class:`.Session`.
@@ -113,7 +113,7 @@ object is entirely designed to be used in a **non-concurrent** fashion, which
in terms of multithreading means "only in one thread at a time". So our
above example of :class:`.scoped_session` usage, where the same :class:`.Session`
object is maintained across multiple calls, suggests that some process needs
to be in place such that mutltiple calls across many threads don't actually get
to be in place such that multiple calls across many threads don't actually get
a handle to the same session. We call this notion **thread local storage**,
which means, a special object is used that will maintain a distinct object
per each application thread. Python provides this via the
+4 -4
View File
@@ -3,7 +3,7 @@
.. _dep_interfaces_orm_toplevel:
Deprecated ORM Event Interfaces
================================
===============================
.. module:: sqlalchemy.orm.interfaces
@@ -17,19 +17,19 @@ until SQLAlchemy 0.5. The non-ORM analogue is described at :ref:`dep_interfaces
a consistent interface to all events without the need for subclassing.
Mapper Events
-----------------
-------------
.. autoclass:: MapperExtension
:members:
Session Events
-----------------
--------------
.. autoclass:: SessionExtension
:members:
Attribute Events
--------------------
----------------
.. autoclass:: AttributeExtension
:members:
+7 -9
View File
@@ -5,12 +5,10 @@ ORM Events
The ORM includes a wide variety of hooks available for subscription.
.. versionadded:: 0.7
The event supersedes the previous system of "extension" classes.
For an introduction to the event API, see :ref:`event_toplevel`. Non-ORM events
such as those regarding connections and low-level statement execution are described in
:ref:`core_event_toplevel`.
For an introduction to the most commonly used ORM events, see the section
:ref:`session_events_toplevel`. The event system in general is discussed
at :ref:`event_toplevel`. Non-ORM events such as those regarding connections
and low-level statement execution are described in :ref:`core_event_toplevel`.
Attribute Events
----------------
@@ -19,7 +17,7 @@ Attribute Events
:members:
Mapper Events
---------------
-------------
.. autoclass:: sqlalchemy.orm.events.MapperEvents
:members:
@@ -37,13 +35,13 @@ Session Events
:members:
Query Events
-------------
------------
.. autoclass:: sqlalchemy.orm.events.QueryEvents
:members:
Instrumentation Events
-----------------------
----------------------
.. automodule:: sqlalchemy.orm.instrumentation
+26 -13
View File
@@ -36,19 +36,19 @@ Directed Graphs
.. automodule:: examples.graphs
Dynamic Relations as Dictionaries
------------------------------------
---------------------------------
.. automodule:: examples.dynamic_dict
.. _examples_generic_associations:
Generic Associations
------------------------
--------------------
.. automodule:: examples.generic_associations
Large Collections
------------------------
-----------------
.. automodule:: examples.large_collection
@@ -58,7 +58,7 @@ Materialized Paths
.. automodule:: examples.materialized_paths
Nested Sets
------------
-----------
.. automodule:: examples.nested_sets
@@ -76,15 +76,22 @@ Relationship Join Conditions
.. automodule:: examples.join_conditions
.. _examples_spaceinvaders:
Space Invaders
--------------
.. automodule:: examples.space_invaders
.. _examples_xmlpersistence:
XML Persistence
------------------------
---------------
.. automodule:: examples.elementtree
Versioning Objects
------------------------
------------------
.. _examples_versioned_history:
@@ -93,22 +100,28 @@ Versioning with a History Table
.. automodule:: examples.versioned_history
.. _examples_versioned_rows:
Versioning using Temporal Rows
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
.. automodule:: examples.versioned_rows
.. _examples_vertical_tables:
Vertical Attribute Mapping
------------------------------------
--------------------------
.. automodule:: examples.vertical
.. _examples_inheritance:
Inheritance Mapping Recipes
============================
===========================
Basic Inheritance Mappings
----------------------------------
--------------------------
.. automodule:: examples.inheritance
@@ -118,14 +131,14 @@ Special APIs
.. _examples_instrumentation:
Attribute Instrumentation
------------------------------------
-------------------------
.. automodule:: examples.custom_attributes
.. _examples_sharding:
Horizontal Sharding
------------------------
-------------------
.. automodule:: examples.sharding
@@ -135,14 +148,14 @@ Extending the ORM
.. _examples_caching:
Dogpile Caching
------------------------
---------------
.. automodule:: examples.dogpile_caching
.. _examples_postgis:
PostGIS Integration
------------------------
-------------------
.. automodule:: examples.postgis
+2
View File
@@ -1,3 +1,5 @@
.. _orm_exceptions_toplevel:
ORM Exceptions
==============
+5 -5
View File
@@ -3,10 +3,10 @@ Events and Internals
====================
.. toctree::
:maxdepth: 2
:maxdepth: 2
events
internals
exceptions
deprecated
events
internals
exceptions
deprecated
+69 -9
View File
@@ -114,7 +114,7 @@ or dictionary is taken into account, so that the proxy should act just like
the underlying collection or attribute does.
Creation of New Values
-----------------------
----------------------
When a list append() event (or set add(), dictionary __setitem__(), or scalar
assignment event) is intercepted by the association proxy, it instantiates a
@@ -151,7 +151,7 @@ Simplifying Association Objects
The "association object" pattern is an extended form of a many-to-many
relationship, and is described at :ref:`association_pattern`. Association
proxies are useful for keeping "association objects" out the way during
proxies are useful for keeping "association objects" out of the way during
regular use.
Suppose our ``userkeywords`` table above had additional columns
@@ -256,7 +256,7 @@ by all these operations::
.. _proxying_dictionaries:
Proxying to Dictionary Based Collections
-----------------------------------------
----------------------------------------
The association proxy can proxy to dictionary based collections as well. SQLAlchemy
mappings usually use the :func:`.attribute_mapped_collection` collection type to
@@ -484,9 +484,6 @@ using the :attr:`~.AssociationProxy.attr` attribute in a star-args context::
q = session.query(User).join(*User.keywords.attr)
.. versionadded:: 0.7.3
:attr:`~.AssociationProxy.attr` attribute in a star-args context.
:attr:`~.AssociationProxy.attr` is composed of :attr:`.AssociationProxy.local_attr` and :attr:`.AssociationProxy.remote_attr`,
which are just synonyms for the actual proxied attributes, and can also
be used for querying::
@@ -497,9 +494,58 @@ be used for querying::
join(uka, User.keywords.local_attr).\
join(ka, User.keywords.remote_attr)
.. versionadded:: 0.7.3
:attr:`.AssociationProxy.local_attr` and :attr:`.AssociationProxy.remote_attr`,
synonyms for the actual proxied attributes, and usable for querying.
.. _cascade_scalar_deletes:
Cascading Scalar Deletes
------------------------
.. versionadded:: 1.3
Given a mapping as::
class A(Base):
__tablename__ = 'test_a'
id = Column(Integer, primary_key=True)
ab = relationship(
'AB', backref='a', uselist=False)
b = association_proxy(
'ab', 'b', creator=lambda b: AB(b=b),
cascade_scalar_deletes=True)
class B(Base):
__tablename__ = 'test_b'
id = Column(Integer, primary_key=True)
ab = relationship('AB', backref='b', cascade='all, delete-orphan')
class AB(Base):
__tablename__ = 'test_ab'
a_id = Column(Integer, ForeignKey(A.id), primary_key=True)
b_id = Column(Integer, ForeignKey(B.id), primary_key=True)
An assigment to ``A.b`` will generate an ``AB`` object::
a.b = B()
The ``A.b`` association is scalar, and includes use of the flag
:paramref:`.AssociationProxy.cascade_scalar_deletes`. When set, setting ``A.b``
to ``None`` will remove ``A.ab`` as well::
a.b = None
assert a.ab is None
When :paramref:`.AssociationProxy.cascade_scalar_deletes` is not set,
the association object ``a.ab`` above would remain in place.
Note that this is not the behavior for collection-based association proxies;
in that case, the intermediary association object is always removed when
members of the proxied collection are removed. Whether or not the row is
deleted depends on the relationship cascade setting.
.. seealso::
:ref:`unitofwork_cascades`
API Documentation
-----------------
@@ -509,5 +555,19 @@ API Documentation
.. autoclass:: AssociationProxy
:members:
:undoc-members:
:inherited-members:
.. autoclass:: AssociationProxyInstance
:members:
:undoc-members:
:inherited-members:
.. autoclass:: ObjectAssociationProxyInstance
:members:
:inherited-members:
.. autoclass:: ColumnAssociationProxyInstance
:members:
:inherited-members:
.. autodata:: ASSOCIATION_PROXY
+111 -31
View File
@@ -16,7 +16,7 @@ occur **once**, rather than for each time that query is built up and executed.
The rationale for this system is to greatly reduce Python interpreter
overhead for everything that occurs **before the SQL is emitted**.
The caching of the "baked" system does **not** in any way reduce SQL calls or
cache the **return results** from the database. A technique that demonstates
cache the **return results** from the database. A technique that demonstrates
the caching of the SQL calls and result sets themselves is available in
:ref:`examples_caching`.
@@ -25,9 +25,12 @@ the caching of the SQL calls and result sets themselves is available in
.. note::
The :mod:`sqlalchemy.ext.baked` extension should be considered
**experimental** as of 1.0.0. It provides a dramatically different system
of producing queries which has yet to be proven at scale.
The :mod:`sqlalchemy.ext.baked` extension is **not for beginners**. Using
it correctly requires a good high level understanding of how SQLAlchemy, the
database driver, and the backend database interact with each other. This
extension presents a very specific kind of optimization that is not ordinarily
needed. As noted above, it **does not cache queries**, only the string
formulation of the SQL itself.
Synopsis
--------
@@ -329,32 +332,113 @@ to arrive at the current "baked" approach. Starting from the
management, removal of all redundant Python execution, and queries built up
with conditionals needed to be addressed, leading to the final approach.
Special Query Techniques
------------------------
This section will describe some techniques for specific query situations.
.. _baked_in:
Using IN expressions
^^^^^^^^^^^^^^^^^^^^
The :meth:`.ColumnOperators.in_` method in SQLAlchemy historically renders
a variable set of bound parameters based on the list of items that's passed
to the method. This doesn't work for baked queries as the length of that
list can change on different calls. To solve this problem, the
:paramref:`.bindparam.expanding` parameter supports a late-rendered IN
expression that is safe to be cached inside of baked query. The actual list
of elements is rendered at statement execution time, rather than at
statement compilation time::
bakery = baked.bakery()
baked_query = bakery(lambda session: session.query(User))
baked_query += lambda q: q.filter(
User.name.in_(bindparam('username', expanding=True)))
result = baked_query.with_session(session).params(
username=['ed', 'fred']).all()
.. seealso::
:paramref:`.bindparam.expanding`
:meth:`.ColumnOperators.in_`
Using Subqueries
^^^^^^^^^^^^^^^^
When using :class:`.Query` objects, it is often needed that one :class:`.Query`
object is used to generate a subquery within another. In the case where the
:class:`.Query` is currently in baked form, an interim method may be used to
retrieve the :class:`.Query` object, using the :meth:`.BakedQuery.to_query`
method. This method is passed the :class:`.Session` or :class:`.Query` that is
the argument to the lambda callable used to generate a particular step
of the baked query::
bakery = baked.bakery()
# a baked query that will end up being used as a subquery
my_subq = bakery(lambda s: s.query(User.id))
my_subq += lambda q: q.filter(User.id == Address.user_id)
# select a correlated subquery in the top columns list,
# we have the "session" argument, pass that
my_q = bakery(
lambda s: s.query(Address.id, my_subq.to_query(s).as_scalar()))
# use a correlated subquery in some of the criteria, we have
# the "query" argument, pass that.
my_q += lambda q: q.filter(my_subq.to_query(q).exists())
.. versionadded:: 1.3
Disabling Baked Queries Session-wide
------------------------------------
The flag :paramref:`.Session.enable_baked_queries` may be set to False,
causing all baked queries to not use the cache when used against that
:class:`.Session`::
session = Session(engine, enable_baked_queries=False)
Like all session flags, it is also accepted by factory objects like
:class:`.sessionmaker` and methods like :meth:`.sessionmaker.configure`.
The immediate rationale for this flag is to reduce memory use in the case
that the query baking used by relationship loaders and other loaders
is not desirable. It also can be used in the case that an application
which is seeing issues potentially due to cache key conflicts from user-defined
baked queries or other baked query issues can turn the behavior off, in
order to identify or eliminate baked queries as the cause of an issue.
.. versionadded:: 1.2
Lazy Loading Integration
------------------------
The baked query can be integrated with SQLAlchemy's lazy loader feature
transparently. A future release of SQLAlchemy may enable this by default,
as its use within lazy loading is completely transparent. For now,
to enable baked lazyloading for all lazyloaders systemwide, call upon
the :func:`.bake_lazy_loaders` function. This will impact all relationships
that use the ``lazy='select'`` strategy as well as all use of the :func:`.lazyload`
per-query strategy.
The baked query system is integrated into SQLAlchemy's lazy loader feature
as used by :func:`.relationship`, and will cache queries for most lazy
load conditions. A small subset of
"lazy loads" may not be cached; these involve query options in conjunction with ad-hoc
:obj:`.aliased` structures that cannot produce a repeatable cache
key.
"Baked" lazy loading may be enabled on a per-:func:`.relationship` basis
using the ``baked_select`` loader strategy::
.. versionchanged:: 1.2 "baked" queries are now the foundation of the
lazy-loader feature of :func:`.relationship`.
class MyClass(Base):
# ...
widgets = relationship("Widget", lazy="baked_select")
The ``baked_select`` strategy is available once any part of the application
has imported the ``sqlalchemy.ext.baked`` module. The "bakery" used by
this feature is local to the mapper for ``MyClass``.
For per-query use, the :func:`.baked_lazyload` strategy may be used,
which works like any other loader option.
Opting out with the bake_queries flag
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
The :func:`.relationship` construct includes a flag
:paramref:`.relationship.bake_queries` which when set to False will cause
that relationship to opt out of caching queries. Additionally, the
:paramref:`.Session.enable_baked_queries` setting can be used to disable
all "baked query" use. These flags can be useful to conserve memory,
when memory conservation is more important than performance for a particular
relationship or for the application overall.
API Documentation
-----------------
@@ -364,13 +448,9 @@ API Documentation
.. autoclass:: BakedQuery
:members:
.. autoclass:: Bakery
:members:
.. autoclass:: Result
:members:
.. autofunction:: bake_lazy_loaders
.. autofunction:: unbake_lazy_loaders
.. autofunction:: baked_lazyload
.. autofunction:: baked_lazyload_all
+51 -4
View File
@@ -49,8 +49,6 @@ assumed to be completed and the 'configure' step has finished::
""
# do something with mappings
.. versionadded:: 0.7.3
``__declare_first__()``
~~~~~~~~~~~~~~~~~~~~~~~
@@ -68,7 +66,7 @@ configuration via the :meth:`.MapperEvents.before_configured` event::
.. _declarative_abstract:
``__abstract__``
~~~~~~~~~~~~~~~~~~~
~~~~~~~~~~~~~~~~
``__abstract__`` causes declarative to skip the production
of a table or mapper for the class entirely. A class can be added within a
@@ -109,6 +107,55 @@ created perhaps within distinct databases::
DefaultBase.metadata.create_all(some_engine)
OtherBase.metadata_create_all(some_other_engine)
.. versionadded:: 0.7.3
``__table_cls__``
~~~~~~~~~~~~~~~~~
Allows the callable / class used to generate a :class:`.Table` to be customized.
This is a very open-ended hook that can allow special customizations
to a :class:`.Table` that one generates here::
class MyMixin(object):
@classmethod
def __table_cls__(cls, name, metadata, *arg, **kw):
return Table(
"my_" + name,
metadata, *arg, **kw
)
The above mixin would cause all :class:`.Table` objects generated to include
the prefix ``"my_"``, followed by the name normally specified using the
``__tablename__`` attribute.
``__table_cls__`` also supports the case of returning ``None``, which
causes the class to be considered as single-table inheritance vs. its subclass.
This may be useful in some customization schemes to determine that single-table
inheritance should take place based on the arguments for the table itself,
such as, define as single-inheritance if there is no primary key present::
class AutoTable(object):
@declared_attr
def __tablename__(cls):
return cls.__name__
@classmethod
def __table_cls__(cls, *arg, **kw):
for obj in arg[1:]:
if (isinstance(obj, Column) and obj.primary_key) or \
isinstance(obj, PrimaryKeyConstraint):
return Table(*arg, **kw)
return None
class Person(AutoTable, Base):
id = Column(Integer, primary_key=True)
class Employee(Person):
employee_name = Column(String)
The above ``Employee`` class would be mapped as single-table inheritance
against ``Person``; the ``employee_name`` column would be added as a member
of the ``Person`` table.
.. versionadded:: 1.0.0

Some files were not shown because too many files have changed in this diff Show More