gpt4 book ai didi

postgresql - 在 SQL Korma 中使用非标准的 postgres 运算符

转载 作者:行者123 更新时间:2023-11-29 12:21:22 26 4
gpt4 key购买 nike

Postgres 的一些复杂功能使用不属于 SQL 标准的运算符。一个简单的例子是一组 POSIX regular expression运算符(operator);我需要它们包含一个使用单词边界的 where 子句表达式。

假设我想找到尺寸为 1 的小部件,其中尺寸是一个包含 json 编码的整数列表的字符串。

示例数据:

ID  Size
1 "[1]"
2 "[1,2,4,12]"
3 "[4,12]"
4 "[2,4]"

这对于原始 SQL 来说是微不足道的:

SELECT * FROM widgets WHERE size ~ '\m1\M'

但是对于 korma 来说非常困难。 Korma 确实允许使用 predicates在 where 映射中,但功能非常有限。一些不起作用的东西:

=> (select "widgets" (where {:size ["~" "\\m1\\M"]}))
ClassCastException java.lang.String cannot be cast to clojure.lang.IFn korma.sql.engine/pred-vec (engine.clj:218)

=> (select "widgets" (where {:size [(raw "~") "\\m1\\M"]}))
Failure to execute query with SQL:
SELECT "widgets".* FROM "widgets" WHERE (?) :: [\m1\M]

=> (select "widgets" (where {:size (raw "~ '\\m1\\M'")}))
Failure to execute query with SQL:
SELECT "widgets".* FROM "widgets" WHERE ("widgets"."size" = ~ '\m1\M') :: []

=> (sql-only (select "widgets" (where {:size [(raw "~ '\\m1\\M'")]})))
"SELECT \"widgets\".* FROM \"widgets\" WHERE (NULL)"

一个复杂的因素是其他条件会在这个条件之后动态添加到 where 映射中。因此,即使以下示例有效,它也不允许构建该 map :

=> (sql-only (select "widgets" (where (raw "size ~ '\\m1\\M'"))))
"SELECT \"widgets\".* FROM \"widgets\" WHERE size ~ '\\m1\\M'"

那么,使用像 ~ 这样的非标准运算符来在 korma 中结合 where 映射执行此匹配是否可行?你会怎么做?最佳替代方案或解决方法?

最佳答案

您可以从官方文档 (http://sqlkorma.com/docs#select) 添加额外的 where 子句:

;; Multiple where's are joined with AND, so this
;; is also the same:
(-> (select* users)
(where {:first "john"})
(where {:last "doe"})
(as-sql))

所以你可以这样做:

(sql-only (select "widgets"
(where (raw "size ~ '\\m1\\M'"))
(where {:.. "?"})))

编辑:另一种选择

您可以创建自己的自定义谓词:

(require '[korma.sql.engine :refer [infix]])

(defn tilde
[k v]
(infix k "~" v))

(sql-only
(select "widgets"
(where {:size [tilde "\\m1\\M"]
:... [like "..."]})))

关于postgresql - 在 SQL Korma 中使用非标准的 postgres 运算符,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21652553/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com