~ubuntu-branches/debian/jessie/sqlalchemy/jessie

« back to all changes in this revision

Viewing changes to lib/sqlalchemy/types.py

  • Committer: Package Import Robot
  • Author(s): Piotr Ożarowski, Jakub Wilk, Piotr Ożarowski
  • Date: 2013-07-06 20:53:52 UTC
  • mfrom: (1.4.23) (16.1.17 experimental)
  • Revision ID: package-import@ubuntu.com-20130706205352-ryppl1eto3illd79
Tags: 0.8.2-1
[ Jakub Wilk ]
* Use canonical URIs for Vcs-* fields.

[ Piotr Ożarowski ]
* New upstream release
* Upload to unstable
* Build depend on python3-all instead of -dev, extensions are not built for
  Python 3.X 

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
# sqlalchemy/types.py
2
 
# Copyright (C) 2005-2012 the SQLAlchemy authors and contributors <see AUTHORS file>
 
2
# Copyright (C) 2005-2013 the SQLAlchemy authors and contributors <see AUTHORS file>
3
3
#
4
4
# This module is part of SQLAlchemy and is released under
5
5
# the MIT License: http://www.opensource.org/licenses/mit-license.php
6
6
 
7
7
"""defines genericized SQL types, each represented by a subclass of
8
 
:class:`~sqlalchemy.types.AbstractType`.  Dialects define further subclasses of these
9
 
types.
 
8
:class:`~sqlalchemy.types.AbstractType`.  Dialects define further subclasses
 
9
of these types.
10
10
 
11
11
For more information see the SQLAlchemy documentation on types.
12
12
 
13
13
"""
14
 
__all__ = [ 'TypeEngine', 'TypeDecorator', 'AbstractType', 'UserDefinedType',
15
 
            'INT', 'CHAR', 'VARCHAR', 'NCHAR', 'NVARCHAR','TEXT', 'Text',
 
14
__all__ = ['TypeEngine', 'TypeDecorator', 'AbstractType', 'UserDefinedType',
 
15
            'INT', 'CHAR', 'VARCHAR', 'NCHAR', 'NVARCHAR', 'TEXT', 'Text',
16
16
            'FLOAT', 'NUMERIC', 'REAL', 'DECIMAL', 'TIMESTAMP', 'DATETIME',
17
 
            'CLOB', 'BLOB', 'BINARY', 'VARBINARY', 'BOOLEAN', 'BIGINT', 'SMALLINT',
18
 
            'INTEGER', 'DATE', 'TIME', 'String', 'Integer', 'SmallInteger',
19
 
            'BigInteger', 'Numeric', 'Float', 'DateTime', 'Date', 'Time',
20
 
            'LargeBinary', 'Binary', 'Boolean', 'Unicode', 'Concatenable',
21
 
            'UnicodeText','PickleType', 'Interval', 'Enum', 'MutableType' ]
 
17
            'CLOB', 'BLOB', 'BINARY', 'VARBINARY', 'BOOLEAN', 'BIGINT',
 
18
            'SMALLINT', 'INTEGER', 'DATE', 'TIME', 'String', 'Integer',
 
19
            'SmallInteger', 'BigInteger', 'Numeric', 'Float', 'DateTime',
 
20
            'Date', 'Time', 'LargeBinary', 'Binary', 'Boolean', 'Unicode',
 
21
            'Concatenable', 'UnicodeText', 'PickleType', 'Interval', 'Enum']
22
22
 
23
 
import inspect
24
23
import datetime as dt
25
24
import codecs
26
25
 
27
 
from sqlalchemy import exc, schema
28
 
from sqlalchemy.sql import expression, operators
29
 
from sqlalchemy.util import pickle
30
 
from sqlalchemy.util.compat import decimal
31
 
from sqlalchemy.sql.visitors import Visitable
32
 
from sqlalchemy import util
33
 
from sqlalchemy import processors, events, event
34
 
import collections
 
26
from . import exc, schema, util, processors, events, event
 
27
from .sql import operators
 
28
from .sql.expression import _DefaultColumnComparator
 
29
from .util import pickle
 
30
from .sql.visitors import Visitable
 
31
import decimal
35
32
default = util.importlater("sqlalchemy.engine", "default")
36
33
 
37
34
NoneType = type(None)
38
35
if util.jython:
39
36
    import array
40
37
 
 
38
 
41
39
class AbstractType(Visitable):
42
40
    """Base for all types - not needed except for backwards
43
41
    compatibility."""
44
42
 
 
43
 
45
44
class TypeEngine(AbstractType):
46
45
    """Base for built-in types."""
47
46
 
 
47
    class Comparator(_DefaultColumnComparator):
 
48
        """Base class for custom comparison operations defined at the
 
49
        type level.  See :attr:`.TypeEngine.comparator_factory`.
 
50
 
 
51
        The public base class for :class:`.TypeEngine.Comparator`
 
52
        is :class:`.ColumnOperators`.
 
53
 
 
54
        """
 
55
 
 
56
        def __init__(self, expr):
 
57
            self.expr = expr
 
58
 
 
59
        def __reduce__(self):
 
60
            return _reconstitute_comparator, (self.expr, )
 
61
 
 
62
    hashable = True
 
63
    """Flag, if False, means values from this type aren't hashable.
 
64
 
 
65
    Used by the ORM when uniquing result lists.
 
66
 
 
67
    """
 
68
 
 
69
    comparator_factory = Comparator
 
70
    """A :class:`.TypeEngine.Comparator` class which will apply
 
71
    to operations performed by owning :class:`.ColumnElement` objects.
 
72
 
 
73
    The :attr:`.comparator_factory` attribute is a hook consulted by
 
74
    the core expression system when column and SQL expression operations
 
75
    are performed.   When a :class:`.TypeEngine.Comparator` class is
 
76
    associated with this attribute, it allows custom re-definition of
 
77
    all existing operators, as well as definition of new operators.
 
78
    Existing operators include those provided by Python operator overloading
 
79
    such as :meth:`.operators.ColumnOperators.__add__` and
 
80
    :meth:`.operators.ColumnOperators.__eq__`,
 
81
    those provided as standard
 
82
    attributes of :class:`.operators.ColumnOperators` such as
 
83
    :meth:`.operators.ColumnOperators.like`
 
84
    and :meth:`.operators.ColumnOperators.in_`.
 
85
 
 
86
    Rudimentary usage of this hook is allowed through simple subclassing
 
87
    of existing types, or alternatively by using :class:`.TypeDecorator`.
 
88
    See the documentation section :ref:`types_operators` for examples.
 
89
 
 
90
    .. versionadded:: 0.8  The expression system was enhanced to support
 
91
      customization of operators on a per-type level.
 
92
 
 
93
    """
 
94
 
48
95
    def copy_value(self, value):
49
96
        return value
50
97
 
78
125
        """
79
126
        return None
80
127
 
 
128
    def column_expression(self, colexpr):
 
129
        """Given a SELECT column expression, return a wrapping SQL expression.
 
130
 
 
131
        This is typically a SQL function that wraps a column expression
 
132
        as rendered in the columns clause of a SELECT statement.
 
133
        It is used for special data types that require
 
134
        columns to be wrapped in some special database function in order
 
135
        to coerce the value before being sent back to the application.
 
136
        It is the SQL analogue of the :meth:`.TypeEngine.result_processor`
 
137
        method.
 
138
 
 
139
        The method is evaluated at statement compile time, as opposed
 
140
        to statement construction time.
 
141
 
 
142
        See also:
 
143
 
 
144
        :ref:`types_sql_value_processing`
 
145
 
 
146
        """
 
147
 
 
148
        return None
 
149
 
 
150
    @util.memoized_property
 
151
    def _has_column_expression(self):
 
152
        """memoized boolean, check if column_expression is implemented.
 
153
 
 
154
        Allows the method to be skipped for the vast majority of expression
 
155
        types that don't use this feature.
 
