summaryrefslogtreecommitdiff
path: root/tests/backends/sqlite
diff options
context:
space:
mode:
authorPaveł Tyślacki <pavel.tyslacki@gmail.com>2019-02-28 00:47:29 +0300
committerTim Graham <timograham@gmail.com>2019-03-13 10:24:28 -0400
commit782d85b6dfa191e67c0f1d572641d8236c79174c (patch)
tree8ca589140652b19f60941c5ff2d361ed81d491d7 /tests/backends/sqlite
parent406de977ea1a6429535d21240e3ecdac06d4516c (diff)
Fixed #30183 -- Added introspection of inline SQLite constraints.
Diffstat (limited to 'tests/backends/sqlite')
-rw-r--r--tests/backends/sqlite/test_introspection.py115
1 files changed, 115 insertions, 0 deletions
diff --git a/tests/backends/sqlite/test_introspection.py b/tests/backends/sqlite/test_introspection.py
index 1695ee549e..e378e0ee56 100644
--- a/tests/backends/sqlite/test_introspection.py
+++ b/tests/backends/sqlite/test_introspection.py
@@ -1,5 +1,7 @@
import unittest
+import sqlparse
+
from django.db import connection
from django.test import TestCase
@@ -25,3 +27,116 @@ class IntrospectionTests(TestCase):
self.assertEqual(field, expected_string)
finally:
cursor.execute('DROP TABLE test_primary')
+
+
+@unittest.skipUnless(connection.vendor == 'sqlite', 'SQLite tests')
+class ParsingTests(TestCase):
+ def parse_definition(self, sql, columns):
+ """Parse a column or constraint definition."""
+ statement = sqlparse.parse(sql)[0]
+ tokens = (token for token in statement.flatten() if not token.is_whitespace)
+ with connection.cursor():
+ return connection.introspection._parse_column_or_constraint_definition(tokens, set(columns))
+
+ def assertConstraint(self, constraint_details, cols, unique=False, check=False):
+ self.assertEqual(constraint_details, {
+ 'unique': unique,
+ 'columns': cols,
+ 'primary_key': False,
+ 'foreign_key': None,
+ 'check': check,
+ 'index': False,
+ })
+
+ def test_unique_column(self):
+ tests = (
+ ('"ref" integer UNIQUE,', ['ref']),
+ ('ref integer UNIQUE,', ['ref']),
+ ('"customname" integer UNIQUE,', ['customname']),
+ ('customname integer UNIQUE,', ['customname']),
+ )
+ for sql, columns in tests:
+ with self.subTest(sql=sql):
+ constraint, details, check, _ = self.parse_definition(sql, columns)
+ self.assertIsNone(constraint)
+ self.assertConstraint(details, columns, unique=True)
+ self.assertIsNone(check)
+
+ def test_unique_constraint(self):
+ tests = (
+ ('CONSTRAINT "ref" UNIQUE ("ref"),', 'ref', ['ref']),
+ ('CONSTRAINT ref UNIQUE (ref),', 'ref', ['ref']),
+ ('CONSTRAINT "customname1" UNIQUE ("customname2"),', 'customname1', ['customname2']),
+ ('CONSTRAINT customname1 UNIQUE (customname2),', 'customname1', ['customname2']),
+ )
+ for sql, constraint_name, columns in tests:
+ with self.subTest(sql=sql):
+ constraint, details, check, _ = self.parse_definition(sql, columns)
+ self.assertEqual(constraint, constraint_name)
+ self.assertConstraint(details, columns, unique=True)
+ self.assertIsNone(check)
+
+ def test_unique_constraint_multicolumn(self):
+ tests = (
+ ('CONSTRAINT "ref" UNIQUE ("ref", "customname"),', 'ref', ['ref', 'customname']),
+ ('CONSTRAINT ref UNIQUE (ref, customname),', 'ref', ['ref', 'customname']),
+ )
+ for sql, constraint_name, columns in tests:
+ with self.subTest(sql=sql):
+ constraint, details, check, _ = self.parse_definition(sql, columns)
+ self.assertEqual(constraint, constraint_name)
+ self.assertConstraint(details, columns, unique=True)
+ self.assertIsNone(check)
+
+ def test_check_column(self):
+ tests = (
+ ('"ref" varchar(255) CHECK ("ref" != \'test\'),', ['ref']),
+ ('ref varchar(255) CHECK (ref != \'test\'),', ['ref']),
+ ('"customname1" varchar(255) CHECK ("customname2" != \'test\'),', ['customname2']),
+ ('customname1 varchar(255) CHECK (customname2 != \'test\'),', ['customname2']),
+ )
+ for sql, columns in tests:
+ with self.subTest(sql=sql):
+ constraint, details, check, _ = self.parse_definition(sql, columns)
+ self.assertIsNone(constraint)
+ self.assertIsNone(details)
+ self.assertConstraint(check, columns, check=True)
+
+ def test_check_constraint(self):
+ tests = (
+ ('CONSTRAINT "ref" CHECK ("ref" != \'test\'),', 'ref', ['ref']),
+ ('CONSTRAINT ref CHECK (ref != \'test\'),', 'ref', ['ref']),
+ ('CONSTRAINT "customname1" CHECK ("customname2" != \'test\'),', 'customname1', ['customname2']),
+ ('CONSTRAINT customname1 CHECK (customname2 != \'test\'),', 'customname1', ['customname2']),
+ )
+ for sql, constraint_name, columns in tests:
+ with self.subTest(sql=sql):
+ constraint, details, check, _ = self.parse_definition(sql, columns)
+ self.assertEqual(constraint, constraint_name)
+ self.assertIsNone(details)
+ self.assertConstraint(check, columns, check=True)
+
+ def test_check_column_with_operators_and_functions(self):
+ tests = (
+ ('"ref" integer CHECK ("ref" BETWEEN 1 AND 10),', ['ref']),
+ ('"ref" varchar(255) CHECK ("ref" LIKE \'test%\'),', ['ref']),
+ ('"ref" varchar(255) CHECK (LENGTH(ref) > "max_length"),', ['ref', 'max_length']),
+ )
+ for sql, columns in tests:
+ with self.subTest(sql=sql):
+ constraint, details, check, _ = self.parse_definition(sql, columns)
+ self.assertIsNone(constraint)
+ self.assertIsNone(details)
+ self.assertConstraint(check, columns, check=True)
+
+ def test_check_and_unique_column(self):
+ tests = (
+ ('"ref" varchar(255) CHECK ("ref" != \'test\') UNIQUE,', ['ref']),
+ ('ref varchar(255) UNIQUE CHECK (ref != \'test\'),', ['ref']),
+ )
+ for sql, columns in tests:
+ with self.subTest(sql=sql):
+ constraint, details, check, _ = self.parse_definition(sql, columns)
+ self.assertIsNone(constraint)
+ self.assertConstraint(details, columns, unique=True)
+ self.assertConstraint(check, columns, check=True)