Redis和查询值

时间:2012-07-01 02:19:30

标签: redis

Redis在概念上与我使用的传统SQL数据库不同,我正在试图弄清楚它是否适合我的项目...我一直在环顾四周但似乎找不到我的答案问题

我有一组我需要存储的用户,每个用户都有一个唯一的ID和几个与之关联的值(例如他们的名字)。看起来我可以简单地将它们存储为哈希:

user:fef982dcfe1a7bcba4849b4c281bba95
"username" "andrewm" "name" "Andrew"

我还有一堆我要存储的邮件,每条邮件都有一些属性,例如发件人和收件人:

message:1a7bcba4849b4c281bfef98a952dcfeb
"sender" "fef982dcfe1a7bcba4849b4c281bba95" "recipient" "82dcfe1a7bcba4849b4c281bba95fef9" "message" "Hi!"

我的问题是,如何检索特定用户发送的所有邮件(由其哈希指定)。我应该使用传统的关系数据库,还是像MongoDB这样的NoSQL数据库(我之前使用过)?如果是这样,有没有人对高性能商店有任何建议?我不会做任何真正的搜索(即MySQL LIKE查询) - 只是键值查找,真的。

2 个答案:

答案 0 :(得分:9)

使用Redis建模这些数据当然是可能的,但您需要考虑数据结构和访问路径。使用Redis时,不会隐式管理访问路径(与RDBMS / MongoDB中的索引一样)。

对于提供的示例,您可以:

user:<user hash> -> hash of user properties
user:<user hash:sent -> set of <msg hash>
user:<user hash>:received -> set of <msg hash>
message:<msg hash> -> hash of message properties

添加/删除邮件意味着在添加/删除邮件对象本身的基础上维护与发件人和收件人相对应的*:sent和*:收到的设置。

检索给定用户的已发送或已接收消息只是一个SMEMBERS命令,如果您想要同时检索消息的属性,则为SORT:

# Get a list of message hash codes only in one roundtrip
smembers user:<user hash>:received

# Get a list of message contents in one roundtrip
sort user:<user hash>:received by nosort get message:*->sender get message:*->message

有关使用排序的基本原理,请参阅:

注1:使用Redis最好使用整数作为键而不是UUID或哈希码(特别是在集合中),因为它们以更有效的方式存储。

注2:如果您需要订购消息,则必须使用列表而不是集合。结果是只能删除最旧的消息,并且只能以有效的方式添加新设置的消息。您可能还要为所有消息添加全局列表。

答案 1 :(得分:1)

Redis的基本数据类型不支持多条件查询,全文搜索等。因此,我们修改了Redis源代码,并将Redis转换为可通过辅助索引像SQL数据一样使用的数据库。

该项目的主页为https://oncedb.com

OnceDB不会更改Redis的数据存储结构。 Redis数据库文件可以直接在OneDB中操作,然后返回给Redis使用。

索引搜索

创建索引

全文搜索的性能很差。您可以通过创建索引来提高性能。该方法是为索引字段创建有序列表,然后在执行条件查询时对这些有序列表执行交集查询操作。

# Create hash data
hmset article:001 poster dota visit 21 key js
hmset article:002 poster dota visit 11 key c
hmset article:003 poster like visit 34 key js
hmset article:004 poster like visit 44 key c

然后我们为以上字段创建索引,权重得分设置为:202000201,一个关于时间的整数,该值是商品的ID值

# Create indexed
zadd *article.poster:dota 20200201 001 20200201 002
zadd *article.poster:like 20200201 003 20200201 004
zadd *article.key:js 20200201 001 20200201 003
zadd *article.key:c 20200201 002 20200201 004
# "visit" using its value as the weight score
zadd *article.visit 21 001 11 002 34 003 44 004

按索引查询

找到两个索引* article.key:js和* article.poster:dota的交集并将它们存储在* tmp1有序列表中:

zinterstore *tmp1 2 *article.key:js *article.poster:dota
> 1

然后* tmp1存储满足key = js和poster = dota条件的ID集:

zrange *tmp1 0 -1
> 001

您可以使用zrangehmget命令来打印相应的HASH值:

zrangehmget *tmp1 0 -1 article: key poster
1) 001
2) 40400402
3) js
4) dota
5) 
6) 

结果与直接全文搜索键= js和发帖人= dota相同

hsearch article:* key = js poster = dota
1) article:001
2) js
3) dota

搜索范围

例如,要搜索访问次数在20到30之间且key = js的数据,可以通过控制权重来实现

创建一个临时索引,仅占用* article.visit的权重和key = js的数据

zinterstore *tmp2 2 *article.key:js *article.visit weights 0 1
> 2

获取20到30之间的数据

zrangebyscore *tmp2 20 30
> 001

您可以使用zrangehmgetbyscore打印相应的哈希数据:

zrangehmgetbyscore *tmp2 20 30 article: key visit
1) 001
2) 21
3) js
4) 21
5) 
6) 

结果与使用全文搜索的结果一致:

hsearch article:* visit >= 20 visit <= 30 key = js
1) article:001
2) 21
3) 
4) js

因为有两个相同的字段,visit> = 20 visit <= 30,所以搜索结果将只输出一个,而第三行中重复的字段将输出为空。

更多的OnceDB扩展说明可以查看:Search, query, calculate, and sum instructions in OnceDB

自动索引

创建和维护Redis索引不是很方便。修改数据后,OneDB可以选择自动创建辅助索引。

创建索引:upsert模式字段运算符值...

使用upsert / insert / update指令和特殊运算符自动创建索引:

上面的示例可以写为:

upsert article id @ 001 poster ? dota visit / 21 key ? js
upsert article id @ 002 poster ? dota visit / 11 key ? c
upsert article id @ 003 poster ? like visit / 34 key ? js
upsert article id @ 004 poster ? like visit / 44 key ? c

操作员:

@:主键 ?:组索引 /:排序索引

操作后将自动创建索引:* article * article.poster:dota * article.poster:like * article.visit * article.key:js * article.key:c

多条件索引查询:从中查找架构到字段运算符的值...

对于具有索引的字段,可以使用find命令在索引字段中进行查询。例如,查询:key = js和poster = dota的数据。您可以使用 ”?”指示这两个字段是分组索引:

find article 0 -1 key ? js poster ? dota
1) 1
2) article:001
3) js
4) dota

1代表数据总量。如果为-1,则表示使用全文本搜索,性能较差。

索引范围查询

您可以添加@以指定索引范围,并使用+指定用于分数权重范围的索引字段。

find article 0@20 -1@30 key ? js visit /+ *
1) 1
2) article:001
3) js
4) 21

删除索引

OnceDB不存储索引定义。删除时,您需要手动指示哪些字段包含索引。您需要指定字段名称和索引运算符。

remove article @ 001 key ? poster ? visit /

您还可以自定义索引名称和体重得分。有关更多说明,请参见:OnceDB data modification and query help documentation