156
 
 
157
        """
 
158
 
 
159
        return self.__class__.column_expression.func_code \
 
160
            is not TypeEngine.column_expression.func_code
 
161
 
 
162
    def bind_expression(self, bindvalue):
 
163
        """"Given a bind value (i.e. a :class:`.BindParameter` instance),
 
164
        return a SQL expression in its place.
 
165
 
 
166
        This is typically a SQL function that wraps the existing bound
 
167
        parameter within the statement.  It is used for special data types
 
168
        that require literals being wrapped in some special database function
 
169
        in order to coerce an application-level value into a database-specific
 
170
        format.  It is the SQL analogue of the
 
171
        :meth:`.TypeEngine.bind_processor` method.
 
172
 
 
173
        The method is evaluated at statement compile time, as opposed
 
174
        to statement construction time.
 
175
 
 
176
        Note that this method, when implemented, should always return
 
177
        the exact same structure, without any conditional logic, as it
 
178
        may be used in an executemany() call against an arbitrary number
 
179
        of bound parameter sets.
 
180
 
 
181
        See also:
 
182
 
 
183
        :ref:`types_sql_value_processing`
 
184
 
 
185
        """
 
186
        return None
 
187
 
 
188
    @util.memoized_property
 
189
    def _has_bind_expression(self):
 
190
        """memoized boolean, check if bind_expression is implemented.
 
191
 
 
192
        Allows the method to be skipped for the vast majority of expression
 
193
        types that don't use this feature.
 
194
 
 
195
        """
 
196
 
 
197
        return self.__class__.bind_expression.func_code \
 
198
            is not TypeEngine.bind_expression.func_code
 
199
 
81
200
    def compare_values(self, x, y):
82
201
        """Compare two values for equality."""
83
202
 
84
203
        return x == y
85
204
 
86
 
    def is_mutable(self):
87
 
        """Return True if the target Python type is 'mutable'.
88
 
 
89
 
        This allows systems like the ORM to know if a column value can
90
 
        be considered 'not changed' by comparing the identity of
91
 
        objects alone.  Values such as dicts, lists which
92
 
        are serialized into strings are examples of "mutable"
93
 
        column structures.
94
 
 
95
 
        .. note::
96
 
 
97
 
           This functionality is now superseded by the
98
 
           ``sqlalchemy.ext.mutable`` extension described in
99
 
           :ref:`mutable_toplevel`.
100
 
 
101
 
        When this method is overridden, :meth:`copy_value` should
102
 
        also be supplied.   The :class:`.MutableType` mixin
103
 
        is recommended as a helper.
104
 
 
105
 
        """
106
 
        return False
107
 
 
108
205
    def get_dbapi_type(self, dbapi):
109
206
        """Return the corresponding type object from the underlying DB-API, if
110
207
        any.
149
246
        The construction of :meth:`.TypeEngine.with_variant` is always
150
247
        from the "fallback" type to that which is dialect specific.
151
248
        The returned type is an instance of :class:`.Variant`, which
152
 
        itself provides a :meth:`~sqlalchemy.types.Variant.with_variant` that can
153
 
        be called repeatedly.
 
249
        itself provides a :meth:`~sqlalchemy.types.Variant.with_variant`
 
250
        that can be called repeatedly.
154
251
 
155
252
        :param type_: a :class:`.TypeEngine` that will be selected
156
253
         as a variant from the originating type, when a dialect
161
258
        .. versionadded:: 0.7.2
162
259
 
163
260
        """
164
 
        return Variant(self, {dialect_name:type_})
165
 
 
166
 
    def _adapt_expression(self, op, othertype):
167
 
        """evaluate the return type of <self> <op> <othertype>,
168
 
        and apply any adaptations to the given operator.
169
 
 
170
 
        """
171
 
        return op, self
 
261
        return Variant(self, {dialect_name: type_})
172
262
 
173
263
    @util.memoized_property
174
264
    def _type_affinity(self):
185
275
            return self.__class__
186
276
 
187
277
    def dialect_impl(self, dialect):
188
 
        """Return a dialect-specific implementation for this :class:`.TypeEngine`."""
 
278
        """Return a dialect-specific implementation for this
 
279
        :class:`.TypeEngine`.
189
280
 
 
281
        """
190
282
        try:
191
283
            return dialect._type_memos[self]['impl']
192
284
        except KeyError:
228
320
                impl = self.adapt(type(self))
229
321
            # this can't be self, else we create a cycle
230
322
            assert impl is not self
231
 
            dialect._type_memos[self] = d = {'impl':impl}
 
323
            dialect._type_memos[self] = d = {'impl': impl}
232
324
            return d
233
325
 
234
326
    def _gen_dialect_impl(self, dialect):
244
336
        """
245
337
        return util.constructor_copy(self, cls, **kw)
246
338
 
247
 
    def _coerce_compared_value(self, op, value):
 
339
    def coerce_compared_value(self, op, value):
248
340
        """Suggest a type for a 'coerced' Python value in an expression.
249
341
 
250
342
        Given an operator and value, gives the type a chance
316
408
    def __repr__(self):
317
409
        return util.generic_repr(self)
318
410
 
 
411
 
 
412
def _reconstitute_comparator(expression):
 
413
    return expression.comparator
 
414
 
 
415
 
319
416
class UserDefinedType(TypeEngine):
320
417
    """Base for user defined types.
321
418
 
352
449
    """
353
450
    __visit_name__ = "user_defined"
354
451
 
355
 
    def _adapt_expression(self, op, othertype):
356
 
        """evaluate the return type of <self> <op> <othertype>,
357
 
        and apply any adaptations to the given operator.
358
 
 
359
 
        """
360
 
        return self.adapt_operator(op), self
361
 
 
362
 
    def adapt_operator(self, op):
363
 
        """A hook which allows the given operator to be adapted
364
 
        to something new.
365
 
 
366
 
        See also UserDefinedType._adapt_expression(), an as-yet-
367
 
        semi-public method with greater capability in this regard.
368
 
 
369
 
        """
370
 
        return op
 
452
    class Comparator(TypeEngine.Comparator):
 
453
        def _adapt_expression(self, op, other_comparator):
 
454
            if hasattr(self.type, 'adapt_operator'):
 
455
                util.warn_deprecated(
 
456
                    "UserDefinedType.adapt_operator is deprecated.  Create "
 
457
                     "a UserDefinedType.Comparator subclass instead which "
 
458
                     "generates the desired expression constructs, given a "
 
459
                     "particular operator."
 
460
                    )
 
461
                return self.type.adapt_operator(op), self.type
 
462
            else:
 
463
                return op, self.type
 
464
 
 
465
    comparator_factory = Comparator
 
466
 
 
467
    def coerce_compared_value(self, op, value):
 
468
        """Suggest a type for a 'coerced' Python value in an expression.
 
469
 
 
470
        Default behavior for :class:`.UserDefinedType` is the
 
471
        same as that of :class:`.TypeDecorator`; by default it returns
 
472
        ``self``, assuming the compared value should be coerced into
 
473
        the same type as this one.  See
 
474
        :meth:`.TypeDecorator.coerce_compared_value` for more detail.
 
475
 
 
476
        .. versionchanged:: 0.8 :meth:`.UserDefinedType.coerce_compared_value`
 
477
           now returns ``self`` by default, rather than falling onto the
 
478
           more fundamental behavior of
 
479
           :meth:`.TypeEngine.coerce_compared_value`.
 
480
 
 
481
        """
 
482
 
 
483
        return self
 
484
 
371
485
 
372
486
class TypeDecorator(TypeEngine):
373
487
    """Allows the creation of types which add additional functionality
477
591
                                 "type being decorated")
478
592
        self.impl = to_instance(self.__class__.impl, *args, **kwargs)
479
593
 
 
594
    coerce_to_is_types = (util.NoneType, )
 
