From fa6dd376bb24845724287d980a98ea50eb1cfab1 Mon Sep 17 00:00:00 2001 From: Mike Bayer Date: Wed, 11 Jan 2017 10:12:12 -0500 Subject: [PATCH] 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 --- doc/build/changelog/changelog_10.rst | 8 + lib/sqlalchemy/connectors/mxodbc.py | 2 +- lib/sqlalchemy/connectors/pyodbc.py | 2 +- lib/sqlalchemy/dialects/firebird/base.py | 8 +- .../dialects/firebird/kinterbasdb.py | 2 +- lib/sqlalchemy/dialects/mssql/pyodbc.py | 4 +- lib/sqlalchemy/dialects/mysql/base.py | 2 +- lib/sqlalchemy/dialects/mysql/cymysql.py | 2 +- lib/sqlalchemy/dialects/mysql/mysqldb.py | 2 +- lib/sqlalchemy/dialects/mysql/oursql.py | 2 +- lib/sqlalchemy/dialects/mysql/zxjdbc.py | 2 +- lib/sqlalchemy/dialects/postgresql/base.py | 20 +- lib/sqlalchemy/dialects/postgresql/ext.py | 2 +- lib/sqlalchemy/dialects/sqlite/base.py | 32 +-- lib/sqlalchemy/dialects/sqlite/pysqlite.py | 4 +- lib/sqlalchemy/engine/base.py | 16 +- lib/sqlalchemy/engine/interfaces.py | 4 +- lib/sqlalchemy/engine/url.py | 2 +- lib/sqlalchemy/events.py | 14 +- lib/sqlalchemy/ext/associationproxy.py | 2 +- lib/sqlalchemy/ext/automap.py | 4 +- lib/sqlalchemy/ext/compiler.py | 6 +- lib/sqlalchemy/ext/declarative/api.py | 2 +- lib/sqlalchemy/ext/hybrid.py | 20 +- lib/sqlalchemy/ext/mutable.py | 6 +- lib/sqlalchemy/orm/__init__.py | 4 +- lib/sqlalchemy/orm/attributes.py | 2 +- lib/sqlalchemy/orm/descriptor_props.py | 2 +- lib/sqlalchemy/orm/events.py | 4 +- lib/sqlalchemy/orm/interfaces.py | 16 +- lib/sqlalchemy/orm/mapper.py | 6 +- lib/sqlalchemy/orm/properties.py | 2 +- lib/sqlalchemy/orm/query.py | 184 +++++++++--------- lib/sqlalchemy/orm/scoping.py | 2 +- lib/sqlalchemy/orm/session.py | 11 +- lib/sqlalchemy/orm/strategy_options.py | 14 +- lib/sqlalchemy/orm/util.py | 18 +- lib/sqlalchemy/pool.py | 6 +- lib/sqlalchemy/processors.py | 6 +- lib/sqlalchemy/sql/compiler.py | 2 +- lib/sqlalchemy/sql/ddl.py | 2 +- lib/sqlalchemy/sql/dml.py | 26 +-- lib/sqlalchemy/sql/elements.py | 50 ++--- lib/sqlalchemy/sql/functions.py | 8 +- lib/sqlalchemy/sql/operators.py | 2 +- lib/sqlalchemy/sql/schema.py | 18 +- lib/sqlalchemy/sql/selectable.py | 64 +++--- lib/sqlalchemy/sql/sqltypes.py | 4 +- lib/sqlalchemy/sql/util.py | 2 +- lib/sqlalchemy/testing/warnings.py | 7 + lib/sqlalchemy/util/compat.py | 66 ++++--- lib/sqlalchemy/util/langhelpers.py | 4 +- test/dialect/postgresql/test_types.py | 2 +- test/dialect/test_sqlite.py | 6 +- test/engine/test_execute.py | 6 +- test/engine/test_logging.py | 20 +- test/engine/test_transaction.py | 4 +- test/ext/declarative/test_clsregistry.py | 4 +- test/ext/test_associationproxy.py | 4 +- test/orm/test_composites.py | 4 +- test/orm/test_events.py | 12 +- test/orm/test_instrumentation.py | 8 +- test/orm/test_joins.py | 8 +- test/orm/test_query.py | 6 +- test/orm/test_relationships.py | 8 +- test/orm/test_session.py | 6 +- test/orm/test_transaction.py | 14 +- test/orm/test_unitofworkv2.py | 20 +- test/sql/test_compiler.py | 4 +- test/sql/test_metadata.py | 6 +- test/sql/test_query.py | 2 +- test/sql/test_resultset.py | 2 +- test/sql/test_returning.py | 2 +- test/sql/test_text.py | 14 +- test/sql/test_update.py | 4 +- tox.ini | 3 +- 76 files changed, 446 insertions(+), 425 deletions(-) diff --git a/doc/build/changelog/changelog_10.rst b/doc/build/changelog/changelog_10.rst index aa3a4c7e6f..b8661f98b4 100644 --- a/doc/build/changelog/changelog_10.rst +++ b/doc/build/changelog/changelog_10.rst @@ -18,6 +18,14 @@ .. changelog:: :version: 1.0.17 + .. change:: + :tags: bug, py3k + :tickets: 3886 + :versions: 1.1.5 + + Fixed Python 3.6 DeprecationWarnings related to escaped strings without + the 'r' modifier, and added test coverage for Python 3.6. + .. change:: :tags: bug, orm :tickets: 3884 diff --git a/lib/sqlalchemy/connectors/mxodbc.py b/lib/sqlalchemy/connectors/mxodbc.py index e3af6fc31a..32e7e1870d 100644 --- a/lib/sqlalchemy/connectors/mxodbc.py +++ b/lib/sqlalchemy/connectors/mxodbc.py @@ -123,7 +123,7 @@ class MxODBCConnector(Connector): # of what we're doing here dbapi_con = connection.connection version = [] - r = re.compile('[.\-]') + r = re.compile(r'[.\-]') # 18 == pyodbc.SQL_DBMS_VER for n in r.split(dbapi_con.getinfo(18)[1]): try: diff --git a/lib/sqlalchemy/connectors/pyodbc.py b/lib/sqlalchemy/connectors/pyodbc.py index 53b775edd4..ee8445dae4 100644 --- a/lib/sqlalchemy/connectors/pyodbc.py +++ b/lib/sqlalchemy/connectors/pyodbc.py @@ -187,7 +187,7 @@ class PyODBCConnector(Connector): # queries. dbapi_con = connection.connection version = [] - r = re.compile('[.\-]') + r = re.compile(r'[.\-]') for n in r.split(dbapi_con.getinfo(self.dbapi.SQL_DBMS_VER)): try: version.append(int(n)) diff --git a/lib/sqlalchemy/dialects/firebird/base.py b/lib/sqlalchemy/dialects/firebird/base.py index de8c7f2a0d..7d4aca5266 100644 --- a/lib/sqlalchemy/dialects/firebird/base.py +++ b/lib/sqlalchemy/dialects/firebird/base.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -""" +r""" .. dialect:: firebird :name: Firebird @@ -55,13 +55,13 @@ extends that to deletes and updates. This is generically exposed by the SQLAlchemy ``returning()`` method, such as:: # INSERT..RETURNING - result = table.insert().returning(table.c.col1, table.c.col2).\\ + result = table.insert().returning(table.c.col1, table.c.col2).\ values(name='foo') print result.fetchall() # UPDATE..RETURNING - raises = empl.update().returning(empl.c.id, empl.c.salary).\\ - where(empl.c.sales>100).\\ + raises = empl.update().returning(empl.c.id, empl.c.salary).\ + where(empl.c.sales>100).\ values(dict(salary=empl.c.salary * 1.1)) print raises.fetchall() diff --git a/lib/sqlalchemy/dialects/firebird/kinterbasdb.py b/lib/sqlalchemy/dialects/firebird/kinterbasdb.py index 4ddda24097..b7c1563e34 100644 --- a/lib/sqlalchemy/dialects/firebird/kinterbasdb.py +++ b/lib/sqlalchemy/dialects/firebird/kinterbasdb.py @@ -160,7 +160,7 @@ class FBDialect_kinterbasdb(FBDialect): def _parse_version_info(self, version): m = match( - '\w+-V(\d+)\.(\d+)\.(\d+)\.(\d+)( \w+ (\d+)\.(\d+))?', version) + r'\w+-V(\d+)\.(\d+)\.(\d+)\.(\d+)( \w+ (\d+)\.(\d+))?', version) if not m: raise AssertionError( "Could not determine version from string '%s'" % version) diff --git a/lib/sqlalchemy/dialects/mssql/pyodbc.py b/lib/sqlalchemy/dialects/mssql/pyodbc.py index 2cccdfeeda..c6368f9696 100644 --- a/lib/sqlalchemy/dialects/mssql/pyodbc.py +++ b/lib/sqlalchemy/dialects/mssql/pyodbc.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -""" +r""" .. dialect:: mssql+pyodbc :name: PyODBC :dbapi: pyodbc @@ -281,7 +281,7 @@ class MSDialect_pyodbc(PyODBCConnector, MSDialect): _get_server_version_info(connection) else: version = [] - r = re.compile('[.\-]') + r = re.compile(r'[.\-]') for n in r.split(raw): try: version.append(int(n)) diff --git a/lib/sqlalchemy/dialects/mysql/base.py b/lib/sqlalchemy/dialects/mysql/base.py index 803265d794..1654ff3278 100644 --- a/lib/sqlalchemy/dialects/mysql/base.py +++ b/lib/sqlalchemy/dialects/mysql/base.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -""" +r""" .. dialect:: mysql :name: MySQL diff --git a/lib/sqlalchemy/dialects/mysql/cymysql.py b/lib/sqlalchemy/dialects/mysql/cymysql.py index 6373e4a586..a5ddb1a9e8 100644 --- a/lib/sqlalchemy/dialects/mysql/cymysql.py +++ b/lib/sqlalchemy/dialects/mysql/cymysql.py @@ -59,7 +59,7 @@ class MySQLDialect_cymysql(MySQLDialect_mysqldb): def _get_server_version_info(self, connection): dbapi_con = connection.connection version = [] - r = re.compile('[.\-]') + r = re.compile(r'[.\-]') for n in r.split(dbapi_con.server_version): try: version.append(int(n)) diff --git a/lib/sqlalchemy/dialects/mysql/mysqldb.py b/lib/sqlalchemy/dialects/mysql/mysqldb.py index ff2572d689..6af860133f 100644 --- a/lib/sqlalchemy/dialects/mysql/mysqldb.py +++ b/lib/sqlalchemy/dialects/mysql/mysqldb.py @@ -184,7 +184,7 @@ class MySQLDialect_mysqldb(MySQLDialect): def _get_server_version_info(self, connection): dbapi_con = connection.connection version = [] - r = re.compile('[.\-]') + r = re.compile(r'[.\-]') for n in r.split(dbapi_con.get_server_info()): try: version.append(int(n)) diff --git a/lib/sqlalchemy/dialects/mysql/oursql.py b/lib/sqlalchemy/dialects/mysql/oursql.py index d4f6f70313..f7f90e9473 100644 --- a/lib/sqlalchemy/dialects/mysql/oursql.py +++ b/lib/sqlalchemy/dialects/mysql/oursql.py @@ -223,7 +223,7 @@ class MySQLDialect_oursql(MySQLDialect): def _get_server_version_info(self, connection): dbapi_con = connection.connection version = [] - r = re.compile('[.\-]') + r = re.compile(r'[.\-]') for n in r.split(dbapi_con.server_info): try: version.append(int(n)) diff --git a/lib/sqlalchemy/dialects/mysql/zxjdbc.py b/lib/sqlalchemy/dialects/mysql/zxjdbc.py index f65661d4a4..9c92be4e6b 100644 --- a/lib/sqlalchemy/dialects/mysql/zxjdbc.py +++ b/lib/sqlalchemy/dialects/mysql/zxjdbc.py @@ -106,7 +106,7 @@ class MySQLDialect_zxjdbc(ZxJDBCConnector, MySQLDialect): def _get_server_version_info(self, connection): dbapi_con = connection.connection version = [] - r = re.compile('[.\-]') + r = re.compile(r'[.\-]') for n in r.split(dbapi_con.dbversion): try: version.append(int(n)) diff --git a/lib/sqlalchemy/dialects/postgresql/base.py b/lib/sqlalchemy/dialects/postgresql/base.py index 8bf6e10c12..4e92422a33 100644 --- a/lib/sqlalchemy/dialects/postgresql/base.py +++ b/lib/sqlalchemy/dialects/postgresql/base.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -""" +r""" .. dialect:: postgresql :name: PostgreSQL @@ -233,17 +233,17 @@ primary key identifiers. To specify an explicit ``RETURNING`` clause, use the :meth:`._UpdateBase.returning` method on a per-statement basis:: # INSERT..RETURNING - result = table.insert().returning(table.c.col1, table.c.col2).\\ + result = table.insert().returning(table.c.col1, table.c.col2).\ values(name='foo') print result.fetchall() # UPDATE..RETURNING - result = table.update().returning(table.c.col1, table.c.col2).\\ + result = table.update().returning(table.c.col1, table.c.col2).\ where(table.c.name=='foo').values(name='bar') print result.fetchall() # DELETE..RETURNING - result = table.delete().returning(table.c.col1, table.c.col2).\\ + result = table.delete().returning(table.c.col1, table.c.col2).\ where(table.c.name=='foo') print result.fetchall() @@ -2215,8 +2215,8 @@ class PGDialect(default.DefaultDialect): def _get_server_version_info(self, connection): v = connection.execute("select version()").scalar() m = re.match( - '.*(?:PostgreSQL|EnterpriseDB) ' - '(\d+)\.(\d+)(?:\.(\d+))?(?:\.\d+)?(?:devel)?', + r'.*(?:PostgreSQL|EnterpriseDB) ' + r'(\d+)\.(\d+)(?:\.(\d+))?(?:\.\d+)?(?:devel)?', v) if not m: raise AssertionError( @@ -2381,12 +2381,12 @@ class PGDialect(default.DefaultDialect): nullable = not notnull is_array = format_type.endswith('[]') - charlen = re.search('\(([\d,]+)\)', format_type) + charlen = re.search(r'\(([\d,]+)\)', format_type) if charlen: charlen = charlen.group(1) - args = re.search('\((.*)\)', format_type) + args = re.search(r'\((.*)\)', format_type) if args and args.group(1): - args = tuple(re.split('\s*,\s*', args.group(1))) + args = tuple(re.split(r'\s*,\s*', args.group(1))) else: args = () kwargs = {} @@ -2906,7 +2906,7 @@ class PGDialect(default.DefaultDialect): domains = {} for domain in c.fetchall(): # strip (30) from character varying(30) - attype = re.search('([^\(]+)', domain['attype']).group(1) + attype = re.search(r'([^\(]+)', domain['attype']).group(1) if domain['visible']: # 'visible' just means whether or not the domain is in a # schema that's on the search path -- or not overridden by diff --git a/lib/sqlalchemy/dialects/postgresql/ext.py b/lib/sqlalchemy/dialects/postgresql/ext.py index 519f19ae3d..ec95f37b4b 100644 --- a/lib/sqlalchemy/dialects/postgresql/ext.py +++ b/lib/sqlalchemy/dialects/postgresql/ext.py @@ -81,7 +81,7 @@ static/sql-createtable.html#SQL-CREATETABLE-EXCLUDE where = None def __init__(self, *elements, **kw): - """ + r""" :param \*elements: A sequence of two tuples of the form ``(column, operator)`` where column must be a column name or Column object and operator must diff --git a/lib/sqlalchemy/dialects/sqlite/base.py b/lib/sqlalchemy/dialects/sqlite/base.py index d6239f0940..76193ff91f 100644 --- a/lib/sqlalchemy/dialects/sqlite/base.py +++ b/lib/sqlalchemy/dialects/sqlite/base.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -""" +r""" .. dialect:: sqlite :name: SQLite @@ -390,7 +390,7 @@ The bug, entirely outside of SQLAlchemy, can be illustrated thusly:: union select x.a, x.b from x where a=2 ''') - assert [c[0] for c in cursor.description] == ['a', 'b'], \\ + assert [c[0] for c in cursor.description] == ['a', 'b'], \ [c[0] for c in cursor.description] The second assertion fails:: @@ -527,7 +527,7 @@ class _DateTimeMixin(object): class DATETIME(_DateTimeMixin, sqltypes.DateTime): - """Represent a Python datetime object in SQLite using a string. + r"""Represent a Python datetime object in SQLite using a string. The default string storage format is:: @@ -621,7 +621,7 @@ class DATETIME(_DateTimeMixin, sqltypes.DateTime): class DATE(_DateTimeMixin, sqltypes.Date): - """Represent a Python date object in SQLite using a string. + r"""Represent a Python date object in SQLite using a string. The default string storage format is:: @@ -682,7 +682,7 @@ class DATE(_DateTimeMixin, sqltypes.Date): class TIME(_DateTimeMixin, sqltypes.Time): - """Represent a Python time object in SQLite using a string. + r"""Represent a Python time object in SQLite using a string. The default string storage format is:: @@ -1308,7 +1308,7 @@ class SQLiteDialect(default.DefaultDialect): constraint_name = None table_data = self._get_table_sql(connection, table_name, schema=schema) if table_data: - PK_PATTERN = 'CONSTRAINT (\w+) PRIMARY KEY' + PK_PATTERN = r'CONSTRAINT (\w+) PRIMARY KEY' result = re.search(PK_PATTERN, table_data, re.I) constraint_name = result.group(1) if result else None @@ -1381,11 +1381,11 @@ class SQLiteDialect(default.DefaultDialect): def parse_fks(): FK_PATTERN = ( - '(?:CONSTRAINT (\w+) +)?' - 'FOREIGN KEY *\( *(.+?) *\) +' - 'REFERENCES +(?:(?:"(.+?)")|([a-z0-9_]+)) *\((.+?)\) *' - '((?:ON (?:DELETE|UPDATE) ' - '(?:SET NULL|SET DEFAULT|CASCADE|RESTRICT|NO ACTION) *)*)' + r'(?:CONSTRAINT (\w+) +)?' + r'FOREIGN KEY *\( *(.+?) *\) +' + r'REFERENCES +(?:(?:"(.+?)")|([a-z0-9_]+)) *\((.+?)\) *' + r'((?:ON (?:DELETE|UPDATE) ' + r'(?:SET NULL|SET DEFAULT|CASCADE|RESTRICT|NO ACTION) *)*)' ) for match in re.finditer(FK_PATTERN, table_data, re.I): ( @@ -1462,10 +1462,10 @@ class SQLiteDialect(default.DefaultDialect): unique_constraints = [] def parse_uqs(): - UNIQUE_PATTERN = '(?:CONSTRAINT "?(.+?)"? +)?UNIQUE *\((.+?)\)' + UNIQUE_PATTERN = r'(?:CONSTRAINT "?(.+?)"? +)?UNIQUE *\((.+?)\)' INLINE_UNIQUE_PATTERN = ( - '(?:(".+?")|([a-z0-9]+)) ' - '+[a-z0-9_ ]+? +UNIQUE') + r'(?:(".+?")|([a-z0-9]+)) ' + r'+[a-z0-9_ ]+? +UNIQUE') for match in re.finditer(UNIQUE_PATTERN, table_data, re.I): name, cols = match.group(1, 2) @@ -1501,8 +1501,8 @@ class SQLiteDialect(default.DefaultDialect): return [] CHECK_PATTERN = ( - '(?:CONSTRAINT (\w+) +)?' - 'CHECK *\( *(.+) *\),? *' + r'(?:CONSTRAINT (\w+) +)?' + r'CHECK *\( *(.+) *\),? *' ) check_constraints = [] # NOTE: we aren't using re.S here because we actually are diff --git a/lib/sqlalchemy/dialects/sqlite/pysqlite.py b/lib/sqlalchemy/dialects/sqlite/pysqlite.py index b788435b73..40a7cbb077 100644 --- a/lib/sqlalchemy/dialects/sqlite/pysqlite.py +++ b/lib/sqlalchemy/dialects/sqlite/pysqlite.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -""" +r""" .. dialect:: sqlite+pysqlite :name: pysqlite :dbapi: sqlite3 @@ -58,7 +58,7 @@ To use a Windows path, regular drive specifications and backslashes can be used. Double backslashes are probably needed:: # absolute path on Windows - e = create_engine('sqlite:///C:\\\\path\\\\to\\\\database.db') + e = create_engine('sqlite:///C:\\path\\to\\database.db') The sqlite ``:memory:`` identifier is the default if no filepath is present. Specify ``sqlite://`` and nothing else:: diff --git a/lib/sqlalchemy/engine/base.py b/lib/sqlalchemy/engine/base.py index 0c75eef5ea..0334d2d7a8 100644 --- a/lib/sqlalchemy/engine/base.py +++ b/lib/sqlalchemy/engine/base.py @@ -165,7 +165,7 @@ class Connection(Connectable): self.close() def execution_options(self, **opt): - """ Set non-SQL options for the connection which take effect + r""" Set non-SQL options for the connection which take effect during execution. The method returns a copy of this :class:`.Connection` which references @@ -175,7 +175,7 @@ class Connection(Connectable): underlying resource, it's usually a good idea to ensure that the copies will be discarded immediately, which is implicit if used as in:: - result = connection.execution_options(stream_results=True).\\ + result = connection.execution_options(stream_results=True).\ execute(stmt) Note that any key/value can be passed to @@ -877,7 +877,7 @@ class Connection(Connectable): return self.execute(object, *multiparams, **params).scalar() def execute(self, object, *multiparams, **params): - """Executes a SQL statement construct and returns a + r"""Executes a SQL statement construct and returns a :class:`.ResultProxy`. :param object: The statement to be executed. May be @@ -1459,7 +1459,7 @@ class Connection(Connectable): util.reraise(*exc_info) def transaction(self, callable_, *args, **kwargs): - """Execute the given function within a transaction boundary. + r"""Execute the given function within a transaction boundary. The function is passed this :class:`.Connection` as the first argument, followed by the given \*args and \**kwargs, @@ -1510,7 +1510,7 @@ class Connection(Connectable): trans.rollback() def run_callable(self, callable_, *args, **kwargs): - """Given a callable object or function, execute it, passing + r"""Given a callable object or function, execute it, passing a :class:`.Connection` as the first argument. The given \*args and \**kwargs are passed subsequent @@ -1769,7 +1769,7 @@ class Engine(Connectable, log.Identified): self.update_execution_options(**execution_options) def update_execution_options(self, **opt): - """Update the default execution_options dictionary + r"""Update the default execution_options dictionary of this :class:`.Engine`. The given keys/values in \**opt are added to the @@ -1978,7 +1978,7 @@ class Engine(Connectable, log.Identified): return Engine._trans_ctx(conn, trans, close_with_result) def transaction(self, callable_, *args, **kwargs): - """Execute the given function within a transaction boundary. + r"""Execute the given function within a transaction boundary. The function is passed a :class:`.Connection` newly procured from :meth:`.Engine.contextual_connect` as the first argument, @@ -2020,7 +2020,7 @@ class Engine(Connectable, log.Identified): return conn.transaction(callable_, *args, **kwargs) def run_callable(self, callable_, *args, **kwargs): - """Given a callable object or function, execute it, passing + r"""Given a callable object or function, execute it, passing a :class:`.Connection` as the first argument. The given \*args and \**kwargs are passed subsequent diff --git a/lib/sqlalchemy/engine/interfaces.py b/lib/sqlalchemy/engine/interfaces.py index 38b5442d86..d0eff1cb1b 100644 --- a/lib/sqlalchemy/engine/interfaces.py +++ b/lib/sqlalchemy/engine/interfaces.py @@ -378,7 +378,7 @@ class Dialect(object): def get_unique_constraints( self, connection, table_name, schema=None, **kw): - """Return information about unique constraints in `table_name`. + r"""Return information about unique constraints in `table_name`. Given a string `table_name` and an optional string `schema`, return unique constraint information as a list of dicts with these keys: @@ -401,7 +401,7 @@ class Dialect(object): def get_check_constraints( self, connection, table_name, schema=None, **kw): - """Return information about check constraints in `table_name`. + r"""Return information about check constraints in `table_name`. Given a string `table_name` and an optional string `schema`, return check constraint information as a list of dicts with these keys: diff --git a/lib/sqlalchemy/engine/url.py b/lib/sqlalchemy/engine/url.py index 9d5b784eb1..1c16584f12 100644 --- a/lib/sqlalchemy/engine/url.py +++ b/lib/sqlalchemy/engine/url.py @@ -156,7 +156,7 @@ class URL(object): return dialect_cls def translate_connect_args(self, names=[], **kw): - """Translate url attributes into a dictionary of connection arguments. + r"""Translate url attributes into a dictionary of connection arguments. Returns attributes of this url (`host`, `database`, `username`, `password`, `port`) as a plain dictionary. The attribute names are diff --git a/lib/sqlalchemy/events.py b/lib/sqlalchemy/events.py index 8a6cb2689b..2ed44f5dd8 100644 --- a/lib/sqlalchemy/events.py +++ b/lib/sqlalchemy/events.py @@ -76,7 +76,7 @@ class DDLEvents(event.Events): _dispatch_target = SchemaEventTarget def before_create(self, target, connection, **kw): - """Called before CREATE statements are emitted. + r"""Called before CREATE statements are emitted. :param target: the :class:`.MetaData` or :class:`.Table` object which is the target of the event. @@ -92,7 +92,7 @@ class DDLEvents(event.Events): """ def after_create(self, target, connection, **kw): - """Called after CREATE statements are emitted. + r"""Called after CREATE statements are emitted. :param target: the :class:`.MetaData` or :class:`.Table` object which is the target of the event. @@ -108,7 +108,7 @@ class DDLEvents(event.Events): """ def before_drop(self, target, connection, **kw): - """Called before DROP statements are emitted. + r"""Called before DROP statements are emitted. :param target: the :class:`.MetaData` or :class:`.Table` object which is the target of the event. @@ -124,7 +124,7 @@ class DDLEvents(event.Events): """ def after_drop(self, target, connection, **kw): - """Called after DROP statements are emitted. + r"""Called after DROP statements are emitted. :param target: the :class:`.MetaData` or :class:`.Table` object which is the target of the event. @@ -717,7 +717,7 @@ class ConnectionEvents(event.Events): """ def handle_error(self, exception_context): - """Intercept all exceptions processed by the :class:`.Connection`. + r"""Intercept all exceptions processed by the :class:`.Connection`. This includes all exceptions emitted by the DBAPI as well as within SQLAlchemy's statement invocation process, including @@ -763,7 +763,7 @@ class ConnectionEvents(event.Events): @event.listens_for(Engine, "handle_error") def handle_exception(context): if isinstance(context.original_exception, - psycopg2.OperationalError) and \\ + psycopg2.OperationalError) and \ "failed" in str(context.original_exception): raise MySpecialException("failed operation") @@ -786,7 +786,7 @@ class ConnectionEvents(event.Events): @event.listens_for(Engine, "handle_error", retval=True) def handle_exception(context): - if context.chained_exception is not None and \\ + if context.chained_exception is not None and \ "special" in context.chained_exception.message: return MySpecialException("failed", cause=context.chained_exception) diff --git a/lib/sqlalchemy/ext/associationproxy.py b/lib/sqlalchemy/ext/associationproxy.py index 4ffd2b6474..6f570a1fa9 100644 --- a/lib/sqlalchemy/ext/associationproxy.py +++ b/lib/sqlalchemy/ext/associationproxy.py @@ -22,7 +22,7 @@ from ..sql import not_, or_ def association_proxy(target_collection, attr, **kw): - """Return a Python property implementing a view of a target + r"""Return a Python property implementing a view of a target attribute which references an attribute on members of the target. diff --git a/lib/sqlalchemy/ext/automap.py b/lib/sqlalchemy/ext/automap.py index c3a40ada8e..57a3a25920 100644 --- a/lib/sqlalchemy/ext/automap.py +++ b/lib/sqlalchemy/ext/automap.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -"""Define an extension to the :mod:`sqlalchemy.ext.declarative` system +r"""Define an extension to the :mod:`sqlalchemy.ext.declarative` system which automatically generates mapped classes and relationships from a database schema, typically though not necessarily one which is reflected. @@ -187,7 +187,7 @@ scheme for class names and a "pluralizer" for collection names using the "Produce a 'camelized' class name, e.g. " "'words_and_underscores' -> 'WordsAndUnderscores'" - return str(tablename[0].upper() + \\ + return str(tablename[0].upper() + \ re.sub(r'_([a-z])', lambda m: m.group(1).upper(), tablename[1:])) _pluralizer = inflect.engine() diff --git a/lib/sqlalchemy/ext/compiler.py b/lib/sqlalchemy/ext/compiler.py index c3f60fd9d0..8b2bc95ce1 100644 --- a/lib/sqlalchemy/ext/compiler.py +++ b/lib/sqlalchemy/ext/compiler.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -"""Provides an API for creation of custom ClauseElements and compilers. +r"""Provides an API for creation of custom ClauseElements and compilers. Synopsis ======== @@ -159,7 +159,7 @@ is a "frozen" dictionary which supplies a generative ``union()`` method):: from sqlalchemy.sql.expression import Executable, ClauseElement class MyInsertThing(Executable, ClauseElement): - _execution_options = \\ + _execution_options = \ Executable._execution_options.union({'autocommit': True}) More succinctly, if the construct is truly similar to an INSERT, UPDATE, or @@ -362,7 +362,7 @@ accommodates two arguments:: Example usage:: - Session.query(Account).\\ + Session.query(Account).\ filter( greatest( Account.checking_balance, diff --git a/lib/sqlalchemy/ext/declarative/api.py b/lib/sqlalchemy/ext/declarative/api.py index eb8935a4a3..7c503d471b 100644 --- a/lib/sqlalchemy/ext/declarative/api.py +++ b/lib/sqlalchemy/ext/declarative/api.py @@ -250,7 +250,7 @@ def declarative_base(bind=None, metadata=None, mapper=None, cls=object, name='Base', constructor=_declarative_constructor, class_registry=None, metaclass=DeclarativeMeta): - """Construct a base class for declarative class definitions. + r"""Construct a base class for declarative class definitions. The new base class will be given a metaclass that produces appropriate :class:`~sqlalchemy.schema.Table` objects and makes diff --git a/lib/sqlalchemy/ext/hybrid.py b/lib/sqlalchemy/ext/hybrid.py index 192e285018..509dd560ad 100644 --- a/lib/sqlalchemy/ext/hybrid.py +++ b/lib/sqlalchemy/ext/hybrid.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -"""Define attributes on ORM-mapped classes that have "hybrid" behavior. +r"""Define attributes on ORM-mapped classes that have "hybrid" behavior. "hybrid" means the attribute has distinct behaviors defined at the class level and at the instance level. @@ -245,7 +245,7 @@ However, at the expression level, it's expected that the ``User`` class will be used in an appropriate context such that an appropriate join to ``SavingsAccount`` will be present:: - >>> print Session().query(User, User.balance).\\ + >>> print Session().query(User, User.balance).\ ... join(User.accounts).filter(User.balance > 5000) SELECT "user".id AS user_id, "user".name AS user_name, account.balance AS account_balance @@ -303,8 +303,8 @@ we can adjust our ``SavingsAccount`` example to aggregate the balances for @balance.expression def balance(cls): - return select([func.sum(SavingsAccount.balance)]).\\ - where(SavingsAccount.user_id==cls.id).\\ + return select([func.sum(SavingsAccount.balance)]).\ + where(SavingsAccount.user_id==cls.id).\ label('total_balance') The above recipe will give us the ``balance`` column which renders @@ -448,7 +448,7 @@ SQL expression versus SQL expression:: >>> sw2 = aliased(SearchWord) >>> print Session().query( ... sw1.word_insensitive, - ... sw2.word_insensitive).\\ + ... sw2.word_insensitive).\ ... filter( ... sw1.word_insensitive > sw2.word_insensitive ... ) @@ -537,7 +537,7 @@ filtered based on the given criterion:: def transform(q): cls = self.__clause_element__() parent_alias = aliased(cls) - return q.join(parent_alias, cls.parent).\\ + return q.join(parent_alias, cls.parent).\ filter(op(parent_alias.parent, other)) return transform @@ -573,8 +573,8 @@ into :class:`.Query.filter`: >>> from sqlalchemy.orm import Session >>> session = Session() - {sql}>>> session.query(Node).\\ - ... with_transformation(Node.grandparent==Node(id=5)).\\ + {sql}>>> session.query(Node).\ + ... with_transformation(Node.grandparent==Node(id=5)).\ ... all() SELECT node.id AS node_id, node.parent_id AS node_parent_id FROM node JOIN node AS node_1 ON node_1.id = node.parent_id @@ -616,8 +616,8 @@ with each class:: .. sourcecode:: pycon+sql - {sql}>>> session.query(Node).\\ - ... with_transformation(Node.grandparent.join).\\ + {sql}>>> session.query(Node).\ + ... with_transformation(Node.grandparent.join).\ ... filter(Node.grandparent==Node(id=5)) SELECT node.id AS node_id, node.parent_id AS node_parent_id FROM node JOIN node AS node_1 ON node_1.id = node.parent_id diff --git a/lib/sqlalchemy/ext/mutable.py b/lib/sqlalchemy/ext/mutable.py index b0e2acdf53..3361c44750 100644 --- a/lib/sqlalchemy/ext/mutable.py +++ b/lib/sqlalchemy/ext/mutable.py @@ -5,7 +5,7 @@ # This module is part of SQLAlchemy and is released under # the MIT License: http://www.opensource.org/licenses/mit-license.php -"""Provide support for tracking of in-place changes to scalar values, +r"""Provide support for tracking of in-place changes to scalar values, which are propagated into ORM change events on owning parent objects. .. versionadded:: 0.7 :mod:`sqlalchemy.ext.mutable` replaces SQLAlchemy's @@ -252,8 +252,8 @@ and to also route attribute set events via ``__setattr__`` to the return self.x, self.y def __eq__(self, other): - return isinstance(other, Point) and \\ - other.x == self.x and \\ + return isinstance(other, Point) and \ + other.x == self.x and \ other.y == self.y def __ne__(self, other): diff --git a/lib/sqlalchemy/orm/__init__.py b/lib/sqlalchemy/orm/__init__.py index 22391e1de4..449173548a 100644 --- a/lib/sqlalchemy/orm/__init__.py +++ b/lib/sqlalchemy/orm/__init__.py @@ -71,7 +71,7 @@ from . import strategies as _strategies def create_session(bind=None, **kwargs): - """Create a new :class:`.Session` + r"""Create a new :class:`.Session` with no automation enabled by default. This function is used primarily for testing. The usual @@ -159,7 +159,7 @@ def backref(name, **kwargs): def deferred(*columns, **kw): - """Indicate a column-based mapped attribute that by default will + r"""Indicate a column-based mapped attribute that by default will not load unless accessed. :param \*columns: columns to be mapped. This is typically a single diff --git a/lib/sqlalchemy/orm/attributes.py b/lib/sqlalchemy/orm/attributes.py index ba14e561aa..fc81db7825 100644 --- a/lib/sqlalchemy/orm/attributes.py +++ b/lib/sqlalchemy/orm/attributes.py @@ -382,7 +382,7 @@ class AttributeImpl(object): parent_token=None, expire_missing=True, send_modified_events=True, **kwargs): - """Construct an AttributeImpl. + r"""Construct an AttributeImpl. \class_ associated class diff --git a/lib/sqlalchemy/orm/descriptor_props.py b/lib/sqlalchemy/orm/descriptor_props.py index 4949169ee4..0792ff2e2c 100644 --- a/lib/sqlalchemy/orm/descriptor_props.py +++ b/lib/sqlalchemy/orm/descriptor_props.py @@ -91,7 +91,7 @@ class CompositeProperty(DescriptorProperty): """ def __init__(self, class_, *attrs, **kwargs): - """Return a composite column-based property for use with a Mapper. + r"""Return a composite column-based property for use with a Mapper. See the mapping documentation section :ref:`mapper_composite` for a full usage example. diff --git a/lib/sqlalchemy/orm/events.py b/lib/sqlalchemy/orm/events.py index 406efb01f2..653f66dd82 100644 --- a/lib/sqlalchemy/orm/events.py +++ b/lib/sqlalchemy/orm/events.py @@ -632,7 +632,7 @@ class MapperEvents(event.Events): _MapperEventsHold._clear() def instrument_class(self, mapper, class_): - """Receive a class when the mapper is first constructed, + r"""Receive a class when the mapper is first constructed, before instrumentation is applied to the mapped class. This event is the earliest phase of mapper construction. @@ -655,7 +655,7 @@ class MapperEvents(event.Events): """ def mapper_configured(self, mapper, class_): - """Called when a specific mapper has completed its own configuration + r"""Called when a specific mapper has completed its own configuration within the scope of the :func:`.configure_mappers` call. The :meth:`.MapperEvents.mapper_configured` event is invoked diff --git a/lib/sqlalchemy/orm/interfaces.py b/lib/sqlalchemy/orm/interfaces.py index dbf8a1b5dd..3fad83ef4e 100644 --- a/lib/sqlalchemy/orm/interfaces.py +++ b/lib/sqlalchemy/orm/interfaces.py @@ -247,7 +247,7 @@ class MapperProperty(_MappedAttribute, InspectionAttr, util.MemoizedSlots): class PropComparator(operators.ColumnOperators): - """Defines SQL operators for :class:`.MapperProperty` objects. + r"""Defines SQL operators for :class:`.MapperProperty` objects. SQLAlchemy allows for operators to be redefined at both the Core and ORM level. :class:`.PropComparator` @@ -273,9 +273,9 @@ class PropComparator(operators.ColumnOperators): # definition of custom PropComparator subclasses - from sqlalchemy.orm.properties import \\ - ColumnProperty,\\ - CompositeProperty,\\ + from sqlalchemy.orm.properties import \ + ColumnProperty,\ + CompositeProperty,\ RelationshipProperty class MyColumnComparator(ColumnProperty.Comparator): @@ -387,14 +387,14 @@ class PropComparator(operators.ColumnOperators): return a.of_type(class_) def of_type(self, class_): - """Redefine this object in terms of a polymorphic subclass. + r"""Redefine this object in terms of a polymorphic subclass. Returns a new PropComparator from which further criterion can be evaluated. e.g.:: - query.join(Company.employees.of_type(Engineer)).\\ + query.join(Company.employees.of_type(Engineer)).\ filter(Engineer.name=='foo') :param \class_: a class or mapper indicating that criterion will be @@ -406,7 +406,7 @@ class PropComparator(operators.ColumnOperators): return self.operate(PropComparator.of_type_op, class_) def any(self, criterion=None, **kwargs): - """Return true if this collection contains any member that meets the + r"""Return true if this collection contains any member that meets the given criterion. The usual implementation of ``any()`` is @@ -424,7 +424,7 @@ class PropComparator(operators.ColumnOperators): return self.operate(PropComparator.any_op, criterion, **kwargs) def has(self, criterion=None, **kwargs): - """Return true if this element references a member which meets the + r"""Return true if this element references a member which meets the given criterion. The usual implementation of ``has()`` is diff --git a/lib/sqlalchemy/orm/mapper.py b/lib/sqlalchemy/orm/mapper.py index 25c6174ea8..f45b56ae71 100644 --- a/lib/sqlalchemy/orm/mapper.py +++ b/lib/sqlalchemy/orm/mapper.py @@ -118,7 +118,7 @@ class Mapper(InspectionAttr): legacy_is_orphan=False, _compiled_cache_size=100, ): - """Return a new :class:`~.Mapper` object. + r"""Return a new :class:`~.Mapper` object. This function is typically used behind the scenes via the Declarative extension. When using Declarative, @@ -698,7 +698,7 @@ class Mapper(InspectionAttr): @property def entity(self): - """Part of the inspection API. + r"""Part of the inspection API. Returns self.class\_. @@ -2886,7 +2886,7 @@ def reconstructor(fn): def validates(*names, **kw): - """Decorate a method as a 'validator' for one or more named properties. + r"""Decorate a method as a 'validator' for one or more named properties. Designates a method as a validator, a method which receives the name of the attribute as well as a value to be assigned, or in the diff --git a/lib/sqlalchemy/orm/properties.py b/lib/sqlalchemy/orm/properties.py index a947ff4355..63e7e1e204 100644 --- a/lib/sqlalchemy/orm/properties.py +++ b/lib/sqlalchemy/orm/properties.py @@ -42,7 +42,7 @@ class ColumnProperty(StrategizedProperty): '_mapped_by_synonym', '_deferred_column_loader') def __init__(self, *columns, **kwargs): - """Provide a column-level property for use with a Mapper. + r"""Provide a column-level property for use with a Mapper. Column-based properties can normally be applied to the mapper's ``properties`` dictionary using the :class:`.Column` element directly. diff --git a/lib/sqlalchemy/orm/query.py b/lib/sqlalchemy/orm/query.py index 57e8a198ca..a4c271ceb0 100644 --- a/lib/sqlalchemy/orm/query.py +++ b/lib/sqlalchemy/orm/query.py @@ -473,7 +473,7 @@ class Query(object): return q.alias(name=name) def cte(self, name=None, recursive=False): - """Return the full SELECT statement represented by this + r"""Return the full SELECT statement represented by this :class:`.Query` represented as a common table expression (CTE). Parameters and usage are the same as those of the @@ -501,8 +501,8 @@ class Query(object): included_parts = session.query( Part.sub_part, Part.part, - Part.quantity).\\ - filter(Part.part=="our part").\\ + Part.quantity).\ + filter(Part.part=="our part").\ cte(name="included_parts", recursive=True) incl_alias = aliased(included_parts, name="pr") @@ -511,7 +511,7 @@ class Query(object): session.query( parts_alias.sub_part, parts_alias.part, - parts_alias.quantity).\\ + parts_alias.quantity).\ filter(parts_alias.part==incl_alias.c.sub_part) ) @@ -519,7 +519,7 @@ class Query(object): included_parts.c.sub_part, func.sum(included_parts.c.quantity). label('total_quantity') - ).\\ + ).\ group_by(included_parts.c.sub_part) .. seealso:: @@ -708,7 +708,7 @@ class Query(object): @_generative() def yield_per(self, count): - """Yield only ``count`` rows at a time. + r"""Yield only ``count`` rows at a time. The purpose of this method is when fetching very large result sets (> 10K rows), to batch results in sub-collections and yield them @@ -730,7 +730,7 @@ class Query(object): Or more selectively using :func:`.lazyload`; such as with an asterisk to specify the default loader scheme:: - q = sess.query(Object).yield_per(100).\\ + q = sess.query(Object).yield_per(100).\ options(lazyload('*'), joinedload(Object.some_related)) .. warning:: @@ -986,7 +986,7 @@ class Query(object): self.session = session def from_self(self, *entities): - """return a Query that selects from this Query's + r"""return a Query that selects from this Query's SELECT statement. :meth:`.Query.from_self` essentially turns the SELECT statement @@ -1013,8 +1013,8 @@ class Query(object): the set of user objects we query against, and then apply additional joins against that row-limited set:: - q = session.query(User).filter(User.name.like('e%')).\\ - limit(5).from_self().\\ + q = session.query(User).filter(User.name.like('e%')).\ + limit(5).from_self().\ join(User.addresses).filter(Address.email.like('q%')) The above query joins to the ``Address`` entity but only against the @@ -1039,9 +1039,9 @@ class Query(object): refer to the ``User`` entity without any additional aliasing applied to it, those references wil be in terms of the subquery:: - q = session.query(User).filter(User.name.like('e%')).\\ - limit(5).from_self().\\ - join(User.addresses).filter(Address.email.like('q%')).\\ + q = session.query(User).filter(User.name.like('e%')).\ + limit(5).from_self().\ + join(User.addresses).filter(Address.email.like('q%')).\ order_by(User.name) The ORDER BY against ``User.name`` is aliased to be in terms of the @@ -1074,8 +1074,8 @@ class Query(object): ``Address`` entity on the outside, but we only wanted the outer query to return the ``Address.email`` column:: - q = session.query(User).filter(User.name.like('e%')).\\ - limit(5).from_self(Address.email).\\ + q = session.query(User).filter(User.name.like('e%')).\ + limit(5).from_self(Address.email).\ join(User.addresses).filter(Address.email.like('q%')) yielding: @@ -1101,10 +1101,10 @@ class Query(object): then a subquery, and then we'd like :func:`.contains_eager` to access the ``User`` columns:: - q = session.query(Address).join(Address.user).\\ + q = session.query(Address).join(Address.user).\ filter(User.name.like('e%')) - q = q.add_entity(User).from_self().\\ + q = q.add_entity(User).from_self().\ options(contains_eager(Address.user)) We use :meth:`.Query.add_entity` above **before** we call @@ -1219,18 +1219,18 @@ class Query(object): # Users, filtered on some arbitrary criterion # and then ordered by related email address - q = session.query(User).\\ - join(User.address).\\ - filter(User.name.like('%ed%')).\\ + q = session.query(User).\ + join(User.address).\ + filter(User.name.like('%ed%')).\ order_by(Address.email) # given *only* User.id==5, Address.email, and 'q', what # would the *next* User in the result be ? - subq = q.with_entities(Address.email).\\ - order_by(None).\\ - filter(User.id==5).\\ + subq = q.with_entities(Address.email).\ + order_by(None).\ + filter(User.id==5).\ subquery() - q = q.join((subq, subq.c.email < Address.email)).\\ + q = q.join((subq, subq.c.email < Address.email)).\ limit(1) .. versionadded:: 0.6.5 @@ -1434,7 +1434,7 @@ class Query(object): @_generative() def params(self, *args, **kwargs): - """add values for bind parameters which may have been + r"""add values for bind parameters which may have been specified in filter(). parameters may be specified using \**kwargs, or optionally a single @@ -1454,7 +1454,7 @@ class Query(object): @_generative(_no_statement_condition, _no_limit_offset) def filter(self, *criterion): - """apply the given filtering criterion to a copy + r"""apply the given filtering criterion to a copy of this :class:`.Query`, using SQL expressions. e.g.:: @@ -1465,7 +1465,7 @@ class Query(object): is that they will be joined together using the :func:`.and_` function:: - session.query(MyClass).\\ + session.query(MyClass).\ filter(MyClass.name == 'some name', MyClass.id > 5) The criterion is any SQL expression object applicable to the @@ -1488,7 +1488,7 @@ class Query(object): self._criterion = criterion def filter_by(self, **kwargs): - """apply the given filtering criterion to a copy + r"""apply the given filtering criterion to a copy of this :class:`.Query`, using keyword expressions. e.g.:: @@ -1499,7 +1499,7 @@ class Query(object): is that they will be joined together using the :func:`.and_` function:: - session.query(MyClass).\\ + session.query(MyClass).\ filter_by(name = 'some name', id = 5) The keyword expressions are extracted from the primary @@ -1576,7 +1576,7 @@ class Query(object): @_generative(_no_statement_condition, _no_limit_offset) def having(self, criterion): - """apply a HAVING criterion to the query and return the + r"""apply a HAVING criterion to the query and return the newly resulting :class:`.Query`. :meth:`~.Query.having` is used in conjunction with @@ -1585,9 +1585,9 @@ class Query(object): HAVING criterion makes it possible to use filters on aggregate functions like COUNT, SUM, AVG, MAX, and MIN, eg.:: - q = session.query(User.id).\\ - join(User.addresses).\\ - group_by(User.id).\\ + q = session.query(User.id).\ + join(User.addresses).\ + group_by(User.id).\ having(func.count(Address.id) > 2) """ @@ -1697,7 +1697,7 @@ class Query(object): return self._set_op(expression.except_all, *q) def join(self, *props, **kwargs): - """Create a SQL JOIN against this :class:`.Query` object's criterion + r"""Create a SQL JOIN against this :class:`.Query` object's criterion and apply generatively, returning the newly resulting :class:`.Query`. **Simple Relationship Joins** @@ -1735,9 +1735,9 @@ class Query(object): :meth:`~.Query.join`, each using an explicit attribute to indicate the source entity:: - q = session.query(User).\\ - join(User.orders).\\ - join(Order.items).\\ + q = session.query(User).\ + join(User.orders).\ + join(Order.items).\ join(Item.keywords) **Joins to a Target Entity or Selectable** @@ -1772,10 +1772,10 @@ class Query(object): a_alias = aliased(Address) - q = session.query(User).\\ - join(User.addresses).\\ - join(a_alias, User.addresses).\\ - filter(Address.email_address=='ed@foo.com').\\ + q = session.query(User).\ + join(User.addresses).\ + join(a_alias, User.addresses).\ + filter(Address.email_address=='ed@foo.com').\ filter(a_alias.email_address=='ed@bar.com') Where above, the generated SQL would be similar to:: @@ -1813,11 +1813,11 @@ class Query(object): :func:`.alias` and :func:`.select` constructs, with either the one or two-argument forms:: - addresses_q = select([Address.user_id]).\\ - where(Address.email_address.endswith("@bar.com")).\\ + addresses_q = select([Address.user_id]).\ + where(Address.email_address.endswith("@bar.com")).\ alias() - q = session.query(User).\\ + q = session.query(User).\ join(addresses_q, addresses_q.c.user_id==User.id) :meth:`~.Query.join` also features the ability to *adapt* a @@ -1826,8 +1826,8 @@ class Query(object): against ``Address``, allowing the relationship denoted by ``User.addresses`` to *adapt* itself to the altered target:: - address_subq = session.query(Address).\\ - filter(Address.email_address == 'ed@foo.com').\\ + address_subq = session.query(Address).\ + filter(Address.email_address == 'ed@foo.com').\ subquery() q = session.query(User).join(address_subq, User.addresses) @@ -1846,7 +1846,7 @@ class Query(object): The above form allows one to fall back onto an explicit ON clause at any time:: - q = session.query(User).\\ + q = session.query(User).\ join(address_subq, User.id==address_subq.c.user_id) **Controlling what to Join From** @@ -1859,8 +1859,8 @@ class Query(object): the :class:`.Query` to select first from the ``User`` entity:: - q = session.query(Address).select_from(User).\\ - join(User.addresses).\\ + q = session.query(Address).select_from(User).\ + join(User.addresses).\ filter(User.name == 'ed') Which will produce SQL similar to:: @@ -1876,7 +1876,7 @@ class Query(object): when a query is being joined algorithmically, such as when querying self-referentially to an arbitrary depth:: - q = session.query(Node).\\ + q = session.query(Node).\ join("children", "children", aliased=True) When ``aliased=True`` is used, the actual "alias" construct @@ -1884,8 +1884,8 @@ class Query(object): :meth:`.Query.filter` will adapt the incoming entity to the last join point:: - q = session.query(Node).\\ - join("children", "children", aliased=True).\\ + q = session.query(Node).\ + join("children", "children", aliased=True).\ filter(Node.name == 'grandchild 1') When using automatic aliasing, the ``from_joinpoint=True`` @@ -1893,19 +1893,19 @@ class Query(object): multiple calls to :meth:`~.Query.join`, so that each path along the way can be further filtered:: - q = session.query(Node).\\ - join("children", aliased=True).\\ - filter(Node.name='child 1').\\ - join("children", aliased=True, from_joinpoint=True).\\ + q = session.query(Node).\ + join("children", aliased=True).\ + filter(Node.name='child 1').\ + join("children", aliased=True, from_joinpoint=True).\ filter(Node.name == 'grandchild 1') The filtering aliases above can then be reset back to the original ``Node`` entity using :meth:`~.Query.reset_joinpoint`:: - q = session.query(Node).\\ - join("children", "children", aliased=True).\\ - filter(Node.name == 'grandchild 1').\\ - reset_joinpoint().\\ + q = session.query(Node).\ + join("children", "children", aliased=True).\ + filter(Node.name == 'grandchild 1').\ + reset_joinpoint().\ filter(Node.name == 'parent 1) For an example of ``aliased=True``, see the distribution @@ -2329,7 +2329,7 @@ class Query(object): @_generative(_no_clauseelement_condition) def select_from(self, *from_obj): - """Set the FROM clause of this :class:`.Query` explicitly. + r"""Set the FROM clause of this :class:`.Query` explicitly. :meth:`.Query.select_from` is often used in conjunction with :meth:`.Query.join` in order to control which entity is selected @@ -2343,8 +2343,8 @@ class Query(object): A typical example:: - q = session.query(Address).select_from(User).\\ - join(User.addresses).\\ + q = session.query(Address).select_from(User).\ + join(User.addresses).\ filter(User.name == 'ed') Which produces SQL equivalent to:: @@ -2377,7 +2377,7 @@ class Query(object): @_generative(_no_clauseelement_condition) def select_entity_from(self, from_obj): - """Set the FROM clause of this :class:`.Query` to a + r"""Set the FROM clause of this :class:`.Query` to a core selectable, applying it as a replacement FROM clause for corresponding mapped entities. @@ -2398,8 +2398,8 @@ class Query(object): select_stmt = select([User]).where(User.id == 7) - q = session.query(User).\\ - select_entity_from(select_stmt).\\ + q = session.query(User).\ + select_entity_from(select_stmt).\ filter(User.name == 'ed') The query generated will select ``User`` entities directly @@ -2419,8 +2419,8 @@ class Query(object): version 0.9, does not affect existing entities. The statement below:: - q = session.query(User).\\ - select_from(select_stmt).\\ + q = session.query(User).\ + select_from(select_stmt).\ filter(User.name == 'ed') Produces SQL where both the ``user`` table as well as the @@ -2546,7 +2546,7 @@ class Query(object): @_generative(_no_statement_condition) def distinct(self, *criterion): - """Apply a ``DISTINCT`` to the query and return the newly resulting + r"""Apply a ``DISTINCT`` to the query and return the newly resulting ``Query``. @@ -2578,7 +2578,7 @@ class Query(object): @_generative() def prefix_with(self, *prefixes): - """Apply the prefixes to the query and return the newly resulting + r"""Apply the prefixes to the query and return the newly resulting ``Query``. :param \*prefixes: optional prefixes, typically strings, @@ -2586,8 +2586,8 @@ class Query(object): e.g.:: - query = sess.query(User.name).\\ - prefix_with('HIGH_PRIORITY').\\ + query = sess.query(User.name).\ + prefix_with('HIGH_PRIORITY').\ prefix_with('SQL_SMALL_RESULT', 'ALL') Would render:: @@ -2609,7 +2609,7 @@ class Query(object): @_generative() def suffix_with(self, *suffixes): - """Apply the suffix to the query and return the newly resulting + r"""Apply the suffix to the query and return the newly resulting ``Query``. :param \*suffixes: optional suffixes, typically strings, @@ -2984,7 +2984,7 @@ class Query(object): statement.with_only_columns([1])) def count(self): - """Return a count of rows this Query would return. + r"""Return a count of rows this Query would return. This generates the SQL for this Query as follows:: @@ -3011,7 +3011,7 @@ class Query(object): # return count of user "id" grouped # by "name" - session.query(func.count(User.id)).\\ + session.query(func.count(User.id)).\ group_by(User.name) from sqlalchemy import distinct @@ -3024,16 +3024,16 @@ class Query(object): return self.from_self(col).scalar() def delete(self, synchronize_session='evaluate'): - """Perform a bulk delete query. + r"""Perform a bulk delete query. Deletes rows matched by this query from the database. E.g.:: - sess.query(User).filter(User.age == 25).\\ + sess.query(User).filter(User.age == 25).\ delete(synchronize_session=False) - sess.query(User).filter(User.age == 25).\\ + sess.query(User).filter(User.age == 25).\ delete(synchronize_session='evaluate') .. warning:: The :meth:`.Query.delete` method is a "bulk" operation, @@ -3081,9 +3081,9 @@ class Query(object): subclasses ``Employee``, a DELETE against the ``Employee`` table would look like:: - session.query(Engineer).\\ - filter(Engineer.id == Employee.id).\\ - filter(Employee.name == 'dilbert').\\ + session.query(Engineer).\ + filter(Engineer.id == Employee.id).\ + filter(Employee.name == 'dilbert').\ delete() However the above SQL will not delete from the Engineer table, @@ -3149,16 +3149,16 @@ class Query(object): return delete_op.rowcount def update(self, values, synchronize_session='evaluate', update_args=None): - """Perform a bulk update query. + r"""Perform a bulk update query. Updates rows matched by this query in the database. E.g.:: - sess.query(User).filter(User.age == 25).\\ + sess.query(User).filter(User.age == 25).\ update({User.age: User.age - 10}, synchronize_session=False) - sess.query(User).filter(User.age == 25).\\ + sess.query(User).filter(User.age == 25).\ update({"age": User.age - 10}, synchronize_session='evaluate') @@ -3251,9 +3251,9 @@ class Query(object): local table using criteria against the ``Employee`` local table might look like:: - session.query(Engineer).\\ - filter(Engineer.id == Employee.id).\\ - filter(Employee.name == 'dilbert').\\ + session.query(Engineer).\ + filter(Engineer.id == Employee.id).\ + filter(Employee.name == 'dilbert').\ update({"engineer_type": "programmer"}) * The polymorphic identity WHERE criteria is **not** included @@ -3697,7 +3697,7 @@ class Bundle(InspectionAttr): is_aliased_class = False def __init__(self, name, *exprs, **kw): - """Construct a new :class:`.Bundle`. + r"""Construct a new :class:`.Bundle`. e.g.:: @@ -4081,7 +4081,7 @@ class QueryContext(object): class AliasOption(interfaces.MapperOption): def __init__(self, alias): - """Return a :class:`.MapperOption` that will indicate to the :class:`.Query` + r"""Return a :class:`.MapperOption` that will indicate to the :class:`.Query` that the main table has been aliased. This is a seldom-used option to suit the @@ -4090,12 +4090,12 @@ class AliasOption(interfaces.MapperOption): statement that aliases the parent table. E.g.:: # define an aliased UNION called 'ulist' - ulist = users.select(users.c.user_id==7).\\ - union(users.select(users.c.user_id>7)).\\ + ulist = users.select(users.c.user_id==7).\ + union(users.select(users.c.user_id>7)).\ alias('ulist') # add on an eager load of "addresses" - statement = ulist.outerjoin(addresses).\\ + statement = ulist.outerjoin(addresses).\ select().apply_labels() # create query, indicating "ulist" will be an diff --git a/lib/sqlalchemy/orm/scoping.py b/lib/sqlalchemy/orm/scoping.py index f51dbc68cd..05b881320c 100644 --- a/lib/sqlalchemy/orm/scoping.py +++ b/lib/sqlalchemy/orm/scoping.py @@ -51,7 +51,7 @@ class scoped_session(object): self.registry = ThreadLocalRegistry(session_factory) def __call__(self, **kw): - """Return the current :class:`.Session`, creating it + r"""Return the current :class:`.Session`, creating it using the :attr:`.scoped_session.session_factory` if not present. :param \**kw: Keyword arguments will be passed to the diff --git a/lib/sqlalchemy/orm/session.py b/lib/sqlalchemy/orm/session.py index 8a1dff1635..081920487d 100644 --- a/lib/sqlalchemy/orm/session.py +++ b/lib/sqlalchemy/orm/session.py @@ -592,7 +592,7 @@ class Session(_SessionClassMethods): weak_identity_map=True, binds=None, extension=None, info=None, query_cls=query.Query): - """Construct a new Session. + r"""Construct a new Session. See also the :class:`.sessionmaker` function which is used to generate a :class:`.Session`-producing callable with a given @@ -897,7 +897,7 @@ class Session(_SessionClassMethods): close_with_result=False, execution_options=None, **kw): - """Return a :class:`.Connection` object corresponding to this + r"""Return a :class:`.Connection` object corresponding to this :class:`.Session` object's transactional state. If this :class:`.Session` is configured with ``autocommit=False``, @@ -976,7 +976,7 @@ class Session(_SessionClassMethods): return conn def execute(self, clause, params=None, mapper=None, bind=None, **kw): - """Execute a SQL expression construct or string statement within + r"""Execute a SQL expression construct or string statement within the current transaction. Returns a :class:`.ResultProxy` representing @@ -2507,7 +2507,7 @@ class Session(_SessionClassMethods): def is_modified(self, instance, include_collections=True, passive=True): - """Return ``True`` if the given instance has locally + r"""Return ``True`` if the given instance has locally modified attributes. This method retrieves the history for each instrumented @@ -2565,6 +2565,7 @@ class Session(_SessionClassMethods): or many-to-one foreign keys) that would result in an UPDATE for this instance upon flush. :param passive: + .. versionchanged:: 0.8 Ignored for backwards compatibility. When using SQLAlchemy 0.7 and earlier, this flag should always @@ -2769,7 +2770,7 @@ class sessionmaker(_SessionClassMethods): autocommit=False, expire_on_commit=True, info=None, **kw): - """Construct a new :class:`.sessionmaker`. + r"""Construct a new :class:`.sessionmaker`. All arguments here except for ``class_`` correspond to arguments accepted by :class:`.Session` directly. See the diff --git a/lib/sqlalchemy/orm/strategy_options.py b/lib/sqlalchemy/orm/strategy_options.py index 2f98dc72aa..bae2b73e26 100644 --- a/lib/sqlalchemy/orm/strategy_options.py +++ b/lib/sqlalchemy/orm/strategy_options.py @@ -552,7 +552,7 @@ See :func:`.orm.%(name)s` for usage examples. @loader_option() def contains_eager(loadopt, attr, alias=None): - """Indicate that the given attribute should be eagerly loaded from + r"""Indicate that the given attribute should be eagerly loaded from columns stated manually in the query. This function is part of the :class:`.Load` interface and supports @@ -561,8 +561,8 @@ def contains_eager(loadopt, attr, alias=None): The option is used in conjunction with an explicit join that loads the desired rows, i.e.:: - sess.query(Order).\\ - join(Order.user).\\ + sess.query(Order).\ + join(Order.user).\ options(contains_eager(Order.user)) The above query would join from the ``Order`` entity to its related @@ -575,8 +575,8 @@ def contains_eager(loadopt, attr, alias=None): the eagerly-loaded rows are to come from an aliased table:: user_alias = aliased(User) - sess.query(Order).\\ - join((user_alias, Order.user)).\\ + sess.query(Order).\ + join((user_alias, Order.user)).\ options(contains_eager(Order.user, alias=user_alias)) .. seealso:: @@ -953,7 +953,7 @@ def defaultload(*keys): @loader_option() def defer(loadopt, key): - """Indicate that the given column-oriented attribute should be deferred, e.g. + r"""Indicate that the given column-oriented attribute should be deferred, e.g. not loaded until accessed. This function is part of the :class:`.Load` interface and supports @@ -1017,7 +1017,7 @@ def defer(key, *addl_attrs): @loader_option() def undefer(loadopt, key): - """Indicate that the given column-oriented attribute should be undeferred, + r"""Indicate that the given column-oriented attribute should be undeferred, e.g. specified within the SELECT statement of the entity as a whole. The column being undeferred is typically set up on the mapping as a diff --git a/lib/sqlalchemy/orm/util.py b/lib/sqlalchemy/orm/util.py index d0fc12fe15..b4d5b8a9e7 100644 --- a/lib/sqlalchemy/orm/util.py +++ b/lib/sqlalchemy/orm/util.py @@ -72,7 +72,7 @@ class CascadeOptions(frozenset): def from_string(cls, arg): values = [ c for c - in re.split('\s*,\s*', arg or "") + in re.split(r'\s*,\s*', arg or "") if c ] return cls(values) @@ -309,7 +309,7 @@ class ORMAdapter(sql_util.ColumnAdapter): class AliasedClass(object): - """Represents an "aliased" form of a mapped class for usage with Query. + r"""Represents an "aliased" form of a mapped class for usage with Query. The ORM equivalent of a :func:`sqlalchemy.sql.expression.alias` construct, this object mimics the mapped class using a @@ -323,8 +323,8 @@ class AliasedClass(object): # find all pairs of users with the same name user_alias = aliased(User) - session.query(User, user_alias).\\ - join((user_alias, User.id > user_alias.id)).\\ + session.query(User, user_alias).\ + join((user_alias, User.id > user_alias.id)).\ filter(User.name==user_alias.name) The resulting object is an instance of :class:`.AliasedClass`. @@ -888,7 +888,7 @@ class _ORMJoin(expression.Join): def join( left, right, onclause=None, isouter=False, full=False, join_to_left=None): - """Produce an inner join between left and right clauses. + r"""Produce an inner join between left and right clauses. :func:`.orm.join` is an extension to the core join interface provided by :func:`.sql.expression.join()`, where the @@ -907,15 +907,15 @@ def join( :meth:`.Query.select_from` method, as in:: from sqlalchemy.orm import join - session.query(User).\\ - select_from(join(User, Address, User.addresses)).\\ + session.query(User).\ + select_from(join(User, Address, User.addresses)).\ filter(Address.email_address=='foo@bar.com') In modern SQLAlchemy the above join can be written more succinctly as:: - session.query(User).\\ - join(User.addresses).\\ + session.query(User).\ + join(User.addresses).\ filter(Address.email_address=='foo@bar.com') See :meth:`.Query.join` for information on modern usage diff --git a/lib/sqlalchemy/pool.py b/lib/sqlalchemy/pool.py index 3aa770e510..b58fdaa672 100644 --- a/lib/sqlalchemy/pool.py +++ b/lib/sqlalchemy/pool.py @@ -31,7 +31,7 @@ proxies = {} def manage(module, **params): - """Return a proxy for a DB-API module that automatically + r"""Return a proxy for a DB-API module that automatically pools connections. Given a DB-API 2.0 module and pool management parameters, returns @@ -44,7 +44,7 @@ def manage(module, **params): :param poolclass: the class used by the pool module to provide pooling. Defaults to :class:`.QueuePool`. - :param \*\*params: will be passed through to *poolclass* + :param \**params: will be passed through to *poolclass* """ try: @@ -1061,7 +1061,7 @@ class QueuePool(Pool): def __init__(self, creator, pool_size=5, max_overflow=10, timeout=30, **kw): - """ + r""" Construct a QueuePool. :param creator: a callable function that returns a DB-API diff --git a/lib/sqlalchemy/processors.py b/lib/sqlalchemy/processors.py index 6db0fade64..17f7eccdab 100644 --- a/lib/sqlalchemy/processors.py +++ b/lib/sqlalchemy/processors.py @@ -114,9 +114,9 @@ def py_fallback(): return bool(value) DATETIME_RE = re.compile( - "(\d+)-(\d+)-(\d+) (\d+):(\d+):(\d+)(?:\.(\d+))?") - TIME_RE = re.compile("(\d+):(\d+):(\d+)(?:\.(\d+))?") - DATE_RE = re.compile("(\d+)-(\d+)-(\d+)") + r"(\d+)-(\d+)-(\d+) (\d+):(\d+):(\d+)(?:\.(\d+))?") + TIME_RE = re.compile(r"(\d+):(\d+):(\d+)(?:\.(\d+))?") + DATE_RE = re.compile(r"(\d+)-(\d+)-(\d+)") str_to_datetime = str_to_datetime_processor_factory(DATETIME_RE, datetime.datetime) diff --git a/lib/sqlalchemy/sql/compiler.py b/lib/sqlalchemy/sql/compiler.py index 99defd861a..aeb40030f1 100644 --- a/lib/sqlalchemy/sql/compiler.py +++ b/lib/sqlalchemy/sql/compiler.py @@ -281,7 +281,7 @@ class Compiled(object): class TypeCompiler(util.with_metaclass(util.EnsureKWArgType, object)): """Produces DDL specification for TypeEngine objects.""" - ensure_kwarg = 'visit_\w+' + ensure_kwarg = r'visit_\w+' def __init__(self, dialect): self.dialect = dialect diff --git a/lib/sqlalchemy/sql/ddl.py b/lib/sqlalchemy/sql/ddl.py index fd930ddc96..5463afe99b 100644 --- a/lib/sqlalchemy/sql/ddl.py +++ b/lib/sqlalchemy/sql/ddl.py @@ -143,7 +143,7 @@ class DDLElement(Executable, _DDLCompiles): @_generative def execute_if(self, dialect=None, callable_=None, state=None): - """Return a callable that will execute this + r"""Return a callable that will execute this DDLElement conditionally. Used to provide a wrapper for event listening:: diff --git a/lib/sqlalchemy/sql/dml.py b/lib/sqlalchemy/sql/dml.py index cd58cbeb05..767e913504 100644 --- a/lib/sqlalchemy/sql/dml.py +++ b/lib/sqlalchemy/sql/dml.py @@ -92,13 +92,13 @@ class UpdateBase( @_generative def returning(self, *cols): - """Add a :term:`RETURNING` or equivalent clause to this statement. + r"""Add a :term:`RETURNING` or equivalent clause to this statement. e.g.:: - stmt = table.update().\\ - where(table.c.data == 'value').\\ - values(status='X').\\ + stmt = table.update().\ + where(table.c.data == 'value').\ + values(status='X').\ returning(table.c.server_flag, table.c.updated_timestamp) @@ -206,7 +206,7 @@ class ValuesBase(UpdateBase): @_generative def values(self, *args, **kwargs): - """specify a fixed VALUES clause for an INSERT statement, or the SET + r"""specify a fixed VALUES clause for an INSERT statement, or the SET clause for an UPDATE. Note that the :class:`.Insert` and :class:`.Update` constructs support @@ -616,21 +616,21 @@ class Update(ValuesBase): return_defaults=False, preserve_parameter_order=False, **dialect_kw): - """Construct an :class:`.Update` object. + r"""Construct an :class:`.Update` object. E.g.:: from sqlalchemy import update - stmt = update(users).where(users.c.id==5).\\ + stmt = update(users).where(users.c.id==5).\ values(name='user #5') Similar functionality is available via the :meth:`~.TableClause.update` method on :class:`.Table`:: - stmt = users.update().\\ - where(users.c.id==5).\\ + stmt = users.update().\ + where(users.c.id==5).\ values(name='user #5') :param table: A :class:`.Table` object representing the database @@ -650,8 +650,8 @@ class Update(ValuesBase): subquery:: users.update().values(name='ed').where( - users.c.name==select([addresses.c.email_address]).\\ - where(addresses.c.user_id==users.c.id).\\ + users.c.name==select([addresses.c.email_address]).\ + where(addresses.c.user_id==users.c.id).\ as_scalar() ) @@ -719,8 +719,8 @@ class Update(ValuesBase): being updated:: users.update().values( - name=select([addresses.c.email_address]).\\ - where(addresses.c.user_id==users.c.id).\\ + name=select([addresses.c.email_address]).\ + where(addresses.c.user_id==users.c.id).\ as_scalar() ) diff --git a/lib/sqlalchemy/sql/elements.py b/lib/sqlalchemy/sql/elements.py index 93ae0c638c..a450efaf02 100644 --- a/lib/sqlalchemy/sql/elements.py +++ b/lib/sqlalchemy/sql/elements.py @@ -105,7 +105,7 @@ def between(expr, lower_bound, upper_bound, symmetric=False): def literal(value, type_=None): - """Return a literal clause, bound to a bind parameter. + r"""Return a literal clause, bound to a bind parameter. Literal clauses are created automatically when non- :class:`.ClauseElement` objects (such as strings, ints, dates, etc.) are @@ -305,7 +305,7 @@ class ClauseElement(Visitable): return cloned_traverse(self, {}, {'bindparam': visit_bindparam}) def compare(self, other, **kw): - """Compare this ClauseElement to the given ClauseElement. + r"""Compare this ClauseElement to the given ClauseElement. Subclasses should override the default behavior, which is a straight identity comparison. @@ -331,7 +331,7 @@ class ClauseElement(Visitable): pass def get_children(self, **kwargs): - """Return immediate child elements of this :class:`.ClauseElement`. + r"""Return immediate child elements of this :class:`.ClauseElement`. This is used for visit traversal. @@ -835,14 +835,14 @@ class ColumnElement(operators.ColumnOperators, ClauseElement): class BindParameter(ColumnElement): - """Represent a "bound expression". + r"""Represent a "bound expression". :class:`.BindParameter` is invoked explicitly using the :func:`.bindparam` function, as in:: from sqlalchemy import bindparam - stmt = select([users_table]).\\ + stmt = select([users_table]).\ where(users_table.c.name == bindparam('username')) Detailed discussion of how :class:`.BindParameter` is used is @@ -864,7 +864,7 @@ class BindParameter(ColumnElement): isoutparam=False, _compared_to_operator=None, _compared_to_type=None): - """Produce a "bound expression". + r"""Produce a "bound expression". The return value is an instance of :class:`.BindParameter`; this is a :class:`.ColumnElement` subclass which represents a so-called @@ -888,7 +888,7 @@ class BindParameter(ColumnElement): from sqlalchemy import bindparam - stmt = select([users_table]).\\ + stmt = select([users_table]).\ where(users_table.c.name == bindparam('username')) The above statement, when rendered, will produce SQL similar to:: @@ -1240,7 +1240,7 @@ class TextClause(Executable, ClauseElement): @classmethod def _create_text(self, text, bind=None, bindparams=None, typemap=None, autocommit=None): - """Construct a new :class:`.TextClause` clause, representing + r"""Construct a new :class:`.TextClause` clause, representing a textual SQL string directly. E.g.:: @@ -1268,7 +1268,7 @@ class TextClause(Executable, ClauseElement): For SQL statements where a colon is required verbatim, as within an inline string, use a backslash to escape:: - t = text("SELECT * FROM users WHERE name='\\:username'") + t = text("SELECT * FROM users WHERE name='\:username'") The :class:`.TextClause` construct includes methods which can provide information about the bound parameters as well as the column @@ -1278,8 +1278,8 @@ class TextClause(Executable, ClauseElement): parameter detail, and :meth:`.TextClause.columns` method allows specification of return columns including names and types:: - t = text("SELECT * FROM users WHERE id=:user_id").\\ - bindparams(user_id=7).\\ + t = text("SELECT * FROM users WHERE id=:user_id").\ + bindparams(user_id=7).\ columns(id=Integer, name=String) for id, name in connection.execute(t): @@ -1301,7 +1301,7 @@ class TextClause(Executable, ClauseElement): can be set explicitly so using the :paramref:`.Connection.execution_options.autocommit` option:: - t = text("EXEC my_procedural_thing()").\\ + t = text("EXEC my_procedural_thing()").\ execution_options(autocommit=True) Note that SQLAlchemy's usual "autocommit" behavior applies to @@ -1333,7 +1333,7 @@ class TextClause(Executable, ClauseElement): Is equivalent to:: - stmt = text("SELECT * FROM table WHERE id=:id").\\ + stmt = text("SELECT * FROM table WHERE id=:id").\ bindparams(bindparam('id', value=5, type_=Integer)) .. deprecated:: 0.9.0 the :meth:`.TextClause.bindparams` method @@ -1495,7 +1495,7 @@ class TextClause(Executable, ClauseElement): stmt = text("SELECT id, name FROM some_table") stmt = stmt.columns(column('id'), column('name')).alias('st') - stmt = select([mytable]).\\ + stmt = select([mytable]).\ select_from( mytable.join(stmt, mytable.c.name == stmt.c.name) ).where(stmt.c.id > 5) @@ -1921,8 +1921,8 @@ class BooleanClauseList(ClauseList, ColumnElement): times against a statement, which will have the effect of each clause being combined using :func:`.and_`:: - stmt = select([users_table]).\\ - where(users_table.c.name == 'wendy').\\ + stmt = select([users_table]).\ + where(users_table.c.name == 'wendy').\ where(users_table.c.enrolled == True) .. seealso:: @@ -2034,7 +2034,7 @@ class Case(ColumnElement): from sqlalchemy import case - stmt = select([users_table]).\\ + stmt = select([users_table]).\ where( case( [ @@ -2056,7 +2056,7 @@ class Case(ColumnElement): __visit_name__ = 'case' def __init__(self, whens, value=None, else_=None): - """Produce a ``CASE`` expression. + r"""Produce a ``CASE`` expression. The ``CASE`` construct in SQL is a conditional object that acts somewhat analogously to an "if/then" construct in other @@ -2067,7 +2067,7 @@ class Case(ColumnElement): from sqlalchemy import case - stmt = select([users_table]).\\ + stmt = select([users_table]).\ where( case( [ @@ -2096,7 +2096,7 @@ class Case(ColumnElement): compared against keyed to result expressions. The statement below is equivalent to the preceding statement:: - stmt = select([users_table]).\\ + stmt = select([users_table]).\ where( case( {"wendy": "W", "jack": "J"}, @@ -2233,7 +2233,7 @@ class Case(ColumnElement): def literal_column(text, type_=None): - """Produce a :class:`.ColumnClause` object that has the + r"""Produce a :class:`.ColumnClause` object that has the :paramref:`.column.is_literal` flag set to True. :func:`.literal_column` is similar to :func:`.column`, except that @@ -2555,7 +2555,7 @@ class UnaryExpression(ColumnElement): from sqlalchemy import desc, nullsfirst - stmt = select([users_table]).\\ + stmt = select([users_table]).\ order_by(nullsfirst(desc(users_table.c.name))) The SQL expression from the above would resemble:: @@ -2598,7 +2598,7 @@ class UnaryExpression(ColumnElement): from sqlalchemy import desc, nullslast - stmt = select([users_table]).\\ + stmt = select([users_table]).\ order_by(nullslast(desc(users_table.c.name))) The SQL expression from the above would resemble:: @@ -2610,7 +2610,7 @@ class UnaryExpression(ColumnElement): :meth:`.ColumnElement.nullslast`, rather than as its standalone function version, as in:: - stmt = select([users_table]).\\ + stmt = select([users_table]).\ order_by(users_table.c.name.desc().nullslast()) .. seealso:: @@ -3292,7 +3292,7 @@ class WithinGroup(ColumnElement): order_by = None def __init__(self, element, *order_by): - """Produce a :class:`.WithinGroup` object against a function. + r"""Produce a :class:`.WithinGroup` object against a function. Used against so-called "ordered set aggregate" and "hypothetical set aggregate" functions, including :class:`.percentile_cont`, diff --git a/lib/sqlalchemy/sql/functions.py b/lib/sqlalchemy/sql/functions.py index 4e87afb94d..08f1d32a50 100644 --- a/lib/sqlalchemy/sql/functions.py +++ b/lib/sqlalchemy/sql/functions.py @@ -191,7 +191,7 @@ class FunctionElement(Executable, ColumnElement, FromClause): return None def alias(self, name=None, flat=False): - """Produce a :class:`.Alias` construct against this + r"""Produce a :class:`.Alias` construct against this :class:`.FunctionElement`. This construct wraps the function in a named alias which @@ -202,8 +202,8 @@ class FunctionElement(Executable, ColumnElement, FromClause): from sqlalchemy.sql import column - stmt = select([column('data_view')]).\\ - select_from(SomeTable).\\ + stmt = select([column('data_view')]).\ + select_from(SomeTable).\ select_from(func.unnest(SomeTable.data).alias('data_view') ) @@ -618,7 +618,7 @@ class random(GenericFunction): class count(GenericFunction): - """The ANSI COUNT aggregate function. With no arguments, + r"""The ANSI COUNT aggregate function. With no arguments, emits COUNT \*. """ diff --git a/lib/sqlalchemy/sql/operators.py b/lib/sqlalchemy/sql/operators.py index 79cc57e420..49744568a4 100644 --- a/lib/sqlalchemy/sql/operators.py +++ b/lib/sqlalchemy/sql/operators.py @@ -159,7 +159,7 @@ class Operators(object): return against def operate(self, op, *other, **kwargs): - """Operate on an argument. + r"""Operate on an argument. This is the lowest level of operation, raises :class:`NotImplementedError` by default. diff --git a/lib/sqlalchemy/sql/schema.py b/lib/sqlalchemy/sql/schema.py index edf939a249..793750f1c0 100644 --- a/lib/sqlalchemy/sql/schema.py +++ b/lib/sqlalchemy/sql/schema.py @@ -116,7 +116,7 @@ class SchemaItem(SchemaEventTarget, visitors.Visitable): class Table(DialectKWArgs, SchemaItem, TableClause): - """Represent a table in a database. + r"""Represent a table in a database. e.g.:: @@ -893,7 +893,7 @@ class Column(SchemaItem, ColumnClause): __visit_name__ = 'column' def __init__(self, *args, **kwargs): - """ + r""" Construct a new ``Column`` object. :param name: The name of this column as represented in the database. @@ -1512,7 +1512,7 @@ class ForeignKey(DialectKWArgs, SchemaItem): initially=None, link_to_name=False, match=None, info=None, **dialect_kw): - """ + r""" Construct a column-level FOREIGN KEY. The :class:`.ForeignKey` object when constructed generates a @@ -2417,7 +2417,7 @@ class Constraint(DialectKWArgs, SchemaItem): def __init__(self, name=None, deferrable=None, initially=None, _create_rule=None, info=None, _type_bound=False, **dialect_kw): - """Create a SQL constraint. + r"""Create a SQL constraint. :param name: Optional, the in-database name of this ``Constraint``. @@ -2604,7 +2604,7 @@ class ColumnCollectionConstraint(ColumnCollectionMixin, Constraint): """A constraint that proxies a ColumnCollection.""" def __init__(self, *columns, **kw): - """ + r""" :param \*columns: A sequence of column names or Column objects. @@ -2671,7 +2671,7 @@ class CheckConstraint(ColumnCollectionConstraint): def __init__(self, sqltext, name=None, deferrable=None, initially=None, table=None, info=None, _create_rule=None, _autoattach=True, _type_bound=False): - """Construct a CHECK constraint. + r"""Construct a CHECK constraint. :param sqltext: A string containing the constraint definition, which will be used @@ -2759,7 +2759,7 @@ class ForeignKeyConstraint(ColumnCollectionConstraint): ondelete=None, deferrable=None, initially=None, use_alter=False, link_to_name=False, match=None, table=None, info=None, **dialect_kw): - """Construct a composite-capable FOREIGN KEY. + r"""Construct a composite-capable FOREIGN KEY. :param columns: A sequence of local column names. The named columns must be defined and present in the parent Table. The names should @@ -3278,7 +3278,7 @@ class Index(DialectKWArgs, ColumnCollectionMixin, SchemaItem): __visit_name__ = 'index' def __init__(self, name, *expressions, **kw): - """Construct an index object. + r"""Construct an index object. :param name: The name of the index @@ -3704,7 +3704,7 @@ class MetaData(SchemaItem): extend_existing=False, autoload_replace=True, **dialect_kwargs): - """Load all available table definitions from the database. + r"""Load all available table definitions from the database. Automatically creates ``Table`` entries in this ``MetaData`` for any table available in the database but not yet present in the diff --git a/lib/sqlalchemy/sql/selectable.py b/lib/sqlalchemy/sql/selectable.py index 1840d646d9..91a12bd33a 100644 --- a/lib/sqlalchemy/sql/selectable.py +++ b/lib/sqlalchemy/sql/selectable.py @@ -103,7 +103,7 @@ def _offset_or_limit_clause_asint(clause, attrname): def subquery(alias, *args, **kwargs): - """Return an :class:`.Alias` object derived + r"""Return an :class:`.Alias` object derived from a :class:`.Select`. name @@ -244,7 +244,7 @@ class HasPrefixes(object): @_generative def prefix_with(self, *expr, **kw): - """Add one or more expressions following the statement keyword, i.e. + r"""Add one or more expressions following the statement keyword, i.e. SELECT, INSERT, UPDATE, or DELETE. Generative. This is used to support backend-specific prefix keywords such as those @@ -281,7 +281,7 @@ class HasSuffixes(object): @_generative def suffix_with(self, *expr, **kw): - """Add one or more expressions following the statement as a whole. + r"""Add one or more expressions following the statement as a whole. This is used to support backend-specific suffix keywords on certain constructs. @@ -1055,14 +1055,14 @@ class Join(FromClause): "join explicitly." % (a.description, b.description)) def select(self, whereclause=None, **kwargs): - """Create a :class:`.Select` from this :class:`.Join`. + r"""Create a :class:`.Select` from this :class:`.Join`. The equivalent long-hand form, given a :class:`.Join` object ``j``, is:: from sqlalchemy import select - j = select([j.left, j.right], **kw).\\ - where(whereclause).\\ + j = select([j.left, j.right], **kw).\ + where(whereclause).\ select_from(j) :param whereclause: the WHERE criterion that will be sent to @@ -1082,7 +1082,7 @@ class Join(FromClause): @util.dependencies("sqlalchemy.sql.util") def alias(self, sqlutil, name=None, flat=False): - """return an alias of this :class:`.Join`. + r"""return an alias of this :class:`.Join`. The default behavior here is to first produce a SELECT construct from this :class:`.Join`, then to produce an @@ -1107,9 +1107,9 @@ class Join(FromClause): from sqlalchemy import select, alias j = alias( - select([j.left, j.right]).\\ - select_from(j).\\ - with_labels(True).\\ + select([j.left, j.right]).\ + select_from(j).\ + with_labels(True).\ correlate(False), name=name ) @@ -1438,7 +1438,7 @@ class HasCTE(object): """ def cte(self, name=None, recursive=False): - """Return a new :class:`.CTE`, or Common Table Expression instance. + r"""Return a new :class:`.CTE`, or Common Table Expression instance. Common table expressions are a SQL standard whereby SELECT statements can draw upon secondary statements specified along @@ -1493,7 +1493,7 @@ class HasCTE(object): ]).group_by(orders.c.region).cte("regional_sales") - top_regions = select([regional_sales.c.region]).\\ + top_regions = select([regional_sales.c.region]).\ where( regional_sales.c.total_sales > select([ @@ -1528,8 +1528,8 @@ class HasCTE(object): included_parts = select([ parts.c.sub_part, parts.c.part, - parts.c.quantity]).\\ - where(parts.c.part=='our part').\\ + parts.c.quantity]).\ + where(parts.c.part=='our part').\ cte(recursive=True) @@ -1548,7 +1548,7 @@ class HasCTE(object): included_parts.c.sub_part, func.sum(included_parts.c.quantity). label('total_quantity') - ]).\\ + ]).\ group_by(included_parts.c.sub_part) result = conn.execute(statement).fetchall() @@ -2279,7 +2279,7 @@ class CompoundSelect(GenerativeSelect): @classmethod def _create_union(cls, *selects, **kwargs): - """Return a ``UNION`` of multiple selectables. + r"""Return a ``UNION`` of multiple selectables. The returned object is an instance of :class:`.CompoundSelect`. @@ -2299,7 +2299,7 @@ class CompoundSelect(GenerativeSelect): @classmethod def _create_union_all(cls, *selects, **kwargs): - """Return a ``UNION ALL`` of multiple selectables. + r"""Return a ``UNION ALL`` of multiple selectables. The returned object is an instance of :class:`.CompoundSelect`. @@ -2319,7 +2319,7 @@ class CompoundSelect(GenerativeSelect): @classmethod def _create_except(cls, *selects, **kwargs): - """Return an ``EXCEPT`` of multiple selectables. + r"""Return an ``EXCEPT`` of multiple selectables. The returned object is an instance of :class:`.CompoundSelect`. @@ -2336,7 +2336,7 @@ class CompoundSelect(GenerativeSelect): @classmethod def _create_except_all(cls, *selects, **kwargs): - """Return an ``EXCEPT ALL`` of multiple selectables. + r"""Return an ``EXCEPT ALL`` of multiple selectables. The returned object is an instance of :class:`.CompoundSelect`. @@ -2353,7 +2353,7 @@ class CompoundSelect(GenerativeSelect): @classmethod def _create_intersect(cls, *selects, **kwargs): - """Return an ``INTERSECT`` of multiple selectables. + r"""Return an ``INTERSECT`` of multiple selectables. The returned object is an instance of :class:`.CompoundSelect`. @@ -2370,7 +2370,7 @@ class CompoundSelect(GenerativeSelect): @classmethod def _create_intersect_all(cls, *selects, **kwargs): - """Return an ``INTERSECT ALL`` of multiple selectables. + r"""Return an ``INTERSECT ALL`` of multiple selectables. The returned object is an instance of :class:`.CompoundSelect`. @@ -2874,7 +2874,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): @_generative def with_hint(self, selectable, text, dialect_name='*'): - """Add an indexing or other executional context hint for the given + r"""Add an indexing or other executional context hint for the given selectable to this :class:`.Select`. The text of the hint is rendered in the appropriate @@ -2886,7 +2886,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): the table or alias. E.g. when using Oracle, the following:: - select([mytable]).\\ + select([mytable]).\ with_hint(mytable, "index(%(name)s ix_mytable)") Would render SQL as:: @@ -2897,8 +2897,8 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): hint to a particular backend. Such as, to add hints for both Oracle and Sybase simultaneously:: - select([mytable]).\\ - with_hint(mytable, "index(%(name)s ix_mytable)", 'oracle').\\ + select([mytable]).\ + with_hint(mytable, "index(%(name)s ix_mytable)", 'oracle').\ with_hint(mytable, "WITH INDEX ix_mytable", 'sybase') .. seealso:: @@ -3060,7 +3060,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): @_generative def with_only_columns(self, columns): - """Return a new :func:`.select` construct with its columns + r"""Return a new :func:`.select` construct with its columns clause replaced with the given columns. .. versionchanged:: 0.7.3 @@ -3111,7 +3111,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): else (i.e. not in the WHERE clause, etc.) is to set it using :meth:`.Select.select_from`:: - >>> s1 = select([table1.c.a, table2.c.b]).\\ + >>> s1 = select([table1.c.a, table2.c.b]).\ ... select_from(table1.join(table2, ... table1.c.a==table2.c.a)) >>> s2 = s1.with_only_columns([table2.c.b]) @@ -3174,7 +3174,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): @_generative def distinct(self, *expr): - """Return a new select() construct which will apply DISTINCT to its + r"""Return a new select() construct which will apply DISTINCT to its columns clause. :param \*expr: optional column expressions. When present, @@ -3193,7 +3193,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): @_generative def select_from(self, fromclause): - """return a new :func:`.select` construct with the + r"""return a new :func:`.select` construct with the given FROM expression merged into its list of FROM objects. @@ -3201,7 +3201,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): table1 = table('t1', column('a')) table2 = table('t2', column('b')) - s = select([table1.c.a]).\\ + s = select([table1.c.a]).\ select_from( table1.join(table2, table1.c.a==table2.c.b) ) @@ -3227,7 +3227,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): @_generative def correlate(self, *fromclauses): - """return a new :class:`.Select` which will correlate the given FROM + r"""return a new :class:`.Select` which will correlate the given FROM clauses to that of an enclosing :class:`.Select`. Calling this method turns off the :class:`.Select` object's @@ -3290,7 +3290,7 @@ class Select(HasPrefixes, HasSuffixes, GenerativeSelect): @_generative def correlate_except(self, *fromclauses): - """return a new :class:`.Select` which will omit the given FROM + r"""return a new :class:`.Select` which will omit the given FROM clauses from the auto-correlation process. Calling :meth:`.Select.correlate_except` turns off the diff --git a/lib/sqlalchemy/sql/sqltypes.py b/lib/sqlalchemy/sql/sqltypes.py index 713c8a2ef1..dd5e6d01b1 100644 --- a/lib/sqlalchemy/sql/sqltypes.py +++ b/lib/sqlalchemy/sql/sqltypes.py @@ -660,7 +660,7 @@ class Float(Numeric): def __init__(self, precision=None, asdecimal=False, decimal_return_scale=None, **kwargs): - """ + r""" Construct a Float. :param precision: the numeric precision for use in DDL ``CREATE @@ -1151,7 +1151,7 @@ class Enum(String, SchemaType): __visit_name__ = 'enum' def __init__(self, *enums, **kw): - """Construct an enum. + r"""Construct an enum. Keyword arguments which don't apply to a specific backend are ignored by that backend. diff --git a/lib/sqlalchemy/sql/util.py b/lib/sqlalchemy/sql/util.py index 88ded1aa7b..281d5f6a32 100644 --- a/lib/sqlalchemy/sql/util.py +++ b/lib/sqlalchemy/sql/util.py @@ -462,7 +462,7 @@ def splice_joins(left, right, stop_on=None): def reduce_columns(columns, *clauses, **kw): - """given a list of columns, return a 'reduced' set based on natural + r"""given a list of columns, return a 'reduced' set based on natural equivalents. the set is reduced to the smallest list of columns which have no natural diff --git a/lib/sqlalchemy/testing/warnings.py b/lib/sqlalchemy/testing/warnings.py index 6d8ca6b7ac..3d1c098868 100644 --- a/lib/sqlalchemy/testing/warnings.py +++ b/lib/sqlalchemy/testing/warnings.py @@ -20,6 +20,13 @@ def setup_filters(): warnings.filterwarnings('error', category=sa_exc.SADeprecationWarning) warnings.filterwarnings('error', category=sa_exc.SAWarning) + # some selected deprecations... + warnings.filterwarnings('error', category=DeprecationWarning) + warnings.filterwarnings( + "ignore", category=DeprecationWarning, message=".*StopIteration") + warnings.filterwarnings( + "ignore", category=DeprecationWarning, message=".*inspect.getargspec") + def assert_warnings(fn, warning_msgs, regex=False): """Assert that each of the given warnings are emitted by fn. diff --git a/lib/sqlalchemy/util/compat.py b/lib/sqlalchemy/util/compat.py index beffc85419..5c615b0bc9 100644 --- a/lib/sqlalchemy/util/compat.py +++ b/lib/sqlalchemy/util/compat.py @@ -8,6 +8,7 @@ """Handle Python version/platform incompatibilities.""" import sys +from contextlib import contextmanager try: import threading @@ -231,35 +232,38 @@ def with_metaclass(meta, *bases): return metaclass('temporary_class', None, {}) -from contextlib import contextmanager -try: - from contextlib import nested -except ImportError: - # removed in py3k, credit to mitsuhiko for - # workaround - - @contextmanager - def nested(*managers): - exits = [] - vars = [] - exc = (None, None, None) - try: - for mgr in managers: - exit = mgr.__exit__ - enter = mgr.__enter__ - vars.append(enter()) - exits.append(exit) - yield vars - except: - exc = sys.exc_info() - finally: - while exits: - exit = exits.pop() - try: - if exit(*exc): - exc = (None, None, None) - except: - exc = sys.exc_info() - if exc != (None, None, None): - reraise(exc[0], exc[1], exc[2]) + +@contextmanager +def nested(*managers): + """Implement contextlib.nested, mostly for unit tests. + + As tests still need to run on py2.6 we can't use multiple-with yet. + + Function is removed in py3k but also emits deprecation warning in 2.7 + so just roll it here for everyone. + + """ + + exits = [] + vars = [] + exc = (None, None, None) + try: + for mgr in managers: + exit = mgr.__exit__ + enter = mgr.__enter__ + vars.append(enter()) + exits.append(exit) + yield vars + except: + exc = sys.exc_info() + finally: + while exits: + exit = exits.pop() + try: + if exit(*exc): + exc = (None, None, None) + except: + exc = sys.exc_info() + if exc != (None, None, None): + reraise(exc[0], exc[1], exc[2]) diff --git a/lib/sqlalchemy/util/langhelpers.py b/lib/sqlalchemy/util/langhelpers.py index 00572fca83..973de426c3 100644 --- a/lib/sqlalchemy/util/langhelpers.py +++ b/lib/sqlalchemy/util/langhelpers.py @@ -221,7 +221,7 @@ class PluginLoader(object): def get_cls_kwargs(cls, _set=None): - """Return the full set of inherited kwargs for the given `cls`. + r"""Return the full set of inherited kwargs for the given `cls`. Probes a class's __init__ method, collecting all named arguments. If the __init__ defines a \**kwargs catch-all, then the constructor is presumed @@ -1006,7 +1006,7 @@ def asint(value): def coerce_kw_type(kw, key, type_, flexi_bool=True): - """If 'key' is present in dict 'kw', coerce its value to type 'type\_' if + r"""If 'key' is present in dict 'kw', coerce its value to type 'type\_' if necessary. If 'flexi_bool' is True, the string '0' is considered false when coercing to boolean. """ diff --git a/test/dialect/postgresql/test_types.py b/test/dialect/postgresql/test_types.py index b558d09fb1..c4106c68ea 100644 --- a/test/dialect/postgresql/test_types.py +++ b/test/dialect/postgresql/test_types.py @@ -1709,7 +1709,7 @@ class HStoreTest(AssertsCompiledSQL, fixtures.TestBase): assert_raises_message( ValueError, r'''After u?'\[\.\.\.\], "key1"=>"value1", ', could not parse ''' - '''residual at position 36: u?'crapcrapcrap, "key3"\[\.\.\.\]''', + r'''residual at position 36: u?'crapcrapcrap, "key3"\[\.\.\.\]''', proc, '"key2"=>"value2", "key1"=>"value1", ' 'crapcrapcrap, "key3"=>"value3"' diff --git a/test/dialect/test_sqlite.py b/test/dialect/test_sqlite.py index 1ac67bd319..6735ae30d6 100644 --- a/test/dialect/test_sqlite.py +++ b/test/dialect/test_sqlite.py @@ -248,7 +248,7 @@ class DateTimeTest(fixtures.TestBase, AssertsCompiledSQL): "%(year)04d%(month)02d%(day)02d" "%(hour)02d%(minute)02d%(second)02d%(microsecond)06d" ), - regexp="(\d{4})(\d{2})(\d{2})(\d{2})(\d{2})(\d{2})(\d{6})", + regexp=r"(\d{4})(\d{2})(\d{2})(\d{2})(\d{2})(\d{2})(\d{6})", ) bp = sldt.bind_processor(None) eq_(bp(dt), '20080627120000000125') @@ -272,7 +272,7 @@ class DateTest(fixtures.TestBase, AssertsCompiledSQL): eq_(str(dt), '2008-06-27') sldt = sqlite.DATE( storage_format="%(month)02d/%(day)02d/%(year)04d", - regexp="(?P\d+)/(?P\d+)/(?P\d+)", + regexp=r"(?P\d+)/(?P\d+)/(?P\d+)", ) bp = sldt.bind_processor(None) eq_(bp(dt), '06/27/2008') @@ -306,7 +306,7 @@ class TimeTest(fixtures.TestBase, AssertsCompiledSQL): eq_(str(dt), '2008-06-27') sldt = sqlite.DATE( storage_format="%(year)04d%(month)02d%(day)02d", - regexp="(\d{4})(\d{2})(\d{2})", + regexp=r"(\d{4})(\d{2})(\d{2})", ) bp = sldt.bind_processor(None) eq_(bp(dt), '20080627') diff --git a/test/engine/test_execute.py b/test/engine/test_execute.py index 49b29f7f21..c9f78aa5e6 100644 --- a/test/engine/test_execute.py +++ b/test/engine/test_execute.py @@ -292,7 +292,7 @@ class ExecuteTest(fixtures.TestBase): assert_raises_message( tsa.exc.StatementError, r"\(test.engine.test_execute.SomeException\) " - "nope \[SQL\: u?'SELECT 1 ", + r"nope \[SQL\: u?'SELECT 1 ", conn.execute, select([1]). where( @@ -1636,7 +1636,7 @@ class HandleErrorTest(fixtures.TestBase): assert_raises_message( tsa.exc.StatementError, r"\(test.engine.test_execute.SomeException\) " - "nope \[SQL\: u?'SELECT 1 ", + r"nope \[SQL\: u?'SELECT 1 ", conn.execute, select([1]).where( column('foo') == literal('bar', MyType())) @@ -1828,7 +1828,7 @@ class HandleErrorTest(fixtures.TestBase): assert_raises_message( tsa.exc.StatementError, r"\(test.engine.test_execute.SomeException\) " - "nope \[SQL\: u?'SELECT 1 ", + r"nope \[SQL\: u?'SELECT 1 ", conn.execute, select([1]).where( column('foo') == literal('bar', MyType())) diff --git a/test/engine/test_logging.py b/test/engine/test_logging.py index 51ebc52506..e9bc23b415 100644 --- a/test/engine/test_logging.py +++ b/test/engine/test_logging.py @@ -185,11 +185,11 @@ class LogParamsTest(fixtures.TestBase): assert_raises_message( tsa.exc.DBAPIError, r".*'INSERT INTO nonexistent \(data\) values \(:data\)'\] " - "\[parameters: " - "\[{'data': '0'}, {'data': '1'}, {'data': '2'}, " - "{'data': '3'}, {'data': '4'}, {'data': '5'}, " - "{'data': '6'}, {'data': '7'} ... displaying 10 of " - "100 total bound parameter sets ... {'data': '98'}, {'data': '99'}\]", + r"\[parameters: " + r"\[{'data': '0'}, {'data': '1'}, {'data': '2'}, " + r"{'data': '3'}, {'data': '4'}, {'data': '5'}, " + r"{'data': '6'}, {'data': '7'} ... displaying 10 of " + r"100 total bound parameter sets ... {'data': '98'}, {'data': '99'}\]", lambda: self.eng.execute( "INSERT INTO nonexistent (data) values (:data)", [{"data": str(i)} for i in range(100)] @@ -200,11 +200,11 @@ class LogParamsTest(fixtures.TestBase): assert_raises_message( tsa.exc.DBAPIError, r".*INSERT INTO nonexistent \(data\) values " - "\(\?\)'\] \[parameters: \[\('0',\), \('1',\), \('2',\), \('3',\), " - "\('4',\), \('5',\), \('6',\), \('7',\) " - "... displaying " - "10 of 100 total bound parameter sets ... " - "\('98',\), \('99',\)\]", + r"\(\?\)'\] \[parameters: \[\('0',\), \('1',\), \('2',\), \('3',\), " + r"\('4',\), \('5',\), \('6',\), \('7',\) " + r"... displaying " + r"10 of 100 total bound parameter sets ... " + r"\('98',\), \('99',\)\]", lambda: self.eng.execute( "INSERT INTO nonexistent (data) values (?)", [(str(i), ) for i in range(100)] diff --git a/test/engine/test_transaction.py b/test/engine/test_transaction.py index 82a0c63172..7e95fb4fa9 100644 --- a/test/engine/test_transaction.py +++ b/test/engine/test_transaction.py @@ -227,7 +227,7 @@ class TransactionTest(fixtures.TestBase): with expect_warnings( "An exception has occurred during handling of a previous " "exception. The previous exception " - "is:.*..SQL\:.*RELEASE SAVEPOINT" + r"is:.*..SQL\:.*RELEASE SAVEPOINT" ): def go(): with connection.begin_nested() as savepoint: @@ -235,7 +235,7 @@ class TransactionTest(fixtures.TestBase): connection, savepoint._savepoint) assert_raises_message( exc.DBAPIError, - ".*SQL\:.*ROLLBACK TO SAVEPOINT", + r".*SQL\:.*ROLLBACK TO SAVEPOINT", go ) diff --git a/test/ext/declarative/test_clsregistry.py b/test/ext/declarative/test_clsregistry.py index 535fd00b35..000479f09d 100644 --- a/test/ext/declarative/test_clsregistry.py +++ b/test/ext/declarative/test_clsregistry.py @@ -155,8 +155,8 @@ class ClsRegistryTest(fixtures.TestBase): resolver = resolver("Foo") assert_raises_message( exc.InvalidRequestError, - "When initializing mapper some_parent, expression " - "'Foo' failed to locate a name \('Foo'\).", + r"When initializing mapper some_parent, expression " + r"'Foo' failed to locate a name \('Foo'\).", resolver ) diff --git a/test/ext/test_associationproxy.py b/test/ext/test_associationproxy.py index 98e40b11ee..5e4ebfe63e 100644 --- a/test/ext/test_associationproxy.py +++ b/test/ext/test_associationproxy.py @@ -1464,7 +1464,7 @@ class ComparatorTest(fixtures.MappedTest, AssertsCompiledSQL): assert_raises_message( exc.ArgumentError, - "Non-empty has\(\) not allowed", + r"Non-empty has\(\) not allowed", User.singular_value.has, User.singular_value == "singular4" ) @@ -1476,7 +1476,7 @@ class ComparatorTest(fixtures.MappedTest, AssertsCompiledSQL): assert_raises_message( exc.ArgumentError, - "Non-empty has\(\) not allowed", + r"Non-empty has\(\) not allowed", User.singular_value.has, singular_value="singular4" ) diff --git a/test/orm/test_composites.py b/test/orm/test_composites.py index 48027ec2d0..799c7f9bdc 100644 --- a/test/orm/test_composites.py +++ b/test/orm/test_composites.py @@ -764,8 +764,8 @@ class ConfigurationTest(fixtures.MappedTest): # renders here, so the "%" operator in the string needs to # apply the tuple also r"Composite expects Column objects or mapped " - "attributes/attribute names as " - "arguments, got: \(Column", + r"attributes/attribute names as " + r"arguments, got: \(Column", configure_mappers ) diff --git a/test/orm/test_events.py b/test/orm/test_events.py index 594aabdab2..28f0f6998c 100644 --- a/test/orm/test_events.py +++ b/test/orm/test_events.py @@ -388,17 +388,17 @@ class MapperEventsTest(_RemoveListeners, _fixtures.FixtureTest): mapper(User, users) assert_raises_message( sa.exc.SAWarning, - "before_configured' and 'after_configured' ORM events only " - "invoke with the mapper\(\) function or Mapper class as " - "the target.", + r"before_configured' and 'after_configured' ORM events only " + r"invoke with the mapper\(\) function or Mapper class as " + r"the target.", event.listen, User, 'before_configured', m1 ) assert_raises_message( sa.exc.SAWarning, - "before_configured' and 'after_configured' ORM events only " - "invoke with the mapper\(\) function or Mapper class as " - "the target.", + r"before_configured' and 'after_configured' ORM events only " + r"invoke with the mapper\(\) function or Mapper class as " + r"the target.", event.listen, User, 'after_configured', m1 ) diff --git a/test/orm/test_instrumentation.py b/test/orm/test_instrumentation.py index c3d24ebe7d..88308f19c8 100644 --- a/test/orm/test_instrumentation.py +++ b/test/orm/test_instrumentation.py @@ -467,10 +467,10 @@ class MapperInitTest(fixtures.ORMTest): assert_raises_message( sa.exc.SAWarning, r"__del__\(\) method on class " - " will cause " - "unreachable cycles and memory leaks, as SQLAlchemy " - "instrumentation often creates reference cycles. " - "Please remove this method.", + r" will cause " + r"unreachable cycles and memory leaks, as SQLAlchemy " + r"instrumentation often creates reference cycles. " + r"Please remove this method.", mapper, A, self.fixture() ) diff --git a/test/orm/test_joins.py b/test/orm/test_joins.py index 01f8627bc9..0fe829ea41 100644 --- a/test/orm/test_joins.py +++ b/test/orm/test_joins.py @@ -442,8 +442,8 @@ class JoinTest(QueryTest, AssertsCompiledSQL): assert_raises_message( sa_exc.InvalidRequestError, - "Don't know how to join from x; please use select_from\(\) to " - "establish the left entity/selectable of this join", + r"Don't know how to join from x; please use select_from\(\) to " + r"establish the left entity/selectable of this join", sess.query(literal_column('x'), User).join, Address ) @@ -455,8 +455,8 @@ class JoinTest(QueryTest, AssertsCompiledSQL): assert_raises_message( sa_exc.InvalidRequestError, - "No entities to join from; please use select_from\(\) to " - "establish the left entity/selectable of this join", + r"No entities to join from; please use select_from\(\) to " + r"establish the left entity/selectable of this join", sess.query().join, Address ) diff --git a/test/orm/test_query.py b/test/orm/test_query.py index 57408e10ef..7125fa9c1e 100644 --- a/test/orm/test_query.py +++ b/test/orm/test_query.py @@ -4087,14 +4087,14 @@ class ImmediateTest(_fixtures.FixtureTest): assert_raises_message( sa.orm.exc.NoResultFound, - "No row was found for one\(\)", + r"No row was found for one\(\)", sess.query(User).filter(User.id == 99).one) eq_(sess.query(User).filter(User.id == 7).one().id, 7) assert_raises_message( sa.orm.exc.MultipleResultsFound, - "Multiple rows were found for one\(\)", + r"Multiple rows were found for one\(\)", sess.query(User).one) assert_raises( @@ -4151,7 +4151,7 @@ class ImmediateTest(_fixtures.FixtureTest): assert_raises_message( sa.orm.exc.MultipleResultsFound, - "Multiple rows were found for one_or_none\(\)", + r"Multiple rows were found for one_or_none\(\)", sess.query(User).one_or_none) eq_(sess.query(User.id, User.name).filter(User.id == 99).one_or_none(), None) diff --git a/test/orm/test_relationships.py b/test/orm/test_relationships.py index 93db643a6a..552550c5ea 100644 --- a/test/orm/test_relationships.py +++ b/test/orm/test_relationships.py @@ -725,7 +725,7 @@ class CompositeSelfRefFKTest(fixtures.MappedTest, AssertsCompiledSQL): assert_raises_message( exc.SAWarning, r"relationship .* will copy column .* to column " - "employee_t.company_id, which conflicts with relationship\(s\)", + r"employee_t.company_id, which conflicts with relationship\(s\)", configure_mappers ) @@ -1615,9 +1615,9 @@ class ManualBackrefTest(_fixtures.FixtureTest): assert_raises_message(sa.exc.ArgumentError, r"reverse_property 'dingaling' on relationship " - "User.addresses references " - "relationship Address.dingaling, which does not " - "reference mapper Mapper\|User\|users", + r"User.addresses references " + r"relationship Address.dingaling, which does not " + r"reference mapper Mapper\|User\|users", configure_mappers) diff --git a/test/orm/test_session.py b/test/orm/test_session.py index 5cc8aec208..4409959dc7 100644 --- a/test/orm/test_session.py +++ b/test/orm/test_session.py @@ -1746,19 +1746,19 @@ class FlushWarningsTest(fixtures.MappedTest): Address = self.classes.Address def evt(mapper, conn, instance): object_session(instance).add(Address(email='x1')) - self._test(evt, "Session.add\(\)") + self._test(evt, r"Session.add\(\)") def test_plain_merge(self): Address = self.classes.Address def evt(mapper, conn, instance): object_session(instance).merge(Address(email='x1')) - self._test(evt, "Session.merge\(\)") + self._test(evt, r"Session.merge\(\)") def test_plain_delete(self): Address = self.classes.Address def evt(mapper, conn, instance): object_session(instance).delete(Address(email='x1')) - self._test(evt, "Session.delete\(\)") + self._test(evt, r"Session.delete\(\)") def _test(self, fn, method): User = self.classes.User diff --git a/test/orm/test_transaction.py b/test/orm/test_transaction.py index 85125e2b7d..477861f7a2 100644 --- a/test/orm/test_transaction.py +++ b/test/orm/test_transaction.py @@ -490,9 +490,9 @@ class SessionTransactionTest(FixtureTest): trans2.rollback() assert_raises_message( sa_exc.InvalidRequestError, - "This Session's transaction has been rolled back by a nested " - "rollback\(\) call. To begin a new transaction, issue " - "Session.rollback\(\) first.", + r"This Session's transaction has been rolled back by a nested " + r"rollback\(\) call. To begin a new transaction, issue " + r"Session.rollback\(\) first.", trans.commit ) @@ -506,10 +506,10 @@ class SessionTransactionTest(FixtureTest): trans2.rollback(_capture_exception=True) assert_raises_message( sa_exc.InvalidRequestError, - "This Session's transaction has been rolled back due to a " - "previous exception during flush. To begin a new transaction " - "with this Session, first issue Session.rollback\(\). " - "Original exception was: test", + r"This Session's transaction has been rolled back due to a " + r"previous exception during flush. To begin a new transaction " + r"with this Session, first issue Session.rollback\(\). " + r"Original exception was: test", trans.commit ) diff --git a/test/orm/test_unitofworkv2.py b/test/orm/test_unitofworkv2.py index b084071dbc..352ba2de79 100644 --- a/test/orm/test_unitofworkv2.py +++ b/test/orm/test_unitofworkv2.py @@ -1476,8 +1476,8 @@ class BasicStaleChecksTest(fixtures.MappedTest): p1.data = 3 assert_raises_message( orm_exc.StaleDataError, - "UPDATE statement on table 'parent' expected to " - "update 1 row\(s\); 0 were matched.", + r"UPDATE statement on table 'parent' expected to " + r"update 1 row\(s\); 0 were matched.", sess.flush ) @@ -1506,8 +1506,8 @@ class BasicStaleChecksTest(fixtures.MappedTest): p1.data = 3 assert_raises_message( orm_exc.StaleDataError, - "UPDATE statement on table 'parent' expected to " - "update 1 row\(s\); 0 were matched.", + r"UPDATE statement on table 'parent' expected to " + r"update 1 row\(s\); 0 were matched.", sess.flush ) @@ -1567,8 +1567,8 @@ class BasicStaleChecksTest(fixtures.MappedTest): p1.data = literal(1) assert_raises_message( orm_exc.StaleDataError, - "UPDATE statement on table 'parent' expected to " - "update 1 row\(s\); 0 were matched.", + r"UPDATE statement on table 'parent' expected to " + r"update 1 row\(s\); 0 were matched.", sess.flush ) @@ -1587,8 +1587,8 @@ class BasicStaleChecksTest(fixtures.MappedTest): assert_raises_message( exc.SAWarning, - "DELETE statement on table 'parent' expected to " - "delete 1 row\(s\); 0 were matched.", + r"DELETE statement on table 'parent' expected to " + r"delete 1 row\(s\); 0 were matched.", sess.commit ) @@ -1607,8 +1607,8 @@ class BasicStaleChecksTest(fixtures.MappedTest): assert_raises_message( exc.SAWarning, - "DELETE statement on table 'parent' expected to " - "delete 2 row\(s\); 0 were matched.", + r"DELETE statement on table 'parent' expected to " + r"delete 2 row\(s\); 0 were matched.", sess.flush ) diff --git a/test/sql/test_compiler.py b/test/sql/test_compiler.py index 38ca09c0a3..3e7c3d9a3c 100644 --- a/test/sql/test_compiler.py +++ b/test/sql/test_compiler.py @@ -742,8 +742,8 @@ class SelectTest(fixtures.TestBase, AssertsCompiledSQL): assert_raises_message( exc.InvalidRequestError, r"Select objects don't have a type\. Call as_scalar\(\) " - "on this Select object to return a 'scalar' " - "version of this Select\.", + r"on this Select object to return a 'scalar' " + r"version of this Select\.", func.coalesce, select([table1.c.myid]) ) diff --git a/test/sql/test_metadata.py b/test/sql/test_metadata.py index f790c2aa0c..ef61a7e878 100644 --- a/test/sql/test_metadata.py +++ b/test/sql/test_metadata.py @@ -3050,7 +3050,7 @@ class ConstraintTest(fixtures.TestBase): return t2 assert_raises_message( exc.ArgumentError, - "Element Table\('t2', .* is not a string name or column element", + r"Element Table\('t2', .* is not a string name or column element", Index, "foo", SomeClass() ) @@ -4213,8 +4213,8 @@ class NamingConventionTest(fixtures.TestBase, AssertsCompiledSQL): assert_raises_message( exc.InvalidRequestError, - "Naming convention including \%\(constraint_name\)s token " - "requires that constraint is explicitly named.", + r"Naming convention including \%\(constraint_name\)s token " + r"requires that constraint is explicitly named.", schema.CreateTable(u1).compile, dialect=default.DefaultDialect() ) diff --git a/test/sql/test_query.py b/test/sql/test_query.py index aca933fc98..5a201d9049 100644 --- a/test/sql/test_query.py +++ b/test/sql/test_query.py @@ -250,7 +250,7 @@ class QueryTest(fixtures.TestBase): a_eq(prep(r'select \foo'), r'select \foo') a_eq(prep(r"time='12\:30:00'"), r"time='12\:30:00'") - a_eq(prep(":this \:that"), "? :that") + a_eq(prep(r":this \:that"), "? :that") a_eq(prep(r"(\:that$other)"), "(:that$other)") a_eq(prep(r".\:that$ :other."), ".:that$ ?.") diff --git a/test/sql/test_resultset.py b/test/sql/test_resultset.py index 64d496a8f1..561176a244 100644 --- a/test/sql/test_resultset.py +++ b/test/sql/test_resultset.py @@ -1409,7 +1409,7 @@ class PositionalTextTest(fixtures.TablesTest): with assertions.expect_warnings( r"Number of columns in textual SQL \(4\) is " - "smaller than number of columns requested \(2\)"): + r"smaller than number of columns requested \(2\)"): result = testing.db.execute(stmt) row = result.first() diff --git a/test/sql/test_returning.py b/test/sql/test_returning.py index 87994ae9f9..96f9eeee40 100644 --- a/test/sql/test_returning.py +++ b/test/sql/test_returning.py @@ -129,7 +129,7 @@ class ReturningTest(fixtures.TestBase, AssertsExecutionResults): ) assert_raises_message( sa_exc.InvalidRequestError, - "Can't call inserted_primary_key when returning\(\) is used.", + r"Can't call inserted_primary_key when returning\(\) is used.", getattr, result, "inserted_primary_key" ) diff --git a/test/sql/test_text.py b/test/sql/test_text.py index 20cb2a6fbd..4a273e1ee2 100644 --- a/test/sql/test_text.py +++ b/test/sql/test_text.py @@ -253,7 +253,8 @@ class BindParamTest(fixtures.TestBase, AssertsCompiledSQL): def test_missing_bind_kw(self): assert_raises_message( exc.ArgumentError, - "This text\(\) construct doesn't define a bound parameter named 'bar'", + r"This text\(\) construct doesn't define " + r"a bound parameter named 'bar'", text(":foo").bindparams, foo=5, bar=7) @@ -261,7 +262,8 @@ class BindParamTest(fixtures.TestBase, AssertsCompiledSQL): def test_missing_bind_posn(self): assert_raises_message( exc.ArgumentError, - "This text\(\) construct doesn't define a bound parameter named 'bar'", + r"This text\(\) construct doesn't define " + r"a bound parameter named 'bar'", text(":foo").bindparams, bindparam( 'foo', @@ -273,8 +275,8 @@ class BindParamTest(fixtures.TestBase, AssertsCompiledSQL): def test_escaping_colons(self): # test escaping out text() params with a backslash self.assert_compile( - text("select * from foo where clock='05:06:07' " - "and mork='\:mindy'"), + text(r"select * from foo where clock='05:06:07' " + r"and mork='\:mindy'"), "select * from foo where clock='05:06:07' and mork=':mindy'", checkparams={}, params={}, @@ -284,8 +286,8 @@ class BindParamTest(fixtures.TestBase, AssertsCompiledSQL): def test_escaping_double_colons(self): self.assert_compile( text( - "SELECT * FROM pg_attribute WHERE " - "attrelid = :tab\:\:regclass"), + r"SELECT * FROM pg_attribute WHERE " + r"attrelid = :tab\:\:regclass"), "SELECT * FROM pg_attribute WHERE " "attrelid = %(tab)s::regclass", params={'tab': None}, diff --git a/test/sql/test_update.py b/test/sql/test_update.py index 6bacdcf725..033f2f6808 100644 --- a/test/sql/test_update.py +++ b/test/sql/test_update.py @@ -306,8 +306,8 @@ class UpdateTest(_UpdateFromTestBase, fixtures.TablesTest, AssertsCompiledSQL): table1 = self.tables.mytable testing.assert_raises_message( ValueError, - "When preserve_parameter_order is True, values\(\) " - "only accepts a list of 2-tuples", + r"When preserve_parameter_order is True, values\(\) " + r"only accepts a list of 2-tuples", table1.update(preserve_parameter_order=True).values, {"description": "foo", "name": "bar"} ) diff --git a/tox.ini b/tox.ini index 3c577eb0de..e0f75ed21a 100644 --- a/tox.ini +++ b/tox.ini @@ -1,6 +1,6 @@ [tox] -envlist = py{26,27,34,35}-{cext,nocext} +envlist = py{26,27,34,35,36}-{cext,nocext} [testenv] # note that we have a .coveragerc file that points coverage specifically @@ -76,4 +76,3 @@ commands = python -m flake8 {posargs} show-source = True ignore = E711,E712,E721,N806,D exclude=.venv,.git,.tox,dist,doc,*egg,build - -- 2.47.2