Robospice:从SpiceRequest保存到缓存

时间:2013-07-07 03:56:38

标签: java android robospice

我有一个SpiceRequest,其作用是预先缓存一堆数据,然后可以在单独的SpiceRequests中单独加载。

例如,假设我的应用程序通过SpiceRequest下载特定影院的电影时间,我需要一个复合SpiceRequest,它可以下载并预先缓存区域内所有影院的所有影片时间。

让我们调用这个AllMoviesSpiceRequest,它是SpringAndroidSpiceRequest的子类。它的loadDataFromNetwork()方法对getRestTemplate()。getForObject()进行了多次调用。它将所有数据放入一个包含对象并返回它。

我的计划是调用onRequestSuccess为每个影院调用SpiceManager.putInCache。问题是所有影院的数据集都很大,大约16 MB,并且由于JsonWriter.string()无法序列化大字符串而导致OutOfMemory错误。

是否有可能在下载时直接从AllMoviesSpiceRequest缓存每个影院?我不确定从SpiceRequest创建和调用SpiceManager是否安全。或者有更好的方法吗?

以下是一些示例代码,可以提供您的想法:

public class AllMoviesSpiceRequest extends 
    SpringAndroidSpiceRequest<AllMovieTimes> {

    public AllMovieTimes loadDataFromNetwork() throws Exception {

        AllMovieTimes allMovieTimes = new AllMovieTimes();

        // Get all the theaters
        Theaters theaters = getRestTemplate().getForObject(
            THEATER_JSON_URL + "/" + regionId, Theaters.class);

        // Get all the movies
        for(Theater t : theaters.all()) {
            MovieTimes mt = getRestTemplate().getForObject(
                MOVIES_JSON_URL + "/" + t.getId(), MovieTimes.class);

            allMovieTimes.add(mt);
            // Can I call spiceManager.putInCacheHere???
        }

        // OutOfMemoryError!!!
        return allMovieTimes; 
    }
}

private class AllMoviesRequestListener implements 
    RequestListener<AllMovieTimes> { 

    public void onRequestSuccess(AllMovieTimes allMovieTimes) {

        // Add all the movies to the cache
        for(MovieTime mt : allMovieTimes) {
            spiceManager.putInCache(mt.getCacheKey(), mt);
        }
    }
}

提前致谢...

1 个答案:

答案 0 :(得分:1)

如果你的结果太大而无法由杰克逊处理,那可能是一个设计问题。

实际上,拥有16 MB的json对移动设备来说不是一个好的解决方案。它会让用户使用可用的手机很长一段时间,这不是Android应用程序的工作方式。即使RS允许在后台下载数据,你也应该非常关心响应能力。

在RS中,所有由REST请求产生的数据都将直接保存,以后不可能将它们拆分。杰克逊/格森序列化至少也是如此。 Json不是一个数据库,以后不能给你一个选择性的数据访问权。

我可以回答你应该使用ORMLite(可能还有RS ORMLite模块)在数据库中进行数据序列化,这可能允许您将内容存储在单独的表中,以后您可以选择性地检索它们。 / p>

然而,这里真正的答案是你应该放弃下载如此大量的数据,或者使用类似二进制格式(protobuf,kryo?)的东西,并将内容存储在数据库中。

但最简单,更常见的解决方案是下载少量数据。