595
    """Specify those Python types which should be coerced at the expression
 
596
    level to "IS <constant>" when compared using ``==`` (and same for
 
597
        ``IS NOT`` in conjunction with ``!=``.
 
598
 
 
599
    For most SQLAlchemy types, this includes ``NoneType``, as well as ``bool``.
 
600
 
 
601
    :class:`.TypeDecorator` modifies this list to only include ``NoneType``,
 
602
    as typedecorator implementations that deal with boolean types are common.
 
603
 
 
604
    Custom :class:`.TypeDecorator` classes can override this attribute to
 
605
    return an empty tuple, in which case no values will be coerced to
 
606
    constants.
 
607
 
 
608
    ..versionadded:: 0.8.2
 
609
        Added :attr:`.TypeDecorator.coerce_to_is_types` to allow for easier
 
610
        control of ``__eq__()`` ``__ne__()`` operations.
 
611
 
 
612
    """
 
613
 
 
614
    class Comparator(TypeEngine.Comparator):
 
615
        def operate(self, op, *other, **kwargs):
 
616
            kwargs['_python_is_types'] = self.expr.type.coerce_to_is_types
 
617
            return super(TypeDecorator.Comparator, self).operate(
 
618
                                                        op, *other, **kwargs)
 
619
 
 
620
        def reverse_operate(self, op, other, **kwargs):
 
621
            kwargs['_python_is_types'] = self.expr.type.coerce_to_is_types
 
622
            return super(TypeDecorator.Comparator, self).reverse_operate(
 
623
                                                        op, other, **kwargs)
 
624
 
 
625
    @property
 
626
    def comparator_factory(self):
 
627
        return type("TDComparator",
 
628
                    (TypeDecorator.Comparator, self.impl.comparator_factory),
 
629
                    {})
480
630
 
481
631
    def _gen_dialect_impl(self, dialect):
482
632
        """
507
657
        return self.impl._type_affinity
508
658
 
509
659
    def type_engine(self, dialect):
510
 
        """Return a dialect-specific :class:`.TypeEngine` instance for this :class:`.TypeDecorator`.
 
660
        """Return a dialect-specific :class:`.TypeEngine` instance
 
661
        for this :class:`.TypeDecorator`.
511
662
 
512
663
        In most cases this returns a dialect-adapted form of
513
664
        the :class:`.TypeEngine` type represented by ``self.impl``.
514
665
        Makes usage of :meth:`dialect_impl` but also traverses
515
666
        into wrapped :class:`.TypeDecorator` instances.
516
 
        Behavior can be customized here by overriding :meth:`load_dialect_impl`.
 
667
        Behavior can be customized here by overriding
 
668
        :meth:`load_dialect_impl`.
517
669
 
518
670
        """
519
671
        adapted = dialect.type_descriptor(self)
594
746
 
595
747
        raise NotImplementedError()
596
748
 
 
749
    @util.memoized_property
 
750
    def _has_bind_processor(self):
 
751
        """memoized boolean, check if process_bind_param is implemented.
 
752
 
 
753
        Allows the base process_bind_param to raise
 
754
        NotImplementedError without needing to test an expensive
 
755
        exception throw.
 
756
 
 
757
        """
 
758
 
 
759
        return self.__class__.process_bind_param.func_code \
 
760
            is not TypeDecorator.process_bind_param.func_code
 
761
 
597
762
    def bind_processor(self, dialect):
598
763
        """Provide a bound value processing function for the
599
764
        given :class:`.Dialect`.
613
778
        :meth:`result_processor` method of this class.
614
779
 
615
780
        """
616
 
        if self.__class__.process_bind_param.func_code \
617
 
            is not TypeDecorator.process_bind_param.func_code:
 
781
        if self._has_bind_processor:
618
782
            process_param = self.process_bind_param
619
783
            impl_processor = self.impl.bind_processor(dialect)
620
784
            if impl_processor:
629
793
        else:
630
794
            return self.impl.bind_processor(dialect)
631
795
 
 
796
    @util.memoized_property
 
797
    def _has_result_processor(self):
 
798
        """memoized boolean, check if process_result_value is implemented.
 
799
 
 
800
        Allows the base process_result_value to raise
 
801
        NotImplementedError without needing to test an expensive
 
802
        exception throw.
 
803
 
 
804
        """
 
805
        return self.__class__.process_result_value.func_code \
 
806
            is not TypeDecorator.process_result_value.func_code
 
807
 
632
808
    def result_processor(self, dialect, coltype):
633
 
        """Provide a result value processing function for the given :class:`.Dialect`.
 
809
        """Provide a result value processing function for the given
 
810
        :class:`.Dialect`.
634
811
 
635
812
        This is the method that fulfills the :class:`.TypeEngine`
636
813
        contract for result value conversion.   :class:`.TypeDecorator`
648
825
        :meth:`bind_processor` method of this class.
649
826
 
650
827
        """
651
 
        if self.__class__.process_result_value.func_code \
652
 
            is not TypeDecorator.process_result_value.func_code:
 
828
        if self._has_result_processor:
653
829
            process_value = self.process_result_value
654
830
            impl_processor = self.impl.result_processor(dialect,
655
831
                    coltype)
683
859
        """
684
860
        return self
685
861
 
686
 
    def _coerce_compared_value(self, op, value):
687
 
        """See :meth:`.TypeEngine._coerce_compared_value` for a description."""
688
 
 
689
 
        return self.coerce_compared_value(op, value)
690
 
 
691
862
    def copy(self):
692
863
        """Produce a copy of this :class:`.TypeDecorator` instance.
693
864
 
703
874
        return instance
704
875
 
705
876
    def get_dbapi_type(self, dbapi):
706
 
        """Return the DBAPI type object represented by this :class:`.TypeDecorator`.
 
877
        """Return the DBAPI type object represented by this
 
878
        :class:`.TypeDecorator`.
707
879
 
708
880
        By default this calls upon :meth:`.TypeEngine.get_dbapi_type` of the
709
881
        underlying "impl".
710
882
        """
711
883
        return self.impl.get_dbapi_type(dbapi)
712
884
 
713
 
    def copy_value(self, value):
714
 
        """Given a value, produce a copy of it.
715
 
 
716
 
        By default this calls upon :meth:`.TypeEngine.copy_value`
717
 
        of the underlying "impl".
718
 
 
719
 
        :meth:`.copy_value` will return the object
720
 
        itself, assuming "mutability" is not enabled.
721
 
        Only the :class:`.MutableType` mixin provides a copy
722
 
        function that actually produces a new object.
723
 
        The copying function is used by the ORM when
724
 
        "mutable" types are used, to memoize the original
725
 
        version of an object as loaded from the database,
726
 
        which is then compared to the possibly mutated
727
 
        version to check for changes.
728
 
 
729
 
        Modern implementations should use the
730
 
        ``sqlalchemy.ext.mutable`` extension described in
731
 
        :ref:`mutable_toplevel` for intercepting in-place
732
 
        changes to values.
733
 
 
734
 
        """
735
 
        return self.impl.copy_value(value)
736
 
 
737
885
    def compare_values(self, x, y):
738
886
        """Given two values, compare them for equality.
739
887
 
749
897
        """
750
898
        return self.impl.compare_values(x, y)
751
899
 
752
 
    def is_mutable(self):
753
 
        """Return True if the target Python type is 'mutable'.
754
 
 
755
 
        This allows systems like the ORM to know if a column value can
756
 
        be considered 'not changed' by comparing the identity of
757
 
        objects alone.  Values such as dicts, lists which
758
 
        are serialized into strings are examples of "mutable"
759
 
        column structures.
760
 
 
761
 
        .. note::
762
 
 
763
 
           This functionality is now superseded by the
764
 
           ``sqlalchemy.ext.mutable`` extension described in
765
 
           :ref:`mutable_toplevel`.
766
 
 
767
 
        """
768
 
        return self.impl.is_mutable()
769
 
 
770
 
    def _adapt_expression(self, op, othertype):
