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

如何在Dojo中实现缓存?解决产品代码列表重复请求问题

解决方案与建议

针对你在Dojo Widget中缓存10K条产品代码列表的需求,这里有几个可行的实现方案,都是Dojo生态里常用的,完全避开cookie的限制:

1. 使用dojo/store/Cache(推荐,Dojo 1.x原生方案)

Dojo的dojo/store/Cache就是专门为这类场景设计的,它能把底层数据存储(比如用JsonRest发起HTTP请求)和缓存存储(比如Memory)结合起来。第一次请求时会从服务端拉取数据并自动存入缓存,后续读取操作直接从缓存获取,完全不用你手动处理逻辑。

示例代码大概是这样的:

require([
    "dojo/store/JsonRest",
    "dojo/store/Memory",
    "dojo/store/Cache",
    "dojo/domReady!"
], function(JsonRest, Memory, Cache) {
    // 定义远程数据存储
    var productStore = new JsonRest({
        target: "/api/product-codes" // 你的服务端接口地址
    });
    // 包装成带缓存的存储
    var cachedProductStore = Cache(productStore, new Memory());
    
    // 在你的Widget里使用这个缓存后的store
    // 第一次调用会发请求,之后直接读内存缓存
    cachedProductStore.query().then(function(productCodes) {
        // 把数据渲染到Filtering Select
        yourFilteringSelect.set("store", cachedProductStore);
    });
});

这个方案的好处是完全利用Dojo原生API,逻辑简洁,内存缓存足够应对10K条数据的规模。

2. 手动维护dojo/store/Memory缓存

如果你想更灵活地控制缓存时机(比如只在特定条件下缓存),可以自己维护一个Memory存储作为缓存:

require([
    "dojo/store/JsonRest",
    "dojo/store/Memory",
    "dojo/promise/when",
    "dojo/domReady!"
], function(JsonRest, Memory, when) {
    var productCache = null;
    var productRemoteStore = new JsonRest({ target: "/api/product-codes" });
    
    function getProductCodes() {
        if (productCache) {
            // 缓存存在,直接返回缓存数据的Promise
            return when(productCache.query());
        }
        // 缓存不存在,发起请求并存入缓存
        return productRemoteStore.query().then(function(data) {
            productCache = new Memory({ data: data });
            return data;
        });
    }
    
    // 在Widget中调用
    getProductCodes().then(function(codes) {
        yourFilteringSelect.set("store", productCache);
    });
});

这种方式适合需要自定义缓存失效逻辑的场景,比如定时清理缓存或者根据某些业务条件刷新缓存。

3. 结合localStorage实现持久化缓存

如果需要页面刷新后依然保留缓存(内存缓存会在页面关闭后丢失),可以用浏览器的localStorage来存储数据,配合Memory store使用:

require([
    "dojo/store/JsonRest",
    "dojo/store/Memory",
    "dojo/promise/when",
    "dojo/domReady!"
], function(JsonRest, Memory, when) {
    var CACHE_KEY = "product_codes_cache";
    var productCache = null;
    
    function loadCacheFromLocalStorage() {
        var cachedData = localStorage.getItem(CACHE_KEY);
        if (cachedData) {
            try {
                return new Memory({ data: JSON.parse(cachedData) });
            } catch(e) {
                // 解析失败,清空缓存
                localStorage.removeItem(CACHE_KEY);
            }
        }
        return null;
    }
    
    function saveCacheToLocalStorage(data) {
        try {
            localStorage.setItem(CACHE_KEY, JSON.stringify(data));
        } catch(e) {
            // 存储失败(比如空间不足),忽略即可
            console.warn("Failed to save product codes to localStorage", e);
        }
    }
    
    function getProductCodes() {
        productCache = loadCacheFromLocalStorage();
        if (productCache) {
            return when(productCache.query());
        }
        return new JsonRest({ target: "/api/product-codes" }).query().then(function(data) {
            productCache = new Memory({ data: data });
            saveCacheToLocalStorage(data);
            return data;
        });
    }
    
    // 在Widget中使用
    getProductCodes().then(function(codes) {
        yourFilteringSelect.set("store", productCache);
    });
});

10K条产品代码序列化后体积很小,远低于localStorage的5MB限制,完全不用担心空间问题。如果服务端数据更新了,记得提供一个清理缓存的逻辑(比如增加版本号,或者监听服务端的更新通知)。

学习资源参考

  • Dojo官方文档中关于dojo/store模块的章节,重点看Cache、Memory和JsonRest的API说明,里面有详细的使用示例和参数解释。
  • Dojo官方教程里的「Working with Data Stores」主题,其中专门有小节讲解缓存策略的实现,能帮你更深入理解Dojo存储体系的设计思路。
  • 如果你用的是Dojo 2.x(现名@dojo/framework),可以参考它的@dojo/stores包,里面有更现代化的状态管理和缓存方案,不过Dojo 1.x的方案依然是目前最广泛使用的。

内容的提问来源于stack exchange,提问作者Shital

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.15 06:47:32