]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commitdiff
- Added new MySQL-specific :class:`.mysql.DATETIME` which includes
authorMike Bayer <mike_mp@zzzcomputing.com>
Wed, 19 Feb 2014 20:49:37 +0000 (15:49 -0500)
committerMike Bayer <mike_mp@zzzcomputing.com>
Wed, 19 Feb 2014 20:49:59 +0000 (15:49 -0500)
fractional seconds support; also added fractional seconds support
to :class:`.mysql.TIMESTAMP`.  DBAPI support is limited, though
fractional seconds are known to be supported by MySQL Connector/Python.
Patch courtesy Geert JM Vanderkelen. #2941

doc/build/changelog/changelog_08.rst
lib/sqlalchemy/dialects/mysql/base.py
test/dialect/mysql/test_types.py

index 7b116101bcd49dcc071f5b8fb86b7c4e870a62d5..39d58f5e3ac8679522febb9ff732c5087550e74a 100644 (file)
 .. changelog::
     :version: 0.8.5
 
+     .. change::
+        :tags: feature, mysql
+        :versions: 0.9.3
+        :tickets: 2941
+
+        Added new MySQL-specific :class:`.mysql.DATETIME` which includes
+        fractional seconds support; also added fractional seconds support
+        to :class:`.mysql.TIMESTAMP`.  DBAPI support is limited, though
+        fractional seconds are known to be supported by MySQL Connector/Python.
+        Patch courtesy Geert JM Vanderkelen.
+
      .. change::
         :tags: bug, mysql
         :versions: 0.9.3