771
 
        """
772
 
        #todo
773
 
        """
774
 
        op, typ =self.impl._adapt_expression(op, othertype)
775
 
        if typ is self.impl:
776
 
            return op, self
777
 
        else:
778
 
            return op, typ
 
900
    def __repr__(self):
 
901
        return util.generic_repr(self, to_inspect=self.impl)
 
902
 
779
903
 
780
904
class Variant(TypeDecorator):
781
905
    """A wrapping type that selects among a variety of
792
916
        """Construct a new :class:`.Variant`.
793
917
 
794
918
        :param base: the base 'fallback' type
795
 
        :param mapping: dictionary of string dialect names to :class:`.TypeEngine`
796
 
         instances.
 
919
        :param mapping: dictionary of string dialect names to
 
920
          :class:`.TypeEngine` instances.
797
921
 
798
922
        """
799
923
        self.impl = base
826
950
        mapping[dialect_name] = type_
827
951
        return Variant(self.impl, mapping)
828
952
 
829
 
class MutableType(object):
830
 
    """A mixin that marks a :class:`.TypeEngine` as representing
831
 
    a mutable Python object type.   This functionality is used
832
 
    only by the ORM.
833
 
 
834
 
    .. versionchanged:: 0.7
835
 
       :class:`.MutableType` is superseded
836
 
       by the ``sqlalchemy.ext.mutable`` extension described in
837
 
       :ref:`mutable_toplevel`.   This extension provides an event
838
 
       driven approach to in-place mutation detection that does not
839
 
       incur the severe performance penalty of the :class:`.MutableType`
840
 
       approach.
841
 
 
842
 
    "mutable" means that changes can occur in place to a value
843
 
    of this type.   Examples includes Python lists, dictionaries,
844
 
    and sets, as well as user-defined objects.  The primary
845
 
    need for identification of "mutable" types is by the ORM,
846
 
    which applies special rules to such values in order to guarantee
847
 
    that changes are detected.  These rules may have a significant
848
 
    performance impact, described below.
849
 
 
850
 
    A :class:`.MutableType` usually allows a flag called
851
 
    ``mutable=False`` to enable/disable the "mutability" flag,
852
 
    represented on this class by :meth:`is_mutable`.  Examples
853
 
    include :class:`.PickleType` and
854
 
    :class:`~sqlalchemy.dialects.postgresql.base.ARRAY`.  Setting
855
 
    this flag to ``True`` enables mutability-specific behavior
856
 
    by the ORM.
857
 
 
858
 
    The :meth:`copy_value` and :meth:`compare_values` functions
859
 
    represent a copy and compare function for values of this
860
 
    type - implementing subclasses should override these
861
 
    appropriately.
862
 
 
863
 
    .. warning::
864
 
 
865
 
        The usage of mutable types has significant performance
866
 
        implications when using the ORM. In order to detect changes, the
867
 
        ORM must create a copy of the value when it is first
868
 
        accessed, so that changes to the current value can be compared
869
 
        against the "clean" database-loaded value. Additionally, when the
870
 
        ORM checks to see if any data requires flushing, it must scan
871
 
        through all instances in the session which are known to have
872
 
        "mutable" attributes and compare the current value of each
873
 
        one to its "clean"
874
 
        value. So for example, if the Session contains 6000 objects (a
875
 
        fairly large amount) and autoflush is enabled, every individual
876
 
        execution of :class:`.Query` will require a full scan of that subset of
877
 
        the 6000 objects that have mutable attributes, possibly resulting
878
 
        in tens of thousands of additional method calls for every query.
879
 
 
880
 
        .. versionchanged:: 0.7
881
 
            As of SQLAlchemy 0.7, the ``sqlalchemy.ext.mutable`` is provided
882
 
            which allows an event driven approach to in-place
883
 
            mutation detection. This approach should now be favored over
884
 
            the usage of :class:`.MutableType` with ``mutable=True``.
885
 
            ``sqlalchemy.ext.mutable`` is described in :ref:`mutable_toplevel`.
886
 
 
887
 
    """
888
 
 
889
 
    def is_mutable(self):
890
 
        """Return True if the target Python type is 'mutable'.
891
 
 
892
 
        For :class:`.MutableType`, this method is set to
893
 
        return ``True``.
894
 
 
895
 
        """
896
 
        return True
897
 
 
898
 
    def copy_value(self, value):
899
 
        """Unimplemented."""
900
 
        raise NotImplementedError()
901
 
 
902
 
    def compare_values(self, x, y):
903
 
        """Compare *x* == *y*."""
904
 
        return x == y
905
953
 
906
954
def to_instance(typeobj, *arg, **kw):
907
955
    if typeobj is None:
912
960
    else:
913
961
        return typeobj
914
962
 
 
963
 
915
964
def adapt_type(typeobj, colspecs):
916
965
    if isinstance(typeobj, type):
917
966
        typeobj = typeobj()
934
983
    return typeobj.adapt(impltype)
935
984
 
936
985
 
937
 
 
938
 
 
939
986
class NullType(TypeEngine):
940
987
    """An unknown type.
941
988
 
951
998
    """
952
999
    __visit_name__ = 'null'
953
1000
 
954
 
    def _adapt_expression(self, op, othertype):
955
 
        if isinstance(othertype, NullType) or not operators.is_commutative(op):
956
 
            return op, self
957
 
        else:
958
 
            return othertype._adapt_expression(op, self)
 
1001
    class Comparator(TypeEngine.Comparator):
 
1002
        def _adapt_expression(self, op, other_comparator):
 
1003
            if isinstance(other_comparator, NullType.Comparator) or \
 
1004
                not operators.is_commutative(op):
 
1005
                return op, self.expr.type
 
1006
            else:
 
1007
                return other_comparator._adapt_expression(op, self)
 
1008
    comparator_factory = Comparator
959
1009
 
960
1010
NullTypeEngine = NullType
961
1011
 
 
1012
 
962
1013
class Concatenable(object):
963
1014
    """A mixin that marks a type as supporting 'concatenation',
964
1015
    typically strings."""
965
1016
 
966
 
    def _adapt_expression(self, op, othertype):
967
 
        if op is operators.add and issubclass(othertype._type_affinity,
968
 
                (Concatenable, NullType)):
969
 
            return operators.concat_op, self
970
 
        else:
971
 
            return op, self
 
1017
    class Comparator(TypeEngine.Comparator):
 
1018
        def _adapt_expression(self, op, other_comparator):
 
1019
            if op is operators.add and isinstance(other_comparator,
 
1020
                    (Concatenable.Comparator, NullType.Comparator)):
 
1021
                return operators.concat_op, self.expr.type
 
1022
            else:
 
1023
                return op, self.expr.type
 
1024
 
 
1025
    comparator_factory = Comparator
 
1026
 
972
1027
 
973
1028
class _DateAffinity(object):
974
1029
    """Mixin date/time specific expression adaptations.
983
1038
    def _expression_adaptations(self):
984
1039
        raise NotImplementedError()
985
1040
 
986
 
    _blank_dict = util.immutabledict()
987
 
    def _adapt_expression(self, op, othertype):
988
 
        othertype = othertype._type_affinity
989
 
        return op, \
990
 
                self._expression_adaptations.get(op, self._blank_dict).\
991
 
                get(othertype, NULLTYPE)
 
1041
    class Comparator(TypeEngine.Comparator):
 
1042
        _blank_dict = util.immutabledict()
 
1043
 
 
1044
        def _adapt_expression(self, op, other_comparator):
 
1045
            othertype = other_comparator.type._type_affinity
 
1046
            return op, \
 
1047
                    self.type._expression_adaptations.get(op, self._blank_dict).\
 
1048
                    get(othertype, NULLTYPE)
 
1049
    comparator_factory = Comparator
 
1050
 
992
1051
 
