script:
- tox
+
+
+# This branch is still far from passing tests
+branches:
+ except:
+ - cython
# Copyright (C) 2020 The Psycopg Team
+from . import pq
from .consts import VERSION as __version__ # noqa
from .connection import AsyncConnection, Connection
NotSupportedError,
)
-# register default adapters
-from . import types # noqa
-
from .dbapi20 import BINARY, DATETIME, NUMBER, ROWID, STRING
from .dbapi20 import Binary, Date, DateFromTicks, Time, TimeFromTicks
from .dbapi20 import Timestamp, TimestampFromTicks
threadsafety = 2
paramstyle = "pyformat"
+
+# register default adapters
+from . import types # noqa
+
+# Override adapters with fast version if available
+if pq.__impl__ == "c":
+ from ._psycopg3 import register_builtin_c_loaders
+
+ register_builtin_c_loaders()
+
+
__all__ = (
["Warning", "Error", "InterfaceError", "DatabaseError", "DataError"]
+ ["OperationalError", "IntegrityError", "InternalError"]
include "types/numeric.pyx"
include "types/text.pyx"
+include "adapt.pyx"
include "transform.pyx"
--- /dev/null
+
+ctypedef object (*cloader_func)(const char *data, size_t length, void *context)
+# ctypedef void * (*get_context_func)(PGconn_ptr conn)
+
+cdef void register_c_loader(object pyloader, cloader_func cloader)
--- /dev/null
+from psycopg3.adapt cimport cloader_func
+
+from psycopg3.types cimport numeric
+
+
+import logging
+logger = logging.getLogger("psycopg3.adapt")
+
+
+cdef class CLoader:
+ cdef object pyloader
+ cdef cloader_func cloader
+
+
+cloaders = {}
+
+cdef void register_c_loader(object pyloader, cloader_func cloader):
+ """
+ Map a python loader to an optimised C version.
+
+ Whenever the python loader would be used the C version may be chosen in
+ preference.
+ """
+ cdef CLoader cl = CLoader()
+ cl.pyloader = pyloader
+ cl.cloader = cloader
+ cloaders[pyloader] = cl
+
+
+def register_builtin_c_loaders():
+ if cloaders:
+ logger.warning("c loaders already registered")
+ return
+
+ logger.debug("registering optimised c loaders")
+ register_numeric_c_loaders()
+
+
+cdef void register_numeric_c_loaders():
+ logger.debug("registering optimised numeric c loaders")
+ from psycopg3.types import numeric
+ register_c_loader(numeric.load_int, load_int_text)
+ register_c_loader(numeric.load_int2_binary, load_int2_binary)
+ register_c_loader(numeric.load_int4_binary, load_int4_binary)
+ register_c_loader(numeric.load_int8_binary, load_int8_binary)
+ register_c_loader(numeric.load_oid_binary, load_oid_binary)
from psycopg3.pq cimport libpq
from psycopg3.pq.pq_cython cimport PGresult
+from psycopg3.adapt cimport cloader_func
from psycopg3 import errors as e
from psycopg3.pq.enums import Format
TEXT_OID = 25
-ctypedef object (*cloader_func)(const char *data, size_t length, void *context)
cdef struct RowLoader:
PyObject *pyloader # borrowed
--- /dev/null
+cdef object load_int_text(const char *data, size_t length, void *context)
+cdef object load_int2_binary(const char *data, size_t length, void *context)
+cdef object load_int4_binary(const char *data, size_t length, void *context)
+cdef object load_int8_binary(const char *data, size_t length, void *context)
+cdef object load_oid_binary(const char *data, size_t length, void *context)
+cdef object load_bool_binary(const char *data, size_t length, void *context)