From: Philip Jenvey Date: Sun, 9 Aug 2009 00:56:52 +0000 (+0000) Subject: o oracle+zxjdbc type handling additions X-Git-Tag: rel_0_6beta1~345 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=a53d4e2ab48a003a957ba374c65ea999dcd962e4;p=thirdparty%2Fsqlalchemy%2Fsqlalchemy.git o oracle+zxjdbc type handling additions o avoid returning tests on oracle+zxjdbc for now --- diff --git a/lib/sqlalchemy/dialects/oracle/zxjdbc.py b/lib/sqlalchemy/dialects/oracle/zxjdbc.py index a0ad088b2d..0956d7ab65 100644 --- a/lib/sqlalchemy/dialects/oracle/zxjdbc.py +++ b/lib/sqlalchemy/dialects/oracle/zxjdbc.py @@ -1,14 +1,69 @@ """Support for the Oracle database via the zxjdbc JDBC connector.""" +import decimal import re +try: + from com.ziclix.python.sql.handler import OracleDataHandler +except ImportError: + OracleDataHandler = None + +from sqlalchemy import types as sqltypes, util from sqlalchemy.connectors.zxJDBC import ZxJDBCConnector from sqlalchemy.dialects.oracle.base import OracleDialect +from sqlalchemy.engine.default import DefaultExecutionContext -class Oracle_jdbc(ZxJDBCConnector, OracleDialect): +class _JDBCDate(sqltypes.Date): + + def result_processor(self, dialect): + def process(value): + if value is None: + return None + else: + return value.date() + return process + + +class _JDBCNumeric(sqltypes.Numeric): + + def result_processor(self, dialect): + if self.asdecimal: + return None + else: + def process(value): + if isinstance(value, decimal.Decimal): + return float(value) + else: + return value + return process + + +class Oracle_jdbcExecutionContext(DefaultExecutionContext): + def create_cursor(self): + cursor = self._connection.connection.cursor() + cursor.cursor.datahandler = OracleDataHandler(cursor.cursor.datahandler) + return cursor + + +class Oracle_jdbc(ZxJDBCConnector, OracleDialect): + execution_ctx_cls = Oracle_jdbcExecutionContext jdbc_db_name = 'oracle' jdbc_driver_name = 'oracle.jdbc.driver.OracleDriver' + implicit_returning = False + + colspecs = util.update_copy( + OracleDialect.colspecs, + { + sqltypes.Date : _JDBCDate, + sqltypes.Numeric: _JDBCNumeric + } + ) + + def initialize(self, connection): + super(Oracle_jdbc, self).initialize(connection) + self.implicit_returning = False + def create_connect_args(self, url): hostname = url.host port = url.port or '1521' @@ -16,9 +71,9 @@ class Oracle_jdbc(ZxJDBCConnector, OracleDialect): jdbc_url = 'jdbc:oracle:thin:@%s:%s:%s' % (hostname, port, dbname) return [[jdbc_url, url.username, url.password, self.jdbc_driver_name], self._driver_kwargs()] - + def _get_server_version_info(self, connection): version = re.search(r'Release ([\d\.]+)', connection.connection.dbversion).group(1) return tuple(int(x) for x in version.split('.')) - + dialect = Oracle_jdbc diff --git a/lib/sqlalchemy/test/requires.py b/lib/sqlalchemy/test/requires.py index f3f4ec1911..c1f8d31689 100644 --- a/lib/sqlalchemy/test/requires.py +++ b/lib/sqlalchemy/test/requires.py @@ -140,6 +140,7 @@ def returning(fn): no_support('maxdb', 'not supported by database'), no_support('sybase', 'not supported by database'), no_support('informix', 'not supported by database'), + no_support('oracle+zxjdbc', 'FIXME: tricky; currently broken'), ) def two_phase_transactions(fn): diff --git a/test/dialect/test_oracle.py b/test/dialect/test_oracle.py index 444f24cf28..85c3097be1 100644 --- a/test/dialect/test_oracle.py +++ b/test/dialect/test_oracle.py @@ -14,7 +14,7 @@ import os class OutParamTest(TestBase, AssertsExecutionResults): - __only_on__ = 'oracle' + __only_on__ = 'oracle+cx_oracle' @classmethod def setup_class(cls): @@ -364,6 +364,7 @@ class TypesTest(TestBase, AssertsCompiledSQL): ]: assert isinstance(start.dialect_impl(dialect), test), "wanted %r got %r" % (test, start.dialect_impl(dialect)) + @testing.requires.returning def test_int_not_float(self): m = MetaData(testing.db) t1 = Table('t1', m, Column('foo', Integer)) @@ -421,6 +422,7 @@ class TypesTest(TestBase, AssertsCompiledSQL): finally: testing.db.execute("DROP TABLE Z_TEST") + @testing.fails_on('+zxjdbc', 'auto_convert_lobs not applicable') def test_raw_lobs(self): engine = testing_engine(options=dict(auto_convert_lobs=False)) metadata = MetaData() diff --git a/test/sql/test_query.py b/test/sql/test_query.py index 0e3b9dff20..d10313d14f 100644 --- a/test/sql/test_query.py +++ b/test/sql/test_query.py @@ -80,7 +80,8 @@ class QueryTest(TestBase): ret[c.key] = row[c] return ret - if testing.against('firebird', 'postgresql', 'oracle', 'mssql'): + if (testing.against('firebird', 'postgresql', 'oracle', 'mssql') and + not testing.against('oracle+zxjdbc')): test_engines = [ engines.testing_engine(options={'implicit_returning':False}), engines.testing_engine(options={'implicit_returning':True}), @@ -167,7 +168,8 @@ class QueryTest(TestBase): eq_(r.inserted_primary_key, [12, 1]) def test_autoclose_on_insert(self): - if testing.against('firebird', 'postgresql', 'oracle', 'mssql'): + if (testing.against('firebird', 'postgresql', 'oracle', 'mssql') and + not testing.against('oracle+zxjdbc')): test_engines = [ engines.testing_engine(options={'implicit_returning':False}), engines.testing_engine(options={'implicit_returning':True}), diff --git a/test/sql/test_returning.py b/test/sql/test_returning.py index 1b69c55ffc..474e0b3692 100644 --- a/test/sql/test_returning.py +++ b/test/sql/test_returning.py @@ -5,7 +5,7 @@ from sqlalchemy.test.schema import Table, Column from sqlalchemy.types import TypeDecorator class ReturningTest(TestBase, AssertsExecutionResults): - __unsupported_on__ = ('sqlite', 'mysql', 'maxdb', 'sybase', 'access') + __unsupported_on__ = ('sqlite', 'mysql', 'maxdb', 'sybase', 'access', 'oracle+zxjdbc') def setup(self): meta = MetaData(testing.db) @@ -137,7 +137,7 @@ class ReturningTest(TestBase, AssertsExecutionResults): eq_(result2.fetchall(), [(2,False),]) class SequenceReturningTest(TestBase): - __unsupported_on__ = ('sqlite', 'mysql', 'maxdb', 'sybase', 'access', 'mssql') + __unsupported_on__ = ('sqlite', 'mysql', 'maxdb', 'sybase', 'access', 'mssql', 'oracle+zxjdbc') def setup(self): meta = MetaData(testing.db) @@ -160,7 +160,7 @@ class SequenceReturningTest(TestBase): class KeyReturningTest(TestBase, AssertsExecutionResults): """test returning() works with columns that define 'key'.""" - __unsupported_on__ = ('sqlite', 'mysql', 'maxdb', 'sybase', 'access') + __unsupported_on__ = ('sqlite', 'mysql', 'maxdb', 'sybase', 'access', 'oracle+zxjdbc') def setup(self): meta = MetaData(testing.db)