[Python-modules-commits] [psycopg2] 01/06: Imported Upstream version 2.7.3
Scott Kitterman
kitterman at moszumanska.debian.org
Wed Aug 9 05:01:13 UTC 2017
This is an automated email from the git hooks/post-receive script.
kitterman pushed a commit to branch debian/master
in repository psycopg2.
commit 948e3debc862e75d96587ad7b66f4033b0e932ff
Author: Scott Kitterman <scott at kitterman.com>
Date: Wed Aug 9 00:27:16 2017 -0400
Imported Upstream version 2.7.3
---
NEWS | 43 +++++-
PKG-INFO | 30 ++--
README.rst | 26 ++--
doc/src/connection.rst | 3 +
doc/src/cursor.rst | 5 +-
doc/src/errorcodes.rst | 2 +-
doc/src/extensions.rst | 8 +-
doc/src/extras.rst | 19 ++-
doc/src/install.rst | 22 ++-
doc/src/sql.rst | 5 +
doc/src/usage.rst | 2 +-
lib/__init__.py | 2 +-
lib/_json.py | 9 +-
lib/errorcodes.py | 8 ++
lib/extensions.py | 8 +-
lib/extras.py | 6 +
lib/pool.py | 2 +-
lib/psycopg1.py | 4 +-
lib/sql.py | 25 ++--
psycopg/connection_type.c | 63 ++++++++-
psycopg/cursor.h | 1 +
psycopg/cursor_int.c | 80 +++++++++++
psycopg/cursor_type.c | 85 +-----------
psycopg/lobject_type.c | 5 +-
psycopg/pqpath.c | 28 +++-
psycopg/psycopg.h | 2 +
psycopg/replication_connection_type.c | 56 +++-----
psycopg/replication_cursor_type.c | 19 ++-
psycopg/typecast.c | 6 +
psycopg/typecast_array.c | 1 +
psycopg/typecast_builtins.c | 8 +-
psycopg/typecast_datetime.c | 248 +++++++++++++++++++++++++---------
psycopg/typecast_mxdatetime.c | 1 +
psycopg/utils.c | 24 ++++
psycopg2.egg-info/PKG-INFO | 30 ++--
scripts/make_errorcodes.py | 15 +-
scripts/travis_prepare.sh | 8 +-
scripts/travis_test.sh | 6 +-
setup.py | 7 +-
tests/test_connection.py | 111 +++++++++++++--
tests/test_cursor.py | 75 ++++++++--
tests/test_dates.py | 45 ++++++
tests/test_green.py | 85 ++++++++++++
tests/test_lobject.py | 14 ++
tests/test_replication.py | 37 +++++
tests/test_sql.py | 26 +++-
tests/test_types_extras.py | 28 +++-
47 files changed, 1017 insertions(+), 326 deletions(-)
diff --git a/NEWS b/NEWS
index 88689f6..6c67cb5 100644
--- a/NEWS
+++ b/NEWS
@@ -1,6 +1,44 @@
Current release
---------------
+What's new in psycopg 2.7.3
+^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Restored default :sql:`timestamptz[]` typecasting to Python `!datetime`.
+ Regression introduced in Psycopg 2.7.2 (:ticket:`#578`).
+
+
+What's new in psycopg 2.7.2
+^^^^^^^^^^^^^^^^^^^^^^^^^^^
+
+- Fixed inconsistent state in externally closed connections
+ (:tickets:`#263, #311, #443`). Was fixed in 2.6.2 but not included in
+ 2.7 by mistake.
+- Fixed Python exceptions propagation in green callback (:ticket:`#410`).
+- Don't display the password in `connection.dsn` when the connection
+ string is specified as an URI (:ticket:`#528`).
+- Return objects with timezone parsing "infinity" :sql:`timestamptz`
+ (:ticket:`#536`).
+- Dropped dependency on VC9 runtime on Windows binary packages
+ (:ticket:`#541`).
+- Fixed segfault in `~connection.lobject()` when *mode*\=\ `!None`
+ (:ticket:`#544`).
+- Fixed `~connection.lobject()` keyword argument *lobject_factory*
+ (:ticket:`#545`).
+- Fixed `~psycopg2.extras.ReplicationCursor.consume_stream()`
+ *keepalive_interval* argument (:ticket:`#547`).
+- Maybe fixed random import error on Python 3.6 in multiprocess
+ environment (:ticket:`#550`).
+- Fixed random `!SystemError` upon receiving abort signal (:ticket:`#551`).
+- Accept `~psycopg2.sql.Composable` objects in
+ `~psycopg2.extras.ReplicationCursor.start_replication_expert()`
+ (:ticket:`554`).
+- Parse intervals returned as microseconds from Redshift (:ticket:`#558`).
+- Added `~psycopg2.extras.Json` `!prepare()` method to consider connection
+ params when adapting (:ticket:`#562`).
+- `~psycopg2.errorcodes` map updated to PostgreSQL 10 beta 1.
+
+
What's new in psycopg 2.7.1
^^^^^^^^^^^^^^^^^^^^^^^^^^^
@@ -82,6 +120,8 @@ What's new in psycopg 2.6.3
What's new in psycopg 2.6.2
^^^^^^^^^^^^^^^^^^^^^^^^^^^
+- Fixed inconsistent state in externally closed connections
+ (:tickets:`#263, #311, #443`).
- Report the server response status on errors (such as :ticket:`#281`).
- Raise `!NotSupportedError` on unhandled server response status
(:ticket:`#352`).
@@ -91,7 +131,8 @@ What's new in psycopg 2.6.2
(:ticket:`#333`).
- Fixed `!PersistentConnectionPool` on Python 3 (:ticket:`#348`).
- Fixed segfault on `repr()` of an unitialized connection (:ticket:`#361`).
-- Allow adapting bytes using QuotedString on Python 3 too (:ticket:`#365`).
+- Allow adapting bytes using `~psycopg2.extensions.QuotedString` on Python 3
+ (:ticket:`#365`).
- Added support for setuptools/wheel (:ticket:`#370`).
- Fix build on Windows with Python 3.5, VS 2015 (:ticket:`#380`).
- Fixed `!errorcodes.lookup` initialization thread-safety (:ticket:`#382`).
diff --git a/PKG-INFO b/PKG-INFO
index 9a7352a..8ec7484 100644
--- a/PKG-INFO
+++ b/PKG-INFO
@@ -1,12 +1,12 @@
Metadata-Version: 1.1
Name: psycopg2
-Version: 2.7.1
+Version: 2.7.3
Summary: psycopg2 - Python-PostgreSQL Database Adapter
Home-page: http://initd.org/psycopg/
Author: Federico Di Gregorio
Author-email: fog at initd.org
License: LGPL with exceptions or ZPL
-Download-URL: http://initd.org/psycopg/tarballs/PSYCOPG-2-7/psycopg2-2.7.1.tar.gz
+Download-URL: http://initd.org/psycopg/tarballs/PSYCOPG-2-7/psycopg2-2.7.3.tar.gz
Description: Psycopg is the most popular PostgreSQL database adapter for the Python
programming language. Its main features are the complete implementation of
the Python DB API 2.0 specification and the thread safety (several threads can
@@ -27,7 +27,7 @@ Description: Psycopg is the most popular PostgreSQL database adapter for the Pyt
Documentation
-------------
- Documentation is included in the 'doc' directory and is `available online`__.
+ Documentation is included in the ``doc`` directory and is `available online`__.
.. __: http://initd.org/psycopg/docs/
@@ -36,22 +36,20 @@ Description: Psycopg is the most popular PostgreSQL database adapter for the Pyt
------------
If your ``pip`` version supports wheel_ packages it should be possible to
- install a binary version of Psycopg including all the dependencies. Just run::
+ install a binary version of Psycopg including all the dependencies from PyPI_.
+ Just run::
- pip install psycopg2
+ $ pip install -U pip # make sure your pip is up-to-date
+ $ pip install psycopg2
- If you want to build Psycopg from source you will need some prerequisite (a C
- compiler, Python and libpq development packages). If you have what you need
- the standard::
-
- python setup.py build
- sudo python setup.py install
-
- should work no problem. In case you have any problem check the 'install' and
- the 'faq' documents in the docs or online__.
+ If you want to build Psycopg from source you will need some prerequisites (a C
+ compiler, development packages): please check the install_ and the faq_
+ documents in the ``doc`` dir for the details.
.. _wheel: http://pythonwheels.com/
- .. __: http://initd.org/psycopg/docs/install.html#install-from-source
+ .. _PyPI: https://pypi.python.org/pypi/psycopg2
+ .. _install: http://initd.org/psycopg/docs/install.html#install-from-source
+ .. _faq: http://initd.org/psycopg/docs/faq.html#faq-compile
For any other resource (source code repository, bug tracker, mailing list)
please check the `project homepage`__.
@@ -67,7 +65,7 @@ Description: Psycopg is the most popular PostgreSQL database adapter for the Pyt
:alt: Linux and OSX build status
.. |appveyor| image:: https://ci.appveyor.com/api/projects/status/github/psycopg/psycopg2?branch=master&svg=true
- :target: https://ci.appveyor.com/project/psycopg/psycopg2
+ :target: https://ci.appveyor.com/project/psycopg/psycopg2/branch/master
:alt: Windows build status
Platform: any
diff --git a/README.rst b/README.rst
index efbe38e..69b1d83 100644
--- a/README.rst
+++ b/README.rst
@@ -21,7 +21,7 @@ Psycopg 2 is both Unicode and Python 3 friendly.
Documentation
-------------
-Documentation is included in the 'doc' directory and is `available online`__.
+Documentation is included in the ``doc`` directory and is `available online`__.
.. __: http://initd.org/psycopg/docs/
@@ -30,22 +30,20 @@ Installation
------------
If your ``pip`` version supports wheel_ packages it should be possible to
-install a binary version of Psycopg including all the dependencies. Just run::
+install a binary version of Psycopg including all the dependencies from PyPI_.
+Just run::
- pip install psycopg2
+ $ pip install -U pip # make sure your pip is up-to-date
+ $ pip install psycopg2
-If you want to build Psycopg from source you will need some prerequisite (a C
-compiler, Python and libpq development packages). If you have what you need
-the standard::
-
- python setup.py build
- sudo python setup.py install
-
-should work no problem. In case you have any problem check the 'install' and
-the 'faq' documents in the docs or online__.
+If you want to build Psycopg from source you will need some prerequisites (a C
+compiler, development packages): please check the install_ and the faq_
+documents in the ``doc`` dir for the details.
.. _wheel: http://pythonwheels.com/
-.. __: http://initd.org/psycopg/docs/install.html#install-from-source
+.. _PyPI: https://pypi.python.org/pypi/psycopg2
+.. _install: http://initd.org/psycopg/docs/install.html#install-from-source
+.. _faq: http://initd.org/psycopg/docs/faq.html#faq-compile
For any other resource (source code repository, bug tracker, mailing list)
please check the `project homepage`__.
@@ -61,5 +59,5 @@ please check the `project homepage`__.
:alt: Linux and OSX build status
.. |appveyor| image:: https://ci.appveyor.com/api/projects/status/github/psycopg/psycopg2?branch=master&svg=true
- :target: https://ci.appveyor.com/project/psycopg/psycopg2
+ :target: https://ci.appveyor.com/project/psycopg/psycopg2/branch/master
:alt: Windows build status
diff --git a/doc/src/connection.rst b/doc/src/connection.rst
index 53f908f..fbbc53e 100644
--- a/doc/src/connection.rst
+++ b/doc/src/connection.rst
@@ -343,6 +343,9 @@ The ``connection`` class
Read-only string containing the connection string used by the
connection.
+ If a password was specified in the connection string it will be
+ obscured.
+
.. index::
pair: Transaction; Autocommit
diff --git a/doc/src/cursor.rst b/doc/src/cursor.rst
index c03cea8..417ab6c 100644
--- a/doc/src/cursor.rst
+++ b/doc/src/cursor.rst
@@ -601,7 +601,10 @@ The ``cursor`` class
The *sql* statement should be in the form :samp:`COPY {table} TO
STDOUT` to export :samp:`{table}` to the *file* object passed as
argument or :samp:`COPY {table} FROM STDIN` to import the content of
- the *file* object into :samp:`{table}`.
+ the *file* object into :samp:`{table}`. If you need to compose a
+ :sql:`COPY` statement dynamically (because table, fields, or query
+ parameters are in Python variables) you may use the objects provided
+ by the `psycopg2.sql` module.
*file* must be a readable file-like object (as required by
`~cursor.copy_from()`) for *sql* statement :sql:`COPY ... FROM STDIN`
diff --git a/doc/src/errorcodes.rst b/doc/src/errorcodes.rst
index d662d0c..ed40b1f 100644
--- a/doc/src/errorcodes.rst
+++ b/doc/src/errorcodes.rst
@@ -50,7 +50,7 @@ An example of the available constants defined in the module:
'42P01'
Constants representing all the error values defined by PostgreSQL versions
-between 8.1 and 9.4 are included in the module.
+between 8.1 and 10 beta 1 are included in the module.
.. autofunction:: lookup(code)
diff --git a/doc/src/extensions.rst b/doc/src/extensions.rst
index ae40b72..8545fcf 100644
--- a/doc/src/extensions.rst
+++ b/doc/src/extensions.rst
@@ -548,8 +548,6 @@ Other functions
The *scope* must be a `connection` or a `cursor`, the underlying
connection encoding is used for any necessary character conversion.
- Requires libpq >= 9.0.
-
.. versionadded:: 2.7
.. seealso:: libpq docs for `PQescapeIdentifier()`__
@@ -825,10 +823,12 @@ from the database. See :ref:`unicode-handling` for details.
.. data:: PYDATE
PYDATETIME
+ PYDATETIMETZ
PYINTERVAL
PYTIME
PYDATEARRAY
PYDATETIMEARRAY
+ PYDATETIMETZARRAY
PYINTERVALARRAY
PYTIMEARRAY
@@ -837,10 +837,12 @@ from the database. See :ref:`unicode-handling` for details.
.. data:: MXDATE
MXDATETIME
+ MXDATETIMETZ
MXINTERVAL
MXTIME
MXDATEARRAY
MXDATETIMEARRAY
+ MXDATETIMETZARRAY
MXINTERVALARRAY
MXTIMEARRAY
@@ -853,3 +855,5 @@ from the database. See :ref:`unicode-handling` for details.
module. In older versions they can be imported from the implementation
module `!psycopg2._psycopg`.
+.. versionchanged:: 2.7.2
+ added `!*DATETIMETZ*` objects.
diff --git a/doc/src/extras.rst b/doc/src/extras.rst
index f162bf1..36118e7 100644
--- a/doc/src/extras.rst
+++ b/doc/src/extras.rst
@@ -136,6 +136,11 @@ Logging cursor
.. autoclass:: LoggingCursor
+.. note::
+
+ Queries that are executed with `cursor.executemany()` are not logged.
+
+
.. autoclass:: MinTimeLoggingConnection
:members: initialize,filter
@@ -337,7 +342,7 @@ The individual messages in the replication stream are represented by
*This parameter should not be set with physical replication or with
logical replication plugins that produce binary output.*
- This function constructs a ``START_REPLICATION`` command and calls
+ This function constructs a |START_REPLICATION|_ command and calls
`start_replication_expert()` internally.
After starting the replication, to actually consume the incoming
@@ -345,11 +350,19 @@ The individual messages in the replication stream are represented by
`read_message()` in case of :ref:`asynchronous connection
<async-support>`.
+ .. |START_REPLICATION| replace:: :sql:`START_REPLICATION`
+ .. _START_REPLICATION: https://www.postgresql.org/docs/current/static/protocol-replication.html
+
.. method:: start_replication_expert(command, decode=False)
Start replication on the connection using provided
- ``START_REPLICATION`` command. See `start_replication()` for
- description of *decode* parameter.
+ |START_REPLICATION|_ command.
+
+ :param command: The full replication command. It can be a string or a
+ `~psycopg2.sql.Composable` instance for dynamic generation.
+ :param decode: a flag indicating that unicode conversion should be
+ performed on messages received from the server.
+
.. method:: consume_stream(consume, keepalive_interval=10)
diff --git a/doc/src/install.rst b/doc/src/install.rst
index 8290e67..9119753 100644
--- a/doc/src/install.rst
+++ b/doc/src/install.rst
@@ -56,11 +56,20 @@ using something like ``pip install -U pip``)
.. note::
The binary packages come with their own versions of a few C libraries,
- among which libpq and libssl, which will be used regardless of other
+ among which ``libpq`` and ``libssl``, which will be used regardless of other
libraries available on the client: upgrading the system libraries will not
upgrade the libraries used by `!psycopg2`. Please build `!psycopg2` from
source if you want to maintain binary upgradeability.
+.. warning::
+
+ Because the `!psycopg` wheel package uses its own ``libssl`` binary, it is
+ incompatible with other extension modules binding with ``libssl`` as well,
+ for instance the Python `ssl` module: the result will likely be a
+ segfault. If you need using both `!psycopg2` and other libraries using
+ ``libssl`` please :ref:`install psycopg from source
+ <install-from-source>`.
+
If you prefer to use the system libraries available on your client you can use
the :command:`pip` ``--no-binary`` option:
@@ -105,8 +114,8 @@ Build prerequisites
These notes illustrate how to compile Psycopg on Linux. If you want to compile
Psycopg on other platforms you may have to adjust some details accordingly.
-Psycopg is a C wrapper to the libpq PostgreSQL client library. To install it
-from sources you will need:
+Psycopg is a C wrapper around the libpq_ PostgreSQL client library. To install
+it from sources you will need:
- A C compiler.
@@ -133,6 +142,13 @@ from sources you will need:
You only need :program:`pg_config` to compile `!psycopg2`, not for its
regular usage.
+Once everything is in place it's just a matter of running the standard:
+
+.. code-block:: console
+
+ $ python setup.py build
+ $ python setup.py install
+
Runtime requirements
^^^^^^^^^^^^^^^^^^^^
diff --git a/doc/src/sql.rst b/doc/src/sql.rst
index 0aee451..fe807c6 100644
--- a/doc/src/sql.rst
+++ b/doc/src/sql.rst
@@ -55,6 +55,11 @@ from the query parameters::
.format(sql.Identifier('my_table')),
[10, 20])
+The objects exposed by the `!sql` module can be used to compose a query as a
+Python string (using the `~Composable.as_string()` method) or passed directly
+to cursor methods such as `~cursor.execute()`, `~cursor.executemany()`,
+`~cursor.copy_expert()`.
+
.. autoclass:: Composable
diff --git a/doc/src/usage.rst b/doc/src/usage.rst
index cde0242..660f290 100644
--- a/doc/src/usage.rst
+++ b/doc/src/usage.rst
@@ -870,7 +870,7 @@ PostgreSQL |COPY|__ command to move data from files to tables and back.
Currently no adaptation is provided between Python and PostgreSQL types on
|COPY|: the file can be any Python file-like object but its format must be in
-the format accepted by `PostgreSQL COPY command`__ (data fromat, escaped
+the format accepted by `PostgreSQL COPY command`__ (data format, escaped
characters, etc).
.. __: COPY_
diff --git a/lib/__init__.py b/lib/__init__.py
index 492b924..f4d4fc7 100644
--- a/lib/__init__.py
+++ b/lib/__init__.py
@@ -65,7 +65,7 @@ from psycopg2 import tz # noqa
# Register default adapters.
-import psycopg2.extensions as _ext
+from psycopg2 import extensions as _ext
_ext.register_adapter(tuple, _ext.SQL_IN)
_ext.register_adapter(type(None), _ext.NoneAdapter)
diff --git a/lib/_json.py b/lib/_json.py
index b137a2d..92a9def 100644
--- a/lib/_json.py
+++ b/lib/_json.py
@@ -66,6 +66,7 @@ class Json(object):
"""
def __init__(self, adapted, dumps=None):
self.adapted = adapted
+ self._conn = None
if dumps is not None:
self._dumps = dumps
@@ -93,9 +94,15 @@ class Json(object):
"json module not available: "
"you should provide a dumps function")
+ def prepare(self, conn):
+ self._conn = conn
+
def getquoted(self):
s = self.dumps(self.adapted)
- return QuotedString(s).getquoted()
+ qs = QuotedString(s)
+ if self._conn is not None:
+ qs.prepare(self._conn)
+ return qs.getquoted()
if sys.version_info < (3,):
def __str__(self):
diff --git a/lib/errorcodes.py b/lib/errorcodes.py
index f56e25a..24fcf25 100644
--- a/lib/errorcodes.py
+++ b/lib/errorcodes.py
@@ -93,6 +93,7 @@ CLASS_PROGRAM_LIMIT_EXCEEDED = '54'
CLASS_OBJECT_NOT_IN_PREREQUISITE_STATE = '55'
CLASS_OPERATOR_INTERVENTION = '57'
CLASS_SYSTEM_ERROR = '58'
+CLASS_SNAPSHOT_FAILURE = '72'
CLASS_CONFIGURATION_FILE_ERROR = 'F0'
CLASS_FOREIGN_DATA_WRAPPER_ERROR = 'HV'
CLASS_PL_PGSQL_ERROR = 'P0'
@@ -172,6 +173,7 @@ INVALID_USE_OF_ESCAPE_CHARACTER = '2200C'
INVALID_ESCAPE_OCTET = '2200D'
ZERO_LENGTH_CHARACTER_STRING = '2200F'
MOST_SPECIFIC_TYPE_MISMATCH = '2200G'
+SEQUENCE_GENERATOR_LIMIT_EXCEEDED = '2200H'
NOT_AN_XML_DOCUMENT = '2200L'
INVALID_XML_DOCUMENT = '2200M'
INVALID_XML_CONTENT = '2200N'
@@ -233,6 +235,7 @@ SCHEMA_AND_DATA_STATEMENT_MIXING_NOT_SUPPORTED = '25007'
HELD_CURSOR_REQUIRES_SAME_ISOLATION_LEVEL = '25008'
NO_ACTIVE_SQL_TRANSACTION = '25P01'
IN_FAILED_SQL_TRANSACTION = '25P02'
+IDLE_IN_TRANSACTION_SESSION_TIMEOUT = '25P03'
# Class 26 - Invalid SQL Statement Name
INVALID_SQL_STATEMENT_NAME = '26000'
@@ -314,6 +317,7 @@ WRONG_OBJECT_TYPE = '42809'
INVALID_FOREIGN_KEY = '42830'
CANNOT_COERCE = '42846'
UNDEFINED_FUNCTION = '42883'
+GENERATED_ALWAYS = '428C9'
RESERVED_NAME = '42939'
UNDEFINED_TABLE = '42P01'
UNDEFINED_PARAMETER = '42P02'
@@ -359,6 +363,7 @@ OBJECT_NOT_IN_PREREQUISITE_STATE = '55000'
OBJECT_IN_USE = '55006'
CANT_CHANGE_RUNTIME_PARAM = '55P02'
LOCK_NOT_AVAILABLE = '55P03'
+UNSAFE_NEW_ENUM_VALUE_USAGE = '55P04'
# Class 57 - Operator Intervention
OPERATOR_INTERVENTION = '57000'
@@ -374,6 +379,9 @@ IO_ERROR = '58030'
UNDEFINED_FILE = '58P01'
DUPLICATE_FILE = '58P02'
+# Class 72 - Snapshot Failure
+SNAPSHOT_TOO_OLD = '72000'
+
# Class F0 - Configuration File Error
CONFIG_FILE_ERROR = 'F0000'
LOCK_FILE_EXISTS = 'F0001'
diff --git a/lib/extensions.py b/lib/extensions.py
index 00d71f0..91b8133 100644
--- a/lib/extensions.py
+++ b/lib/extensions.py
@@ -43,16 +43,16 @@ from psycopg2._psycopg import ( # noqa
try:
from psycopg2._psycopg import ( # noqa
- MXDATE, MXDATETIME, MXINTERVAL, MXTIME,
- MXDATEARRAY, MXDATETIMEARRAY, MXINTERVALARRAY, MXTIMEARRAY,
+ MXDATE, MXDATETIME, MXDATETIMETZ, MXINTERVAL, MXTIME, MXDATEARRAY,
+ MXDATETIMEARRAY, MXDATETIMETZARRAY, MXINTERVALARRAY, MXTIMEARRAY,
DateFromMx, TimeFromMx, TimestampFromMx, IntervalFromMx, )
except ImportError:
pass
try:
from psycopg2._psycopg import ( # noqa
- PYDATE, PYDATETIME, PYINTERVAL, PYTIME,
- PYDATEARRAY, PYDATETIMEARRAY, PYINTERVALARRAY, PYTIMEARRAY,
+ PYDATE, PYDATETIME, PYDATETIMETZ, PYINTERVAL, PYTIME, PYDATEARRAY,
+ PYDATETIMEARRAY, PYDATETIMETZARRAY, PYINTERVALARRAY, PYTIMEARRAY,
DateFromPy, TimeFromPy, TimestampFromPy, IntervalFromPy, )
except ImportError:
pass
diff --git a/lib/extras.py b/lib/extras.py
index 9e16165..69c7f32 100644
--- a/lib/extras.py
+++ b/lib/extras.py
@@ -1178,6 +1178,9 @@ def execute_batch(cur, sql, argslist, page_size=100):
fewer multi-statement commands, each one containing at most *page_size*
statements, resulting in a reduced number of server roundtrips.
+ After the execution of the functtion the `cursor.rowcount` property will
+ **not** contain a total result.
+
"""
for page in _paginate(argslist, page_size=page_size):
sqls = [cur.mogrify(sql, args) for args in page]
@@ -1212,6 +1215,9 @@ def execute_values(cur, sql, argslist, template=None, page_size=100):
.. __: https://www.postgresql.org/docs/current/static/queries-values.html
+ After the execution of the functtion the `cursor.rowcount` property will
+ **not** contain a total result.
+
While :sql:`INSERT` is an obvious candidate for this function it is
possible to use it with other statements, for example::
diff --git a/lib/pool.py b/lib/pool.py
index e57875c..a91c9cc 100644
--- a/lib/pool.py
+++ b/lib/pool.py
@@ -25,7 +25,7 @@ This module implements thread-safe (and not) connection pools.
# License for more details.
import psycopg2
-import psycopg2.extensions as _ext
+from psycopg2 import extensions as _ext
class PoolError(psycopg2.Error):
diff --git a/lib/psycopg1.py b/lib/psycopg1.py
index 3808aaa..0ee7942 100644
--- a/lib/psycopg1.py
+++ b/lib/psycopg1.py
@@ -28,12 +28,12 @@ old code while porting to psycopg 2. Import it as follows::
# FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
# License for more details.
-import psycopg2._psycopg as _2psycopg # noqa
+from psycopg2 import _psycopg as _2psycopg # noqa
from psycopg2.extensions import cursor as _2cursor
from psycopg2.extensions import connection as _2connection
from psycopg2 import * # noqa
-import psycopg2.extensions as _ext
+from psycopg2 import extensions as _ext
_2connect = connect
diff --git a/lib/sql.py b/lib/sql.py
index e7d42e6..d89e117 100644
--- a/lib/sql.py
+++ b/lib/sql.py
@@ -1,7 +1,7 @@
"""SQL composition utility module
"""
-# psycopg/sql.py - Implementation of the JSON adaptation objects
+# psycopg/sql.py - SQL composition utility module
#
# Copyright (C) 2016 Daniele Varrazzo <daniele.varrazzo at gmail.com>
#
@@ -36,8 +36,9 @@ class Composable(object):
"""
Abstract base class for objects that can be used to compose an SQL string.
- `!Composable` objects can be passed directly to `~cursor.execute()` and
- `~cursor.executemany()` in place of the query string.
+ `!Composable` objects can be passed directly to `~cursor.execute()`,
+ `~cursor.executemany()`, `~cursor.copy_expert()` in place of the query
+ string.
`!Composable` objects can be joined using the ``+`` operator: the result
will be a `Composed` instance containing the objects joined. The operator
@@ -58,9 +59,9 @@ class Composable(object):
:param context: the context to evaluate the string into.
:type context: `connection` or `cursor`
- The method is automatically invoked by `~cursor.execute()` and
- `~cursor.executemany()` if a `!Composable` is passed instead of the
- query string.
+ The method is automatically invoked by `~cursor.execute()`,
+ `~cursor.executemany()`, `~cursor.copy_expert()` if a `!Composable` is
+ passed instead of the query string.
"""
raise NotImplementedError
@@ -84,11 +85,11 @@ class Composable(object):
class Composed(Composable):
"""
- A `Composable` object made of a sequence of `Composable`.
+ A `Composable` object made of a sequence of `!Composable`.
- The object is usually created using `Composable` operators and methods.
+ The object is usually created using `!Composable` operators and methods.
However it is possible to create a `!Composed` directly specifying a
- sequence of `Composable` as arguments.
+ sequence of `!Composable` as arguments.
Example::
@@ -290,9 +291,9 @@ class Identifier(Composable):
"""
A `Composable` representing an SQL identifer.
- Identifiers usually represent names of database objects, such as tables
- or fields. They follow `different rules`__ than SQL string literals for
- escaping (e.g. they use double quotes).
+ Identifiers usually represent names of database objects, such as tables or
+ fields. PostgreSQL identifiers follow `different rules`__ than SQL string
+ literals for escaping (e.g. they use double quotes instead of single).
.. __: https://www.postgresql.org/docs/current/static/sql-syntax-lexical.html# \
SQL-SYNTAX-IDENTIFIERS
diff --git a/psycopg/connection_type.c b/psycopg/connection_type.c
index 26100b2..8c5085b 100644
--- a/psycopg/connection_type.c
+++ b/psycopg/connection_type.c
@@ -938,7 +938,7 @@ psyco_conn_lobject(connectionObject *self, PyObject *args, PyObject *keywds)
PyObject *obj;
static char *kwlist[] = {"oid", "mode", "new_oid", "new_file",
- "cursor_factory", NULL};
+ "lobject_factory", NULL};
if (!PyArg_ParseTupleAndKeywords(args, keywds, "|IzIzO", kwlist,
&oid, &smode, &new_oid, &new_file,
@@ -1248,10 +1248,58 @@ static struct PyGetSetDef connectionObject_getsets[] = {
/* initialization and finalization methods */
+RAISES_NEG static int
+obscure_password(connectionObject *conn)
+{
+ PQconninfoOption *options;
+ PyObject *d = NULL, *v = NULL, *dsn = NULL;
+ char *tmp;
+ int rv = -1;
+
+ if (!conn || !conn->dsn) {
+ return 0;
+ }
+
+ if (!(options = PQconninfoParse(conn->dsn, NULL))) {
+ /* unlikely: the dsn was already tested valid */
+ return 0;
+ }
+
+ if (!(d = psycopg_dict_from_conninfo_options(
+ options, /* include_password = */ 1))) {
+ goto exit;
+ }
+ if (NULL == PyDict_GetItemString(d, "password")) {
+ /* the dsn doesn't have a password */
+ rv = 0;
+ goto exit;
+ }
+
+ /* scrub the password and put back the connection string together */
+ if (!(v = Text_FromUTF8("xxx"))) { goto exit; }
+ if (0 > PyDict_SetItemString(d, "password", v)) { goto exit; }
+ if (!(dsn = psycopg_make_dsn(Py_None, d))) { goto exit; }
+ if (!(dsn = psycopg_ensure_bytes(dsn))) { goto exit; }
+
+ /* Replace the connection string on the connection object */
+ tmp = conn->dsn;
+ psycopg_strdup(&conn->dsn, Bytes_AS_STRING(dsn), -1);
+ PyMem_Free(tmp);
+
+ rv = 0;
+
+exit:
+ PQconninfoFree(options);
+ Py_XDECREF(v);
+ Py_XDECREF(d);
+ Py_XDECREF(dsn);
+
+ return rv;
+}
+
static int
connection_setup(connectionObject *self, const char *dsn, long int async)
{
- char *pos;
int res = -1;
Dprintf("connection_setup: init connection object at %p, "
@@ -1288,15 +1336,16 @@ connection_setup(connectionObject *self, const char *dsn, long int async)
exit:
/* here we obfuscate the password even if there was a connection error */
- pos = strstr(self->dsn, "password");
- if (pos != NULL) {
- for (pos = pos+9 ; *pos != '\0' && *pos != ' '; pos++)
- *pos = 'x';
+ {
+ PyObject *ptype = NULL, *pvalue = NULL, *ptb = NULL;
+ PyErr_Fetch(&ptype, &pvalue, &ptb);
+ obscure_password(self);
+ PyErr_Restore(ptype, pvalue, ptb);
}
-
return res;
}
+
static int
connection_clear(connectionObject *self)
{
diff --git a/psycopg/cursor.h b/psycopg/cursor.h
index 3c94fe3..d89bf21 100644
--- a/psycopg/cursor.h
+++ b/psycopg/cursor.h
@@ -95,6 +95,7 @@ BORROWED HIDDEN PyObject *curs_get_cast(cursorObject *self, PyObject *oid);
HIDDEN void curs_reset(cursorObject *self);
HIDDEN int psyco_curs_withhold_set(cursorObject *self, PyObject *pyvalue);
HIDDEN int psyco_curs_scrollable_set(cursorObject *self, PyObject *pyvalue);
+HIDDEN PyObject *psyco_curs_validate_sql_basic(cursorObject *self, PyObject *sql);
/* exception-raising macros */
#define EXC_IF_CURS_CLOSED(self) \
diff --git a/psycopg/cursor_int.c b/psycopg/cursor_int.c
index dd4c0d7..bacef77 100644
--- a/psycopg/cursor_int.c
+++ b/psycopg/cursor_int.c
@@ -80,3 +80,83 @@ curs_reset(cursorObject *self)
Py_CLEAR(self->description);
Py_CLEAR(self->casts);
}
+
+
+/* Return 1 if `obj` is a `psycopg2.sql.Composable` instance, else 0
+ * Set an exception and return -1 in case of error.
+ */
+RAISES_NEG static int
+_curs_is_composible(PyObject *obj)
+{
+ int rv = -1;
+ PyObject *m = NULL;
+ PyObject *comp = NULL;
+
+ if (!(m = PyImport_ImportModule("psycopg2.sql"))) { goto exit; }
+ if (!(comp = PyObject_GetAttrString(m, "Composable"))) { goto exit; }
+ rv = PyObject_IsInstance(obj, comp);
+
+exit:
+ Py_XDECREF(comp);
+ Py_XDECREF(m);
+ return rv;
+
+}
+
+/* Performs very basic validation on an incoming SQL string.
+ * Returns a new reference to a str instance on success; NULL on failure,
+ * after having set an exception.
+ */
+PyObject *
+psyco_curs_validate_sql_basic(cursorObject *self, PyObject *sql)
+{
+ PyObject *rv = NULL;
+ PyObject *comp = NULL;
+ int iscomp;
+
+ if (!sql || !PyObject_IsTrue(sql)) {
+ psyco_set_error(ProgrammingError, self,
+ "can't execute an empty query");
+ goto exit;
+ }
+
+ if (Bytes_Check(sql)) {
+ /* Necessary for ref-count symmetry with the unicode case: */
+ Py_INCREF(sql);
+ rv = sql;
+ }
+ else if (PyUnicode_Check(sql)) {
+ if (!(rv = conn_encode(self->conn, sql))) { goto exit; }
+ }
+ else if (0 != (iscomp = _curs_is_composible(sql))) {
+ if (iscomp < 0) { goto exit; }
+ if (!(comp = PyObject_CallMethod(sql, "as_string", "O", self->conn))) {
+ goto exit;
+ }
+
+ if (Bytes_Check(comp)) {
+ rv = comp;
+ comp = NULL;
+ }
+ else if (PyUnicode_Check(comp)) {
+ if (!(rv = conn_encode(self->conn, comp))) { goto exit; }
+ }
+ else {
+ PyErr_Format(PyExc_TypeError,
+ "as_string() should return a string: got %s instead",
+ Py_TYPE(comp)->tp_name);
+ goto exit;
+ }
+ }
+ else {
+ /* the is not unicode or string, raise an error */
+ PyErr_Format(PyExc_TypeError,
+ "argument 1 must be a string or unicode object: got %s instead",
+ Py_TYPE(sql)->tp_name);
+ goto exit;
+ }
+
+exit:
+ Py_XDECREF(comp);
+ return rv;
+}
diff --git a/psycopg/cursor_type.c b/psycopg/cursor_type.c
index 5031033..a70e9d3 100644
--- a/psycopg/cursor_type.c
+++ b/psycopg/cursor_type.c
@@ -267,85 +267,6 @@ _mogrify(PyObject *var, PyObject *fmt, cursorObject *curs, PyObject **new)
return 0;
}
-/* Return 1 if `obj` is a `psycopg2.sql.Composable` instance, else 0
- * Set an exception and return -1 in case of error.
- */
-RAISES_NEG static int
-_curs_is_composible(PyObject *obj)
-{
- int rv = -1;
- PyObject *m = NULL;
- PyObject *comp = NULL;
-
- if (!(m = PyImport_ImportModule("psycopg2.sql"))) { goto exit; }
- if (!(comp = PyObject_GetAttrString(m, "Composable"))) { goto exit; }
- rv = PyObject_IsInstance(obj, comp);
-
-exit:
- Py_XDECREF(comp);
- Py_XDECREF(m);
- return rv;
-
-}
-
-static PyObject *_psyco_curs_validate_sql_basic(
- cursorObject *self, PyObject *sql
- )
-{
- PyObject *rv = NULL;
- PyObject *comp = NULL;
- int iscomp;
-
- /* Performs very basic validation on an incoming SQL string.
- Returns a new reference to a str instance on success; NULL on failure,
- after having set an exception. */
-
- if (!sql || !PyObject_IsTrue(sql)) {
- psyco_set_error(ProgrammingError, self,
- "can't execute an empty query");
- goto exit;
- }
-
- if (Bytes_Check(sql)) {
- /* Necessary for ref-count symmetry with the unicode case: */
- Py_INCREF(sql);
- rv = sql;
- }
- else if (PyUnicode_Check(sql)) {
- if (!(rv = conn_encode(self->conn, sql))) { goto exit; }
- }
- else if (0 != (iscomp = _curs_is_composible(sql))) {
- if (iscomp < 0) { goto exit; }
- if (!(comp = PyObject_CallMethod(sql, "as_string", "O", self->conn))) {
- goto exit;
- }
-
- if (Bytes_Check(comp)) {
- rv = comp;
- comp = NULL;
- }
- else if (PyUnicode_Check(comp)) {
- if (!(rv = conn_encode(self->conn, comp))) { goto exit; }
- }
- else {
- PyErr_Format(PyExc_TypeError,
- "as_string() should return a string: got %s instead",
- Py_TYPE(comp)->tp_name);
- goto exit;
- }
- }
- else {
- /* the is not unicode or string, raise an error */
- PyErr_Format(PyExc_TypeError,
- "argument 1 must be a string or unicode object: got %s instead",
- Py_TYPE(sql)->tp_name);
- goto exit;
- }
-
-exit:
- Py_XDECREF(comp);
- return rv;
-}
/* Merge together a query string and its arguments.
*
@@ -425,7 +346,7 @@ _psyco_curs_execute(cursorObject *self,
PyObject *fquery, *cvt = NULL;
const char *scroll;
- operation = _psyco_curs_validate_sql_basic(self, operation);
+ operation = psyco_curs_validate_sql_basic(self, operation);
/* Any failure from here forward should 'goto fail' rather than 'return 0'
directly. */
@@ -622,7 +543,7 @@ _psyco_curs_mogrify(cursorObject *self,
{
... 1546 lines suppressed ...
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/python-modules/packages/psycopg2.git
More information about the Python-modules-commits
mailing list