PostgreSQL jsonb,`?`和JDBC

Jas*_*son 5 postgresql jdbc anorm jsonb

我正在使用PostgreSQL 9.4和令人敬畏的JSONB字段类型.我试图查询文档中的字段.以下适用于psql CLI

SELECT id FROM program WHERE document -> 'dept' ? 'CS'
Run Code Online (Sandbox Code Playgroud)

当我尝试通过我的Scala应用程序运行相同的查询时,我收到以下错误.我正在使用Play框架和Anorm,所以查询看起来像这样

SQL(s"SELECT id FROM program WHERE document -> 'dept' ? {dept}")
.on('dept -> "CS")
....
Run Code Online (Sandbox Code Playgroud)

SQLException ::没有为参数5指定值.(SimpleParameterList.java:223)

(在我的实际查询中有更多参数)

我可以通过将我的参数转换为类型jsonb并使用@>运算符来检查包含来解决这个问题.

SQL(s"SELECT id FROM program WHERE document -> 'dept' @> {dept}::jsonb")
.on('dept -> "CS")
....
Run Code Online (Sandbox Code Playgroud)

我不太热衷于工作.我不知道演员阵容是否有性能损失,但这是额外的打字,并且不明显.

还有什么我可以做的吗?

Fra*_*ens 7

作为避免的解决方法?运算符,您可以创建一个完全相同的新运算符.

这是原始运算符的代码:

CREATE OPERATOR ?(
  PROCEDURE = jsonb_exists,
  LEFTARG = jsonb,
  RIGHTARG = text,
  RESTRICT = contsel,
  JOIN = contjoinsel);

SELECT '{"a":1, "b":2}'::jsonb ? 'b'; -- true
Run Code Online (Sandbox Code Playgroud)

使用不同的名称,没有任何冲突,例如# - #并创建一个新名称:

CREATE OPERATOR #-#(
  PROCEDURE = jsonb_exists,
  LEFTARG = jsonb,
  RIGHTARG = text,
  RESTRICT = contsel,
  JOIN = contjoinsel);

SELECT '{"a":1, "b":2}'::jsonb #-# 'b'; -- true
Run Code Online (Sandbox Code Playgroud)

在代码中使用此新运算符,它应该可以工作.

检查pgAdmin - > pg_catalog - >运算符是否为使用的所有运算符?在名字里.


Mar*_*eel 5

在 JDBC(和标准 SQL)中,问号被保留为参数占位符。不允许其他用途。

请参阅JDBC 规范是否阻止“?” 被用作运算符(引号之外)?以及关于 jdbc-spec-discuss 的讨论

当前的 PostgreSQL JDBC 驱动程序会将所有出现的问号(外部文本或注释)转换为 PostgreSQL 特定的参数占位符。我不确定 PostgreSQL JDBC 项目是否已经做了任何事情(比如引入上面链接中讨论的转义)来解决这个问题。快速查看代码和文档表明他们没有,但我没有深入挖掘。

附录:如bobmarksie 的回答所示,当前版本的 PostgreSQL JDBC 驱动程序现在支持通过加倍来转义问号(即:使用??而不是?)。