Convert plain text queries to SQL to allow argument escaping.

Bump 0.5.6, refs #115.
This commit is contained in:
Friedrich Lindenberg 2015-01-18 13:39:30 +01:00
parent 18bd02419a
commit bdcd371b5a
2 changed files with 12 additions and 7 deletions

View File

@ -1,15 +1,17 @@
import logging import logging
import threading import threading
import re import re
from sqlalchemy.util import safe_reraise
import six
from six.moves.urllib.parse import urlencode, parse_qs from six.moves.urllib.parse import urlencode, parse_qs
from sqlalchemy import create_engine from sqlalchemy import create_engine
from sqlalchemy import Integer, String
from sqlalchemy.sql import text
from sqlalchemy.pool import NullPool from sqlalchemy.pool import NullPool
from sqlalchemy.schema import MetaData, Column from sqlalchemy.schema import MetaData, Column
from sqlalchemy.schema import Table as SQLATable from sqlalchemy.schema import Table as SQLATable
from sqlalchemy import Integer, String from sqlalchemy.util import safe_reraise
from alembic.migration import MigrationContext from alembic.migration import MigrationContext
from alembic.operations import Operations from alembic.operations import Operations
@ -251,18 +253,21 @@ class Database(object):
""" """
Run a statement on the database directly, allowing for the Run a statement on the database directly, allowing for the
execution of arbitrary read/write queries. A query can either be execution of arbitrary read/write queries. A query can either be
a plain text string, or a `SQLAlchemy expression <http://docs.sqlalchemy.org/en/latest/core/tutorial.html#selecting>`_. The returned a plain text string, or a `SQLAlchemy expression <http://docs.sqlalchemy.org/en/latest/core/tutorial.html#selecting>`_.
iterator will yield each result sequentially. If a plain string is passed in, it will be converted to an expression automatically.
If a SQLAlchemy expression is passed into the function, keyword Keyword arguments will be used for parameter binding. See the `SQLAlchemy
arguments will be used for parameter binding. See the `SQLAlchemy
documentation <http://docs.sqlalchemy.org/en/rel_0_9/core/connections.html#sqlalchemy.engine.Connection.execute>`_ for details. documentation <http://docs.sqlalchemy.org/en/rel_0_9/core/connections.html#sqlalchemy.engine.Connection.execute>`_ for details.
The returned iterator will yield each result sequentially.
:: ::
res = db.query('SELECT user, COUNT(*) c FROM photos GROUP BY user') res = db.query('SELECT user, COUNT(*) c FROM photos GROUP BY user')
for row in res: for row in res:
print(row['user'], row['c']) print(row['user'], row['c'])
""" """
if isinstance(query, six.string_types):
query = text(query)
return ResultIter(self.executable.execute(query, **kw)) return ResultIter(self.executable.execute(query, **kw))
def __repr__(self): def __repr__(self):

View File

@ -8,7 +8,7 @@ if sys.version_info[:2] <= (2, 6):
setup( setup(
name='dataset', name='dataset',
version='0.5.5', version='0.5.6',
description="Toolkit for Python-based data processing.", description="Toolkit for Python-based data processing.",
long_description="", long_description="",
classifiers=[ classifiers=[