下载过程中的错误处理逻辑是:
1. 在DownThread的run方法发现异常,调用sendMessage(int type, int data)创建消息添加到队列中。
@Override
public void run() {
InputStream is = null;
HttpURLConnection conn = null;
try {
file.seek(start);
URL connUrl = new URL(url);
conn = (HttpURLConnection) connUrl.openConnection();
conn.setRequestMethod("GET");
conn.setConnectTimeout(DownTask.connectTimeout);
conn.setRequestProperty("Range", "bytes=" + start + "-" + end);
int responseCode = conn.getResponseCode();
Logger.d(TAG, "下载资源的字节范围:" + start + "-" + end);
if (start > end) {
sendMessage(DownMessage.MSG_SUCCESS, 0);
return;
}
if (responseCode == HttpURLConnection.HTTP_PARTIAL || responseCode == HttpURLConnection.HTTP_OK) {
is = new BufferedInputStream(conn.getInputStream(), 8192);
byte[] buffer = new byte[204800];// 20K缓存
int len = 0;
while ((len = is.read(buffer)) != -1 && running) {
file.write(buffer, 0, len);
sendMessage(DownMessage.MSG_UPDATE, len);
}
sendMessage(DownMessage.MSG_SUCCESS, 0);
} else {
sendMessage(DownMessage.MSG_ERROR, 10);
}
} catch (IOException ex) {
try {
sendMessage(DownMessage.MSG_ERROR, 0);
} catch (InterruptedException e) {
e.printStackTrace();
}
ex.printStackTrace();
} catch (InterruptedException ex) {
ex.printStackTrace();
} finally {
try {
sendMessage(DownMessage.MSG_STOP, 0);
} catch (InterruptedException e1) {
}
if (file != null) {
try {
file.close();
} catch (IOException e) {
}
}
file = null;
if (is != null) {
try {
is.close();
} catch (IOException e) {
}
}
is = null;
if (conn != null)
conn.disconnect();
conn = null;
release();
}
}
2. 在DownTask的run方法之while循环中取出队列中的消息并且进行处理。不同类别的消息分别进行不同处理,消息类别有:MSG_SUCCESS, MSG_ERROR, MSG_UPDATE, MSG_STOP等。
DownMessage msg;
running = true;
while (running) {
msg = queue.take();
switch (msg.type) {
case DownMessage.MSG_SUCCESS:
running = false;
if (downListener != null)
downListener.onDownFinish();
break;
case DownMessage.MSG_UPDATE:
if (downListener != null) {
downListener.onDownUpdate(msg.data);
}
break;
case DownMessage.MSG_ERROR:
running = false;
if (downThread != null) {
downThread.canleDown();
}
notifyDownError(ERROR_UNKNOWN);
break;
case DownMessage.MSG_STOP:
running = false;
if (downListener != null) {
downListener.onDownPause();
}
break;
}
recyle(msg);
downListener.onDownError因大量使用,所以在提取出来,放在notifyDownError方法中。
/**
* 下载出错
*
* @param type
*/
private void notifyDownError(int type) {
if (downListener != null)
downListener.onDownError(type);
}
3. 在DownService中实现OnDownListener接口,在接口方法中调用句柄Handler对象来处理不同类别的消息,处理操作包括更新数据库表,展现Toast提示等。
在启动一个下载任务时,实现OnDownListener接口。
/**
* 启动一个下载任务。
*
* @param down
* @param downTask
*/
public void launchDownloadTask(final Down down, DownTask downTask) {
downListener = new OnDownListener() {
@Override
public void onDownUpdate(int len) {
downHandler.obtainMessage(UPDATE_DOWN, len, 0, down).sendToTarget();
}
@Override
public void onDownStart(int total) {
if (down.getLength() < 1) {
down.setLength(total);
down.setLengthStr(Formatter.formatFileSize(DownService.this, total));
}
}
@Override
public void onDownFinish() {
downHandler.obtainMessage(DOWN_FINISH, down).sendToTarget();
}
@Override
public void onDownError(int type) {
handler.obtainMessage(DOWN_FAIL, type, 0, down).sendToTarget();
}
@Override
public void onDownPause() {
downHandler.obtainMessage(PAUSE_DOWN, down).sendToTarget();
}
};
downTask.setOnDownListener(downListener);
executorService.execute(downTask);
}
wifi断开导致IO异常,创建MSG_ERROR消息,添加到队列中。从队列中取出MSG_ERROR消息并处理:取消DownThread线程,设置running为false以结束while循环,在OnDownListener接口实现类中,调用Handler对象更新数据库表等。
亿速云「云服务器」,即开即用、新一代英特尔至强铂金CPU、三副本存储NVMe SSD云盘,价格低至29元/月。点击查看>>
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。