Use JSONB to store Dict field on PostgreSQL backend
issue10858 review379371002
This commit is contained in:
1 parent
acd9408451
commit
a1a2e6eb70
6 files changed
+23
-45
No files matched your search
@@ -1,3 +1,5 @@
|
||||
* Use JSONB to store Dict field on PostgreSQL backend
|
||||
|
||||
Version 6.2.0 - 2021-11-01
|
||||
* Bug fixes (see mercurial logs for details)
|
||||
* Allow to cast to date with timezone
|
||||
|
||||
@@ -198,13 +198,14 @@ class Database(DatabaseInterface):
|
||||
flavor = Flavor(ilike=True)
|
||||
|
||||
TYPES_MAPPING = {
|
||||
'INTEGER': SQLType('INT4', 'INT4'),
|
||||
'BIGINT': SQLType('INT8', 'INT8'),
|
||||
'FLOAT': SQLType('FLOAT8', 'FLOAT8'),
|
||||
'BLOB': SQLType('BYTEA', 'BYTEA'),
|
||||
'DATETIME': SQLType('TIMESTAMP', 'TIMESTAMP(0)'),
|
||||
'TIMESTAMP': SQLType('TIMESTAMP', 'TIMESTAMP(6)'),
|
||||
'FLOAT': SQLType('FLOAT8', 'FLOAT8'),
|
||||
'FULLTEXT': SQLType('TSVECTOR', 'TSVECTOR'),
|
||||
'INTEGER': SQLType('INT4', 'INT4'),
|
||||
'JSON': SQLType('JSONB', 'JSONB'),
|
||||
'TIMESTAMP': SQLType('TIMESTAMP', 'TIMESTAMP(6)'),
|
||||
}
|
||||
|
||||
def __new__(cls, name=_default_name):
|
||||
|
||||
@@ -334,10 +334,11 @@ class Database(DatabaseInterface):
|
||||
IN_MAX = 200
|
||||
|
||||
TYPES_MAPPING = {
|
||||
'DATETIME': SQLType('TIMESTAMP', 'TIMESTAMP'),
|
||||
'BIGINT': SQLType('INTEGER', 'INTEGER'),
|
||||
'BOOL': SQLType('BOOLEAN', 'BOOLEAN'),
|
||||
'DATETIME': SQLType('TIMESTAMP', 'TIMESTAMP'),
|
||||
'FULLTEXT': SQLType('TEXT', 'TEXT'),
|
||||
'JSON': SQLType('TEXT', 'TEXT'),
|
||||
}
|
||||
|
||||
def __new__(cls, name=_default_name):
|
||||
|
||||
@@ -21,7 +21,7 @@ dumps = partial(
|
||||
class Dict(Field):
|
||||
'Define dict field.'
|
||||
_type = 'dict'
|
||||
_sql_type = 'TEXT'
|
||||
_sql_type = 'JSON'
|
||||
_py_type = dict
|
||||
|
||||
def __init__(self, schema_model, string='', help='', required=False,
|
||||
|
||||
@@ -34,10 +34,11 @@ class DictRequired(ModelSQL):
|
||||
dico = fields.Dict(None, 'Test Dict', required=True)
|
||||
|
||||
|
||||
class DictJSONB(ModelSQL):
|
||||
'Dict JSONB'
|
||||
__name__ = 'test.dict_jsonb'
|
||||
class DictText(ModelSQL):
|
||||
'Dict TEXT'
|
||||
__name__ = 'test.dict_text'
|
||||
dico = fields.Dict('test.dict.schema', 'Test Dict')
|
||||
dico._sql_type = 'TEXT'
|
||||
|
||||
|
||||
class DictNoSchema(ModelSQL):
|
||||
@@ -69,7 +70,7 @@ def register(module):
|
||||
Dict,
|
||||
DictDefault,
|
||||
DictRequired,
|
||||
DictJSONB,
|
||||
DictText,
|
||||
DictNoSchema,
|
||||
DictUnaccentedOn,
|
||||
DictUnaccentedOff,
|
||||
|
||||
@@ -8,7 +8,6 @@ from trytond.model.exceptions import RequiredValidationError
|
||||
from trytond.pool import Pool
|
||||
from trytond.tests.test_tryton import activate_module, with_transaction
|
||||
from trytond.tests.test_tryton import ExtensionTestCase
|
||||
from trytond.transaction import Transaction
|
||||
|
||||
|
||||
class FieldDictTestCase(unittest.TestCase):
|
||||
@@ -48,11 +47,6 @@ class FieldDictTestCase(unittest.TestCase):
|
||||
'fr: France'),
|
||||
}])
|
||||
|
||||
def set_jsonb(self, table):
|
||||
cursor = Transaction().connection.cursor()
|
||||
cursor.execute('ALTER TABLE "%s" '
|
||||
'ALTER COLUMN dico TYPE json USING dico::json' % table)
|
||||
|
||||
@with_transaction()
|
||||
def test_create(self):
|
||||
"Test create dict"
|
||||
@@ -167,16 +161,9 @@ class FieldDictTestCase(unittest.TestCase):
|
||||
}])
|
||||
|
||||
@with_transaction()
|
||||
@unittest.skipIf(
|
||||
backend.name != 'postgresql', 'jsonb only supported by postgresql')
|
||||
def test_create_jsonb(self):
|
||||
"Test create dict as jsonb"
|
||||
connection = Transaction().connection
|
||||
if backend.Database().get_version(connection) < (9, 2):
|
||||
return
|
||||
|
||||
Dict = Pool().get('test.dict_jsonb')
|
||||
self.set_jsonb(Dict._table)
|
||||
def test_create_text(self):
|
||||
"Test create dict as text"
|
||||
Dict = Pool().get('test.dict_text')
|
||||
|
||||
dict_, = Dict.create([{
|
||||
'dico': {'a': 1, 'b': 2},
|
||||
@@ -214,16 +201,9 @@ class FieldDictTestCase(unittest.TestCase):
|
||||
self.assertDictEqual(dict_.dico, {'y': 1})
|
||||
|
||||
@with_transaction()
|
||||
@unittest.skipIf(
|
||||
backend.name != 'postgresql', 'jsonb only supported by postgresql')
|
||||
def test_write_jsonb(self):
|
||||
"Test write dict as jsonb"
|
||||
connection = Transaction().connection
|
||||
if backend.Database().get_version(connection) < (9, 2):
|
||||
return
|
||||
|
||||
Dict = Pool().get('test.dict_jsonb')
|
||||
self.set_jsonb(Dict._table)
|
||||
def test_write_text(self):
|
||||
"Test write dict as text"
|
||||
Dict = Pool().get('test.dict_text')
|
||||
dict_, = Dict.create([{
|
||||
'dico': {'a': 1, 'b': 2},
|
||||
}])
|
||||
@@ -827,17 +807,10 @@ class FieldDictTestCase(unittest.TestCase):
|
||||
self.assertListEqual(dicts_b_b, [])
|
||||
|
||||
@with_transaction()
|
||||
@unittest.skipIf(
|
||||
backend.name != 'postgresql', 'jsonb only supported by postgresql')
|
||||
def test_search_element_jsonb(self):
|
||||
"Test search dict element on jsonb"
|
||||
connection = Transaction().connection
|
||||
if backend.Database().get_version(connection) < (9, 2):
|
||||
return
|
||||
|
||||
def test_search_element_text(self):
|
||||
"Test search dict element on text"
|
||||
pool = Pool()
|
||||
Dict = pool.get('test.dict_noschema')
|
||||
self.set_jsonb(Dict._table)
|
||||
Dict = pool.get('test.dict_text')
|
||||
dict_, = Dict.create([{
|
||||
'dico': {'a': 'Foo'},
|
||||
}])
|
||||
|
||||
Reference in new issue
Block a user