CouchDB不区分大小写并且支持类似于MySQL的OR选项

6

我是一名couchDB的新手,需要一些支持。

在MySQL中,我可以简单地运行以下查询:

SELECT `name`, `id`, `desc` FROM `table` 
WHERE `name`="jack" OR `cat` LIKE "%|52224|%";

以下是我的两个问题:

我开始创建一个视图(还没有“喜欢”选项和其他内容):

function(doc) {
    emit([doc.name, doc.cat], {
"name" : doc.name,
"desc" : doc.desc,
"id" : doc._id
});
}

1. 当我使用 "emit([doc.name" 时,字符串必须完全匹配(区分大小写)。
-> 我如何使这个选项不区分大小写?
就像在mysql中一样,我可以查询 ("Jack, jack, jAck, JAck,...) 吗?

2. 如何创建OR选项?

当我使用 [doc.name, doc.cat] 时,我也被强制要求请求两个变量。
但当我只有其中一个时,
我怎么能查询而不为每个选项创建单独的视图?

1个回答

9
为了实现不区分大小写的搜索,您只需要将键转换为小写:
emit([doc.name.toLowerCase(), doc.cat.toLowerCase()])
现在,如果您将查询转换为小写,就可以进行不区分大小写的匹配。这种解决方案的问题在于,如果您既想进行区分大小写的搜索,又想进行不区分大小写的搜索,则可以发出两个值:
[doc.name.toLowerCase(), doc.name, doc.cat]
并使用startkey和endkey来过滤结果,或者创建一个单独的视图。
第二个问题有点棘手。
首先,如果您仅需要按doc.name过滤,则可以发送带有startkey=["jack",0]endkey=["jack",'zzzzzz']的请求,这将返回所有具有doc.name="jack"doc.cat0'zzzzzz'之间的文档(可能有更好的方法来表示“任何cat”,但我现在找不到)。
如果您需要一个真正的OR,那么应该为每个文档发出两行:
emit(doc.name, doc); emit(doc.cat, doc);
这样,您可以在请求中POST所需的键:{"keys": ["jack", "cat_name"]}
这将返回具有"jack""cat_name"键的每个文档。但是,具有这两个键的文档将返回两次,因此您必须在应用程序代码中过滤重复项。
您还可以使用couchdb-lucene解决您的两个问题,可能还有更多。它是couchdb用户实现高级查询的流行选择。

非常感谢,那您会建议我创建2个视图并查询2次,还是发射2次?谢谢! - heuri
对于大小写敏感和不敏感的搜索,使用两种视图可以使应用程序逻辑更加简单。但是对于OR查询,您应该发出两次查询,因为这样您只需要进行一次查询,而不是两次,并且在任何情况下都必须过滤重复项。 - allait

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接