993
1052
class String(Concatenable, TypeEngine):
994
1053
    """The base for all string and character types.
1005
1064
 
1006
1065
    __visit_name__ = 'string'
1007
1066
 
1008
 
    def __init__(self, length=None, convert_unicode=False,
1009
 
                        assert_unicode=None, unicode_error=None,
 
1067
    def __init__(self, length=None, collation=None,
 
1068
                        convert_unicode=False,
 
1069
                        unicode_error=None,
1010
1070
                        _warn_on_bytestring=False
1011
1071
                        ):
1012
1072
        """
1013
1073
        Create a string-holding type.
1014
1074
 
1015
1075
        :param length: optional, a length for the column for use in
1016
 
          DDL statements.  May be safely omitted if no ``CREATE
 
1076
          DDL and CAST expressions.  May be safely omitted if no ``CREATE
1017
1077
          TABLE`` will be issued.  Certain databases may require a
1018
1078
          ``length`` for use in DDL, and will raise an exception when
1019
1079
          the ``CREATE TABLE`` DDL is issued if a ``VARCHAR``
1020
1080
          with no length is included.  Whether the value is
1021
1081
          interpreted as bytes or characters is database specific.
1022
1082
 
 
1083
        :param collation: Optional, a column-level collation for
 
1084
          use in DDL and CAST expressions.  Renders using the
 
1085
          COLLATE keyword supported by SQLite, MySQL, and Postgresql.
 
1086
          E.g.::
 
1087
 
 
1088
            >>> from sqlalchemy import cast, select, String
 
1089
            >>> print select([cast('some string', String(collation='utf8'))])
 
1090
            SELECT CAST(:param_1 AS VARCHAR COLLATE utf8) AS anon_1
 
1091
 
 
1092
          .. versionadded:: 0.8 Added support for COLLATE to all
 
1093
             string types.
 
1094
 
1023
1095
        :param convert_unicode: When set to ``True``, the
1024
1096
          :class:`.String` type will assume that
1025
1097
          input is to be passed as Python ``unicode`` objects,
1047
1119
          cause SQLAlchemy's encode/decode services to be
1048
1120
          used unconditionally.
1049
1121
 
1050
 
        :param assert_unicode: Deprecated.  A warning is emitted
1051
 
          when a non-``unicode`` object is passed to the
1052
 
          :class:`.Unicode` subtype of :class:`.String`,
1053
 
          or the :class:`.UnicodeText` subtype of :class:`.Text`.
1054
 
          See :class:`.Unicode` for information on how to
1055
 
          control this warning.
1056
 
 
1057
1122
        :param unicode_error: Optional, a method to use to handle Unicode
1058
1123
          conversion errors. Behaves like the ``errors`` keyword argument to
1059
1124
          the standard library's ``string.decode()`` functions.   This flag
1070
1135
            raise exc.ArgumentError("convert_unicode must be 'force' "
1071
1136
                                        "when unicode_error is set.")
1072
1137
 
1073
 
        if assert_unicode:
1074
 
            util.warn_deprecated('assert_unicode is deprecated. '
1075
 
                                 'SQLAlchemy emits a warning in all '
1076
 
                                 'cases where it would otherwise like '
1077
 
                                 'to encode a Python unicode object '
1078
 
                                 'into a specific encoding but a plain '
1079
 
                                 'bytestring is received. This does '
1080
 
                                 '*not* apply to DBAPIs that coerce '
1081
 
                                 'Unicode natively.')
1082
1138
        self.length = length
 
1139
        self.collation = collation
1083
1140
        self.convert_unicode = convert_unicode
1084
1141
        self.unicode_error = unicode_error
1085
1142
        self._warn_on_bytestring = _warn_on_bytestring
1104
1161
            else:
1105
1162
                encoder = codecs.getencoder(dialect.encoding)
1106
1163
                warn_on_bytestring = self._warn_on_bytestring
 
1164
 
1107
1165
                def process(value):
1108
1166
                    if isinstance(value, unicode):
1109
1167
                        return encoder(value, self.unicode_error)[0]
1153
1211
    def get_dbapi_type(self, dbapi):
1154
1212
        return dbapi.STRING
1155
1213
 
 
1214
 
1156
1215
class Text(String):
1157
1216
    """A variably sized string type.
1158
1217
 
1159
1218
    In SQL, usually corresponds to CLOB or TEXT. Can also take Python
1160
1219
    unicode objects and encode to the database's encoding in bind
1161
 
    params (and the reverse for result sets.)
 
1220
    params (and the reverse for result sets.)  In general, TEXT objects
 
1221
    do not have a length; while some databases will accept a length
 
1222
    argument here, it will be rejected by others.
1162
1223
 
1163
1224
    """
1164
1225
    __visit_name__ = 'text'
1165
1226
 
 
1227
 
1166
1228
class Unicode(String):
1167
1229
    """A variable length Unicode string type.
1168
1230
 
1233
1295
        kwargs.setdefault('_warn_on_bytestring', True)
1234
1296
        super(Unicode, self).__init__(length=length, **kwargs)
1235
1297
 
 
1298
 
1236
1299
class UnicodeText(Text):
1237
1300
    """An unbounded-length Unicode string type.
1238
1301
 
1278
1341
        # TODO: need a dictionary object that will
1279
1342
        # handle operators generically here, this is incomplete
