You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用localForage遍历IndexedDB中前缀为field-的存储键

嘿,刚好对这个场景熟!咱们分两种情况来解决,看你的数据量选合适的方法就行~

方案1:简单直接的过滤法(适合小数据集)

localForage 本身提供了 keys() 方法可以获取所有存储的键,我们只需要在拿到所有键之后,过滤出以 field- 开头的就行。这个方法代码简洁,容易维护,适合存储的键数量不多的场景。

async function getFieldKeys() {
  // 获取所有键
  const allKeys = await localForage.keys();
  // 过滤出前缀为'field-'的键
  return allKeys.filter(key => key.startsWith('field-'));
}

// 使用示例:拿到键之后遍历操作
getFieldKeys().then(keys => {
  console.log('找到的field前缀键:', keys);
  // 遍历每个键获取对应的值
  keys.forEach(async key => {
    const value = await localForage.getItem(key);
    console.log(`${key} 对应的值:`, value);
  });
}).catch(err => {
  console.error('获取键失败:', err);
});
方案2:高效的游标范围查询(适合大数据集)

如果你的 IndexedDB 里存储了大量键,全量获取所有键再过滤就有点浪费性能了。这时候可以直接操作 localForage 底层的 IndexedDB 实例,利用游标范围查询来只遍历符合前缀的键,不用加载所有键到内存里。

async function getFieldKeysEfficiently() {
  return new Promise((resolve, reject) => {
    // 获取localForage实例
    const instance = localForage.getInstance();
    // 打开数据库连接
    instance.open().then(() => {
      const db = instance._dbInfo.db;
      const storeName = instance._dbInfo.storeName;
      // 创建只读事务
      const transaction = db.transaction(storeName, 'readonly');
      const store = transaction.objectStore(storeName);
      
      // 构建前缀范围:从'field-'到'field-\uffff'(\uffff是Unicode最大字符,确保覆盖所有以field-开头的键)
      const keyRange = IDBKeyRange.bound('field-', 'field-\uffff', false, false);
      // 打开游标查询符合范围的键
      const cursorRequest = store.openCursor(keyRange);
      
      const fieldKeys = [];
      cursorRequest.onsuccess = (event) => {
        const cursor = event.target.result;
        if (cursor) {
          // 收集符合条件的键
          fieldKeys.push(cursor.key);
          // 继续下一个游标
          cursor.continue();
        } else {
          // 游标遍历完成,返回结果
          resolve(fieldKeys);
        }
      };
      
      cursorRequest.onerror = (event) => {
        reject(event.target.error);
      };
    }).catch(reject);
  });
}

// 使用示例
getFieldKeysEfficiently().then(keys => {
  console.log('高效获取的field前缀键:', keys);
}).catch(err => {
  console.error('获取键失败:', err);
});

额外优化:同时获取键和值

如果你需要同时拿到键和对应的值,在游标里可以直接获取 cursor.value,不用再单独调用 getItem(),进一步提升效率:

async function getFieldEntries() {
  return new Promise((resolve, reject) => {
    const instance = localForage.getInstance();
    instance.open().then(() => {
      const db = instance._dbInfo.db;
      const storeName = instance._dbInfo.storeName;
      const transaction = db.transaction(storeName, 'readonly');
      const store = transaction.objectStore(storeName);
      
      const keyRange = IDBKeyRange.bound('field-', 'field-\uffff', false, false);
      const cursorRequest = store.openCursor(keyRange);
      
      const entries = [];
      cursorRequest.onsuccess = (event) => {
        const cursor = event.target.result;
        if (cursor) {
          entries.push({ key: cursor.key, value: cursor.value });
          cursor.continue();
        } else {
          resolve(entries);
        }
      };
      
      cursorRequest.onerror = (event) => {
        reject(event.target.error);
      };
    }).catch(reject);
  });
}

注意事项

  • 方案2直接用到了 localForage 的内部属性(_dbInfo),虽然目前主流版本都兼容,但如果未来 localForage 更新底层实现,可能会失效。如果你的项目需要长期稳定,优先选方案1;如果性能是核心需求,可以用方案2并做好版本测试。
  • 两种方法都支持 async/await,记得做好错误捕获,避免未处理的Promise异常。

内容的提问来源于stack exchange,提问作者H. K.

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.25 02:30:07