summaryrefslogtreecommitdiff
path: root/lib/sqlalchemy/dialects/postgresql/base.py
diff options
context:
space:
mode:
authorMike Bayer <mike_mp@zzzcomputing.com>2019-11-07 15:31:48 -0500
committerMike Bayer <mike_mp@zzzcomputing.com>2019-11-11 14:37:55 -0500
commit01cbf4d7b8acab54a054bb36dc2792b518b5cd1f (patch)
tree09e59ba5a962f02444ca39d8f242c0b3bd86cdb0 /lib/sqlalchemy/dialects/postgresql/base.py
parentbbe754784ae4630dd0ebf30d3bc2be566f8a8fef (diff)
downloadsqlalchemy-01cbf4d7b8acab54a054bb36dc2792b518b5cd1f.tar.gz
Add type accessors for JSON indexed/pathed element access
Added new accessors to expressions of type :class:`.JSON` to allow for specific datatype access and comparison, covering strings, integers, numeric, boolean elements. This revises the documented approach of CASTing to string when comparing values, instead adding specific functionality into the PostgreSQL, SQlite, MySQL dialects to reliably deliver these basic types in all cases. The change also delivers a new feature to the test exclusions system so that combinations and exclusions can be used together. Fixes: #4276 Change-Id: Ica5a926c060feb40a0a7cd60b9d6e061d7825728
Diffstat (limited to 'lib/sqlalchemy/dialects/postgresql/base.py')
-rw-r--r--lib/sqlalchemy/dialects/postgresql/base.py31
1 files changed, 27 insertions, 4 deletions
diff --git a/lib/sqlalchemy/dialects/postgresql/base.py b/lib/sqlalchemy/dialects/postgresql/base.py
index d6fd2623b..6d97033d0 100644
--- a/lib/sqlalchemy/dialects/postgresql/base.py
+++ b/lib/sqlalchemy/dialects/postgresql/base.py
@@ -1559,13 +1559,36 @@ class PGCompiler(compiler.SQLCompiler):
self.process(element.stop, **kw),
)
- def visit_json_getitem_op_binary(self, binary, operator, **kw):
+ def visit_json_getitem_op_binary(
+ self, binary, operator, _cast_applied=False, **kw
+ ):
+ if (
+ not _cast_applied
+ and binary.type._type_affinity is not sqltypes.JSON
+ ):
+ kw["_cast_applied"] = True
+ return self.process(sql.cast(binary, binary.type), **kw)
+
kw["eager_grouping"] = True
- return self._generate_generic_binary(binary, " -> ", **kw)
- def visit_json_path_getitem_op_binary(self, binary, operator, **kw):
+ return self._generate_generic_binary(
+ binary, " -> " if not _cast_applied else " ->> ", **kw
+ )
+
+ def visit_json_path_getitem_op_binary(
+ self, binary, operator, _cast_applied=False, **kw
+ ):
+ if (
+ not _cast_applied
+ and binary.type._type_affinity is not sqltypes.JSON
+ ):
+ kw["_cast_applied"] = True
+ return self.process(sql.cast(binary, binary.type), **kw)
+
kw["eager_grouping"] = True
- return self._generate_generic_binary(binary, " #> ", **kw)
+ return self._generate_generic_binary(
+ binary, " #> " if not _cast_applied else " #>> ", **kw
+ )
def visit_getitem_binary(self, binary, operator, **kw):
return "%s[%s]" % (