Postgresql:比较数组导致“格式错误的数组文字”错误

时间:2016-01-12 04:34:37

标签: ruby-on-rails arrays postgresql rails-activerecord

我有一个Rails应用程序和一个包含像["manager", "engineer"]等数组的列,以及这样的where语句:

where("? = ANY roles", query)
如果我传递单个值进行查询,

可以找到。我希望能够传递多个值。我做了一些谷歌搜索,找到了一个简单的解决方案:

where("? && roles", query )

除非我传递类似"['admin', 'guest']"的内容,否则会收到此错误:

PG::InvalidTextRepresentation: ERROR:  malformed array literal: "['admin', 'guest']"
LINE 1: ....                                       $1 AND ('[''admin'...
                                                             ^
DETAIL:  "[" must introduce explicitly-specified array dimensions.

我怀疑有一些奇怪的引用逃避问题,但我无法弄清楚。这些错误消息会产生一堆JSON Q& As,但没有任何解决方案可以跳出来。

更新

我似乎总是在发布问题后找到线索 - 我试过了:

where("'{guest, admin}'::text[] && roles", query )

并且它有效 - 我仍然不知道为什么,但确实如此。现在我看不到如何让?回到那里,所以我可以搜索它。

更新2

我在下面给出了第一个答案并进行了一些重构,以获得我认为简单优雅的解决方案:

where("'{#{roles}}'::text[] && roles")

这样我就可以将一个简单的文本字符串传递给我的应用程序助手,这个where子句就在这里。它处理单个和多个查询。

2 个答案:

答案 0 :(得分:3)

对于数组,使用数组构造函数语法几乎总是更好。来自fine manual

  

<强> 4.2.12。阵列构造函数

     

数组构造函数是一个表达式,它使用其成员元素的值构建数组值。一个简单的数组构造函数包含关键字ARRAY,左方括号[,数组元素值的表达式列表(用逗号分隔),最后是右方括号{{1} }。例如:

]

ActiveRecord会将占位符的数组值扩展为逗号分隔列表,这正是括号内SELECT ARRAY[1,2,3+4]; array --------- {1,2,7} (1 row) 语法所需的内容。所以你要说:

array[...]

如果where('array[?] && roles', query) 是单个值,这甚至是正确的。

更新而言,这是:

query

是一个字符串文字('{guest, admin}'::text[] ),后跟一个类型转换('{guest, admin}')到一个文本数组(::)。字符串中的text[]语法是另一种形式的数组,易于阅读但是正确构建的麻烦; fine manual也涵盖了这种形式:

  

<强> 8.15.2。数组值输入

     

要将数组值写为文字常量,请将元素值括在花括号中并用逗号分隔。

我只使用'{...}'版本,因为它更易于使用,并且更明确地说明数组元素的类型。

答案 1 :(得分:0)

修改

不要做这个答案所暗示的,因为它是危险和脆弱的。这是我真正没有想到的事情之一,并且后悔在公开发表

您希望将数组文字的格式设置为'{"admin", "guest"}'

对已编辑的OP

的响应
query_terms = ["admin", "guest"]
query = "{#{ query_terms.map {|term| %Q("#{ term }") }.join(",") }}"
where("? && roles",  query)