AsyncTaskLoader 不离线缓存数据
AsyncTaskLoader does not cache data offline
我创建了一个 AsyncTaskLoader 用于从 API 加载 JSON 数据。但是,我注意到如果我旋转设备的屏幕,它会尝试再次从 API 加载数据。
因此,如果我关闭 Internet 连接并旋转屏幕,加载程序将无法 return 数据,因为 HTTP 请求失败。
// NewsLoader.java
public class NewsLoader extends AsyncTaskLoader<String> {
private String url;
public NewsLoader(@NonNull Context context, String url) {
super(context);
this.url = url.trim();
}
@Override
protected void onStartLoading() {
forceLoad();
}
@Override
public String loadInBackground() {
if (url == null || url.isEmpty()) return null;
return NetworkUtils.fetchNews(url);
}
}
然后,
// NewsActivity.java
// Initialising the loader
LoaderManager.getInstance(this).initLoader(LOADER_ID, args, this);
// onCreateLoader method
public Loader<String> onCreateLoader(int id, @Nullable Bundle args) {
// Process args and get url
return new NewsLoader(this, url);
}
据我所知,这不是加载程序的正常行为。知道哪里出了问题吗?
我终于弄明白问题出在哪里了。数据必须手动缓存,在 deliverResult() 中拦截加载的数据并保存在实例变量中供以后使用。
这是更新后的代码。
// NewsLoader.java
public class NewsLoader extends AsyncTaskLoader<String> {
private String url;
private String cachedData = null;
public NewsLoader(@NonNull Context context, String url) {
super(context);
this.url = url.trim();
}
@Override
protected void onStartLoading() {
if (cachedData != null) deliverResult(cachedData);
else forceLoad();
}
@Override
public String loadInBackground() {
if (url == null || url.isEmpty()) return null;
return NetworkUtils.fetchNews(url);
}
@Override
public void deliverResult(String data) {
cachedData = data;
super.deliverResult(data);
}
}
我创建了一个 AsyncTaskLoader 用于从 API 加载 JSON 数据。但是,我注意到如果我旋转设备的屏幕,它会尝试再次从 API 加载数据。
因此,如果我关闭 Internet 连接并旋转屏幕,加载程序将无法 return 数据,因为 HTTP 请求失败。
// NewsLoader.java
public class NewsLoader extends AsyncTaskLoader<String> {
private String url;
public NewsLoader(@NonNull Context context, String url) {
super(context);
this.url = url.trim();
}
@Override
protected void onStartLoading() {
forceLoad();
}
@Override
public String loadInBackground() {
if (url == null || url.isEmpty()) return null;
return NetworkUtils.fetchNews(url);
}
}
然后,
// NewsActivity.java
// Initialising the loader
LoaderManager.getInstance(this).initLoader(LOADER_ID, args, this);
// onCreateLoader method
public Loader<String> onCreateLoader(int id, @Nullable Bundle args) {
// Process args and get url
return new NewsLoader(this, url);
}
据我所知,这不是加载程序的正常行为。知道哪里出了问题吗?
我终于弄明白问题出在哪里了。数据必须手动缓存,在 deliverResult() 中拦截加载的数据并保存在实例变量中供以后使用。
这是更新后的代码。
// NewsLoader.java
public class NewsLoader extends AsyncTaskLoader<String> {
private String url;
private String cachedData = null;
public NewsLoader(@NonNull Context context, String url) {
super(context);
this.url = url.trim();
}
@Override
protected void onStartLoading() {
if (cachedData != null) deliverResult(cachedData);
else forceLoad();
}
@Override
public String loadInBackground() {
if (url == null || url.isEmpty()) return null;
return NetworkUtils.fetchNews(url);
}
@Override
public void deliverResult(String data) {
cachedData = data;
super.deliverResult(data);
}
}