Redis SCAN 没有给出 NodeJS 中的所有匹配项

Redis SCAN not giving all matches in NodeJS

我正在使用带有 redis npm 包的 Node.JS 脚本来检索与模式 animals:toFeed:* 匹配的所有 Redis 键。匹配的一个例子是键 animals:toFeed:17ed160f59c5b31caf7e741a4e62cb7785414cd.

使用下面的代码,可以有 10 个匹配项,但代码只会 return 2-3 个。可能是什么问题,我们该如何解决?

使用 Redis 4.0.11,Node.js8.11.3,redis 2.8.0 npm 包

async function scanAsync(cursor, pattern, results) {
    return redis.scanAsync(cursor, 'MATCH', pattern, 'COUNT', '10')
        .then(function(reply) {
            cursor = reply[0]
            if(cursor === '0') {
                console.log('Scan complete')
            } else {
                console.log('Match #', i)
                let keys = reply[1]
                keys.forEach(function(key, i) {
                    results.push(key)
                })
                return scanAsync(cursor, pattern, results)
            }
        })
}

let keys = []
let prefix = 'animals:toFeed:*'
await scanAsync('0', prefix, keys) 

更新

  1. 重启redis。仍有不完整的 SCAN 结果
  2. 删除了所有与模式匹配的键并添加了一些键。现在,在进行 SCAN 时,一切都已 returned。播放一个小时后,它会再次 return 搜索不完整的结果。重复此操作已无法解决问题。

当光标等于 '0' 时,您忘记将键添加到 results,但您应该始终添加这些键。

您可以这样考虑您的代码:

async function scanAsync(cursor, pattern, results) {
    return redis.scanAsync(cursor, 'MATCH', pattern, 'COUNT', '10')
        .then(function(reply) {

            let keys = reply[1]
            keys.forEach(function(key) {
                results.push(key)
            })

            cursor = reply[0]
            if(cursor === '0') {
                console.log('Scan complete')
            } else {
                return scanAsync(cursor, pattern, results)
            }
        })
}

... 或者你使用 redis-async-gen, which prevents you from having to carefully control all of this yourself. (Read more about it here.)

const redis = require('redis')
const client = redis.createClient(…)
const generators = require('redis-async-gen')
const { keysMatching } = generators.using(client)

const results = []
for await (const key of keysMatching('test*')) {
  results.push(key)
}