我们选择将用户和位置数据存储在 Redis 哈希中。哈希非常适合存储领域对象。回想一下,我们选择将每个用户存储在一个键包含用户 ID 的哈希中。例如,这是在 RedisInsight 中看到的用户 852
如果你使用 redis-cli,可以使用 HGETALL
命令查看用户 852:
127.0.0.1:6379> hgetall ncc:users:852
1) "id"
2) "852"
3) "firstName"
4) "Dominik"
5) "lastName"
6) "Schiffmann"
7) "email"
8) "[email protected]"
9) "password"
10) "$2b$05$xbkSwODz1tWqdE7xWb393eiYIQcdiEdbbvhK88.Xr9sW7WxdI26qi"
11) "numCheckins"
12) "9353"
13) "lastCheckin"
14) "1488517098363"
15) "lastSeenAt"
16) "124"
将数据存储在哈希中意味着,只要知道键,我们就可以轻松有效地检索哈希的内容。因此,查找用户 852 非常简单,但我们如何执行以下任何操作呢?
[email protected]
的用户。Redis 是一个键值数据库。这意味着它的数据模型针对按键检索进行了优化。上面的查询仅知道哈希键无法解决 - 我们需要其他机制来索引数据。
在传统的键值数据库中,这意味着添加代码来创建和手动更新索引。例如,要解决“哪个用户拥有邮箱地址 [email protected]
”的查询,我们可以创建一个包含该邮箱地址的新 String 键,其值为用户 ID
127.0.0.1:6379> set ncc:users:byemail:[email protected] 852
OK
现在,如果我们只知道 Dominik 的邮箱地址想要获取其用户详细信息,我们需要执行以下两个步骤
127.0.0.1:6379> get ncc:users:byemail:[email protected]
"852"
127.0.0.1:6379> hgetall ncc:users:852
1) "id"
2) "852"
3) "firstName"
4) "Dominik"
5) "lastName"
6) "Schiffmann"
7) "email"
8) "[email protected]"
9) "password"
10) "$2b$05$xbkSwODz1tWqdE7xWb393eiYIQcdiEdbbvhK88.Xr9sW7WxdI26qi"
11) "numCheckins"
12) "9353"
13) "lastCheckin"
14) "1488517098363"
15) "lastSeenAt"
16) "124"
我们还需要在应用代码中自行保持此信息与 ncc:users:852
的哈希更改同步并保持最新。
可以使用其他 Redis 数据类型创建其他类型的二级索引。例如,我们可以 使用 Redis Sorted Set 作为二级索引,允许我们执行范围查询,例如“查找签到次数在 1000 到 3000 之间的所有用户”。同样,我们必须在应用代码中自行填充和维护这个额外的数据结构。
Redis Stack 为我们解决了所有这些问题以及更多问题。它为 Redis 添加了一个索引、查询和全文搜索引擎,该引擎自动跟踪索引哈希中数据的变化。Redis Stack 提供了一种灵活的查询语言,可以回答诸如“查找加州奥克兰 10 英里范围内所有评级至少为 3 星且签到次数超过 200 次的健身房”之类的问题,而无需在应用中添加代码来构建或维护二级数据结构。
观看视频,了解如何在我们的 Node.js 示例应用中使用 Redis Stack。
在本练习中,你将完成实现一个使用 Redis 返回最后签到在给定位置的所有用户的路由。
使用你的 IDE 打开 node-js-crash-course
文件夹,并找到文件 src/routes/user_routes.js
。
在此文件中,你将看到一个部分实现的路由 /users/at/:locationId
。要完成此练习,你需要替换此行
const searchResults = await redis.performSearch(
redis.getKeyName('usersidx'),
'TODO... YOUR QUERY HERE',
);
替换为包含正确查询的行,该查询返回其“lastSeenAt”字段设置为 locationId 值的用户。你需要为此使用“数字范围”语法,因为“lastSeenAt”字段被索引为数字。请务必查看 Redis 的 查询语法文档 以获取帮助。
要测试你的代码,请确保 API 服务器组件正在运行
$ npm run dev
(记住,这将使用 nodemon 在你保存代码更改时自动重启服务器)。
然后,在浏览器中访问 http://localhost:8081/api/users/at/33
。如果你的查询正确,你应该会看到类似于以下的输出(实际用户可能不同,只需确保每个用户的 lastSeenAt
值与你提供的位置 ID 相符 - 在本例中为 33)
[
{
"id": "238",
"firstName": "Jonas",
"lastName": "Nielsen",
"numCheckins": "7149",
"lastCheckin": "1515248028256",
"lastSeenAt": "33"
},
{
"id": "324",
"firstName": "Frans",
"lastName": "Potze",
"numCheckins": "8623",
"lastCheckin": "1515976232073",
"lastSeenAt": "33"
},
...
]
为了帮助你开发查询,请使用 RedisInsight 工作台中的任一指南,或阅读更多关于 FT.SEARCH 命令 的信息。
使用 Express + Redis Stack 以 RESTful 方式查找大脚怪
其他资源