【问题标题】:How to use Redis cache for pagination?如何使用 Redis 缓存进行分页?
【发布时间】:2020-06-23 11:56:18
【问题描述】:

我想使用 redis 缓存进行分页,我正在使用 Node.js 作为我的后端,我正在使用 npm redis-scanner 包,用于通过键进行扫描。 在这里,我无法转到特定键并从 redis 缓存中获取下 15 个键。我该怎么做?

【问题讨论】:

  • 您可以将数据存储为列表并使用lrange。
  • 我将数据存储为键值对
  • 那你不能。

标签: node.js npm redis node-redis redis-cache


【解决方案1】:

你可以像这样使用ioredis:

const Redis = require("ioredis");

async getByCursor({ cursor }) {
    const db = new Redis();
    const stream = db.scanStream({ count: 5 }); // count = number of items to return per page
    try {
      const scan = () =>
        new Promise((resolve, reject) => {
          let items = [];
          stream.on("data", (page) => {
            items = [...items, page]; // page = ['key1', 'key2', etc.]
          });
          stream.on("end", () => {
            resolve(items); // items = [['key1', 'key2'], ['key3', 'key4']]
          });
        });
      const keys = await scan();
      return Promise.all(
        keys[cursor].map(async (key) => JSON.parse(await db.get(key)))
      );
    } catch (e) {
      console.error(e);
      return Promise.resolve([]);
    }
  }

或稍快:

async getByCursor({ cursor }) {
    const stream = db.scanStream({ count: 5 });
    try {
      return new Promise((resolve, reject) => {
        let pageCount = 0;
        stream.on("data", (page) => {
          pageCount = pageCount + 1;
          if (pageCount == Number(cursor)) {
            resolve(
              Promise.all(
                page.map(async (id) => unpack(await db.get(id)))
              ).catch((e) => {
                console.error(e);
                reject([]);
              })
            );
          }
        });
      });
    } catch (e) {
      console.error(e);
    }

使用光标

此处提供光标值 1,例如作为参数或查询时调用你的'items-by-cursor'节点路由给你前5个项目,下一页的值为2等。请注意,计数只是一个估计值,即你不能依赖它总是返回严格 5 个键(有关详细信息,请参阅下面的文档链接)。您可以查看https://react-query.tanstack.com/examples/load-more-infinite-scroll 获取前端解决方案,以获取要发送到路由的相关游标。

性能说明

与通过调用 db.get('*') 和/或过滤路由中的结果通过所有键获取所有项目相比,通过流获取键值对是非阻塞的。因此,建议将此实现用于生产。

更多 ioredis 文档

https://github.com/luin/ioredis#streamify-scanning

【讨论】:

    猜你喜欢
    • 2020-01-27
    • 2014-10-21
    • 2021-08-29
    • 2021-08-16
    • 2018-10-12
    • 2013-12-31
    • 2013-03-22
    • 2020-09-28
    • 2015-08-01
    相关资源
    最近更新 更多