JCR-SQL中CONTAINS函数特殊字符转义失效问题咨询
搞定JCR-SQL里CONTAINS用*匹配的奇怪问题
兄弟,我太懂你这困惑了!之前在AEM里写JCR查询的时候也踩过这个坑。
先给你说为啥会这样:在JCR的CONTAINS函数里,*本身就是通配符,代表匹配任意长度的任意字符(包括空字符),所以你写CONTAINS(., '*')的时候,相当于告诉查询引擎“给我所有有内容的节点”,自然就返回了路径下的所有节点,不管实际属性里有没有星号字符。
那该怎么解决?分两种情况:
情况1:你确实想找包含星号*字符的节点
这时候得正确转义星号。注意JCR里转义特殊字符要用反斜杠\,但在SQL语句的字符串中,反斜杠本身也需要被转义,所以最终要写成\\*。修改后的查询应该是这样:
SELECT jcr:title, jcr:created, jcr:description FROM cq:PageContent WHERE jcr:path LIKE '/content/.../%' AND CONTAINS(., '\\*') ORDER BY jcr:created ASC
另外提一句,如果是用Oak(AEM的底层JCR实现),要确保你的全文索引配置里没有忽略星号这类特殊字符,不然可能还是查不到。
情况2:你其实是想找有非空内容的节点
如果你的初衷只是过滤掉空内容的节点,那完全没必要用CONTAINS,直接用IS NOT NULL更高效,还不会有通配符的混淆:
SELECT jcr:title, jcr:created, jcr:description FROM cq:PageContent WHERE jcr:path LIKE '/content/.../%' AND (jcr:title IS NOT NULL OR jcr:description IS NOT NULL) ORDER BY jcr:created ASC
要是你想检查节点本身是否存在任何属性内容,部分JCR实现支持EXISTS(.),不过这个兼容性不如IS NOT NULL,得看你用的具体平台。
最后说下你之前转义没用的原因:应该是只加了一个反斜杠,SQL字符串里单个反斜杠会被当作转义符处理掉,根本没传到JCR解析器那里,所以自然还是按通配符处理了。
内容的提问来源于stack exchange,提问作者Mikołaj Mański
相关产品推荐
相关产品推荐