1280
1343
        return {
1281
 
            operators.add:{
1282
 
                Date:Date,
1283
 
                Integer:Integer,
1284
 
                Numeric:Numeric,
 
1344
            operators.add: {
 
1345
                Date: Date,
 
1346
                Integer: self.__class__,
 
1347
                Numeric: Numeric,
1285
1348
            },
1286
 
            operators.mul:{
1287
 
                Interval:Interval,
1288
 
                Integer:Integer,
1289
 
                Numeric:Numeric,
 
1349
            operators.mul: {
 
1350
                Interval: Interval,
 
1351
                Integer: self.__class__,
 
1352
                Numeric: Numeric,
1290
1353
            },
1291
1354
            # Py2K
1292
 
            operators.div:{
1293
 
                Integer:Integer,
1294
 
                Numeric:Numeric,
 
1355
            operators.div: {
 
1356
                Integer: self.__class__,
 
1357
                Numeric: Numeric,
1295
1358
            },
1296
1359
            # end Py2K
1297
 
            operators.truediv:{
1298
 
                Integer:Integer,
1299
 
                Numeric:Numeric,
 
1360
            operators.truediv: {
 
1361
                Integer: self.__class__,
 
1362
                Numeric: Numeric,
1300
1363
            },
1301
 
            operators.sub:{
1302
 
                Integer:Integer,
1303
 
                Numeric:Numeric,
 
1364
            operators.sub: {
 
1365
                Integer: self.__class__,
 
1366
                Numeric: Numeric,
1304
1367
            },
1305
1368
        }
1306
1369
 
 
1370
 
1307
1371
class SmallInteger(Integer):
1308
1372
    """A type for smaller ``int`` integers.
1309
1373
 
1343
1407
       implementations however, most of which contain an import for plain
1344
1408
       ``decimal`` in their source code, even though some such as psycopg2
1345
1409
       provide hooks for alternate adapters. SQLAlchemy imports ``decimal``
1346
 
       globally as well. While the alternate ``Decimal`` class can be patched
1347
 
       into SQLA's ``decimal`` module, overall the most straightforward and
 
1410
       globally as well.  The most straightforward and
1348
1411
       foolproof way to use "cdecimal" given current DBAPI and Python support
1349
1412
       is to patch it directly into sys.modules before anything else is
1350
1413
       imported::
1453
1516
    @util.memoized_property
1454
1517
    def _expression_adaptations(self):
1455
1518
        return {
1456
 
            operators.mul:{
1457
 
                Interval:Interval,
1458
 
                Numeric:Numeric,
1459
 
                Integer:Numeric,
 
1519
            operators.mul: {
 
1520
                Interval: Interval,
 
1521
                Numeric: self.__class__,
 
1522
                Integer: self.__class__,
1460
1523
            },
1461
1524
            # Py2K
1462
 
            operators.div:{
1463
 
                Numeric:Numeric,
1464
 
                Integer:Numeric,
 
1525
            operators.div: {
 
1526
                Numeric: self.__class__,
 
1527
                Integer: self.__class__,
1465
1528
            },
1466
1529
            # end Py2K
1467
 
            operators.truediv:{
1468
 
                Numeric:Numeric,
1469
 
                Integer:Numeric,
1470
 
            },
1471
 
            operators.add:{
1472
 
                Numeric:Numeric,
1473
 
                Integer:Numeric,
1474
 
            },
1475
 
            operators.sub:{
1476
 
                Numeric:Numeric,
1477
 
                Integer:Numeric,
 
1530
            operators.truediv: {
 
1531
                Numeric: self.__class__,
 
1532
                Integer: self.__class__,
 
1533
            },
 
1534
            operators.add: {
 
1535
                Numeric: self.__class__,
 
1536
                Integer: self.__class__,
 
1537
            },
 
1538
            operators.sub: {
 
1539
                Numeric: self.__class__,
 
1540
                Integer: self.__class__,
1478
1541
            }
1479
1542
        }
1480
1543
 
 
1544
 
1481
1545
class Float(Numeric):
1482
1546
    """A type for ``float`` numbers.
1483
1547
 
1504
1568
        :param \**kwargs: deprecated.  Additional arguments here are ignored
1505
1569
         by the default :class:`.Float` type.  For database specific
1506
1570
         floats that support additional arguments, see that dialect's
1507
 
         documentation for details, such as :class:`sqlalchemy.dialects.mysql.FLOAT`.
 
1571
         documentation for details, such as
 
1572
         :class:`sqlalchemy.dialects.mysql.FLOAT`.
1508
1573
 
1509
1574
        """
1510
1575
        self.precision = precision
1522
1587
    @util.memoized_property
1523
1588
    def _expression_adaptations(self):
1524
1589
        return {
1525
 
            operators.mul:{
1526
 
                Interval:Interval,
1527
 
                Numeric:Float,
 
1590
            operators.mul: {
 
1591
                Interval: Interval,
 
1592
                Numeric: self.__class__,
1528
1593
            },
1529
1594
            # Py2K
1530
 
            operators.div:{
1531
 
                Numeric:Float,
 
1595
            operators.div: {
 
1596
                Numeric: self.__class__,
1532
1597
            },
1533
1598
            # end Py2K
1534
 
            operators.truediv:{
1535
 
                Numeric:Float,
1536
 
            },
1537
 
            operators.add:{
1538
 
                Numeric:Float,
1539
 
            },
1540
 
            operators.sub:{
1541
 
                Numeric:Float,
 
1599
            operators.truediv: {
 
1600
                Numeric: self.__class__,
 
1601
            },
 
1602
            operators.add: {
 
1603
                Numeric: self.__class__,
 
1604
            },
 
1605
            operators.sub: {
 
1606
                Numeric: self.__class__,
1542
1607
            }
1543
1608
        }
1544
1609
 
1577
1642
    @util.memoized_property
1578
1643
    def _expression_adaptations(self):
1579
1644
        return {
1580
 
            operators.add:{
1581
 
                Interval:DateTime,
 
1645
            operators.add: {
 
1646
                Interval: self.__class__,
1582
1647
            },
1583
 
            operators.sub:{
1584
 
                Interval:DateTime,
1585
 
                DateTime:Interval,
 
1648
            operators.sub: {
 
1649
                Interval: self.__class__,
 
1650
                DateTime: Interval,
1586
1651
            },
1587
1652
        }
1588
1653
 
1589
1654
 
1590
 
class Date(_DateAffinity,TypeEngine):
 
1655
class Date(_DateAffinity, TypeEngine):
1591
1656
    """A type for ``datetime.date()`` objects."""
1592
1657
 
1593
1658
    __visit_name__ = 'date'
1602
1667
    @util.memoized_property
1603
1668
    def _expression_adaptations(self):
1604
1669
        return {
1605
 
            operators.add:{
1606
 
                Integer:Date,
1607
 
                Interval:DateTime,
1608
 
                Time:DateTime,
 
1670
            operators.add: {
 
1671
                Integer: self.__class__,
 
1672
                Interval: DateTime,
 
1673
                Time: DateTime,
1609
1674
            },
1610
 
            operators.sub:{
 
1675
            operators.sub: {
1611
1676
                # date - integer = date
1612
 
                Integer:Date,
 
1677
                Integer: self.__class__,
1613
1678
 
1614
1679
                # date - date = integer.
1615
 
                Date:Integer,
 
1680
                Date: Integer,
1616
1681
 
1617
 
                Interval:DateTime,
 
1682
                Interval: DateTime,
1618
1683
 
1619
1684
                # date - datetime = interval,
1620
1685
                # this one is not in the PG docs
1621
1686
                # but works
1622
 
                DateTime:Interval,
 
1687
                DateTime: Interval,
1623
1688
            },
1624
1689
        }
1625
1690
 
1626
1691
 
1627
 
class Time(_DateAffinity,TypeEngine):
 
1692
class Time(_DateAffinity, TypeEngine):
1628
1693
    """A type for ``datetime.time()`` objects."""
1629
1694
 
1630
1695
    __visit_name__ = 'time'
1642
1707
    @util.memoized_property
1643
1708
    def _expression_adaptations(self):
1644
1709
        return {
1645
 
            operators.add:{
1646
 
                Date:DateTime,
1647
 
                Interval:Time
 
1710
            operators.add: {
 
1711
                Date: DateTime,
 
1712
                Interval: self.__class__
1648
1713
            },
1649
 
            operators.sub:{
1650
 
                Time:Interval,
1651
 
                Interval:Time,
 
1714
            operators.sub: {
 
1715
                Time: Interval,
 
1716
                Interval: self.__class__,
1652
1717
            },
1653
1718
        }
1654
1719
 
1671
1736
    # here, though pg8000 does to indicate "bytea"
1672
1737
    def bind_processor(self, dialect):
1673
1738
        DBAPIBinary = dialect.dbapi.Binary
 
1739
 
1674
1740
        def process(value):
1675
1741
            x = self
1676
1742
            if value is not None:
1680
1746
        return process
1681
1747
 
1682
1748
    # Python 3 has native bytes() type
1683
 
    # both sqlite3 and pg8000 seem to return it
1684
 
    # (i.e. and not 'memoryview')
 
1749
    # both sqlite3 and pg8000 seem to return it,
 
1750
    # psycopg2 as of 2.5 returns 'memoryview'
 
1751
    # Py3K
 
1752
    #def result_processor(self, dialect, coltype):
 
1753
    #    def process(value):
 
1754
    #        if value is not None:
 
1755
    #            value = bytes(value)
 
1756
    #        return value
 
1757
    #    return process
1685
1758
    # Py2K
1686
1759
    def result_processor(self, dialect, coltype):
1687
1760
        if util.jython:
1697
1770
        return process
1698
1771
    # end Py2K
1699
1772
 
1700
 
    def _coerce_compared_value(self, op, value):
1701
 
        """See :meth:`.TypeEngine._coerce_compared_value` for a description."""
 
1773
    def coerce_compared_value(self, op, value):
 
1774
        """See :meth:`.TypeEngine.coerce_compared_value` for a description."""
1702
1775
 
1703
1776
        if isinstance(value, basestring):
1704
1777
            return self
1705
1778
        else:
1706
 
            return super(_Binary, self)._coerce_compared_value(op, value)
 
1779
            return super(_Binary, self).coerce_compared_value(op, value)
1707
1780
 
1708
1781
    def get_dbapi_type(self, dbapi):
1709
1782
        return dbapi.BINARY
1710
1783
 
 
1784
 
1711
1785
class LargeBinary(_Binary):
1712
1786
    """A type for large binary byte data.
1713
1787
 
1735
1809
        """
1736
1810
        _Binary.__init__(self, length=length)
1737
1811
 
 
1812
 
1738
1813
class Binary(LargeBinary):
1739
1814
    """Deprecated.  Renamed to LargeBinary."""
1740
1815
 
1743
1818
                             'LargeBinary.')
1744
1819
        LargeBinary.__init__(self, *arg, **kw)
1745
1820
 
 
1821
 
1746
1822
class SchemaType(events.SchemaEventTarget):
1747
1823
    """Mark a type as possibly requiring schema-level DDL for usage.
1748
1824
 
1751
1827
    constraints, triggers, and other rules.
1752
1828
 
1753
1829
    :class:`.SchemaType` classes can also be targets for the
1754
 
    :meth:`.DDLEvents.before_parent_attach` and :meth:`.DDLEvents.after_parent_attach`
1755
 
    events, where the events fire off surrounding the association of
1756
 
    the type object with a parent :class:`.Column`.
 
1830
    :meth:`.DDLEvents.before_parent_attach` and
 
1831
    :meth:`.DDLEvents.after_parent_attach` events, where the events fire off
 
1832
    surrounding the association of the type object with a parent
 
1833
    :class:`.Column`.
 
1834
 
 
1835
    .. seealso::
 
1836
 
 
1837
        :class:`.Enum`
 
1838
 
 
1839
        :class:`.Boolean`
 
1840
 
1757
1841
 
1758
1842
    """
1759
1843
 
1762
1846
        self.quote = kw.pop('quote', None)
1763
1847
        self.schema = kw.pop('schema', None)
1764
1848
        self.metadata = kw.pop('metadata', None)
 
1849
        self.inherit_schema = kw.pop('inherit_schema', False)
1765
1850
        if self.metadata:
1766
1851
            event.listen(
1767
1852
                self.metadata,
1778
1863
        column._on_table_attach(util.portable_instancemethod(self._set_table))
1779
1864
 
1780
1865
    def _set_table(self, column, table):
 
1866
        if self.inherit_schema:
 
1867
            self.schema = table.schema
 
1868
 
1781
1869
        event.listen(
1782
1870
            table,
1783
1871
            "before_create",
1803
1891
                util.portable_instancemethod(self._on_metadata_drop)
1804
1892
            )
1805
1893
 
 
1894
    def copy(self, **kw):
 
1895
        return self.adapt(self.__class__)
 
1896
 
 
1897
    def adapt(self, impltype, **kw):
 
1898
        schema = kw.pop('schema', self.schema)
 
1899
        metadata = kw.pop('metadata', self.metadata)
 
1900
        return impltype(name=self.name,
 
1901
                    quote=self.quote,
 
1902
                    schema=schema,
 
1903
                    metadata=metadata,
 
1904
                    inherit_schema=self.inherit_schema,
 
1905
                    **kw
 
1906
                    )
 
1907
 
1806
1908
    @property
1807
1909
    def bind(self):
1808
1910
        return self.metadata and self.metadata.bind or None
1845
1947
        if t.__class__ is not self.__class__ and isinstance(t, SchemaType):
1846
1948
            t._on_metadata_drop(target, bind, **kw)
1847
1949
 
 
1950
 
1848
1951
class Enum(String, SchemaType):
1849
1952
    """Generic Enum Type.
1850
1953
 
1854
1957
    By default, uses the backend's native ENUM type if available,
1855
1958
    else uses VARCHAR + a CHECK constraint.
1856
1959
 
1857
 
    See also:
 
1960
    .. seealso::
1858
1961
 
1859
1962
        :class:`~.postgresql.ENUM` - PostgreSQL-specific type,
1860
1963
        which has additional functionality.
1896
1999
           available. Defaults to True. When False, uses VARCHAR + check
1897
2000
           constraint for all backends.
1898
2001
 
1899
 
        :param schema: Schemaname of this type. For types that exist on the
 
2002
        :param schema: Schema name of this type. For types that exist on the
1900
2003
           target database as an independent schema construct (Postgresql),
1901
2004
           this parameter specifies the named schema in which the type is
1902
2005
           present.
1903
2006
 
 
2007
           .. note::
 
2008
 
 
2009
                The ``schema`` of the :class:`.Enum` type does not
 
2010
                by default make use of the ``schema`` established on the
 
2011
                owning :class:`.Table`.  If this behavior is desired,
 
2012
                set the ``inherit_schema`` flag to ``True``.
 
2013
 
1904
2014
        :param quote: Force quoting to be on or off on the type's name. If
1905
2015
           left as the default of `None`, the usual schema-level "case
1906
2016
           sensitive"/"reserved name" rules are used to determine if this
1907
2017
           type's name should be quoted.
1908
2018
 
 
2019
        :param inherit_schema: When ``True``, the "schema" from the owning
 
2020
           :class:`.Table` will be copied to the "schema" attribute of this
 
2021
           :class:`.Enum`, replacing whatever value was passed for the
 
2022
           ``schema`` attribute.   This also takes effect when using the
 
2023
           :meth:`.Table.tometadata` operation.
 
2024
 
 
2025
           .. versionadded:: 0.8
 
2026
 
1909
2027
        """
1910
2028
        self.enums = enums
1911
2029
        self.native_enum = kw.pop('native_enum', True)
1942
2060
        if self.native_enum:
1943
2061
            SchemaType._set_table(self, column, table)
1944
2062
 
1945
 
 
1946
2063
        e = schema.CheckConstraint(
1947
2064
                        column.in_(self.enums),
1948
2065
                        name=self.name,
1952
2069
        table.append_constraint(e)
1953
2070
 
1954
2071
    def adapt(self, impltype, **kw):
 
2072
        schema = kw.pop('schema', self.schema)
 
2073
        metadata = kw.pop('metadata', self.metadata)
1955
2074
        if issubclass(impltype, Enum):
1956
2075
            return impltype(name=self.name,
1957
2076
                        quote=self.quote,
1958
 
                        schema=self.schema,
1959
 
                        metadata=self.metadata,
 
2077
                        schema=schema,
 
2078
                        metadata=metadata,
1960
2079
                        convert_unicode=self.convert_unicode,
1961
2080
                        native_enum=self.native_enum,
 
2081
                        inherit_schema=self.inherit_schema,
1962
2082
                        *self.enums,
1963
2083
                        **kw
1964
2084
                        )
1965
2085
        else:
1966
2086
            return super(Enum, self).adapt(impltype, **kw)
1967
2087
 
1968
 
class PickleType(MutableType, TypeDecorator):
 
2088
 
 
2089
class PickleType(TypeDecorator):
1969
2090
    """Holds Python objects, which are serialized using pickle.
1970
2091
 
1971
2092
    PickleType builds upon the Binary type to apply Python's
1973
2094
    the way out, allowing any pickleable Python object to be stored as
1974
2095
    a serialized binary field.
1975
2096
 
 
2097
    To allow ORM change events to propagate for elements associated
 
2098
    with :class:`.PickleType`, see :ref:`mutable_toplevel`.
 
2099
 
1976
2100
    """
1977
2101
 
1978
2102
    impl = LargeBinary
1979
2103
 
1980
2104
    def __init__(self, protocol=pickle.HIGHEST_PROTOCOL,
1981
 
                    pickler=None, mutable=False, comparator=None):
 
2105
                    pickler=None, comparator=None):
1982
2106
        """
1983
2107
        Construct a PickleType.
1984
2108
 
1988
2112
          cPickle is not available.  May be any object with
1989
2113
          pickle-compatible ``dumps` and ``loads`` methods.
1990
2114
 
1991
 
        :param mutable: defaults to False; implements
1992
 
          :meth:`AbstractType.is_mutable`.   When ``True``, incoming
1993
 
          objects will be compared against copies of themselves
1994
 
          using the Python "equals" operator, unless the
1995
 
          ``comparator`` argument is present.   See
1996
 
          :class:`.MutableType` for details on "mutable" type
1997
 
          behavior.
1998
 
 
1999
 
          .. versionchanged:: 0.7.0
2000
 
              Default changed from ``True``.
2001
 
 
2002
 
          .. note::
2003
 
 
2004
 
             This functionality is now superseded by the
2005
 
             ``sqlalchemy.ext.mutable`` extension described in
2006
 
             :ref:`mutable_toplevel`.
2007
 
 
2008
2115
        :param comparator: a 2-arg callable predicate used
2009
2116
          to compare values of this type.  If left as ``None``,
2010
2117
          the Python "equals" operator is used to compare values.
2012
2119
        """
2013
2120
        self.protocol = protocol
2014
2121
        self.pickler = pickler or pickle
2015
 
        self.mutable = mutable
2016
2122
        self.comparator = comparator
2017
2123
        super(PickleType, self).__init__()
2018
2124
 
2019
2125
    def __reduce__(self):
2020
2126
        return PickleType, (self.protocol,
2021
2127
                            None,
2022
 
                            self.mutable,
2023
2128
                            self.comparator)
2024
2129
 
2025
2130
    def bind_processor(self, dialect):
2054
2159
                return loads(value)
2055
2160
        return process
2056
2161
 
2057
 
    def copy_value(self, value):
2058
 
        if self.mutable:
2059
 
            return self.pickler.loads(
2060
 
                        self.pickler.dumps(value, self.protocol))
2061
 
        else:
2062
 
            return value
2063
 
 
2064
2162
    def compare_values(self, x, y):
2065
2163
        if self.comparator:
2066
2164
            return self.comparator(x, y)
2067
2165
        else:
2068
2166
            return x == y
2069
2167
 
2070
 
    def is_mutable(self):
2071
 
        """Return True if the target Python type is 'mutable'.
2072
 
 
2073
 
        When this method is overridden, :meth:`copy_value` should
2074
 
        also be supplied.   The :class:`.MutableType` mixin
2075
 
        is recommended as a helper.
2076
 
 
2077
 
        """
2078
 
        return self.mutable
2079
 
 
2080
2168
 
2081
2169
class Boolean(TypeEngine, SchemaType):
2082
2170
    """A bool datatype.
2133
2221
        else:
2134
2222
            return processors.int_to_boolean
2135
2223
 
 
2224
 
2136
2225
class Interval(_DateAffinity, TypeDecorator):
2137
2226
    """A type for ``datetime.timedelta()`` objects.
2138
2227
 
2225
2314
    @util.memoized_property
2226
2315
    def _expression_adaptations(self):
2227
2316
        return {
2228
 
            operators.add:{
2229
 
                Date:DateTime,
2230
 
                Interval:Interval,
2231
 
                DateTime:DateTime,
2232
 
                Time:Time,
2233
 
            },
2234
 
            operators.sub:{
2235
 
                Interval:Interval
2236
 
            },
2237
 
            operators.mul:{
2238
 
                Numeric:Interval
 
2317
            operators.add: {
 
2318
                Date: DateTime,
 
2319
                Interval: self.__class__,
 
2320
                DateTime: DateTime,
 
2321
                Time: Time,
 
2322
            },
 
2323
            operators.sub: {
 
2324
                Interval: self.__class__
 
2325
            },
 
2326
            operators.mul: {
 
2327
                Numeric: self.__class__
2239
2328
            },
2240
2329
            operators.truediv: {
2241
 
                Numeric:Interval
 
2330
                Numeric: self.__class__
2242
2331
            },
2243
2332
            # Py2K
2244
2333
            operators.div: {
2245
 
                Numeric:Interval
 
2334
                Numeric: self.__class__
2246
2335
            }
2247
2336
            # end Py2K
2248
2337
        }
2251
2340
    def _type_affinity(self):
2252
2341
        return Interval
2253
2342
 
2254
 
    def _coerce_compared_value(self, op, value):
2255
 
        """See :meth:`.TypeEngine._coerce_compared_value` for a description."""
 
2343
    def coerce_compared_value(self, op, value):
 
2344
        """See :meth:`.TypeEngine.coerce_compared_value` for a description."""
2256
2345
 
2257
 
        return self.impl._coerce_compared_value(op, value)
 
2346
        return self.impl.coerce_compared_value(op, value)
2258
2347
 
2259
2348
 
2260
2349
class REAL(Float):
2262
2351
 
2263
2352
    __visit_name__ = 'REAL'
2264
2353
 
 
2354
 
2265
2355
class FLOAT(Float):
2266
2356
    """The SQL FLOAT type."""
2267
2357
 
2268
2358
    __visit_name__ = 'FLOAT'
2269
2359
 
 
2360
 
2270
2361
class NUMERIC(Numeric):
2271
2362
    """The SQL NUMERIC type."""
2272
2363
 
2297
2388
 
2298
2389
    __visit_name__ = 'BIGINT'
2299
2390
 
 
2391
 
2300
2392
class TIMESTAMP(DateTime):
2301
2393
    """The SQL TIMESTAMP type."""
2302
2394
 
2305
2397
    def get_dbapi_type(self, dbapi):
2306
2398
        return dbapi.TIMESTAMP
2307
2399
 
 
2400
 
2308
2401
class DATETIME(DateTime):
2309
2402
    """The SQL DATETIME type."""
2310
2403
 
2322
2415
 
2323
2416
    __visit_name__ = 'TIME'
2324
2417
 
 
2418
 
2325
2419
class TEXT(Text):
2326
2420
    """The SQL TEXT type."""
2327
2421
 
2328
2422
    __visit_name__ = 'TEXT'
2329
2423
 
 
2424
 
2330
2425
class CLOB(Text):
2331
2426
    """The CLOB type.
2332
2427
 
2335
2430
 
2336
2431
    __visit_name__ = 'CLOB'
2337
2432
 
 
2433
 
2338
2434
class VARCHAR(String):
2339
2435
    """The SQL VARCHAR type."""
2340
2436
 
2341
2437
    __visit_name__ = 'VARCHAR'
2342
2438
 
 
2439
 
2343
2440
class NVARCHAR(Unicode):
2344
2441
    """The SQL NVARCHAR type."""
2345
2442
 
2346
2443
    __visit_name__ = 'NVARCHAR'
2347
2444
 
 
2445
 
2348
2446
class CHAR(String):
2349
2447
    """The SQL CHAR type."""
2350
2448
 
2362
2460
 
2363
2461
    __visit_name__ = 'BLOB'
2364
2462
 
 
2463
 
2365
2464
class BINARY(_Binary):
2366
2465
    """The SQL BINARY type."""
2367
2466
 
2368
2467
    __visit_name__ = 'BINARY'
2369
2468
 
 
2469
 
2370
2470
class VARBINARY(_Binary):
2371
2471
    """The SQL VARBINARY type."""
2372
2472
 
2385
2485
_type_map = {
2386
2486
    str: String(),
2387
2487
    # Py3K
2388
 
    #bytes : LargeBinary(),
 
2488
    #bytes: LargeBinary(),
2389
2489
    # Py2K
2390
 
    unicode : Unicode(),
 
2490
    unicode: Unicode(),
2391
2491
    # end Py2K
2392
 
    int : Integer(),
2393
 
    float : Numeric(),
 
2492
    int: Integer(),
 
2493
    float: Numeric(),
2394
2494
    bool: BOOLEANTYPE,
2395
 
    decimal.Decimal : Numeric(),
2396
 
    dt.date : Date(),
2397
 
    dt.datetime : DateTime(),
2398
 
    dt.time : Time(),
2399
 
    dt.timedelta : Interval(),
 
2495
    decimal.Decimal: Numeric(),
 
2496
    dt.date: Date(),
 
2497
    dt.datetime: DateTime(),
 
2498
    dt.time: Time(),
 
2499
    dt.timedelta: Interval(),
2400
2500
    NoneType: NULLTYPE
2401
2501
}
2402