index 654ffbd8574c7c853329f65ec17d0b07f3e6a7ef..028111b9ffd5d39bb710d126b955871b95e2f83e 100644 (file)
@@ -340,7 +340,6 @@ reflection will not include foreign keys.  For these tables, you may supply a
 """
 
 import datetime
-import inspect
 import re
 import sys
 
@@ -353,7 +352,7 @@ from ...engine import reflection
 from ...engine import default
 from ... import types as sqltypes
 from ...util import topological
-from ...types import DATE, DATETIME, BOOLEAN, TIME, \
+from ...types import DATE, BOOLEAN, \
                                 BLOB, BINARY, VARBINARY
 
 RESERVED_WORDS = set(
@@ -740,15 +739,7 @@ class BIT(sqltypes.TypeEngine):
 
 
 class TIME(sqltypes.TIME):
-    """MySQL TIME type.
-
-    Recent versions of MySQL add support for
-    fractional seconds precision.   While the
-    :class:`.mysql.TIME` type now supports this,
-    note that many DBAPI drivers may not yet
-    include support.
-
-    """
+    """MySQL TIME type. """
 
     __visit_name__ = 'TIME'
 
@@ -759,9 +750,13 @@ class TIME(sqltypes.TIME):
         :param fsp: fractional seconds precision value.
          MySQL 5.6 supports storage of fractional seconds;
          this parameter will be used when emitting DDL
-         for the TIME type.  Note that many DBAPI drivers
-         may not yet have support for fractional seconds,
-         however.
+         for the TIME type.
+
+         .. note::
+
+            DBAPI driver support for fractional seconds may
+            be limited; current support includes
+            MySQL Connector/Python.
 
         .. versionadded:: 0.8 The MySQL-specific TIME
            type as well as fractional seconds support.
@@ -789,9 +784,64 @@ class TIME(sqltypes.TIME):
 
 
 class TIMESTAMP(sqltypes.TIMESTAMP):
-    """MySQL TIMESTAMP type."""
+    """MySQL TIMESTAMP type.
+
+    """
+
     __visit_name__ = 'TIMESTAMP'
 
+    def __init__(self, timezone=False, fsp=None):
+        """Construct a MySQL TIMESTAMP type.
+
+        :param timezone: not used by the MySQL dialect.
+        :param fsp: fractional seconds precision value.
+         MySQL 5.6.4 supports storage of fractional seconds;
+         this parameter will be used when emitting DDL
+         for the TIMESTAMP type.
+
+         .. note::
+
+            DBAPI driver support for fractional seconds may
+            be limited; current support includes
+            MySQL Connector/Python.
+
+        .. versionadded:: 0.8.5 Added MySQL-specific :class:`.mysql.TIMESTAMP`
+           with fractional seconds support.
+
+        """
+        super(TIMESTAMP, self).__init__(timezone=timezone)
+        self.fsp = fsp
+
+
+class DATETIME(sqltypes.DATETIME):
+    """MySQL DATETIME type.
+
+    """
+
+    __visit_name__ = 'DATETIME'
+
+    def __init__(self, timezone=False, fsp=None):
+        """Construct a MySQL DATETIME type.
+
+        :param timezone: not used by the MySQL dialect.
+        :param fsp: fractional seconds precision value.
+         MySQL 5.6.4 supports storage of fractional seconds;
+         this parameter will be used when emitting DDL
+         for the DATETIME type.
+
+         .. note::
+
+            DBAPI driver support for fractional seconds may
+            be limited; current support includes
+            MySQL Connector/Python.
+
+        .. versionadded:: 0.8.5 Added MySQL-specific :class:`.mysql.DATETIME`
+           with fractional seconds support.
+
+        """
+        super(DATETIME, self).__init__(timezone=timezone)
+        self.fsp = fsp
+
 
 class YEAR(sqltypes.TypeEngine):
     """MySQL YEAR type, for single byte storage of years 1901-2155."""
@@ -1849,7 +1899,10 @@ class MySQLTypeCompiler(compiler.GenericTypeCompiler):
             return "BIT"
 
     def visit_DATETIME(self, type_):
-        return "DATETIME"
+        if getattr(type_, 'fsp', None):
+            return "DATETIME(%d)" % type_.fsp
+        else:
+            return "DATETIME"
 
     def visit_DATE(self, type_):
         return "DATE"
@@ -1861,7 +1914,10 @@ class MySQLTypeCompiler(compiler.GenericTypeCompiler):
             return "TIME"
 
     def visit_TIMESTAMP(self, type_):
-        return 'TIMESTAMP'
+        if getattr(type_, 'fsp', None):
+            return "TIMESTAMP(%d)" % type_.fsp
+        else:
+            return "TIMESTAMP"
 
     def visit_YEAR(self, type_):
         if type_.display_width is None:
index b918abe25645d3645809f8cc021528c9d1dd6c84..4ef0f8f0bd27e66452ccc06749a8e1348a949235 100644 (file)
@@ -363,8 +363,14 @@ class TypesTest(fixtures.TestBase, AssertsExecutionResults, AssertsCompiledSQL):
         roundtrip([False, False, 0, 0, 0], [False, False, False,
                   False, 0])
 
-    def test_timestamp(self):
-        """Exercise funky TIMESTAMP default syntax."""
+    def test_timestamp_fsp(self):
+        self.assert_compile(
+                mysql.TIMESTAMP(fsp=5),
+                "TIMESTAMP(5)"
+        )
+
+    def test_timestamp_defaults(self):
+        """Exercise funky TIMESTAMP default syntax when used in columns."""
 
         columns = [
             ([TIMESTAMP],
@@ -428,7 +434,20 @@ class TypesTest(fixtures.TestBase, AssertsExecutionResults, AssertsCompiledSQL):
             [(now, now), (None, now)]
         )
 
-    def test_time(self):
+    def test_datetime_generic(self):
+        self.assert_compile(
+                mysql.DATETIME(),
+                "DATETIME"
+        )
+
+    def test_datetime_fsp(self):
+        self.assert_compile(
+                mysql.DATETIME(fsp=4),
+                "DATETIME(4)"
+        )
+
+
+    def test_time_generic(self):
         """"Exercise TIME."""
 
         self.assert_compile(
@@ -436,11 +455,13 @@ class TypesTest(fixtures.TestBase, AssertsExecutionResults, AssertsCompiledSQL):
                 "TIME"
         )
 
+    def test_time_fsp(self):
         self.assert_compile(
                 mysql.TIME(fsp=5),
                 "TIME(5)"
         )
 
+    def test_time_result_processor(self):
         eq_(
             mysql.TIME().result_processor(None, None)(
                     datetime.timedelta(seconds=35, minutes=517,