移除`getDownloadTask(String url)`、`getGroupTask(List<String>urls)`、`getFtpDirTask(String path)`等获取任务的api 修复使用`Content-Disposition`的文件名时,第一次下载无法重命名文件的问题 修复使用`Content-Disposition`的文件名时,多次重命名文件的问题v3.6.6
parent
0a447787ea
commit
8c0ef0f879
@ -1,475 +1,458 @@ |
|||||||
/* |
/* |
||||||
* Copyright (C) 2016 AriaLyy(https://github.com/AriaLyy/Aria)
|
* Copyright (C) 2016 AriaLyy(https://github.com/AriaLyy/Aria)
|
||||||
* |
* |
||||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||||
* you may not use this file except in compliance with the License. |
* you may not use this file except in compliance with the License. |
||||||
* You may obtain a copy of the License at |
* You may obtain a copy of the License at |
||||||
* |
* |
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
* |
* |
||||||
* Unless required by applicable law or agreed to in writing, software |
* Unless required by applicable law or agreed to in writing, software |
||||||
* distributed under the License is distributed on an "AS IS" BASIS, |
* distributed under the License is distributed on an "AS IS" BASIS, |
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||||
* See the License for the specific language governing permissions and |
* See the License for the specific language governing permissions and |
||||||
* limitations under the License. |
* limitations under the License. |
||||||
*/ |
*/ |
||||||
package com.arialyy.aria.core.download; |
package com.arialyy.aria.core.download; |
||||||
|
|
||||||
import android.support.annotation.CheckResult; |
import android.support.annotation.CheckResult; |
||||||
import android.support.annotation.NonNull; |
import android.support.annotation.NonNull; |
||||||
import android.text.TextUtils; |
import android.text.TextUtils; |
||||||
import com.arialyy.aria.core.AriaManager; |
import com.arialyy.annotations.DownloadGroup; |
||||||
import com.arialyy.aria.core.command.ICmd; |
import com.arialyy.aria.core.AriaManager; |
||||||
import com.arialyy.aria.core.command.normal.CancelAllCmd; |
import com.arialyy.aria.core.command.ICmd; |
||||||
import com.arialyy.aria.core.command.normal.NormalCmdFactory; |
import com.arialyy.aria.core.command.normal.CancelAllCmd; |
||||||
import com.arialyy.aria.core.common.ProxyHelper; |
import com.arialyy.aria.core.command.normal.NormalCmdFactory; |
||||||
import com.arialyy.aria.core.inf.AbsEntity; |
import com.arialyy.aria.core.common.ProxyHelper; |
||||||
import com.arialyy.aria.core.inf.AbsReceiver; |
import com.arialyy.aria.core.inf.AbsEntity; |
||||||
import com.arialyy.aria.core.inf.ReceiverType; |
import com.arialyy.aria.core.inf.AbsReceiver; |
||||||
import com.arialyy.aria.core.manager.TaskWrapperManager; |
import com.arialyy.aria.core.inf.ReceiverType; |
||||||
import com.arialyy.aria.core.scheduler.DownloadGroupSchedulers; |
import com.arialyy.aria.core.manager.TaskWrapperManager; |
||||||
import com.arialyy.aria.core.scheduler.DownloadSchedulers; |
import com.arialyy.aria.core.scheduler.DownloadGroupSchedulers; |
||||||
import com.arialyy.aria.orm.DbEntity; |
import com.arialyy.aria.core.scheduler.DownloadSchedulers; |
||||||
import com.arialyy.aria.util.ALog; |
import com.arialyy.aria.orm.DbEntity; |
||||||
import com.arialyy.aria.util.CheckUtil; |
import com.arialyy.aria.util.ALog; |
||||||
import com.arialyy.aria.util.CommonUtil; |
import com.arialyy.aria.util.CheckUtil; |
||||||
import java.util.ArrayList; |
import com.arialyy.aria.util.CommonUtil; |
||||||
import java.util.List; |
import com.arialyy.aria.util.DbDataHelper; |
||||||
import java.util.Set; |
import java.util.ArrayList; |
||||||
|
import java.util.List; |
||||||
/** |
import java.util.Set; |
||||||
* Created by lyy on 2016/12/5. |
|
||||||
* 下载功能接收器 |
/** |
||||||
*/ |
* Created by lyy on 2016/12/5. |
||||||
public class DownloadReceiver extends AbsReceiver { |
* 下载功能接收器 |
||||||
private final String TAG = "DownloadReceiver"; |
*/ |
||||||
|
public class DownloadReceiver extends AbsReceiver { |
||||||
/** |
private final String TAG = "DownloadReceiver"; |
||||||
* 设置最大下载速度,单位:kb |
|
||||||
* |
/** |
||||||
* @param maxSpeed 为0表示不限速 |
* 设置最大下载速度,单位:kb |
||||||
* @deprecated {@code Aria.get(Context).getDownloadConfig().setMaxSpeed(int)} |
* |
||||||
*/ |
* @param maxSpeed 为0表示不限速 |
||||||
@Deprecated |
* @deprecated {@code Aria.get(Context).getDownloadConfig().setMaxSpeed(int)} |
||||||
public DownloadReceiver setMaxSpeed(int maxSpeed) { |
*/ |
||||||
AriaManager.getInstance(AriaManager.APP).getDownloadConfig().setMaxSpeed(maxSpeed); |
@Deprecated |
||||||
return this; |
public DownloadReceiver setMaxSpeed(int maxSpeed) { |
||||||
} |
AriaManager.getInstance(AriaManager.APP).getDownloadConfig().setMaxSpeed(maxSpeed); |
||||||
|
return this; |
||||||
/** |
} |
||||||
* 使用下载实体执行下载操作 |
|
||||||
* |
/** |
||||||
* @param entity 下载实体 |
* 使用下载实体执行下载操作 |
||||||
*/ |
* |
||||||
@CheckResult |
* @param entity 下载实体 |
||||||
public DownloadTarget load(DownloadEntity entity) { |
*/ |
||||||
CheckUtil.checkUrlInvalidThrow(entity.getUrl()); |
@CheckResult |
||||||
return new DownloadTarget(entity, targetName); |
public DownloadTarget load(DownloadEntity entity) { |
||||||
} |
CheckUtil.checkUrlInvalidThrow(entity.getUrl()); |
||||||
|
return new DownloadTarget(entity, targetName); |
||||||
/** |
} |
||||||
* 加载Http、https单任务下载地址 |
|
||||||
* |
/** |
||||||
* @param url 下载地址 |
* 加载Http、https单任务下载地址 |
||||||
*/ |
* |
||||||
@CheckResult |
* @param url 下载地址 |
||||||
public DownloadTarget load(@NonNull String url) { |
*/ |
||||||
CheckUtil.checkUrlInvalidThrow(url); |
@CheckResult |
||||||
return new DownloadTarget(url, targetName); |
public DownloadTarget load(@NonNull String url) { |
||||||
} |
CheckUtil.checkUrlInvalidThrow(url); |
||||||
|
return new DownloadTarget(url, targetName); |
||||||
/** |
} |
||||||
* 加载下载地址,如果任务组的中的下载地址改变了,则任务从新的一个任务组 |
|
||||||
* |
/** |
||||||
* @param urls 任务组子任务下载地址列表 |
* 加载下载地址,如果任务组的中的下载地址改变了,则任务从新的一个任务组 |
||||||
* @deprecated {@link #loadGroup(DownloadGroupEntity)} |
* |
||||||
*/ |
* @param urls 任务组子任务下载地址列表 |
||||||
@Deprecated |
* @deprecated {@link #loadGroup(DownloadGroupEntity)} |
||||||
@CheckResult |
*/ |
||||||
public DownloadGroupTarget load(List<String> urls) { |
@Deprecated |
||||||
return loadGroup(urls); |
@CheckResult |
||||||
} |
public DownloadGroupTarget load(List<String> urls) { |
||||||
|
return loadGroup(urls); |
||||||
/** |
} |
||||||
* 加载下载地址,如果任务组的中的下载地址改变了,则任务从新的一个任务组 |
|
||||||
*/ |
/** |
||||||
@CheckResult |
* 加载下载地址,如果任务组的中的下载地址改变了,则任务从新的一个任务组 |
||||||
public DownloadGroupTarget loadGroup(List<String> urls) { |
*/ |
||||||
CheckUtil.checkDownloadUrls(urls); |
@CheckResult |
||||||
return new DownloadGroupTarget(urls, targetName); |
public DownloadGroupTarget loadGroup(List<String> urls) { |
||||||
} |
CheckUtil.checkDownloadUrls(urls); |
||||||
|
return new DownloadGroupTarget(urls, targetName); |
||||||
/** |
} |
||||||
* 使用下载实体执行FTP下载操作 |
|
||||||
* |
/** |
||||||
* @param entity 下载实体 |
* 使用下载实体执行FTP下载操作 |
||||||
*/ |
* |
||||||
@CheckResult |
* @param entity 下载实体 |
||||||
public FtpDownloadTarget loadFtp(DownloadEntity entity) { |
*/ |
||||||
CheckUtil.checkUrlInvalidThrow(entity.getUrl()); |
@CheckResult |
||||||
return new FtpDownloadTarget(entity, targetName); |
public FtpDownloadTarget loadFtp(DownloadEntity entity) { |
||||||
} |
CheckUtil.checkUrlInvalidThrow(entity.getUrl()); |
||||||
|
return new FtpDownloadTarget(entity, targetName); |
||||||
/** |
} |
||||||
* 加载ftp单任务下载地址 |
|
||||||
*/ |
/** |
||||||
@CheckResult |
* 加载ftp单任务下载地址 |
||||||
public FtpDownloadTarget loadFtp(@NonNull String url) { |
*/ |
||||||
CheckUtil.checkUrlInvalidThrow(url); |
@CheckResult |
||||||
return new FtpDownloadTarget(url, targetName); |
public FtpDownloadTarget loadFtp(@NonNull String url) { |
||||||
} |
CheckUtil.checkUrlInvalidThrow(url); |
||||||
|
return new FtpDownloadTarget(url, targetName); |
||||||
/** |
} |
||||||
* 使用任务组实体执行任务组的实体执行任务组的下载操作,后续版本会删除该api |
|
||||||
* |
/** |
||||||
* @param groupEntity 如果加载的任务实体没有子项的下载地址, |
* 使用任务组实体执行任务组的实体执行任务组的下载操作,后续版本会删除该api |
||||||
* 那么你需要使用{@link DownloadGroupTarget#setGroupUrl(List)}设置子项的下载地址 |
* |
||||||
* @deprecated 请使用 {@link #loadGroup(DownloadGroupEntity)} |
* @param groupEntity 如果加载的任务实体没有子项的下载地址, |
||||||
*/ |
* 那么你需要使用{@link DownloadGroupTarget#setGroupUrl(List)}设置子项的下载地址 |
||||||
@Deprecated |
* @deprecated 请使用 {@link #loadGroup(DownloadGroupEntity)} |
||||||
@CheckResult |
*/ |
||||||
public DownloadGroupTarget load(DownloadGroupEntity groupEntity) { |
@Deprecated |
||||||
CheckUtil.checkDownloadUrls(groupEntity.getUrls()); |
@CheckResult |
||||||
return loadGroup(groupEntity); |
public DownloadGroupTarget load(DownloadGroupEntity groupEntity) { |
||||||
} |
CheckUtil.checkDownloadUrls(groupEntity.getUrls()); |
||||||
|
return loadGroup(groupEntity); |
||||||
/** |
} |
||||||
* 使用任务组实体执行任务组的实体执行任务组的下载操作 |
|
||||||
* |
/** |
||||||
* @param groupEntity 如果加载的任务实体没有子项的下载地址, |
* 使用任务组实体执行任务组的实体执行任务组的下载操作 |
||||||
* 那么你需要使用{@link DownloadGroupTarget#setGroupUrl(List)}设置子项的下载地址 |
* |
||||||
*/ |
* @param groupEntity 如果加载的任务实体没有子项的下载地址, |
||||||
@CheckResult |
* 那么你需要使用{@link DownloadGroupTarget#setGroupUrl(List)}设置子项的下载地址 |
||||||
public DownloadGroupTarget loadGroup(DownloadGroupEntity groupEntity) { |
*/ |
||||||
CheckUtil.checkDownloadUrls(groupEntity.getUrls()); |
@CheckResult |
||||||
return new DownloadGroupTarget(groupEntity, targetName); |
public DownloadGroupTarget loadGroup(DownloadGroupEntity groupEntity) { |
||||||
} |
CheckUtil.checkDownloadUrls(groupEntity.getUrls()); |
||||||
|
return new DownloadGroupTarget(groupEntity, targetName); |
||||||
/** |
} |
||||||
* 加载ftp文件夹下载地址 |
|
||||||
*/ |
/** |
||||||
@CheckResult |
* 加载ftp文件夹下载地址 |
||||||
public FtpDirDownloadTarget loadFtpDir(@NonNull String dirUrl) { |
*/ |
||||||
CheckUtil.checkUrlInvalidThrow(dirUrl); |
@CheckResult |
||||||
return new FtpDirDownloadTarget(dirUrl, targetName); |
public FtpDirDownloadTarget loadFtpDir(@NonNull String dirUrl) { |
||||||
} |
CheckUtil.checkUrlInvalidThrow(dirUrl); |
||||||
|
return new FtpDirDownloadTarget(dirUrl, targetName); |
||||||
/** |
} |
||||||
* 将当前类注册到Aria |
|
||||||
*/ |
/** |
||||||
public void register() { |
* 将当前类注册到Aria |
||||||
if (TextUtils.isEmpty(targetName)) { |
*/ |
||||||
ALog.e(TAG, "download register target null"); |
public void register() { |
||||||
return; |
if (TextUtils.isEmpty(targetName)) { |
||||||
} |
ALog.e(TAG, "download register target null"); |
||||||
Object obj = OBJ_MAP.get(getKey()); |
return; |
||||||
if (obj == null) { |
} |
||||||
ALog.e(TAG, String.format("【%s】观察者为空", targetName)); |
Object obj = OBJ_MAP.get(getKey()); |
||||||
return; |
if (obj == null) { |
||||||
} |
ALog.e(TAG, String.format("【%s】观察者为空", targetName)); |
||||||
Set<Integer> set = ProxyHelper.getInstance().checkProxyType(obj.getClass()); |
return; |
||||||
if (set != null && !set.isEmpty()) { |
} |
||||||
for (Integer type : set) { |
Set<Integer> set = ProxyHelper.getInstance().checkProxyType(obj.getClass()); |
||||||
if (type == ProxyHelper.PROXY_TYPE_DOWNLOAD) { |
if (set != null && !set.isEmpty()) { |
||||||
DownloadSchedulers.getInstance().register(obj); |
for (Integer type : set) { |
||||||
} else if (type == ProxyHelper.PROXY_TYPE_DOWNLOAD_GROUP) { |
if (type == ProxyHelper.PROXY_TYPE_DOWNLOAD) { |
||||||
DownloadGroupSchedulers.getInstance().register(obj); |
DownloadSchedulers.getInstance().register(obj); |
||||||
} |
} else if (type == ProxyHelper.PROXY_TYPE_DOWNLOAD_GROUP) { |
||||||
} |
DownloadGroupSchedulers.getInstance().register(obj); |
||||||
} else { |
} |
||||||
ALog.w(TAG, "没有Aria的注解方法"); |
} |
||||||
} |
} else { |
||||||
} |
ALog.w(TAG, "没有Aria的注解方法"); |
||||||
|
} |
||||||
/** |
} |
||||||
* 取消注册,如果是Activity或fragment,Aria会界面销毁时自动调用该方法,不需要你手动调用。 |
|
||||||
* 注意事项: |
/** |
||||||
* 1、如果在activity中一定要调用该方法,那么请在{@code onDestroy()}中调用 |
* 取消注册,如果是Activity或fragment,Aria会界面销毁时自动调用该方法,不需要你手动调用。 |
||||||
* 2、不要在activity的{@code onStop()}中调用改方法 |
* 注意事项: |
||||||
* 3、如果是Dialog或popupwindow,需要你在撤销界面时调用该方法 |
* 1、如果在activity中一定要调用该方法,那么请在{@code onDestroy()}中调用 |
||||||
* 4、如果你是在Module(非android组件类)中注册了Aria,那么你也需要在Module类中调用该方法,而不是在组件类中 |
* 2、不要在activity的{@code onStop()}中调用改方法 |
||||||
* 调用销毁,详情见 |
* 3、如果是Dialog或popupwindow,需要你在撤销界面时调用该方法 |
||||||
* |
* 4、如果你是在Module(非android组件类)中注册了Aria,那么你也需要在Module类中调用该方法,而不是在组件类中 |
||||||
* @see <a href="https://aria.laoyuyu.me/aria_doc/start/any_java.html#%E6%B3%A8%E6%84%8F%E4%BA%8B%E9%A1%B9">module类中销毁</a> |
* 调用销毁,详情见 |
||||||
*/ |
* |
||||||
@Override public void unRegister() { |
* @see <a href="https://aria.laoyuyu.me/aria_doc/start/any_java.html#%E6%B3%A8%E6%84%8F%E4%BA%8B%E9%A1%B9">module类中销毁</a> |
||||||
if (needRmListener) { |
*/ |
||||||
unRegisterListener(); |
@Override public void unRegister() { |
||||||
} |
if (needRmListener) { |
||||||
AriaManager.getInstance(AriaManager.APP).removeReceiver(OBJ_MAP.get(getKey())); |
unRegisterListener(); |
||||||
} |
} |
||||||
|
AriaManager.getInstance(AriaManager.APP).removeReceiver(OBJ_MAP.get(getKey())); |
||||||
@Override public String getType() { |
} |
||||||
return ReceiverType.DOWNLOAD; |
|
||||||
} |
@Override public String getType() { |
||||||
|
return ReceiverType.DOWNLOAD; |
||||||
@Override protected void unRegisterListener() { |
} |
||||||
if (TextUtils.isEmpty(targetName)) { |
|
||||||
ALog.e(TAG, "download unRegisterListener target null"); |
@Override protected void unRegisterListener() { |
||||||
return; |
if (TextUtils.isEmpty(targetName)) { |
||||||
} |
ALog.e(TAG, "download unRegisterListener target null"); |
||||||
Object obj = OBJ_MAP.get(getKey()); |
return; |
||||||
if (obj == null) { |
} |
||||||
ALog.e(TAG, String.format("【%s】观察者为空", targetName)); |
Object obj = OBJ_MAP.get(getKey()); |
||||||
return; |
if (obj == null) { |
||||||
} |
ALog.e(TAG, String.format("【%s】观察者为空", targetName)); |
||||||
Set<Integer> set = ProxyHelper.getInstance().mProxyCache.get(obj.getClass().getName()); |
return; |
||||||
if (set != null) { |
} |
||||||
for (Integer integer : set) { |
Set<Integer> set = ProxyHelper.getInstance().mProxyCache.get(obj.getClass().getName()); |
||||||
if (integer == ProxyHelper.PROXY_TYPE_DOWNLOAD) { |
if (set != null) { |
||||||
DownloadSchedulers.getInstance().unRegister(obj); |
for (Integer integer : set) { |
||||||
} else if (integer == ProxyHelper.PROXY_TYPE_DOWNLOAD_GROUP) { |
if (integer == ProxyHelper.PROXY_TYPE_DOWNLOAD) { |
||||||
DownloadGroupSchedulers.getInstance().unRegister(obj); |
DownloadSchedulers.getInstance().unRegister(obj); |
||||||
} |
} else if (integer == ProxyHelper.PROXY_TYPE_DOWNLOAD_GROUP) { |
||||||
} |
DownloadGroupSchedulers.getInstance().unRegister(obj); |
||||||
} |
} |
||||||
} |
} |
||||||
|
} |
||||||
/** |
} |
||||||
* 通过下载链接获取下载实体 |
|
||||||
* |
/** |
||||||
* @return 如果url错误或查找不到数据,则返回null |
* 通过下载链接获取下载实体 |
||||||
*/ |
* |
||||||
public DownloadEntity getDownloadEntity(String downloadUrl) { |
* @return 如果url错误或查找不到数据,则返回null |
||||||
if (!CheckUtil.checkUrl(downloadUrl)) { |
*/ |
||||||
return null; |
public DownloadEntity getDownloadEntity(String downloadUrl) { |
||||||
} |
CheckUtil.checkUrl(downloadUrl); |
||||||
return DbEntity.findFirst(DownloadEntity.class, "url=? and isGroupChild='false'", downloadUrl); |
return DbEntity.findFirst(DownloadEntity.class, "url=? and isGroupChild='false'", downloadUrl); |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 通过下载地址和文件保存路径获取下载任务实体 |
* 获取组合任务实在实体 |
||||||
* |
* |
||||||
* @param downloadUrl 下载地址 |
* @param urls 组合任务的url |
||||||
* @return 如果url错误或查找不到数据,则返回null |
* @return 如果实体不存在,返回null |
||||||
*/ |
*/ |
||||||
public DTaskWrapper getDownloadTask(String downloadUrl) { |
public DownloadGroupEntity getDownloadGroupEntity(List<String> urls) { |
||||||
if (!CheckUtil.checkUrl(downloadUrl)) { |
CheckUtil.checkDownloadUrls(urls); |
||||||
return null; |
return DbDataHelper.getDGEntity(CommonUtil.getMd5Code(urls)); |
||||||
} |
} |
||||||
if (!taskExists(downloadUrl)) { |
|
||||||
return null; |
/** |
||||||
} |
* 获取组合任务实在实体 |
||||||
return TaskWrapperManager.getInstance().getHttpTaskWrapper(DTaskWrapper.class, downloadUrl); |
* |
||||||
} |
* @param key 组合任务的key,{@link DownloadGroupEntity#getKey()} |
||||||
|
* @return 如果实体不存在,返回null |
||||||
/** |
*/ |
||||||
* 通过下载链接获取保存在数据库的下载任务组实体 |
public DownloadGroupEntity getDownloadGroupEntity(String key) { |
||||||
* |
if (TextUtils.isEmpty(key)) { |
||||||
* @param urls 任务组子任务下载地址列表 |
throw new IllegalArgumentException("key为空"); |
||||||
* @return 返回对应的任务组实体;如果查找不到对应的数据或子任务列表为null,返回null |
} |
||||||
*/ |
return DbDataHelper.getDGEntity(key); |
||||||
public DGTaskWrapper getGroupTask(List<String> urls) { |
} |
||||||
if (urls == null || urls.isEmpty()) { |
|
||||||
ALog.e(TAG, "获取任务组实体失败:任务组子任务下载地址列表为null"); |
/** |
||||||
return null; |
* 获取Ftp文件夹任务的实体 |
||||||
} |
* |
||||||
if (!taskExists(urls)) { |
* @param url ftp文件夹下载路径 |
||||||
return null; |
* @return 如果实体不存在,返回null |
||||||
} |
*/ |
||||||
return TaskWrapperManager.getInstance().getDGTaskWrapper(DGTaskWrapper.class, urls); |
public DownloadGroupEntity getFtpDirEntity(String url) { |
||||||
} |
CheckUtil.checkUrl(url); |
||||||
|
return DbDataHelper.getDGEntity(url); |
||||||
/** |
} |
||||||
* 获取FTP文件夹下载任务实体 |
|
||||||
* |
/** |
||||||
* @param dirUrl FTP文件夹本地下载路径 |
* 下载任务是否存在 |
||||||
* @return 返回对应的任务组实体;如果查找不到对应的数据或路径为null,返回null |
* |
||||||
*/ |
* @return {@code true}存在,{@code false} 不存在 |
||||||
public DGTaskWrapper getFtpDirTask(String dirUrl) { |
*/ |
||||||
if (TextUtils.isEmpty(dirUrl)) { |
public boolean taskExists(String downloadUrl) { |
||||||
ALog.e(TAG, "获取FTP文件夹实体失败:下载路径为null"); |
return DbEntity.checkDataExist(DownloadEntity.class, "url=?", downloadUrl); |
||||||
return null; |
} |
||||||
} |
|
||||||
boolean b = |
/** |
||||||
DownloadGroupEntity.findFirst(DownloadGroupEntity.class, "groupHash=?", dirUrl) != null; |
* 判断任务组是否存在 |
||||||
if (!b) { |
* |
||||||
return null; |
* @return {@code true} 存在;{@code false} 不存在 |
||||||
} |
*/ |
||||||
return TaskWrapperManager.getInstance().getFtpTaskWrapper(DGTaskWrapper.class, dirUrl); |
public boolean taskExists(List<String> urls) { |
||||||
} |
if (urls == null || urls.isEmpty()) { |
||||||
|
return false; |
||||||
/** |
} |
||||||
* 下载任务是否存在 |
String groupHash = CommonUtil.getMd5Code(urls); |
||||||
* |
return DbEntity.checkDataExist(DownloadGroupEntity.class, "groupHash=?", groupHash); |
||||||
* @return {@code true}存在,{@code false} 不存在 |
} |
||||||
*/ |
|
||||||
public boolean taskExists(String downloadUrl) { |
/** |
||||||
return DbEntity.checkDataExist(DownloadEntity.class, "url=?", downloadUrl); |
* 获取所有普通下载任务 |
||||||
} |
* 获取未完成的普通任务列表{@link #getAllNotCompleteTask()} |
||||||
|
* 获取已经完成的普通任务列表{@link #getAllCompleteTask()} |
||||||
/** |
*/ |
||||||
* 判断任务组是否存在 |
public List<DownloadEntity> getTaskList() { |
||||||
* |
return DbEntity.findDatas(DownloadEntity.class, "isGroupChild=? and downloadPath!=''", |
||||||
* @return {@code true} 存在;{@code false} 不存在 |
"false"); |
||||||
*/ |
} |
||||||
public boolean taskExists(List<String> urls) { |
|
||||||
if (urls == null || urls.isEmpty()) { |
/** |
||||||
return false; |
* 分页获取所有普通下载任务 |
||||||
} |
* 获取未完成的普通任务列表{@link #getAllNotCompleteTask()} |
||||||
String groupHash = CommonUtil.getMd5Code(urls); |
* 获取已经完成的普通任务列表{@link #getAllCompleteTask()} |
||||||
return DbEntity.checkDataExist(DownloadGroupEntity.class, "groupHash=?", groupHash); |
* |
||||||
} |
* @param page 当前页,不能小于1 |
||||||
|
* @param num 每页数量,不能小于1 |
||||||
/** |
* @return 如果页数大于总页数,返回null |
||||||
* 获取所有普通下载任务 |
*/ |
||||||
* 获取未完成的普通任务列表{@link #getAllNotCompleteTask()} |
public List<DownloadEntity> getTaskList(int page, int num) { |
||||||
* 获取已经完成的普通任务列表{@link #getAllCompleteTask()} |
CheckUtil.checkPageParams(page, num); |
||||||
*/ |
return DbEntity.findDatas(DownloadEntity.class, page, num, |
||||||
public List<DownloadEntity> getTaskList() { |
"isGroupChild=? and downloadPath!=''", "false"); |
||||||
return DbEntity.findDatas(DownloadEntity.class, "isGroupChild=? and downloadPath!=''", |
} |
||||||
"false"); |
|
||||||
} |
/** |
||||||
|
* 获取所有未完成的普通下载任务 |
||||||
/** |
*/ |
||||||
* 分页获取所有普通下载任务 |
public List<DownloadEntity> getAllNotCompleteTask() { |
||||||
* 获取未完成的普通任务列表{@link #getAllNotCompleteTask()} |
return DbEntity.findDatas(DownloadEntity.class, |
||||||
* 获取已经完成的普通任务列表{@link #getAllCompleteTask()} |
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "false"); |
||||||
* |
} |
||||||
* @param page 当前页,不能小于1 |
|
||||||
* @param num 每页数量,不能小于1 |
/** |
||||||
* @return 如果页数大于总页数,返回null |
* 分页获取所有未完成的普通下载任务 |
||||||
*/ |
* |
||||||
public List<DownloadEntity> getTaskList(int page, int num) { |
* @param page 当前页,不能小于1 |
||||||
CheckUtil.checkPageParams(page, num); |
* @param num 每页数量,不能小于1 |
||||||
return DbEntity.findDatas(DownloadEntity.class, page, num, |
* @return 如果页数大于总页数,返回null |
||||||
"isGroupChild=? and downloadPath!=''", "false"); |
*/ |
||||||
} |
public List<DownloadEntity> getAllNotCompleteTask(int page, int num) { |
||||||
|
CheckUtil.checkPageParams(page, num); |
||||||
/** |
return DbEntity.findDatas(DownloadEntity.class, page, num, |
||||||
* 获取所有未完成的普通下载任务 |
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "false"); |
||||||
*/ |
} |
||||||
public List<DownloadEntity> getAllNotCompleteTask() { |
|
||||||
return DbEntity.findDatas(DownloadEntity.class, |
/** |
||||||
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "false"); |
* 获取所有已经完成的普通任务 |
||||||
} |
*/ |
||||||
|
public List<DownloadEntity> getAllCompleteTask() { |
||||||
/** |
return DbEntity.findDatas(DownloadEntity.class, |
||||||
* 分页获取所有未完成的普通下载任务 |
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "true"); |
||||||
* |
} |
||||||
* @param page 当前页,不能小于1 |
|
||||||
* @param num 每页数量,不能小于1 |
/** |
||||||
* @return 如果页数大于总页数,返回null |
* 分页获取所有已经完成的普通任务 |
||||||
*/ |
* |
||||||
public List<DownloadEntity> getAllNotCompleteTask(int page, int num) { |
* @param page 当前页,不能小于1 |
||||||
CheckUtil.checkPageParams(page, num); |
* @param num 每页数量,不能小于1 |
||||||
return DbEntity.findDatas(DownloadEntity.class, page, num, |
* @return 如果页数大于总页数,返回null |
||||||
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "false"); |
*/ |
||||||
} |
public List<DownloadEntity> getAllCompleteTask(int page, int num) { |
||||||
|
CheckUtil.checkPageParams(page, num); |
||||||
/** |
return DbEntity.findDatas(DownloadEntity.class, |
||||||
* 获取所有已经完成的普通任务 |
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "true"); |
||||||
*/ |
} |
||||||
public List<DownloadEntity> getAllCompleteTask() { |
|
||||||
return DbEntity.findDatas(DownloadEntity.class, |
/** |
||||||
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "true"); |
* 获取任务组列表 |
||||||
} |
* |
||||||
|
* @return 如果没有任务组列表,则返回null |
||||||
/** |
*/ |
||||||
* 分页获取所有已经完成的普通任务 |
public List<DownloadGroupEntity> getGroupTaskList() { |
||||||
* |
List<DGEntityWrapper> wrappers = DbEntity.findRelationData(DGEntityWrapper.class); |
||||||
* @param page 当前页,不能小于1 |
if (wrappers == null || wrappers.isEmpty()) { |
||||||
* @param num 每页数量,不能小于1 |
return null; |
||||||
* @return 如果页数大于总页数,返回null |
} |
||||||
*/ |
List<DownloadGroupEntity> entities = new ArrayList<>(); |
||||||
public List<DownloadEntity> getAllCompleteTask(int page, int num) { |
for (DGEntityWrapper wrapper : wrappers) { |
||||||
CheckUtil.checkPageParams(page, num); |
entities.add(wrapper.groupEntity); |
||||||
return DbEntity.findDatas(DownloadEntity.class, |
} |
||||||
"isGroupChild=? and downloadPath!='' and isComplete=?", "false", "true"); |
return entities; |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 获取任务组列表 |
* 分页获取祝贺任务列表 |
||||||
* |
* |
||||||
* @return 如果没有任务组列表,则返回null |
* @param page 当前页,不能小于1 |
||||||
*/ |
* @param num 每页数量,不能小于1 |
||||||
public List<DownloadGroupEntity> getGroupTaskList() { |
* @return 如果没有任务组列表,则返回null |
||||||
List<DGEntityWrapper> wrappers = DbEntity.findRelationData(DGEntityWrapper.class); |
*/ |
||||||
if (wrappers == null || wrappers.isEmpty()) { |
public List<DownloadGroupEntity> getGroupTaskList(int page, int num) { |
||||||
return null; |
List<DGEntityWrapper> wrappers = DbEntity.findRelationData(DGEntityWrapper.class, page, num); |
||||||
} |
if (wrappers == null || wrappers.isEmpty()) { |
||||||
List<DownloadGroupEntity> entities = new ArrayList<>(); |
return null; |
||||||
for (DGEntityWrapper wrapper : wrappers) { |
} |
||||||
entities.add(wrapper.groupEntity); |
List<DownloadGroupEntity> entities = new ArrayList<>(); |
||||||
} |
for (DGEntityWrapper wrapper : wrappers) { |
||||||
return entities; |
entities.add(wrapper.groupEntity); |
||||||
} |
} |
||||||
|
return entities; |
||||||
/** |
} |
||||||
* 分页获取祝贺任务列表 |
|
||||||
* |
/** |
||||||
* @param page 当前页,不能小于1 |
* 获取普通任务和任务组的任务列表 |
||||||
* @param num 每页数量,不能小于1 |
*/ |
||||||
* @return 如果没有任务组列表,则返回null |
public List<AbsEntity> getTotalTaskList() { |
||||||
*/ |
List<AbsEntity> list = new ArrayList<>(); |
||||||
public List<DownloadGroupEntity> getGroupTaskList(int page, int num) { |
List<DownloadEntity> simpleTask = getTaskList(); |
||||||
List<DGEntityWrapper> wrappers = DbEntity.findRelationData(DGEntityWrapper.class, page, num); |
List<DownloadGroupEntity> groupTask = getGroupTaskList(); |
||||||
if (wrappers == null || wrappers.isEmpty()) { |
if (simpleTask != null && !simpleTask.isEmpty()) { |
||||||
return null; |
list.addAll(simpleTask); |
||||||
} |
} |
||||||
List<DownloadGroupEntity> entities = new ArrayList<>(); |
if (groupTask != null && !groupTask.isEmpty()) { |
||||||
for (DGEntityWrapper wrapper : wrappers) { |
list.addAll(groupTask); |
||||||
entities.add(wrapper.groupEntity); |
} |
||||||
} |
return list; |
||||||
return entities; |
} |
||||||
} |
|
||||||
|
/** |
||||||
/** |
* 停止所有正在下载的任务,并清空等待队列。 |
||||||
* 获取普通任务和任务组的任务列表 |
*/ |
||||||
*/ |
public void stopAllTask() { |
||||||
public List<AbsEntity> getTotalTaskList() { |
AriaManager.getInstance(AriaManager.APP) |
||||||
List<AbsEntity> list = new ArrayList<>(); |
.setCmd(NormalCmdFactory.getInstance() |
||||||
List<DownloadEntity> simpleTask = getTaskList(); |
.createCmd(new DTaskWrapper(null), NormalCmdFactory.TASK_STOP_ALL, |
||||||
List<DownloadGroupEntity> groupTask = getGroupTaskList(); |
ICmd.TASK_TYPE_DOWNLOAD)) |
||||||
if (simpleTask != null && !simpleTask.isEmpty()) { |
.exe(); |
||||||
list.addAll(simpleTask); |
} |
||||||
} |
|
||||||
if (groupTask != null && !groupTask.isEmpty()) { |
/** |
||||||
list.addAll(groupTask); |
* 恢复所有正在下载的任务 |
||||||
} |
* 1.如果执行队列没有满,则开始下载任务,直到执行队列满 |
||||||
return list; |
* 2.如果队列执行队列已经满了,则将所有任务添加到等待队列中 |
||||||
} |
*/ |
||||||
|
public void resumeAllTask() { |
||||||
/** |
AriaManager.getInstance(AriaManager.APP) |
||||||
* 停止所有正在下载的任务,并清空等待队列。 |
.setCmd(NormalCmdFactory.getInstance() |
||||||
*/ |
.createCmd(new DTaskWrapper(null), NormalCmdFactory.TASK_RESUME_ALL, |
||||||
public void stopAllTask() { |
ICmd.TASK_TYPE_DOWNLOAD)) |
||||||
AriaManager.getInstance(AriaManager.APP) |
.exe(); |
||||||
.setCmd(NormalCmdFactory.getInstance() |
} |
||||||
.createCmd(new DTaskWrapper(null), NormalCmdFactory.TASK_STOP_ALL, |
|
||||||
ICmd.TASK_TYPE_DOWNLOAD)) |
/** |
||||||
.exe(); |
* 删除所有任务 |
||||||
} |
* |
||||||
|
* @param removeFile {@code true} 删除已经下载完成的任务,不仅删除下载记录,还会删除已经下载完成的文件,{@code false} |
||||||
/** |
* 如果文件已经下载完成,只删除下载记录 |
||||||
* 恢复所有正在下载的任务 |
*/ |
||||||
* 1.如果执行队列没有满,则开始下载任务,直到执行队列满 |
public void removeAllTask(boolean removeFile) { |
||||||
* 2.如果队列执行队列已经满了,则将所有任务添加到等待队列中 |
final AriaManager ariaManager = AriaManager.getInstance(AriaManager.APP); |
||||||
*/ |
CancelAllCmd cancelCmd = |
||||||
public void resumeAllTask() { |
(CancelAllCmd) CommonUtil.createNormalCmd(new DTaskWrapper(null), |
||||||
AriaManager.getInstance(AriaManager.APP) |
NormalCmdFactory.TASK_CANCEL_ALL, ICmd.TASK_TYPE_DOWNLOAD); |
||||||
.setCmd(NormalCmdFactory.getInstance() |
cancelCmd.removeFile = removeFile; |
||||||
.createCmd(new DTaskWrapper(null), NormalCmdFactory.TASK_RESUME_ALL, |
ariaManager.setCmd(cancelCmd).exe(); |
||||||
ICmd.TASK_TYPE_DOWNLOAD)) |
Set<String> keys = ariaManager.getReceiver().keySet(); |
||||||
.exe(); |
for (String key : keys) { |
||||||
} |
ariaManager.getReceiver().remove(key); |
||||||
|
} |
||||||
/** |
} |
||||||
* 删除所有任务 |
|
||||||
* |
|
||||||
* @param removeFile {@code true} 删除已经下载完成的任务,不仅删除下载记录,还会删除已经下载完成的文件,{@code false} |
|
||||||
* 如果文件已经下载完成,只删除下载记录 |
|
||||||
*/ |
|
||||||
public void removeAllTask(boolean removeFile) { |
|
||||||
final AriaManager ariaManager = AriaManager.getInstance(AriaManager.APP); |
|
||||||
CancelAllCmd cancelCmd = |
|
||||||
(CancelAllCmd) CommonUtil.createNormalCmd(new DTaskWrapper(null), |
|
||||||
NormalCmdFactory.TASK_CANCEL_ALL, ICmd.TASK_TYPE_DOWNLOAD); |
|
||||||
cancelCmd.removeFile = removeFile; |
|
||||||
ariaManager.setCmd(cancelCmd).exe(); |
|
||||||
Set<String> keys = ariaManager.getReceiver().keySet(); |
|
||||||
for (String key : keys) { |
|
||||||
ariaManager.getReceiver().remove(key); |
|
||||||
} |
|
||||||
} |
|
||||||
} |
} |
@ -0,0 +1,101 @@ |
|||||||
|
/* |
||||||
|
* Licensed to the Apache Software Foundation (ASF) under one |
||||||
|
* or more contributor license agreements. See the NOTICE file |
||||||
|
* distributed with this work for additional information |
||||||
|
* regarding copyright ownership. The ASF licenses this file |
||||||
|
* to you under the Apache License, Version 2.0 (the |
||||||
|
* "License"); you may not use this file except in compliance |
||||||
|
* with the License. You may obtain a copy of the License at |
||||||
|
* |
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
* |
||||||
|
* Unless required by applicable law or agreed to in writing, software |
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS, |
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||||
|
* See the License for the specific language governing permissions and |
||||||
|
* limitations under the License. |
||||||
|
*/ |
||||||
|
|
||||||
|
package com.arialyy.aria.core.download.downloader; |
||||||
|
|
||||||
|
import com.arialyy.aria.util.ALog; |
||||||
|
import java.io.DataInputStream; |
||||||
|
import java.io.IOException; |
||||||
|
import java.io.InputStream; |
||||||
|
|
||||||
|
// Data is expected to be a series of data chunks in the form <chunk size><chunk bytes><chunk size><chunk bytes>
|
||||||
|
// The final data chunk should be a 0-length chunk which will indicate end of input.
|
||||||
|
@Deprecated |
||||||
|
public class ChunkedInputStream extends InputStream { |
||||||
|
private static final String TAG = "ChunkedInputStream"; |
||||||
|
|
||||||
|
private DataInputStream din; |
||||||
|
private int unreadBytes = 0; // Bytes remaining in the current chunk of data
|
||||||
|
private byte[] singleByte = new byte[1]; |
||||||
|
private boolean endOfData = false; |
||||||
|
private String id; |
||||||
|
|
||||||
|
public ChunkedInputStream(InputStream in, String id) { |
||||||
|
din = new DataInputStream(in); |
||||||
|
this.id = id; |
||||||
|
ALog.d(TAG, String.format("Creating chunked input for %s", id)); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public void close() throws IOException { |
||||||
|
ALog.d(TAG, String.format("%s: Closing chunked input.", id)); |
||||||
|
din.close(); |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public int read() throws IOException { |
||||||
|
int bytesRead = read(singleByte, 0, 1); |
||||||
|
return (bytesRead == -1) ? -1 : (int) singleByte[0]; |
||||||
|
} |
||||||
|
|
||||||
|
@Override |
||||||
|
public int read(byte[] b, int off, int len) throws IOException { |
||||||
|
int bytesRead = 0; |
||||||
|
|
||||||
|
if (len < 0) { |
||||||
|
throw new IllegalArgumentException(id + ": Negative read length"); |
||||||
|
} else if (len == 0) { |
||||||
|
return 0; |
||||||
|
} |
||||||
|
|
||||||
|
// If there is a current unread chunk, read from that, or else get the next chunk.
|
||||||
|
if (unreadBytes == 0) { |
||||||
|
try { |
||||||
|
// Find the next chunk size
|
||||||
|
unreadBytes = din.readInt(); |
||||||
|
if (ALog.DEBUG) { |
||||||
|
ALog.d(TAG, String.format("%s: Chunk size %s", id, unreadBytes)); |
||||||
|
} |
||||||
|
if (unreadBytes == 0) { |
||||||
|
ALog.d(TAG, String.format("%s: Hit end of data", id)); |
||||||
|
endOfData = true; |
||||||
|
return -1; |
||||||
|
} |
||||||
|
} catch (IOException err) { |
||||||
|
throw new IOException(id + ": Error while attempting to read chunk length", err); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
int bytesToRead = Math.min(len, unreadBytes); |
||||||
|
try { |
||||||
|
din.readFully(b, off, bytesToRead); |
||||||
|
} catch (IOException err) { |
||||||
|
throw new IOException( |
||||||
|
id + ": Error while attempting to read " + bytesToRead + " bytes from current chunk", |
||||||
|
err); |
||||||
|
} |
||||||
|
unreadBytes -= bytesToRead; |
||||||
|
bytesRead += bytesToRead; |
||||||
|
|
||||||
|
return bytesRead; |
||||||
|
} |
||||||
|
|
||||||
|
public boolean isEndOfData() { |
||||||
|
return endOfData; |
||||||
|
} |
||||||
|
} |
File diff suppressed because it is too large
Load Diff
@ -1,257 +1,302 @@ |
|||||||
/* |
/* |
||||||
* Copyright (C) 2016 AriaLyy(https://github.com/AriaLyy/Aria)
|
* Copyright (C) 2016 AriaLyy(https://github.com/AriaLyy/Aria)
|
||||||
* |
* |
||||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||||
* you may not use this file except in compliance with the License. |
* you may not use this file except in compliance with the License. |
||||||
* You may obtain a copy of the License at |
* You may obtain a copy of the License at |
||||||
* |
* |
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
* |
* |
||||||
* Unless required by applicable law or agreed to in writing, software |
* Unless required by applicable law or agreed to in writing, software |
||||||
* distributed under the License is distributed on an "AS IS" BASIS, |
* distributed under the License is distributed on an "AS IS" BASIS, |
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||||
* See the License for the specific language governing permissions and |
* See the License for the specific language governing permissions and |
||||||
* limitations under the License. |
* limitations under the License. |
||||||
*/ |
*/ |
||||||
|
|
||||||
package com.arialyy.aria.orm; |
package com.arialyy.aria.orm; |
||||||
|
|
||||||
import android.content.Context; |
import android.content.Context; |
||||||
import android.database.Cursor; |
import android.database.Cursor; |
||||||
import android.database.sqlite.SQLiteDatabase; |
import android.database.sqlite.SQLiteDatabase; |
||||||
import android.database.sqlite.SQLiteOpenHelper; |
import android.database.sqlite.SQLiteOpenHelper; |
||||||
import com.arialyy.aria.util.ALog; |
import android.os.Build; |
||||||
import java.util.ArrayList; |
import com.arialyy.aria.util.ALog; |
||||||
import java.util.HashMap; |
import java.io.File; |
||||||
import java.util.List; |
import java.util.ArrayList; |
||||||
import java.util.Map; |
import java.util.HashMap; |
||||||
import java.util.Set; |
import java.util.List; |
||||||
|
import java.util.Map; |
||||||
/** |
import java.util.Set; |
||||||
* Created by lyy on 2015/11/2. |
|
||||||
* sql帮助类 |
/** |
||||||
*/ |
* Created by lyy on 2015/11/2. |
||||||
final class SqlHelper extends SQLiteOpenHelper { |
* sql帮助类 |
||||||
private static final String TAG = "SqlHelper"; |
*/ |
||||||
static volatile SqlHelper INSTANCE = null; |
final class SqlHelper extends SQLiteOpenHelper { |
||||||
|
private static final String TAG = "SqlHelper"; |
||||||
private DelegateCommon mDelegate; |
private static volatile SqlHelper INSTANCE = null; |
||||||
|
private Context mContext; |
||||||
synchronized static SqlHelper init(Context context) { |
|
||||||
if (INSTANCE == null) { |
private DelegateCommon mDelegate; |
||||||
synchronized (SqlHelper.class) { |
|
||||||
DelegateCommon delegate = DelegateManager.getInstance().getDelegate(DelegateCommon.class); |
synchronized static SqlHelper init(Context context) { |
||||||
INSTANCE = new SqlHelper(context.getApplicationContext(), delegate); |
if (INSTANCE == null) { |
||||||
SQLiteDatabase db = INSTANCE.getWritableDatabase(); |
synchronized (SqlHelper.class) { |
||||||
db = delegate.checkDb(db); |
DelegateCommon delegate = DelegateManager.getInstance().getDelegate(DelegateCommon.class); |
||||||
// SQLite在3.6.19版本中开始支持外键约束,
|
INSTANCE = new SqlHelper(context.getApplicationContext(), delegate); |
||||||
// 而在Android中 2.1以前的版本使用的SQLite版本是3.5.9, 在2.2版本中使用的是3.6.22.
|
} |
||||||
// 但是为了兼容以前的程序,默认并没有启用该功能,如果要启用该功能
|
} |
||||||
// 需要使用如下语句:
|
return INSTANCE; |
||||||
db.execSQL("PRAGMA foreign_keys=ON;"); |
} |
||||||
Set<String> tables = DBConfig.mapping.keySet(); |
|
||||||
for (String tableName : tables) { |
static SqlHelper getInstance() { |
||||||
Class clazz = DBConfig.mapping.get(tableName); |
return INSTANCE; |
||||||
|
} |
||||||
if (!delegate.tableExists(db, clazz)) { |
|
||||||
delegate.createTable(db, clazz); |
private SqlHelper(Context context, DelegateCommon delegate) { |
||||||
} |
super(DBConfig.SAVE_IN_SDCARD ? new DatabaseContext(context) : context, DBConfig.DB_NAME, null, |
||||||
} |
DBConfig.VERSION); |
||||||
} |
mContext = context; |
||||||
} |
mDelegate = delegate; |
||||||
return INSTANCE; |
} |
||||||
} |
|
||||||
|
@Override public void onOpen(SQLiteDatabase db) { |
||||||
private SqlHelper(Context context, DelegateCommon delegate) { |
super.onOpen(db); |
||||||
super(DBConfig.SAVE_IN_SDCARD ? new DatabaseContext(context) : context, DBConfig.DB_NAME, null, |
} |
||||||
DBConfig.VERSION); |
|
||||||
mDelegate = delegate; |
@Override public void onConfigure(SQLiteDatabase db) { |
||||||
} |
super.onConfigure(db); |
||||||
|
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) { |
||||||
@Override public void onCreate(SQLiteDatabase db) { |
db.setForeignKeyConstraintsEnabled(true); |
||||||
|
} else { |
||||||
} |
// SQLite在3.6.19版本中开始支持外键约束,
|
||||||
|
// 而在Android中 2.1以前的版本使用的SQLite版本是3.5.9, 在2.2版本中使用的是3.6.22.
|
||||||
@Override public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { |
// 但是为了兼容以前的程序,默认并没有启用该功能,如果要启用该功能
|
||||||
if (oldVersion < newVersion) { |
// 需要使用如下语句:
|
||||||
if (oldVersion < 31) { |
db.execSQL("PRAGMA foreign_keys=ON;"); |
||||||
handle314AriaUpdate(db); |
} |
||||||
} else if (oldVersion < 45) { |
if (DBConfig.DEBUG) { |
||||||
handle360AriaUpdate(db); |
db.enableWriteAheadLogging(); |
||||||
} else { |
} |
||||||
handleDbUpdate(db, null, null); |
} |
||||||
} |
|
||||||
} |
@Override public void onCreate(SQLiteDatabase db) { |
||||||
} |
DelegateCommon delegate = DelegateManager.getInstance().getDelegate(DelegateCommon.class); |
||||||
|
Set<String> tables = DBConfig.mapping.keySet(); |
||||||
@Override public void onDowngrade(SQLiteDatabase db, int oldVersion, int newVersion) { |
for (String tableName : tables) { |
||||||
if (oldVersion > newVersion) { |
Class clazz = DBConfig.mapping.get(tableName); |
||||||
handleDbUpdate(db, null, null); |
if (!delegate.tableExists(db, clazz)) { |
||||||
} |
delegate.createTable(db, clazz); |
||||||
} |
} |
||||||
|
} |
||||||
/** |
} |
||||||
* 处理数据库升级,该段代码无法修改表字段 |
|
||||||
* |
@Override public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { |
||||||
* @param modifyColumns 需要修改的表字段的映射,key为表名, |
if (oldVersion < newVersion) { |
||||||
* value{@code Map<String, String>}中的Map的key为老字段名称,value为该老字段对应的新字段名称 |
if (oldVersion < 31) { |
||||||
* @param delColumns 需要删除的表字段,key为表名,value{@code List<String>}为需要删除的字段列表 |
handle314AriaUpdate(db); |
||||||
*/ |
} else if (oldVersion < 45) { |
||||||
private void handleDbUpdate(SQLiteDatabase db, Map<String, Map<String, String>> modifyColumns, |
handle360AriaUpdate(db); |
||||||
Map<String, List<String>> delColumns) { |
} else { |
||||||
if (db == null) { |
handleDbUpdate(db, null, null); |
||||||
ALog.e("SqlHelper", "db 为 null"); |
} |
||||||
return; |
} |
||||||
} else if (!db.isOpen()) { |
} |
||||||
ALog.e("SqlHelper", "db已关闭"); |
|
||||||
return; |
@Override public void onDowngrade(SQLiteDatabase db, int oldVersion, int newVersion) { |
||||||
} |
if (oldVersion > newVersion) { |
||||||
|
handleDbUpdate(db, null, null); |
||||||
try { |
} |
||||||
db.beginTransaction(); |
} |
||||||
Set<String> tables = DBConfig.mapping.keySet(); |
|
||||||
for (String tableName : tables) { |
/** |
||||||
Class clazz = DBConfig.mapping.get(tableName); |
* 获取数据库连接 |
||||||
if (mDelegate.tableExists(db, clazz)) { |
*/ |
||||||
db = mDelegate.checkDb(db); |
SQLiteDatabase getDb() { |
||||||
//修改表名为中介表名
|
SQLiteDatabase db; |
||||||
String alertSql = String.format("ALTER TABLE %s RENAME TO %s_temp", tableName, tableName); |
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { |
||||||
db.execSQL(alertSql); |
SQLiteDatabase.OpenParams params = new SQLiteDatabase.OpenParams.Builder().setOpenFlags( |
||||||
|
SQLiteDatabase.NO_LOCALIZED_COLLATORS | SQLiteDatabase.OPEN_READWRITE | |
||||||
//创建新表
|
SQLiteDatabase.CREATE_IF_NECESSARY).build(); |
||||||
mDelegate.createTable(db, clazz); |
setOpenParams(params); |
||||||
|
db = getWritableDatabase(); |
||||||
String sql = String.format("SELECT COUNT(*) FROM %s_temp", tableName); |
} else { |
||||||
Cursor cursor = db.rawQuery(sql, null); |
//SQLiteDatabase.openOrCreateDatabase()
|
||||||
cursor.moveToFirst(); |
File dbFile = mContext.getDatabasePath(DBConfig.DB_NAME); |
||||||
long count = cursor.getLong(0); |
if (!dbFile.exists()) { |
||||||
cursor.close(); |
db = getWritableDatabase(); |
||||||
|
} else { |
||||||
if (count > 0) { |
// 触发一次SQLiteOpenHelper的流程,再使用NO_LOCALIZED_COLLATORS标志打开数据库
|
||||||
// 获取所有表字段名称
|
db = getReadableDatabase(); |
||||||
Cursor columnC = |
db.close(); |
||||||
db.rawQuery(String.format("PRAGMA table_info(%s_temp)", tableName), null); |
db = SQLiteDatabase.openDatabase(dbFile.getPath(), null, |
||||||
StringBuilder params = new StringBuilder(); |
SQLiteDatabase.NO_LOCALIZED_COLLATORS | SQLiteDatabase.OPEN_READWRITE | |
||||||
|
SQLiteDatabase.CREATE_IF_NECESSARY); |
||||||
while (columnC.moveToNext()) { |
} |
||||||
String columnName = columnC.getString(columnC.getColumnIndex("name")); |
} |
||||||
if (delColumns != null && delColumns.get(tableName) != null) { |
return db; |
||||||
List<String> delColumn = delColumns.get(tableName); |
} |
||||||
if (delColumn != null && !delColumn.isEmpty()) { |
|
||||||
if (delColumn.contains(columnName)) { |
/** |
||||||
continue; |
* 处理数据库升级,该段代码无法修改表字段 |
||||||
} |
* |
||||||
} |
* @param modifyColumns 需要修改的表字段的映射,key为表名, |
||||||
} |
* value{@code Map<String, String>}中的Map的key为老字段名称,value为该老字段对应的新字段名称 |
||||||
|
* @param delColumns 需要删除的表字段,key为表名,value{@code List<String>}为需要删除的字段列表 |
||||||
params.append(columnName).append(","); |
*/ |
||||||
} |
private void handleDbUpdate(SQLiteDatabase db, Map<String, Map<String, String>> modifyColumns, |
||||||
columnC.close(); |
Map<String, List<String>> delColumns) { |
||||||
|
if (db == null) { |
||||||
String oldParamStr = params.toString(); |
ALog.e("SqlHelper", "db 为 null"); |
||||||
oldParamStr = oldParamStr.substring(0, oldParamStr.length() - 1); |
return; |
||||||
String newParamStr = oldParamStr; |
} else if (!db.isOpen()) { |
||||||
// 处理字段名称改变
|
ALog.e("SqlHelper", "db已关闭"); |
||||||
if (modifyColumns != null) { |
return; |
||||||
//newParamStr = params.toString();
|
} |
||||||
Map<String, String> columnMap = modifyColumns.get(tableName); |
|
||||||
if (columnMap != null && !columnMap.isEmpty()) { |
try { |
||||||
Set<String> keys = columnMap.keySet(); |
db.beginTransaction(); |
||||||
for (String key : keys) { |
Set<String> tables = DBConfig.mapping.keySet(); |
||||||
if (newParamStr.contains(key)) { |
for (String tableName : tables) { |
||||||
newParamStr = newParamStr.replace(key, columnMap.get(key)); |
Class clazz = DBConfig.mapping.get(tableName); |
||||||
} |
if (mDelegate.tableExists(db, clazz)) { |
||||||
} |
//修改表名为中介表名
|
||||||
} |
String alertSql = String.format("ALTER TABLE %s RENAME TO %s_temp", tableName, tableName); |
||||||
} |
db.execSQL(alertSql); |
||||||
//恢复数据
|
|
||||||
String insertSql = |
//创建新表
|
||||||
String.format("INSERT INTO %s (%s) SELECT %s FROM %s_temp", tableName, newParamStr, |
mDelegate.createTable(db, clazz); |
||||||
oldParamStr, tableName); |
|
||||||
ALog.d(TAG, "insertSql = " + insertSql); |
String sql = String.format("SELECT COUNT(*) FROM %s_temp", tableName); |
||||||
db.execSQL(insertSql); |
Cursor cursor = db.rawQuery(sql, null); |
||||||
} |
cursor.moveToFirst(); |
||||||
//删除中介表
|
long count = cursor.getLong(0); |
||||||
mDelegate.dropTable(db, tableName + "_temp"); |
cursor.close(); |
||||||
} |
|
||||||
} |
if (count > 0) { |
||||||
db.setTransactionSuccessful(); |
// 获取所有表字段名称
|
||||||
} catch (Exception e) { |
Cursor columnC = |
||||||
ALog.e(TAG, e); |
db.rawQuery(String.format("PRAGMA table_info(%s_temp)", tableName), null); |
||||||
} finally { |
StringBuilder params = new StringBuilder(); |
||||||
db.endTransaction(); |
|
||||||
} |
while (columnC.moveToNext()) { |
||||||
|
String columnName = columnC.getString(columnC.getColumnIndex("name")); |
||||||
mDelegate.close(db); |
if (delColumns != null && delColumns.get(tableName) != null) { |
||||||
} |
List<String> delColumn = delColumns.get(tableName); |
||||||
|
if (delColumn != null && !delColumn.isEmpty()) { |
||||||
/** |
if (delColumn.contains(columnName)) { |
||||||
* 处理3.6以下版本的数据库升级 |
continue; |
||||||
*/ |
} |
||||||
private void handle360AriaUpdate(SQLiteDatabase db) { |
} |
||||||
String[] taskTables = |
} |
||||||
new String[] { "UploadTaskEntity", "DownloadTaskEntity", "DownloadGroupTaskEntity" }; |
|
||||||
for (String taskTable : taskTables) { |
params.append(columnName).append(","); |
||||||
if (mDelegate.tableExists(db, taskTable)) { |
} |
||||||
mDelegate.dropTable(db, taskTable); |
columnC.close(); |
||||||
} |
|
||||||
} |
String oldParamStr = params.toString(); |
||||||
Map<String, Map<String, String>> columnMap = new HashMap<>(); |
oldParamStr = oldParamStr.substring(0, oldParamStr.length() - 1); |
||||||
Map<String, String> map = new HashMap<>(); |
String newParamStr = oldParamStr; |
||||||
map.put("groupName", "groupHash"); |
// 处理字段名称改变
|
||||||
columnMap.put("DownloadEntity", map); |
if (modifyColumns != null) { |
||||||
columnMap.put("DownloadGroupEntity", map); |
//newParamStr = params.toString();
|
||||||
handleDbUpdate(db, columnMap, null); |
Map<String, String> columnMap = modifyColumns.get(tableName); |
||||||
} |
if (columnMap != null && !columnMap.isEmpty()) { |
||||||
|
Set<String> keys = columnMap.keySet(); |
||||||
/** |
for (String key : keys) { |
||||||
* 处理3.4版本之前数据库迁移,主要是修改子表外键字段对应的值 |
if (newParamStr.contains(key)) { |
||||||
*/ |
newParamStr = newParamStr.replace(key, columnMap.get(key)); |
||||||
private void handle314AriaUpdate(SQLiteDatabase db) { |
} |
||||||
String[] taskTables = |
} |
||||||
new String[] { "UploadTaskEntity", "DownloadTaskEntity", "DownloadGroupTaskEntity" }; |
} |
||||||
for (String taskTable : taskTables) { |
} |
||||||
if (mDelegate.tableExists(db, taskTable)) { |
//恢复数据
|
||||||
mDelegate.dropTable(db, taskTable); |
String insertSql = |
||||||
} |
String.format("INSERT INTO %s (%s) SELECT %s FROM %s_temp", tableName, newParamStr, |
||||||
} |
oldParamStr, tableName); |
||||||
|
ALog.d(TAG, "insertSql = " + insertSql); |
||||||
//删除所有主键为null和逐渐重复的数据
|
db.execSQL(insertSql); |
||||||
String[] tables = new String[] { "DownloadEntity", "DownloadGroupEntity" }; |
} |
||||||
String[] keys = new String[] { "downloadPath", "groupName" }; |
//删除中介表
|
||||||
int i = 0; |
mDelegate.dropTable(db, tableName + "_temp"); |
||||||
for (String tableName : tables) { |
} |
||||||
String pColumn = keys[i]; |
} |
||||||
String nullSql = |
db.setTransactionSuccessful(); |
||||||
String.format("DELETE FROM %s WHERE %s='' OR %s IS NULL", tableName, pColumn, pColumn); |
} catch (Exception e) { |
||||||
ALog.d(TAG, nullSql); |
ALog.e(TAG, e); |
||||||
db.execSQL(nullSql); |
} finally { |
||||||
|
db.endTransaction(); |
||||||
//删除所有主键重复的数据
|
} |
||||||
String repeatSql = |
} |
||||||
String.format( |
|
||||||
"DELETE FROM %s WHERE %s IN(SELECT %s FROM %s GROUP BY %s HAVING COUNT(%s) > 1)", |
/** |
||||||
tableName, pColumn, pColumn, tableName, pColumn, pColumn); |
* 处理3.6以下版本的数据库升级 |
||||||
|
*/ |
||||||
ALog.d(TAG, repeatSql); |
private void handle360AriaUpdate(SQLiteDatabase db) { |
||||||
db.execSQL(repeatSql); |
String[] taskTables = |
||||||
i++; |
new String[] { "UploadTaskEntity", "DownloadTaskEntity", "DownloadGroupTaskEntity" }; |
||||||
} |
for (String taskTable : taskTables) { |
||||||
|
if (mDelegate.tableExists(db, taskTable)) { |
||||||
Map<String, Map<String, String>> modifyColumnMap = new HashMap<>(); |
mDelegate.dropTable(db, taskTable); |
||||||
Map<String, String> map = new HashMap<>(); |
} |
||||||
map.put("groupName", "groupHash"); |
} |
||||||
modifyColumnMap.put("DownloadEntity", map); |
Map<String, Map<String, String>> columnMap = new HashMap<>(); |
||||||
modifyColumnMap.put("DownloadGroupEntity", map); |
Map<String, String> map = new HashMap<>(); |
||||||
|
map.put("groupName", "groupHash"); |
||||||
Map<String, List<String>> delColumnMap = new HashMap<>(); |
columnMap.put("DownloadEntity", map); |
||||||
List<String> dEntityDel = new ArrayList<>(); |
columnMap.put("DownloadGroupEntity", map); |
||||||
dEntityDel.add("taskKey"); |
handleDbUpdate(db, columnMap, null); |
||||||
delColumnMap.put("DownloadEntity", dEntityDel); |
} |
||||||
List<String> dgEntityDel = new ArrayList<>(); |
|
||||||
dgEntityDel.add("subtask"); |
/** |
||||||
delColumnMap.put("DownloadGroupEntity", dgEntityDel); |
* 处理3.4版本之前数据库迁移,主要是修改子表外键字段对应的值 |
||||||
|
*/ |
||||||
handleDbUpdate(db, modifyColumnMap, delColumnMap); |
private void handle314AriaUpdate(SQLiteDatabase db) { |
||||||
} |
String[] taskTables = |
||||||
|
new String[] { "UploadTaskEntity", "DownloadTaskEntity", "DownloadGroupTaskEntity" }; |
||||||
|
for (String taskTable : taskTables) { |
||||||
|
if (mDelegate.tableExists(db, taskTable)) { |
||||||
|
mDelegate.dropTable(db, taskTable); |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
//删除所有主键为null和逐渐重复的数据
|
||||||
|
String[] tables = new String[] { "DownloadEntity", "DownloadGroupEntity" }; |
||||||
|
String[] keys = new String[] { "downloadPath", "groupName" }; |
||||||
|
int i = 0; |
||||||
|
for (String tableName : tables) { |
||||||
|
String pColumn = keys[i]; |
||||||
|
String nullSql = |
||||||
|
String.format("DELETE FROM %s WHERE %s='' OR %s IS NULL", tableName, pColumn, pColumn); |
||||||
|
ALog.d(TAG, nullSql); |
||||||
|
db.execSQL(nullSql); |
||||||
|
|
||||||
|
//删除所有主键重复的数据
|
||||||
|
String repeatSql = |
||||||
|
String.format( |
||||||
|
"DELETE FROM %s WHERE %s IN(SELECT %s FROM %s GROUP BY %s HAVING COUNT(%s) > 1)", |
||||||
|
tableName, pColumn, pColumn, tableName, pColumn, pColumn); |
||||||
|
|
||||||
|
ALog.d(TAG, repeatSql); |
||||||
|
db.execSQL(repeatSql); |
||||||
|
i++; |
||||||
|
} |
||||||
|
|
||||||
|
Map<String, Map<String, String>> modifyColumnMap = new HashMap<>(); |
||||||
|
Map<String, String> map = new HashMap<>(); |
||||||
|
map.put("groupName", "groupHash"); |
||||||
|
modifyColumnMap.put("DownloadEntity", map); |
||||||
|
modifyColumnMap.put("DownloadGroupEntity", map); |
||||||
|
|
||||||
|
Map<String, List<String>> delColumnMap = new HashMap<>(); |
||||||
|
List<String> dEntityDel = new ArrayList<>(); |
||||||
|
dEntityDel.add("taskKey"); |
||||||
|
delColumnMap.put("DownloadEntity", dEntityDel); |
||||||
|
List<String> dgEntityDel = new ArrayList<>(); |
||||||
|
dgEntityDel.add("subtask"); |
||||||
|
delColumnMap.put("DownloadGroupEntity", dgEntityDel); |
||||||
|
|
||||||
|
handleDbUpdate(db, modifyColumnMap, delColumnMap); |
||||||
|
} |
||||||
} |
} |
@ -1,254 +1,269 @@ |
|||||||
/* |
/* |
||||||
* Copyright (C) 2016 AriaLyy(https://github.com/AriaLyy/Aria)
|
* Copyright (C) 2016 AriaLyy(https://github.com/AriaLyy/Aria)
|
||||||
* |
* |
||||||
* Licensed under the Apache License, Version 2.0 (the "License"); |
* Licensed under the Apache License, Version 2.0 (the "License"); |
||||||
* you may not use this file except in compliance with the License. |
* you may not use this file except in compliance with the License. |
||||||
* You may obtain a copy of the License at |
* You may obtain a copy of the License at |
||||||
* |
* |
||||||
* http://www.apache.org/licenses/LICENSE-2.0
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
* |
* |
||||||
* Unless required by applicable law or agreed to in writing, software |
* Unless required by applicable law or agreed to in writing, software |
||||||
* distributed under the License is distributed on an "AS IS" BASIS, |
* distributed under the License is distributed on an "AS IS" BASIS, |
||||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||||
* See the License for the specific language governing permissions and |
* See the License for the specific language governing permissions and |
||||||
* limitations under the License. |
* limitations under the License. |
||||||
*/ |
*/ |
||||||
|
|
||||||
package com.arialyy.aria.util; |
package com.arialyy.aria.util; |
||||||
|
|
||||||
import android.text.TextUtils; |
import android.text.TextUtils; |
||||||
import com.arialyy.aria.core.download.DTaskWrapper; |
import com.arialyy.aria.core.download.DTaskWrapper; |
||||||
import com.arialyy.aria.core.download.DownloadEntity; |
import com.arialyy.aria.core.download.DownloadEntity; |
||||||
import com.arialyy.aria.core.inf.AbsTaskWrapper; |
import com.arialyy.aria.core.inf.AbsTaskWrapper; |
||||||
import com.arialyy.aria.core.upload.UTaskWrapper; |
import com.arialyy.aria.core.upload.UTaskWrapper; |
||||||
import com.arialyy.aria.core.upload.UploadEntity; |
import com.arialyy.aria.core.upload.UploadEntity; |
||||||
import com.arialyy.aria.exception.ParamException; |
import com.arialyy.aria.exception.ParamException; |
||||||
import java.io.File; |
import java.io.File; |
||||||
import java.util.List; |
import java.util.List; |
||||||
import java.util.regex.Matcher; |
import java.util.regex.Matcher; |
||||||
import java.util.regex.Pattern; |
import java.util.regex.Pattern; |
||||||
|
|
||||||
/** |
/** |
||||||
* Created by Lyy on 2016/9/23. |
* Created by Lyy on 2016/9/23. |
||||||
* 检查帮助类 |
* 检查帮助类 |
||||||
*/ |
*/ |
||||||
public class CheckUtil { |
public class CheckUtil { |
||||||
private static final String TAG = "CheckUtil"; |
private static final String TAG = "CheckUtil"; |
||||||
|
|
||||||
/** |
/** |
||||||
* 检查ftp上传路径,如果ftp上传路径为空,抛出空指针异常 |
* 检查ftp上传路径,如果ftp上传路径为空,抛出空指针异常 |
||||||
* 如果ftp上传路径不是以"ftp"或"sftp",抛出参数异常 |
* 如果ftp上传路径不是以"ftp"或"sftp",抛出参数异常 |
||||||
* |
* |
||||||
* @param ftpUrl ftp上传路径 |
* @param ftpUrl ftp上传路径 |
||||||
*/ |
*/ |
||||||
public static void checkFtpUploadUrl(String ftpUrl) { |
public static void checkFtpUploadUrl(String ftpUrl) { |
||||||
if (TextUtils.isEmpty(ftpUrl)) { |
if (TextUtils.isEmpty(ftpUrl)) { |
||||||
throw new ParamException("ftp上传路径为空"); |
throw new ParamException("ftp上传路径为空"); |
||||||
} else if (!ftpUrl.startsWith("ftp") || !ftpUrl.startsWith("sftp")) { |
} else if (!ftpUrl.startsWith("ftp") || !ftpUrl.startsWith("sftp")) { |
||||||
throw new ParamException("ftp上传路径无效"); |
throw new ParamException("ftp上传路径无效"); |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 判空 |
* 判空 |
||||||
*/ |
*/ |
||||||
public static void checkNull(Object obj) { |
public static void checkNull(Object obj) { |
||||||
if (obj == null) throw new IllegalArgumentException("不能传入空对象"); |
if (obj == null) throw new IllegalArgumentException("不能传入空对象"); |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 检查分页数据,需要查询的页数,从1开始,如果page小于1 或 num 小于1,则抛出{@link NullPointerException} |
* 检查分页数据,需要查询的页数,从1开始,如果page小于1 或 num 小于1,则抛出{@link NullPointerException} |
||||||
* |
* |
||||||
* @param page 从1 开始 |
* @param page 从1 开始 |
||||||
* @param num 每页数量 |
* @param num 每页数量 |
||||||
*/ |
*/ |
||||||
public static void checkPageParams(int page, int num) { |
public static void checkPageParams(int page, int num) { |
||||||
if (page < 1 || num < 1) throw new NullPointerException("page和num不能小于1"); |
if (page < 1 || num < 1) throw new NullPointerException("page和num不能小于1"); |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 检查sql的expression是否合法 |
* 检查sql的expression是否合法 |
||||||
*/ |
*/ |
||||||
public static void checkSqlExpression(String... expression) { |
public static void checkSqlExpression(String... expression) { |
||||||
if (expression.length == 0) { |
if (expression.length == 0) { |
||||||
throw new IllegalArgumentException("sql语句表达式不能为null"); |
throw new IllegalArgumentException("sql语句表达式不能为null"); |
||||||
} |
} |
||||||
if (expression.length == 1) { |
if (expression.length == 1) { |
||||||
throw new IllegalArgumentException("表达式需要写入参数"); |
throw new IllegalArgumentException("表达式需要写入参数"); |
||||||
} |
} |
||||||
String where = expression[0]; |
String where = expression[0]; |
||||||
if (!where.contains("?")) { |
if (!where.contains("?")) { |
||||||
throw new IllegalArgumentException("请在where语句的'='后编写?"); |
throw new IllegalArgumentException("请在where语句的'='后编写?"); |
||||||
} |
} |
||||||
Pattern pattern = Pattern.compile("\\?"); |
Pattern pattern = Pattern.compile("\\?"); |
||||||
Matcher matcher = pattern.matcher(where); |
Matcher matcher = pattern.matcher(where); |
||||||
int count = 0; |
int count = 0; |
||||||
while (matcher.find()) { |
while (matcher.find()) { |
||||||
count++; |
count++; |
||||||
} |
} |
||||||
if (count < expression.length - 1) { |
if (count < expression.length - 1) { |
||||||
throw new IllegalArgumentException("条件语句的?个数不能小于参数个数"); |
throw new IllegalArgumentException("条件语句的?个数不能小于参数个数"); |
||||||
} |
} |
||||||
if (count > expression.length - 1) { |
if (count > expression.length - 1) { |
||||||
throw new IllegalArgumentException("条件语句的?个数不能大于参数个数"); |
throw new IllegalArgumentException("条件语句的?个数不能大于参数个数"); |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 检查下载实体 |
* 检查下载实体 |
||||||
*/ |
*/ |
||||||
public static void checkDownloadEntity(DownloadEntity entity) { |
public static void checkDownloadEntity(DownloadEntity entity) { |
||||||
checkUrlInvalidThrow(entity.getUrl()); |
checkUrlInvalidThrow(entity.getUrl()); |
||||||
entity.setUrl(entity.getUrl()); |
entity.setUrl(entity.getUrl()); |
||||||
checkPath(entity.getDownloadPath()); |
checkPath(entity.getDownloadPath()); |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 检测下载链接是否为null |
* 检测下载链接是否为null |
||||||
*/ |
*/ |
||||||
public static void checkPath(String path) { |
public static void checkPath(String path) { |
||||||
if (TextUtils.isEmpty(path)) { |
if (TextUtils.isEmpty(path)) { |
||||||
throw new IllegalArgumentException("保存路径不能为null"); |
throw new IllegalArgumentException("保存路径不能为null"); |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 检测url是否合法,如果url不合法,将抛异常 |
* 检测url是否合法,如果url不合法,将抛异常 |
||||||
*/ |
*/ |
||||||
public static void checkUrlInvalidThrow(String url) { |
public static void checkUrlInvalidThrow(String url) { |
||||||
if (TextUtils.isEmpty(url)) { |
if (TextUtils.isEmpty(url)) { |
||||||
throw new IllegalArgumentException("url不能为null"); |
throw new IllegalArgumentException("url不能为null"); |
||||||
} else if (!url.startsWith("http") && !url.startsWith("ftp")) { |
} else if (!url.startsWith("http") && !url.startsWith("ftp")) { |
||||||
throw new IllegalArgumentException("url错误"); |
throw new IllegalArgumentException("url错误"); |
||||||
} |
} |
||||||
int index = url.indexOf("://"); |
int index = url.indexOf("://"); |
||||||
if (index == -1) { |
if (index == -1) { |
||||||
throw new IllegalArgumentException("url不合法"); |
throw new IllegalArgumentException("url不合法"); |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
/** |
/** |
||||||
* 检测url是否合法 |
* 检测url是否合法,如果url不合法,将抛出{@link IllegalArgumentException}异常 |
||||||
* |
*/ |
||||||
* @return {@code true} 合法,{@code false} 非法 |
public static void checkUrl(String url) { |
||||||
*/ |
if (TextUtils.isEmpty(url)) { |
||||||
public static boolean checkUrl(String url) { |
throw new NullPointerException("url为空"); |
||||||
if (TextUtils.isEmpty(url)) { |
} else if (!url.startsWith("http") && !url.startsWith("ftp")) { |
||||||
ALog.e(TAG, "url不能为null"); |
throw new IllegalArgumentException(String.format("url【%s】错误", url)); |
||||||
return false; |
} |
||||||
} else if (!url.startsWith("http") && !url.startsWith("ftp")) { |
int index = url.indexOf("://"); |
||||||
ALog.e(TAG, "url【" + url + "】错误"); |
if (index == -1) { |
||||||
return false; |
throw new IllegalArgumentException(String.format("url【%s】不合法", url)); |
||||||
} |
} |
||||||
int index = url.indexOf("://"); |
} |
||||||
if (index == -1) { |
|
||||||
ALog.e(TAG, "url【" + url + "】不合法"); |
/** |
||||||
} |
* 检测url是否合法 |
||||||
return true; |
* |
||||||
} |
* @return {@code true} 合法,{@code false} 非法 |
||||||
|
*/ |
||||||
/** |
public static boolean checkUrlNotThrow(String url) { |
||||||
* 检测下载链接组是否为null |
if (TextUtils.isEmpty(url)) { |
||||||
*/ |
ALog.e(TAG, "url不能为null"); |
||||||
public static void checkDownloadUrls(List<String> urls) { |
return false; |
||||||
if (urls == null || urls.isEmpty()) { |
} else if (!url.startsWith("http") && !url.startsWith("ftp")) { |
||||||
throw new IllegalArgumentException("链接组不能为null"); |
ALog.e(TAG, "url【" + url + "】错误"); |
||||||
} |
return false; |
||||||
} |
} |
||||||
|
int index = url.indexOf("://"); |
||||||
/** |
if (index == -1) { |
||||||
* 检查下载任务组保存路径 |
ALog.e(TAG, "url【" + url + "】不合法"); |
||||||
*/ |
} |
||||||
public static void checkDownloadPaths(List<String> paths) { |
return true; |
||||||
if (paths == null || paths.isEmpty()) { |
} |
||||||
throw new IllegalArgumentException("链接保存路径不能为null"); |
|
||||||
} |
/** |
||||||
} |
* 检测下载链接组是否为null |
||||||
|
*/ |
||||||
/** |
public static void checkDownloadUrls(List<String> urls) { |
||||||
* 检测上传地址是否为null |
if (urls == null || urls.isEmpty()) { |
||||||
*/ |
throw new IllegalArgumentException("链接组不能为null"); |
||||||
public static void checkUploadPath(String uploadPath) { |
} |
||||||
if (TextUtils.isEmpty(uploadPath)) { |
} |
||||||
throw new IllegalArgumentException("上传地址不能为null"); |
|
||||||
} |
/** |
||||||
File file = new File(uploadPath); |
* 检查下载任务组保存路径 |
||||||
if (!file.exists()) { |
*/ |
||||||
throw new IllegalArgumentException("上传文件不存在"); |
public static void checkDownloadPaths(List<String> paths) { |
||||||
} |
if (paths == null || paths.isEmpty()) { |
||||||
} |
throw new IllegalArgumentException("链接保存路径不能为null"); |
||||||
|
} |
||||||
/** |
} |
||||||
* 检查任务实体 |
|
||||||
*/ |
/** |
||||||
public static void checkTaskEntity(AbsTaskWrapper entity) { |
* 检测上传地址是否为null |
||||||
if (entity instanceof DTaskWrapper) { |
*/ |
||||||
checkDownloadTaskEntity(((DTaskWrapper) entity).getEntity()); |
public static void checkUploadPath(String uploadPath) { |
||||||
} else if (entity instanceof UTaskWrapper) { |
if (TextUtils.isEmpty(uploadPath)) { |
||||||
checkUploadTaskEntity(((UTaskWrapper) entity).getEntity()); |
throw new IllegalArgumentException("上传地址不能为null"); |
||||||
} |
} |
||||||
} |
File file = new File(uploadPath); |
||||||
|
if (!file.exists()) { |
||||||
/** |
throw new IllegalArgumentException("上传文件不存在"); |
||||||
* 检查命令实体 |
} |
||||||
* |
} |
||||||
* @param checkType 删除命令和停止命令不需要检查下载链接和保存路径 |
|
||||||
* @return {@code false}实体无效 |
/** |
||||||
*/ |
* 检查任务实体 |
||||||
public static boolean checkCmdEntity(AbsTaskWrapper entity, boolean checkType) { |
*/ |
||||||
boolean b = false; |
public static void checkTaskEntity(AbsTaskWrapper entity) { |
||||||
if (entity instanceof DTaskWrapper) { |
if (entity instanceof DTaskWrapper) { |
||||||
DownloadEntity entity1 = ((DTaskWrapper) entity).getEntity(); |
checkDownloadTaskEntity(((DTaskWrapper) entity).getEntity()); |
||||||
if (entity1 == null) { |
} else if (entity instanceof UTaskWrapper) { |
||||||
ALog.e(TAG, "下载实体不能为空"); |
checkUploadTaskEntity(((UTaskWrapper) entity).getEntity()); |
||||||
} else if (checkType && TextUtils.isEmpty(entity1.getUrl())) { |
} |
||||||
ALog.e(TAG, "下载链接不能为空"); |
} |
||||||
} else if (checkType && TextUtils.isEmpty(entity1.getDownloadPath())) { |
|
||||||
ALog.e(TAG, "保存路径不能为空"); |
/** |
||||||
} else { |
* 检查命令实体 |
||||||
b = true; |
* |
||||||
} |
* @param checkType 删除命令和停止命令不需要检查下载链接和保存路径 |
||||||
} else if (entity instanceof UTaskWrapper) { |
* @return {@code false}实体无效 |
||||||
UploadEntity entity1 = ((UTaskWrapper) entity).getEntity(); |
*/ |
||||||
if (entity1 == null) { |
public static boolean checkCmdEntity(AbsTaskWrapper entity, boolean checkType) { |
||||||
ALog.e(TAG, "上传实体不能为空"); |
boolean b = false; |
||||||
} else if (TextUtils.isEmpty(entity1.getFilePath())) { |
if (entity instanceof DTaskWrapper) { |
||||||
ALog.e(TAG, "上传文件路径不能为空"); |
DownloadEntity entity1 = ((DTaskWrapper) entity).getEntity(); |
||||||
} else { |
if (entity1 == null) { |
||||||
b = true; |
ALog.e(TAG, "下载实体不能为空"); |
||||||
} |
} else if (checkType && TextUtils.isEmpty(entity1.getUrl())) { |
||||||
} |
ALog.e(TAG, "下载链接不能为空"); |
||||||
return b; |
} else if (checkType && TextUtils.isEmpty(entity1.getDownloadPath())) { |
||||||
} |
ALog.e(TAG, "保存路径不能为空"); |
||||||
|
} else { |
||||||
/** |
b = true; |
||||||
* 检查上传实体是否合法 |
} |
||||||
*/ |
} else if (entity instanceof UTaskWrapper) { |
||||||
private static void checkUploadTaskEntity(UploadEntity entity) { |
UploadEntity entity1 = ((UTaskWrapper) entity).getEntity(); |
||||||
if (entity == null) { |
if (entity1 == null) { |
||||||
throw new NullPointerException("上传实体不能为空"); |
ALog.e(TAG, "上传实体不能为空"); |
||||||
} else if (TextUtils.isEmpty(entity.getFilePath())) { |
} else if (TextUtils.isEmpty(entity1.getFilePath())) { |
||||||
throw new IllegalArgumentException("上传文件路径不能为空"); |
ALog.e(TAG, "上传文件路径不能为空"); |
||||||
} else if (TextUtils.isEmpty(entity.getFileName())) { |
} else { |
||||||
throw new IllegalArgumentException("上传文件名不能为空"); |
b = true; |
||||||
} |
} |
||||||
} |
} |
||||||
|
return b; |
||||||
/** |
} |
||||||
* 检测下载实体是否合法 |
|
||||||
* 合法(true) |
/** |
||||||
* |
* 检查上传实体是否合法 |
||||||
* @param entity 下载实体 |
*/ |
||||||
*/ |
private static void checkUploadTaskEntity(UploadEntity entity) { |
||||||
private static void checkDownloadTaskEntity(DownloadEntity entity) { |
if (entity == null) { |
||||||
if (entity == null) { |
throw new NullPointerException("上传实体不能为空"); |
||||||
throw new NullPointerException("下载实体不能为空"); |
} else if (TextUtils.isEmpty(entity.getFilePath())) { |
||||||
} else if (TextUtils.isEmpty(entity.getUrl())) { |
throw new IllegalArgumentException("上传文件路径不能为空"); |
||||||
throw new IllegalArgumentException("下载链接不能为空"); |
} else if (TextUtils.isEmpty(entity.getFileName())) { |
||||||
} else if (TextUtils.isEmpty(entity.getFileName())) { |
throw new IllegalArgumentException("上传文件名不能为空"); |
||||||
throw new NullPointerException("文件名不能为null"); |
} |
||||||
} else if (TextUtils.isEmpty(entity.getDownloadPath())) { |
} |
||||||
throw new NullPointerException("文件保存路径不能为null"); |
|
||||||
} |
/** |
||||||
} |
* 检测下载实体是否合法 |
||||||
|
* 合法(true) |
||||||
|
* |
||||||
|
* @param entity 下载实体 |
||||||
|
*/ |
||||||
|
private static void checkDownloadTaskEntity(DownloadEntity entity) { |
||||||
|
if (entity == null) { |
||||||
|
throw new NullPointerException("下载实体不能为空"); |
||||||
|
} else if (TextUtils.isEmpty(entity.getUrl())) { |
||||||
|
throw new IllegalArgumentException("下载链接不能为空"); |
||||||
|
} else if (TextUtils.isEmpty(entity.getFileName())) { |
||||||
|
throw new NullPointerException("文件名不能为null"); |
||||||
|
} else if (TextUtils.isEmpty(entity.getDownloadPath())) { |
||||||
|
throw new NullPointerException("文件保存路径不能为null"); |
||||||
|
} |
||||||
|
} |
||||||
} |
} |
@ -1,219 +1,226 @@ |
|||||||
## 开发日志 |
## 开发日志 |
||||||
+ v_3.6.4 |
+ v_3.6.4 |
||||||
- 优化任务接收器的代码结构 |
- 优化任务接收器的代码结构 |
||||||
- 修复`DbEntity.saveAll()`失败的问题 |
- 修复`DbEntity.saveAll()`失败的问题 |
||||||
- 修复分块任务重命名失败的问题 |
- 修复分块任务重命名失败的问题 |
||||||
+ v_3.6.3 (2019/4/2) |
- fix bug https://github.com/AriaLyy/Aria/issues/379 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/377 |
- 移除`getDownloadTask(String url)`、`getGroupTask(List<String> urls)`、`getFtpDirTask(String path)` |
||||||
+ v_3.6.2 (2019/4/1) |
等获取任务的api,如果你希望获取对应状态,请使用实体的状态判断,如:`getDownloadEntity()`、`getDownloadGroupEntity()` |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/368 |
`getFtpDirEntity()` |
||||||
- 增加gradle 5.0支持 |
- fix bug https://github.com/AriaLyy/Aria/issues/388 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/374 |
- 修复使用`Content-Disposition`的文件名时,第一次下载无法重命名文件的问题 |
||||||
- 增加分页功能,详情见:https://aria.laoyuyu.me/aria_doc/api/task_list.html#%E4%BB%BB%E5%8A%A1%E5%88%97%E8%A1%A8%E5%88%86%E9%A1%B5%EF%BC%88362%E4%BB%A5%E4%B8%8A%E7%89%88%E6%9C%AC%E6%94%AF%E6%8C%81%EF%BC%89 |
- 修复使用`Content-Disposition`的文件名时,多次重命名文件的问题 |
||||||
+ v_3.6.1 (2019/3/5) |
+ v_3.6.3 (2019/4/2) |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/367 |
- fix bug https://github.com/AriaLyy/Aria/issues/377 |
||||||
+ v_3.6 (2019/2/27) |
+ v_3.6.2 (2019/4/1) |
||||||
- 优化数据库写入\修改的速度 |
- fix bug https://github.com/AriaLyy/Aria/issues/368 |
||||||
- 精减任务实体的存储 |
- 增加gradle 5.0支持 |
||||||
- 增加下载组合任务的配置 |
- fix bug https://github.com/AriaLyy/Aria/issues/374 |
||||||
- useBroadcast\notNetRetry这两个配置,统一在AppConfig中配置 |
- 增加分页功能,详情见:https://aria.laoyuyu.me/aria_doc/api/task_list.html#%E4%BB%BB%E5%8A%A1%E5%88%97%E8%A1%A8%E5%88%86%E9%A1%B5%EF%BC%88362%E4%BB%A5%E4%B8%8A%E7%89%88%E6%9C%AC%E6%94%AF%E6%8C%81%EF%BC%89 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/361 |
+ v_3.6.1 (2019/3/5) |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/365 |
- fix bug https://github.com/AriaLyy/Aria/issues/367 |
||||||
+ v_3.5.4 (2019/1/8) |
+ v_3.6 (2019/2/27) |
||||||
- 修复不支持断点的下载地址,重复下载出现的数据库主键冲突问题 |
- 优化数据库写入\修改的速度 |
||||||
+ v_3.5.3 (2018/12/23) |
- 精减任务实体的存储 |
||||||
- 修复ftps不能加载默认证书的bug https://github.com/AriaLyy/Aria/issues/334 |
- 增加下载组合任务的配置 |
||||||
- 优化注解性能,移除不必要的判断代码 |
- useBroadcast\notNetRetry这两个配置,统一在AppConfig中配置 |
||||||
- 增加广播支持,详情见:http://aria.laoyuyu.me/aria_doc/api/use_broadcast.html |
- fix bug https://github.com/AriaLyy/Aria/issues/361 |
||||||
- 增加get参数支持 |
- fix bug https://github.com/AriaLyy/Aria/issues/365 |
||||||
```java |
+ v_3.5.4 (2019/1/8) |
||||||
Aria.download(SingleTaskActivity.this) |
- 修复不支持断点的下载地址,重复下载出现的数据库主键冲突问题 |
||||||
.load(DOWNLOAD_URL) // url 必须是主体url,也就是?前面的内容 |
+ v_3.5.3 (2018/12/23) |
||||||
.setFilePath(path, true) |
- 修复ftps不能加载默认证书的bug https://github.com/AriaLyy/Aria/issues/334 |
||||||
.asGet() |
- 优化注解性能,移除不必要的判断代码 |
||||||
.setParams(params) // 设置参数 |
- 增加广播支持,详情见:http://aria.laoyuyu.me/aria_doc/api/use_broadcast.html |
||||||
.start(); |
- 增加get参数支持 |
||||||
``` |
```java |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/335 |
Aria.download(SingleTaskActivity.this) |
||||||
- 新增进度百分比保存 https://github.com/AriaLyy/Aria/issues/336 |
.load(DOWNLOAD_URL) // url 必须是主体url,也就是?前面的内容 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/335 |
.setFilePath(path, true) |
||||||
+ v_3.5.2 |
.asGet() |
||||||
- 添加Serializable接口支持 https://github.com/AriaLyy/Aria/issues/320 |
.setParams(params) // 设置参数 |
||||||
- 失败回调增加错误原因 https://github.com/AriaLyy/Aria/issues/310 |
.start(); |
||||||
``` |
``` |
||||||
@Download.onTaskFail void taskFail(DownloadTask task, Exception e) { |
- fix bug https://github.com/AriaLyy/Aria/issues/335 |
||||||
e.getMessage(); |
- 新增进度百分比保存 https://github.com/AriaLyy/Aria/issues/336 |
||||||
... |
- fix bug https://github.com/AriaLyy/Aria/issues/335 |
||||||
} |
+ v_3.5.2 |
||||||
``` |
- 添加Serializable接口支持 https://github.com/AriaLyy/Aria/issues/320 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/322 |
- 失败回调增加错误原因 https://github.com/AriaLyy/Aria/issues/310 |
||||||
- 新增201 重定向支持 https://github.com/AriaLyy/Aria/issues/318 |
``` |
||||||
- 修复使用`useServerFileName(true)`中含有`"`导致的文件后缀名错误问题 |
@Download.onTaskFail void taskFail(DownloadTask task, Exception e) { |
||||||
- 优化logcat日志提示 |
e.getMessage(); |
||||||
- 修改下载线程的优先级为`Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);` |
... |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/319 |
} |
||||||
- 修复分卡下载失败的问题 https://github.com/AriaLyy/Aria/issues/326 |
``` |
||||||
- 初始化Aria时会将所有数据库状态为下载中的任务改为已停止,防止应用被kill后,任务状态错误 |
- fix bug https://github.com/AriaLyy/Aria/issues/322 |
||||||
- 初始化时自动判断文件是否被删除,文件被删除的任务将自动重置默认值 |
- 新增201 重定向支持 https://github.com/AriaLyy/Aria/issues/318 |
||||||
- 修复刷新url后,文件无法删除的 bug |
- 修复使用`useServerFileName(true)`中含有`"`导致的文件后缀名错误问题 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/309 |
- 优化logcat日志提示 |
||||||
- 优化配置文件的读取 |
- 修改下载线程的优先级为`Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);` |
||||||
+ v_3.5.1 |
- fix bug https://github.com/AriaLyy/Aria/issues/319 |
||||||
- 优化`taskExists`方法 |
- 修复分卡下载失败的问题 https://github.com/AriaLyy/Aria/issues/326 |
||||||
- 添加`post`参数请求支持 |
- 初始化Aria时会将所有数据库状态为下载中的任务改为已停止,防止应用被kill后,任务状态错误 |
||||||
```java |
- 初始化时自动判断文件是否被删除,文件被删除的任务将自动重置默认值 |
||||||
Aria.download(SingleTaskActivity.this) |
- 修复刷新url后,文件无法删除的 bug |
||||||
.load(DOWNLOAD_URL) |
- fix bug https://github.com/AriaLyy/Aria/issues/309 |
||||||
.setFilePath(path) |
- 优化配置文件的读取 |
||||||
.asPost() // post请求 |
+ v_3.5.1 |
||||||
.setParam("key", "value") //传递参数 |
- 优化`taskExists`方法 |
||||||
//.setParams(Map<String, String>) // 传递多参数 |
- 添加`post`参数请求支持 |
||||||
.start(); |
```java |
||||||
``` |
Aria.download(SingleTaskActivity.this) |
||||||
- 增加强制设置文件路径的api, https://github.com/AriaLyy/Aria/issues/311 |
.load(DOWNLOAD_URL) |
||||||
``` |
.setFilePath(path) |
||||||
Aria.download(SingleTaskActivity.this) |
.asPost() // post请求 |
||||||
.load(DOWNLOAD_URL) |
.setParam("key", "value") //传递参数 |
||||||
.setFilePath(path, true) // true表示忽略路径是否被占用 |
//.setParams(Map<String, String>) // 传递多参数 |
||||||
.start(); |
.start(); |
||||||
``` |
``` |
||||||
+ v_3.5 |
- 增加强制设置文件路径的api, https://github.com/AriaLyy/Aria/issues/311 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/302 |
```java |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/283 |
Aria.download(SingleTaskActivity.this) |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/305 |
.load(DOWNLOAD_URL) |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/306 |
.setFilePath(path, true) // true表示忽略路径是否被占用 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/272 (现在,停止所有任务,未开始的任务状态将变为停止) |
.start(); |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/277 |
``` |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/303 |
+ v_3.5 |
||||||
- 优化停止任务的速度 |
- fix bug https://github.com/AriaLyy/Aria/issues/302 |
||||||
- 修复组合任务修改子任务文件名失败的问题 |
- fix bug https://github.com/AriaLyy/Aria/issues/283 |
||||||
+ v_3.4.12 |
- fix bug https://github.com/AriaLyy/Aria/issues/305 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/286 |
- fix bug https://github.com/AriaLyy/Aria/issues/306 |
||||||
- 优化线程池任务 |
- fix bug https://github.com/AriaLyy/Aria/issues/272 (现在,停止所有任务,未开始的任务状态将变为停止) |
||||||
+ v_3.4.11 |
- fix bug https://github.com/AriaLyy/Aria/issues/277 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/288 |
- fix bug https://github.com/AriaLyy/Aria/issues/303 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/282 |
- 优化停止任务的速度 |
||||||
+ v_3.4.10 |
- 修复组合任务修改子任务文件名失败的问题 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/280 |
+ v_3.4.12 |
||||||
+ v_3.4.9 |
- fix bug https://github.com/AriaLyy/Aria/issues/286 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/276 |
- 优化线程池任务 |
||||||
+ v_3.4.8 |
+ v_3.4.11 |
||||||
- 组合任务新增`updateUrls(List<String>)`用于修改组合子任务的url,[see](https://aria.laoyuyu.me/aria_doc/api/update_url.html) |
- fix bug https://github.com/AriaLyy/Aria/issues/288 |
||||||
- 出于安全考虑,FTP数据库去掉密码的保存 |
- fix bug https://github.com/AriaLyy/Aria/issues/282 |
||||||
- 增加FTPS支持 [see](https://aria.laoyuyu.me/aria_doc/download/ftps.html) |
+ v_3.4.10 |
||||||
- 增加速度限制支持[see](https://aria.laoyuyu.me/aria_doc/api/speed_handle.html) |
- fix bug https://github.com/AriaLyy/Aria/issues/280 |
||||||
- 增加内存空间不足验证 |
+ v_3.4.9 |
||||||
+ v_3.4.7 |
- fix bug https://github.com/AriaLyy/Aria/issues/276 |
||||||
- 修复分块任务异常操作导致的问题 |
+ v_3.4.8 |
||||||
+ v_3.4.6 |
- 组合任务新增`updateUrls(List<String>)`用于修改组合子任务的url,[see](https://aria.laoyuyu.me/aria_doc/api/update_url.html) |
||||||
- 修复android 4.4.4 版本多dex下无法进行回调的问题 |
- 出于安全考虑,FTP数据库去掉密码的保存 |
||||||
- 新增`updateUrl(newUrl)`用于修改任务的url,[see](https://aria.laoyuyu.me/aria_doc/api/task_handle.html#%E6%9B%B4%E6%96%B0%E4%BB%BB%E5%8A%A1url) |
- 增加FTPS支持 [see](https://aria.laoyuyu.me/aria_doc/download/ftps.html) |
||||||
- 优化分块下载 |
- 增加速度限制支持[see](https://aria.laoyuyu.me/aria_doc/api/speed_handle.html) |
||||||
- 修复了字符串中有特殊字符导致的路径冲突问题;修复ftp分块下载失败问题 |
- 增加内存空间不足验证 |
||||||
- 修复连接中有`+`导致的地址呗使用问题。 |
+ v_3.4.7 |
||||||
- 修复表重复创建导致的崩溃问题 https://github.com/AriaLyy/Aria/issues/264 |
- 修复分块任务异常操作导致的问题 |
||||||
+ v_3.4.4 |
+ v_3.4.6 |
||||||
- 实现[多线程分块下载](https://aria.laoyuyu.me/aria_doc/start/config.html) |
- 修复android 4.4.4 版本多dex下无法进行回调的问题 |
||||||
- 修复`stopAll()`和`resumeAll()`导致的进度为0问题 |
- 新增`updateUrl(newUrl)`用于修改任务的url,[see](https://aria.laoyuyu.me/aria_doc/api/task_handle.html#%E6%9B%B4%E6%96%B0%E4%BB%BB%E5%8A%A1url) |
||||||
- 修复任务组添加header无效的问题 |
- 优化分块下载 |
||||||
+ v_3.4.3 |
- 修复了字符串中有特殊字符导致的路径冲突问题;修复ftp分块下载失败问题 |
||||||
- 修复在activity 的onStop中取消注册导致的内存泄露问题 |
- 修复连接中有`+`导致的地址呗使用问题。 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/258 |
- 修复表重复创建导致的崩溃问题 https://github.com/AriaLyy/Aria/issues/264 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/259 |
+ v_3.4.4 |
||||||
+ v_3.4.2 |
- 实现[多线程分块下载](https://aria.laoyuyu.me/aria_doc/start/config.html) |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/248 |
- 修复`stopAll()`和`resumeAll()`导致的进度为0问题 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/247 |
- 修复任务组添加header无效的问题 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/250 |
+ v_3.4.3 |
||||||
- 添加任务判断是否存在的api |
- 修复在activity 的onStop中取消注册导致的内存泄露问题 |
||||||
- 添加代理api |
- fix bug https://github.com/AriaLyy/Aria/issues/258 |
||||||
- 修复删除所有没有进出等待的问题 |
- fix bug https://github.com/AriaLyy/Aria/issues/259 |
||||||
- 进度有时出错的问题 |
+ v_3.4.2 |
||||||
- FTP添加超时处理 |
- fix bug https://github.com/AriaLyy/Aria/issues/248 |
||||||
+ v_3.4.1 |
- fix bug https://github.com/AriaLyy/Aria/issues/247 |
||||||
- 移除记录配置文件,改用数据库记录任务记录 |
- fix bug https://github.com/AriaLyy/Aria/issues/250 |
||||||
- 上传配置添加io超时时间、缓存大小配置 |
- 添加任务判断是否存在的api |
||||||
- 添加没有网络也会重试的开关 |
- 添加代理api |
||||||
- 修复多次删除记录的bug |
- 修复删除所有没有进出等待的问题 |
||||||
- 文件长度现在可动态增加,详情见 https://aria.laoyuyu.me/aria_doc/start/config.html |
- 进度有时出错的问题 |
||||||
- 修复多module同时引用Aria导致打正式包出错的问题 https://github.com/AriaLyy/Aria/issues/240 |
- FTP添加超时处理 |
||||||
+ v_3.4 |
+ v_3.4.1 |
||||||
- 优化大量代码 |
- 移除记录配置文件,改用数据库记录任务记录 |
||||||
- 重构Aria的ORM模型,提高了数据读取的可靠性和读写速度 |
- 上传配置添加io超时时间、缓存大小配置 |
||||||
- 现在可在任意类中使用Aria了,[使用方法](http://aria.laoyuyu.me/aria_doc/start/any_java.html) |
- 添加没有网络也会重试的开关 |
||||||
- 添加`window.location.replace("http://xxxx")`类型的网页重定向支持 |
- 修复多次删除记录的bug |
||||||
- 支持gzip、deflate 压缩类型的输入流 |
- 文件长度现在可动态增加,详情见 https://aria.laoyuyu.me/aria_doc/start/config.html |
||||||
- 添加`useServerFileName`,可使用服务端响应header的`Content-Disposition`携带的文件名 |
- 修复多module同时引用Aria导致打正式包出错的问题 https://github.com/AriaLyy/Aria/issues/240 |
||||||
+ v_3.3.16 |
+ v_3.4 |
||||||
- 修复一个activity启动多次,无法进行回掉的bug https://github.com/AriaLyy/Aria/issues/200 |
- 优化大量代码 |
||||||
- 优化target代码结构,移除路径被占用的提示 |
- 重构Aria的ORM模型,提高了数据读取的可靠性和读写速度 |
||||||
- 添加支持chunked模式的下载 |
- 现在可在任意类中使用Aria了,[使用方法](http://aria.laoyuyu.me/aria_doc/start/any_java.html) |
||||||
- 去掉上一个版本"//"的限制 |
- 添加`window.location.replace("http://xxxx")`类型的网页重定向支持 |
||||||
+ v_3.3.14 |
- 支持gzip、deflate 压缩类型的输入流 |
||||||
- 修复ftp上传和下载的兼容性问题 |
- 添加`useServerFileName`,可使用服务端响应header的`Content-Disposition`携带的文件名 |
||||||
- 如果url中的path有"//"将替换为"/" |
+ v_3.3.16 |
||||||
- 修复http上传成功后,如果服务器没有设置返回码导致上传失败的问题 |
- 修复一个activity启动多次,无法进行回掉的bug https://github.com/AriaLyy/Aria/issues/200 |
||||||
- 上传实体UploadEntity增加responseStr字段,http上传完成后,在被`@Upload.onComplete`注解的方法中,可通过`task.getEntity().getResponseStr())`获取服务器返回的数据 |
- 优化target代码结构,移除路径被占用的提示 |
||||||
- 如果服务器存在已上传了一部分的文件,用户执行删除该FTP上传任务,再次重新上传,会出现550,权限错误;本版本已修复该问题 |
- 添加支持chunked模式的下载 |
||||||
+ v_3.3.13 |
- 去掉上一个版本"//"的限制 |
||||||
- 添加`@Download.onWait、@Upload.onWait、@DownloadGroup.onWait`三个新注解,队列已经满了,继续创建新任务,任务处于等待中,将会执行被这三个注解标志的方法 |
+ v_3.3.14 |
||||||
- app被kill,但是还存在等待中的任务A;第二次重新启动,先创建一个新的任务B,Aria会自动把B放进等待队列中,这时再次创建任务A,会导致重复下载,进度错乱的问题;本版本已修复这个问题 |
- 修复ftp上传和下载的兼容性问题 |
||||||
+ v_3.3.11 |
- 如果url中的path有"//"将替换为"/" |
||||||
- 添加进度更新间隔api,在`aria_config.xml`配置`<updateInterval value="1000"/>`或在代码中调用 |
- 修复http上传成功后,如果服务器没有设置返回码导致上传失败的问题 |
||||||
`AriaManager.getInstance(AriaManager.APP).getDownloadConfig().setUpdateInterval(3000)`便可以改变进度刷新间隔 |
- 上传实体UploadEntity增加responseStr字段,http上传完成后,在被`@Upload.onComplete`注解的方法中,可通过`task.getEntity().getResponseStr())`获取服务器返回的数据 |
||||||
- 修复下载过程中kill进程可能出现的文件错误的问题 https://github.com/AriaLyy/Aria/issues/192 |
- 如果服务器存在已上传了一部分的文件,用户执行删除该FTP上传任务,再次重新上传,会出现550,权限错误;本版本已修复该问题 |
||||||
- 修复http上传的空指针问题 https://github.com/AriaLyy/Aria/issues/193 |
+ v_3.3.13 |
||||||
- 修复下载地址中含有`'`导致的崩溃问题 https://github.com/AriaLyy/Aria/issues/194 |
- 添加`@Download.onWait、@Upload.onWait、@DownloadGroup.onWait`三个新注解,队列已经满了,继续创建新任务,任务处于等待中,将会执行被这三个注解标志的方法 |
||||||
+ v_3.3.10 |
- app被kill,但是还存在等待中的任务A;第二次重新启动,先创建一个新的任务B,Aria会自动把B放进等待队列中,这时再次创建任务A,会导致重复下载,进度错乱的问题;本版本已修复这个问题 |
||||||
- 修复地址切换导致下载失败的问题 https://github.com/AriaLyy/Aria/issues/181 |
+ v_3.3.11 |
||||||
- 添加重置状态的api,当下载信息不改变,只是替换了服务器的对应的文件,可用`Aria.download(this).load(url).resetState()`重置下载状态 https://github.com/AriaLyy/Aria/issues/182 |
- 添加进度更新间隔api,在`aria_config.xml`配置`<updateInterval value="1000"/>`或在代码中调用 |
||||||
+ v_3.3.9 |
`AriaManager.getInstance(AriaManager.APP).getDownloadConfig().setUpdateInterval(3000)`便可以改变进度刷新间隔 |
||||||
- 添加POST支持 |
- 修复下载过程中kill进程可能出现的文件错误的问题 https://github.com/AriaLyy/Aria/issues/192 |
||||||
- 任务执行的过程中,如果调用removeRecord()方法,将会取消任务 https://github.com/AriaLyy/Aria/issues/174 |
- 修复http上传的空指针问题 https://github.com/AriaLyy/Aria/issues/193 |
||||||
- 修复一个数据库初始化的问题 https://github.com/AriaLyy/Aria/issues/173 |
- 修复下载地址中含有`'`导致的崩溃问题 https://github.com/AriaLyy/Aria/issues/194 |
||||||
- 修复head头部信息过长时出现的崩溃问题 https://github.com/AriaLyy/Aria/issues/177 |
+ v_3.3.10 |
||||||
+ v_3.3.7 |
- 修复地址切换导致下载失败的问题 https://github.com/AriaLyy/Aria/issues/181 |
||||||
- 修复一个线程重启的问题 https://github.com/AriaLyy/Aria/issues/160 |
- 添加重置状态的api,当下载信息不改变,只是替换了服务器的对应的文件,可用`Aria.download(this).load(url).resetState()`重置下载状态 https://github.com/AriaLyy/Aria/issues/182 |
||||||
- 修复配置文件异常问题、格式化速度为0问题 https://github.com/AriaLyy/Aria/issues/161 |
+ v_3.3.9 |
||||||
+ v_3.3.6 |
- 添加POST支持 |
||||||
- 增加日志输出级别控制 |
- 任务执行的过程中,如果调用removeRecord()方法,将会取消任务 https://github.com/AriaLyy/Aria/issues/174 |
||||||
- 修复公网FTP地址不能下载的问题 https://github.com/AriaLyy/Aria/issues/146 |
- 修复一个数据库初始化的问题 https://github.com/AriaLyy/Aria/issues/173 |
||||||
- 修复http下载地址有空格的时候下载失败的问题 https://github.com/AriaLyy/Aria/issues/131 |
- 修复head头部信息过长时出现的崩溃问题 https://github.com/AriaLyy/Aria/issues/177 |
||||||
- 修复Activity在`onDestroy()`中调用`Aria.download(this).unRegister();`导致回调失效的问题 |
+ v_3.3.7 |
||||||
- 修复Adapter下载FTP任务问题、任务调度问题 https://github.com/AriaLyy/Aria/issues/157 |
- 修复一个线程重启的问题 https://github.com/AriaLyy/Aria/issues/160 |
||||||
- 优化代码,优化了IO性能 |
- 修复配置文件异常问题、格式化速度为0问题 https://github.com/AriaLyy/Aria/issues/161 |
||||||
+ v_3.3.5 修复任务组、上传任务无法启动的bug |
+ v_3.3.6 |
||||||
+ v_3.3.4 优化任务代码结构,修复上一个版本暂停后无法自动执行任务的问题 |
- 增加日志输出级别控制 |
||||||
+ v_3.3.3 修复进度条错乱的问题,修复同一时间多次调用start导致重复下载的问题 |
- 修复公网FTP地址不能下载的问题 https://github.com/AriaLyy/Aria/issues/146 |
||||||
+ v_3.3.2 新加reTry(),修复上一个版本不会回调失败事件的问题;增加running状态下5秒钟保存一次数据库的功能;修复FTP断点上传文件不完整的问题 |
- 修复http下载地址有空格的时候下载失败的问题 https://github.com/AriaLyy/Aria/issues/131 |
||||||
+ v_3.3.1 增加网络事件,网络未连接,将不会重试下载,修复删除未开始任务,状态回调错误 |
- 修复Activity在`onDestroy()`中调用`Aria.download(this).unRegister();`导致回调失效的问题 |
||||||
+ v_3.3.0 增加任务组子任务暂停和开始控制功能、修复5.0系统以上数据库多生成两个字段的bug、去掉addSchedulerListener事件 |
- 修复Adapter下载FTP任务问题、任务调度问题 https://github.com/AriaLyy/Aria/issues/157 |
||||||
+ v_3.2.26 修复任务组有时注解不起作用的问题 |
- 优化代码,优化了IO性能 |
||||||
+ v_3.2.25 修复删除任务组文件,记录无法删除的问题 |
+ v_3.3.5 修复任务组、上传任务无法启动的bug |
||||||
+ v_3.2.17 修复一个版本兼容性问题,线程中使用Aria出错问题 |
+ v_3.3.4 优化任务代码结构,修复上一个版本暂停后无法自动执行任务的问题 |
||||||
+ v_3.2.15 修复大型文件分段下载失败的问题,修复中文URL乱码问题 |
+ v_3.3.3 修复进度条错乱的问题,修复同一时间多次调用start导致重复下载的问题 |
||||||
+ v_3.2.14 修复恢复所有任务的api接口,不能恢复下载组任务的问题 |
+ v_3.3.2 新加reTry(),修复上一个版本不会回调失败事件的问题;增加running状态下5秒钟保存一次数据库的功能;修复FTP断点上传文件不完整的问题 |
||||||
+ v_3.2.13 修复某些服务器头文件返回描述文件格式错误的问题、修复有时删除任务,需要两次删除的问题 |
+ v_3.3.1 增加网络事件,网络未连接,将不会重试下载,修复删除未开始任务,状态回调错误 |
||||||
+ v_3.2.12 实现FTP多线程断点续传下载,FTP断点续传上传功能 |
+ v_3.3.0 增加任务组子任务暂停和开始控制功能、修复5.0系统以上数据库多生成两个字段的bug、去掉addSchedulerListener事件 |
||||||
+ v_3.2.9 修复任务组下载完成两次回掉的问题,修复又是获取不到下载状态的问题 |
+ v_3.2.26 修复任务组有时注解不起作用的问题 |
||||||
+ v_3.2.8 修复下载超过2G大小的文件失败的问题 |
+ v_3.2.25 修复删除任务组文件,记录无法删除的问题 |
||||||
+ v_3.2.7 移除设置文件名的api接口,修复断开网络时出现的进度条错误的问题 |
+ v_3.2.17 修复一个版本兼容性问题,线程中使用Aria出错问题 |
||||||
+ v_3.2.6 移除广播事件,增加任务组下载功能 |
+ v_3.2.15 修复大型文件分段下载失败的问题,修复中文URL乱码问题 |
||||||
+ v_3.1.9 修复stopAll队列没有任务时崩溃的问题,增加针对单个任务监听的功能 |
+ v_3.2.14 修复恢复所有任务的api接口,不能恢复下载组任务的问题 |
||||||
+ v_3.1.7 修复某些文件下载不了的bug,增加apt注解方法,事件获取更加简单了 |
+ v_3.2.13 修复某些服务器头文件返回描述文件格式错误的问题、修复有时删除任务,需要两次删除的问题 |
||||||
+ v_3.1.6 取消任务时onTaskCancel回调两次的bug |
+ v_3.2.12 实现FTP多线程断点续传下载,FTP断点续传上传功能 |
||||||
+ v_3.1.5 优化代码结构,增加优先下载任务功能。 |
+ v_3.2.9 修复任务组下载完成两次回掉的问题,修复又是获取不到下载状态的问题 |
||||||
+ v_3.1.4 修复快速切换,暂停、恢复功能时,概率性出现的重新下载问题,添加onPre()回调,onPre()用于请求地址之前执行界面UI更新操作。 |
+ v_3.2.8 修复下载超过2G大小的文件失败的问题 |
||||||
+ v_3.1.0 添加Aria配置文件,优化代码 |
+ v_3.2.7 移除设置文件名的api接口,修复断开网络时出现的进度条错误的问题 |
||||||
+ v_3.0.3 修复暂停后删除任务,闪退问题,添加删除记录的api |
+ v_3.2.6 移除广播事件,增加任务组下载功能 |
||||||
+ v_3.0.2 支持30x重定向链接下载 |
+ v_3.1.9 修复stopAll队列没有任务时崩溃的问题,增加针对单个任务监听的功能 |
||||||
+ v_3.0.0 添加上传任务支持,修复一些已发现的bug |
+ v_3.1.7 修复某些文件下载不了的bug,增加apt注解方法,事件获取更加简单了 |
||||||
+ v_2.4.4 修复不支持断点的下载链接拿不到文件大小的问题 |
+ v_3.1.6 取消任务时onTaskCancel回调两次的bug |
||||||
+ v_2.4.3 修复404链接卡顿的问题 |
+ v_3.1.5 优化代码结构,增加优先下载任务功能。 |
||||||
+ v_2.4.2 修复失败重试无效的bug |
+ v_3.1.4 修复快速切换,暂停、恢复功能时,概率性出现的重新下载问题,添加onPre()回调,onPre()用于请求地址之前执行界面UI更新操作。 |
||||||
+ v_2.4.1 修复下载慢的问题,修复application、service 不能使用的问题 |
+ v_3.1.0 添加Aria配置文件,优化代码 |
||||||
+ v_2.4.0 支持https链接下载 |
+ v_3.0.3 修复暂停后删除任务,闪退问题,添加删除记录的api |
||||||
+ v_2.3.8 修复数据错乱的bug、添加fragment支持 |
+ v_3.0.2 支持30x重定向链接下载 |
||||||
+ v_2.3.6 添加dialog、popupWindow支持 |
+ v_3.0.0 添加上传任务支持,修复一些已发现的bug |
||||||
+ v_2.3.3 添加断点支持、修改下载逻辑,让使用更加简单、修复一个内存泄露的bug |
+ v_2.4.4 修复不支持断点的下载链接拿不到文件大小的问题 |
||||||
+ v_2.3.1 重命名为Aria,下载流程简化 |
+ v_2.4.3 修复404链接卡顿的问题 |
||||||
|
+ v_2.4.2 修复失败重试无效的bug |
||||||
|
+ v_2.4.1 修复下载慢的问题,修复application、service 不能使用的问题 |
||||||
|
+ v_2.4.0 支持https链接下载 |
||||||
|
+ v_2.3.8 修复数据错乱的bug、添加fragment支持 |
||||||
|
+ v_2.3.6 添加dialog、popupWindow支持 |
||||||
|
+ v_2.3.3 添加断点支持、修改下载逻辑,让使用更加简单、修复一个内存泄露的bug |
||||||
|
+ v_2.3.1 重命名为Aria,下载流程简化 |
||||||
+ v_2.1.1 增加,选择最大下载任务数接口 |
+ v_2.1.1 增加,选择最大下载任务数接口 |
@ -1,172 +1,172 @@ |
|||||||
# Aria |
# Aria |
||||||
</br> |
</br> |
||||||
## [ENGLISH DOC](https://github.com/AriaLyy/Aria/blob/master/ENGLISH_README.md)</br> |
## [ENGLISH DOC](https://github.com/AriaLyy/Aria/blob/master/ENGLISH_README.md)</br> |
||||||
## [中文文档](https://aria.laoyuyu.me/aria_doc) |
## [中文文档](https://aria.laoyuyu.me/aria_doc) |
||||||
Aria项目源于工作中遇到的一个文件下载管理的需求,当时被下载折磨的痛不欲生,从那时起便萌生了编写一个简单易用,稳当高效的下载框架,aria经历了1.0到3.0的开发,算是越来越接近当初所制定的目标了。 |
Aria项目源于工作中遇到的一个文件下载管理的需求,当时被下载折磨的痛不欲生,从那时起便萌生了编写一个简单易用,稳当高效的下载框架,aria经历了1.0到3.0的开发,算是越来越接近当初所制定的目标了。 |
||||||
|
|
||||||
Aria有以下特点: |
Aria有以下特点: |
||||||
+ 简单、方便 |
+ 简单、方便 |
||||||
- 可以在Activity、Service、Fragment、Dialog、popupWindow、Notification等组件中使用 |
- 可以在Activity、Service、Fragment、Dialog、popupWindow、Notification等组件中使用 |
||||||
- 支持HTTP\FTP断点续传下载、多任务自动调度 |
- 支持HTTP\FTP断点续传下载、多任务自动调度 |
||||||
- 支持多文件打包下载,多文件共享同一进度(如:视频 + 封面 + 字幕) |
- 支持多文件打包下载,多文件共享同一进度(如:视频 + 封面 + 字幕) |
||||||
- 支持下载FTP文件夹 |
- 支持下载FTP文件夹 |
||||||
- 支持HTTP表单上传 |
- 支持HTTP表单上传 |
||||||
- 支持文件FTP断点续传上传 |
- 支持文件FTP断点续传上传 |
||||||
- 支持FTPS/SFTP断点续传,[see](https://aria.laoyuyu.me/aria_doc/download/ftps.html) |
- 支持FTPS/SFTP断点续传,[see](https://aria.laoyuyu.me/aria_doc/download/ftps.html) |
||||||
+ 支持https地址下载 |
+ 支持https地址下载 |
||||||
- 在配置文件中很容易就可以设置CA证书的信息 |
- 在配置文件中很容易就可以设置CA证书的信息 |
||||||
+ 支持[多线程分块下载](https://aria.laoyuyu.me/aria_doc/start/config.html),能更有效的发挥机器IO性能 |
+ 支持[多线程分块下载](https://aria.laoyuyu.me/aria_doc/start/config.html),能更有效的发挥机器IO性能 |
||||||
+ 支持300、301、302重定向下载链接下载 |
+ 支持300、301、302重定向下载链接下载 |
||||||
+ 下载支持文件长度动态增加,文件下载初始化时将不再占用过多的内存空间,见[动态长度配置](https://aria.laoyuyu.me/aria_doc/start/config.html#%E4%B8%8B%E8%BD%BD%E5%8A%A8%E6%80%81%E6%96%87%E4%BB%B6%E8%AF%B4%E6%98%8E) |
+ 下载支持文件长度动态增加,文件下载初始化时将不再占用过多的内存空间,见[动态长度配置](https://aria.laoyuyu.me/aria_doc/start/config.html#%E4%B8%8B%E8%BD%BD%E5%8A%A8%E6%80%81%E6%96%87%E4%BB%B6%E8%AF%B4%E6%98%8E) |
||||||
|
|
||||||
[怎样使用Aria?](#使用) |
[怎样使用Aria?](#使用) |
||||||
|
|
||||||
如果你觉得Aria对你有帮助,您的star和issues将是对我最大支持.`^_^` |
如果你觉得Aria对你有帮助,您的star和issues将是对我最大支持.`^_^` |
||||||
|
|
||||||
## 示例 |
## 示例 |
||||||
* 多任务下载 |
* 多任务下载 |
||||||
|
|
||||||
 |
 |
||||||
|
|
||||||
* 速度限制 |
* 速度限制 |
||||||
|
|
||||||
 |
 |
||||||
|
|
||||||
* 多文件打包下载 |
* 多文件打包下载 |
||||||
|
|
||||||
<img src="https://github.com/AriaLyy/DownloadUtil/blob/master/img/group_task.gif" width="360" height="640"/> |
<img src="https://github.com/AriaLyy/DownloadUtil/blob/master/img/group_task.gif" width="360" height="640"/> |
||||||
|
|
||||||
|
|
||||||
## 引入库 |
## 引入库 |
||||||
[](https://bintray.com/arialyy/maven/AriaApi/_latestVersion) |
[](https://bintray.com/arialyy/maven/AriaApi/_latestVersion) |
||||||
[](https://bintray.com/arialyy/maven/AriaCompiler/_latestVersion) |
[](https://bintray.com/arialyy/maven/AriaCompiler/_latestVersion) |
||||||
|
|
||||||
```java |
```java |
||||||
compile 'com.arialyy.aria:aria-core:3.6.3' |
compile 'com.arialyy.aria:aria-core:3.6.3' |
||||||
annotationProcessor 'com.arialyy.aria:aria-compiler:3.6.3' |
annotationProcessor 'com.arialyy.aria:aria-compiler:3.6.3' |
||||||
``` |
``` |
||||||
如果出现android support依赖错误,请将 `compile 'com.arialyy.aria:aria-core:<last-version>'`替换为 |
如果出现android support依赖错误,请将 `compile 'com.arialyy.aria:aria-core:<last-version>'`替换为 |
||||||
``` |
``` |
||||||
api('com.arialyy.aria:aria-core:<last-version>'){ |
api('com.arialyy.aria:aria-core:<last-version>'){ |
||||||
exclude group: 'com.android.support' |
exclude group: 'com.android.support' |
||||||
} |
} |
||||||
``` |
``` |
||||||
如果你使用的是kotlin,请使用kotlin官方提供的方法配置apt,[kotlin kapt官方配置传送门](https://www.kotlincn.net/docs/reference/kapt.html) |
如果你使用的是kotlin,请使用kotlin官方提供的方法配置apt,[kotlin kapt官方配置传送门](https://www.kotlincn.net/docs/reference/kapt.html) |
||||||
|
|
||||||
__注意:3.5.4以下版本升级时,需要更新[配置文件]!!(https://aria.laoyuyu.me/aria_doc/start/config.html)__ |
__注意:3.5.4以下版本升级时,需要更新[配置文件]!!(https://aria.laoyuyu.me/aria_doc/start/config.html)__ |
||||||
|
|
||||||
*** |
*** |
||||||
## 使用 |
## 使用 |
||||||
由于Aria涉及到文件和网络的操作,因此需要你在manifest文件中添加以下权限,如果你希望在6.0以上的系统中使用Aria,那么你需要动态向安卓系统申请文件系统读写权限,[如何使用安卓系统权限](https://developer.android.com/training/permissions/index.html?hl=zh-cn) |
由于Aria涉及到文件和网络的操作,因此需要你在manifest文件中添加以下权限,如果你希望在6.0以上的系统中使用Aria,那么你需要动态向安卓系统申请文件系统读写权限,[如何使用安卓系统权限](https://developer.android.com/training/permissions/index.html?hl=zh-cn) |
||||||
```xml |
```xml |
||||||
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/> |
<uses-permission android:name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/> |
||||||
<uses-permission android:name="android.permission.INTERNET"/> |
<uses-permission android:name="android.permission.INTERNET"/> |
||||||
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> |
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/> |
||||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/> |
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/> |
||||||
``` |
``` |
||||||
|
|
||||||
## 使用Aria |
## 使用Aria |
||||||
### 基本使用 |
### 基本使用 |
||||||
例子为单任务下载,只需要很简单的代码,便可以实现下载功能 |
例子为单任务下载,只需要很简单的代码,便可以实现下载功能 |
||||||
```java |
```java |
||||||
Aria.download(this) |
Aria.download(this) |
||||||
.load(DOWNLOAD_URL) //读取下载地址 |
.load(DOWNLOAD_URL) //读取下载地址 |
||||||
.setDownloadPath(DOWNLOAD_PATH) //设置文件保存的完整路径 |
.setDownloadPath(DOWNLOAD_PATH) //设置文件保存的完整路径 |
||||||
.start(); //启动下载 |
.start(); //启动下载 |
||||||
``` |
``` |
||||||
|
|
||||||
### 任务状态的获取 |
### 任务状态的获取 |
||||||
基于解耦合的考虑,Aria的下载功能是和状态获取相分离的,状态的获取并不会集成到链式代码中,但是Aria提供了另一种更简单更灵活的方案。 |
基于解耦合的考虑,Aria的下载功能是和状态获取相分离的,状态的获取并不会集成到链式代码中,但是Aria提供了另一种更简单更灵活的方案。 |
||||||
通过注解,你可以很容易获取任务的所有状态。 |
通过注解,你可以很容易获取任务的所有状态。 |
||||||
|
|
||||||
1. 将对象注册到Aria |
1. 将对象注册到Aria |
||||||
```java |
```java |
||||||
protected void onCreate(Bundle savedInstanceState) { |
protected void onCreate(Bundle savedInstanceState) { |
||||||
super.onCreate(savedInstanceState); |
super.onCreate(savedInstanceState); |
||||||
Aria.download(this).register(); |
Aria.download(this).register(); |
||||||
} |
} |
||||||
``` |
``` |
||||||
|
|
||||||
2. 通过注解获取任务执行状态 |
2. 通过注解获取任务执行状态 |
||||||
**注意:** |
**注意:** |
||||||
- 注解回掉采用Apt的方式实现,所以,你不需要担心这会影响你机器的性能 |
- 注解回掉采用Apt的方式实现,所以,你不需要担心这会影响你机器的性能 |
||||||
- 被注解的方法**不能被private修饰** |
- 被注解的方法**不能被private修饰** |
||||||
- 被注解的方法**只能有一个参数,并且参数类型必须是`DownloadTask`或`UploadTask`或`DownloadGroupTask`** |
- 被注解的方法**只能有一个参数,并且参数类型必须是`DownloadTask`或`UploadTask`或`DownloadGroupTask`** |
||||||
- 方法名可以为任意字符串 |
- 方法名可以为任意字符串 |
||||||
|
|
||||||
```java |
```java |
||||||
//在这里处理任务执行中的状态,如进度进度条的刷新 |
//在这里处理任务执行中的状态,如进度进度条的刷新 |
||||||
@Download.onTaskRunning protected void running(DownloadTask task) { |
@Download.onTaskRunning protected void running(DownloadTask task) { |
||||||
if(task.getUrl().eques(url)){ |
if(task.getKey().eques(url)){ |
||||||
.... |
.... |
||||||
可以通过url判断是否是指定任务的回调 |
可以通过url判断是否是指定任务的回调 |
||||||
} |
} |
||||||
int p = task.getPercent(); //任务进度百分比 |
int p = task.getPercent(); //任务进度百分比 |
||||||
String speed = task.getConvertSpeed(); //转换单位后的下载速度,单位转换需要在配置文件中打开 |
String speed = task.getConvertSpeed(); //转换单位后的下载速度,单位转换需要在配置文件中打开 |
||||||
String speed1 = task.getSpeed(); //原始byte长度速度 |
String speed1 = task.getSpeed(); //原始byte长度速度 |
||||||
} |
} |
||||||
|
|
||||||
@Download.onTaskComplete void taskComplete(DownloadTask task) { |
@Download.onTaskComplete void taskComplete(DownloadTask task) { |
||||||
//在这里处理任务完成的状态 |
//在这里处理任务完成的状态 |
||||||
} |
} |
||||||
``` |
``` |
||||||
|
|
||||||
|
|
||||||
### 版本日志 |
### 版本日志 |
||||||
* v3.6.3 (2019/4/2) |
* v3.6.3 (2019/4/2) |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/368 |
- fix bug https://github.com/AriaLyy/Aria/issues/368 |
||||||
- 增加gradle 5.0支持 |
- 增加gradle 5.0支持 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/374 |
- fix bug https://github.com/AriaLyy/Aria/issues/374 |
||||||
- fix bug https://github.com/AriaLyy/Aria/issues/377 |
- fix bug https://github.com/AriaLyy/Aria/issues/377 |
||||||
- 增加分页获取任务列表api, 详情见:https://aria.laoyuyu.me/aria_doc/api/task_list.html#%E4%BB%BB%E5%8A%A1%E5%88%97%E8%A1%A8%E5%88%86%E9%A1%B5%EF%BC%88362%E4%BB%A5%E4%B8%8A%E7%89%88%E6%9C%AC%E6%94%AF%E6%8C%81%EF%BC%89 |
- 增加分页获取任务列表api, 详情见:https://aria.laoyuyu.me/aria_doc/api/task_list.html#%E4%BB%BB%E5%8A%A1%E5%88%97%E8%A1%A8%E5%88%86%E9%A1%B5%EF%BC%88362%E4%BB%A5%E4%B8%8A%E7%89%88%E6%9C%AC%E6%94%AF%E6%8C%81%EF%BC%89 |
||||||
|
|
||||||
[更多版本记录](https://github.com/AriaLyy/Aria/blob/master/DEV_LOG.md) |
[更多版本记录](https://github.com/AriaLyy/Aria/blob/master/DEV_LOG.md) |
||||||
|
|
||||||
## 混淆配置 |
## 混淆配置 |
||||||
``` |
``` |
||||||
-dontwarn com.arialyy.aria.** |
-dontwarn com.arialyy.aria.** |
||||||
-keep class com.arialyy.aria.**{*;} |
-keep class com.arialyy.aria.**{*;} |
||||||
-keep class **$$DownloadListenerProxy{ *; } |
-keep class **$$DownloadListenerProxy{ *; } |
||||||
-keep class **$$UploadListenerProxy{ *; } |
-keep class **$$UploadListenerProxy{ *; } |
||||||
-keep class **$$DownloadGroupListenerProxy{ *; } |
-keep class **$$DownloadGroupListenerProxy{ *; } |
||||||
-keepclasseswithmembernames class * { |
-keepclasseswithmembernames class * { |
||||||
@Download.* <methods>; |
@Download.* <methods>; |
||||||
@Upload.* <methods>; |
@Upload.* <methods>; |
||||||
@DownloadGroup.* <methods>; |
@DownloadGroup.* <methods>; |
||||||
} |
} |
||||||
|
|
||||||
``` |
``` |
||||||
|
|
||||||
## 其他 |
## 其他 |
||||||
有任何问题,可以在[issues](https://github.com/AriaLyy/Aria/issues)给我留言反馈。</br> |
有任何问题,可以在[issues](https://github.com/AriaLyy/Aria/issues)给我留言反馈。</br> |
||||||
在提交问题前,希望你已经查看过[wiki](https://aria.laoyuyu.me/aria_doc/)或搜索过[issues](https://github.com/AriaLyy/Aria/issues)。</br> |
在提交问题前,希望你已经查看过[wiki](https://aria.laoyuyu.me/aria_doc/)或搜索过[issues](https://github.com/AriaLyy/Aria/issues)。</br> |
||||||
交流群:524329160 |
交流群:524329160 |
||||||
|
|
||||||
*** |
*** |
||||||
|
|
||||||
License |
License |
||||||
------- |
------- |
||||||
|
|
||||||
Copyright 2016 AriaLyy(https://github.com/AriaLyy/Aria) |
Copyright 2016 AriaLyy(https://github.com/AriaLyy/Aria) |
||||||
|
|
||||||
Licensed under the Apache License, Version 2.0 (the "License"); |
Licensed under the Apache License, Version 2.0 (the "License"); |
||||||
you may not use this file except in compliance with the License. |
you may not use this file except in compliance with the License. |
||||||
You may obtain a copy of the License at |
You may obtain a copy of the License at |
||||||
|
|
||||||
http://www.apache.org/licenses/LICENSE-2.0 |
http://www.apache.org/licenses/LICENSE-2.0 |
||||||
|
|
||||||
Unless required by applicable law or agreed to in writing, software |
Unless required by applicable law or agreed to in writing, software |
||||||
distributed under the License is distributed on an "AS IS" BASIS, |
distributed under the License is distributed on an "AS IS" BASIS, |
||||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
||||||
See the License for the specific language governing permissions and |
See the License for the specific language governing permissions and |
||||||
limitations under the License. |
limitations under the License. |
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,161 +1,161 @@ |
|||||||
<?xml version="1.0" encoding="utf-8"?> |
<?xml version="1.0" encoding="utf-8"?> |
||||||
<aria> |
<aria> |
||||||
<!--注意,修改该配置文件中的属性会覆盖代码中所设置的属性--> |
<!--注意,修改该配置文件中的属性会覆盖代码中所设置的属性--> |
||||||
|
|
||||||
<!--Aria框架配置--> |
<!--Aria框架配置--> |
||||||
<app> |
<app> |
||||||
<!--是否使用AriaCrashHandler来捕获异常,异常日志保存在:/mnt/sdcard/Android/data/{package_name}/files/log/--> |
<!--是否使用AriaCrashHandler来捕获异常,异常日志保存在:/mnt/sdcard/Android/data/{package_name}/files/log/--> |
||||||
<useAriaCrashHandler value="true"/> |
<useAriaCrashHandler value="true"/> |
||||||
<!--设置Aria的日志级别,{@link ALog#LOG_LEVEL_VERBOSE}--> |
<!--设置Aria的日志级别,{@link ALog#LOG_LEVEL_VERBOSE}--> |
||||||
<logLevel value="2"/> |
<logLevel value="2"/> |
||||||
<!-- 是否检查网络 true: 检查网络,false: 不检查网络--> |
<!-- 是否检查网络 true: 检查网络,false: 不检查网络--> |
||||||
<netCheck value="false"/> |
<netCheck value="false"/> |
||||||
<!--除非无法使用注解,否则不建议使用广播来接受任务状态,true:使用广播接收任务状态,false:不适用广播接收状态 --> |
<!--除非无法使用注解,否则不建议使用广播来接受任务状态,true:使用广播接收任务状态,false:不适用广播接收状态 --> |
||||||
<!-- http://aria.laoyuyu.me/aria_doc/api/use_broadcast.html --> |
<!-- http://aria.laoyuyu.me/aria_doc/api/use_broadcast.html --> |
||||||
<useBroadcast value="true"/> |
<useBroadcast value="true"/> |
||||||
<!--断网的时候是否重试,true:断网也重试;false:断网不重试,直接走失败的回调--> |
<!--断网的时候是否重试,true:断网也重试;false:断网不重试,直接走失败的回调--> |
||||||
<notNetRetry value="true"/> |
<notNetRetry value="true"/> |
||||||
</app> |
</app> |
||||||
|
|
||||||
|
|
||||||
<!--普通下载任务--> |
<!--普通下载任务--> |
||||||
<download> |
<download> |
||||||
|
|
||||||
<!--设置任务最大下载速度,0表示不限速,单位为:kb--> |
<!--设置任务最大下载速度,0表示不限速,单位为:kb--> |
||||||
<maxSpeed value="128"/> |
<maxSpeed value="128"/> |
||||||
|
|
||||||
<!-- |
<!-- |
||||||
多线程下载是否使用块下载模式,{@code true}使用,{@code false}不使用 |
多线程下载是否使用块下载模式,{@code true}使用,{@code false}不使用 |
||||||
注意: |
注意: |
||||||
1、使用分块模式,在I/O性能底下的手机上,合并文件需要的时间会更加长; |
1、使用分块模式,在I/O性能底下的手机上,合并文件需要的时间会更加长; |
||||||
2、优点是使用多线程的块下载,初始化时,文件初始化时将不会预占用对应长度的空间; |
2、优点是使用多线程的块下载,初始化时,文件初始化时将不会预占用对应长度的空间; |
||||||
3、只对新的多线程下载任务有效 |
3、只对新的多线程下载任务有效 |
||||||
4、只对多线程的任务有效 |
4、只对多线程的任务有效 |
||||||
--> |
--> |
||||||
<useBlock value="true"/> |
<useBlock value="true"/> |
||||||
|
|
||||||
<!--设置下载线程数,下载线程数不能小于1 |
<!--设置下载线程数,下载线程数不能小于1 |
||||||
注意: |
注意: |
||||||
1、线程下载数改变后,新的下载任务才会生效; |
1、线程下载数改变后,新的下载任务才会生效; |
||||||
2、如果任务大小小于1m,该设置不会生效; |
2、如果任务大小小于1m,该设置不会生效; |
||||||
3、从3.4.1开始,如果线程数为1,文件初始化时将不再预占用对应长度的空间,下载多少byte,则占多大的空间; |
3、从3.4.1开始,如果线程数为1,文件初始化时将不再预占用对应长度的空间,下载多少byte,则占多大的空间; |
||||||
对于3.4.1之前版本的未完成的老任务,依然采用原来的文件空间占用方式; |
对于3.4.1之前版本的未完成的老任务,依然采用原来的文件空间占用方式; |
||||||
--> |
--> |
||||||
<threadNum value="1"/> |
<threadNum value="3"/> |
||||||
|
|
||||||
<!--设置下载队列最大任务数, 默认为2--> |
<!--设置下载队列最大任务数, 默认为2--> |
||||||
<maxTaskNum value="1"/> |
<maxTaskNum value="1"/> |
||||||
|
|
||||||
<!--设置下载失败,重试次数,默认为10--> |
<!--设置下载失败,重试次数,默认为10--> |
||||||
<reTryNum value="1"/> |
<reTryNum value="1"/> |
||||||
|
|
||||||
<!--设置重试间隔,单位为毫秒,默认2000毫秒--> |
<!--设置重试间隔,单位为毫秒,默认2000毫秒--> |
||||||
<reTryInterval value="5000"/> |
<reTryInterval value="5000"/> |
||||||
|
|
||||||
<!--设置url连接超时时间,单位为毫秒,默认5000毫秒--> |
<!--设置url连接超时时间,单位为毫秒,默认5000毫秒--> |
||||||
<connectTimeOut value="5000"/> |
<connectTimeOut value="5000"/> |
||||||
|
|
||||||
<!--设置IO流读取时间,单位为毫秒,默认20000毫秒,该时间不能少于10000毫秒--> |
<!--设置IO流读取时间,单位为毫秒,默认20000毫秒,该时间不能少于10000毫秒--> |
||||||
<iOTimeOut value="10000"/> |
<iOTimeOut value="10000"/> |
||||||
|
|
||||||
<!--设置写文件buff大小,该数值大小不能小于2048,数值变小,下载速度会变慢--> |
<!--设置写文件buff大小,该数值大小不能小于2048,数值变小,下载速度会变慢--> |
||||||
<buffSize value="8192"/> |
<buffSize value="8192"/> |
||||||
|
|
||||||
<!--设置https ca 证书信息;path 为assets目录下的CA证书完整路径,name 为CA证书名--> |
<!--设置https ca 证书信息;path 为assets目录下的CA证书完整路径,name 为CA证书名--> |
||||||
<ca name="" path=""/> |
<ca name="" path=""/> |
||||||
|
|
||||||
<!--是否需要转换速度单位,转换完成后为:1b/s、1kb/s、1mb/s、1gb/s、1tb/s,如果不需要将返回byte长度--> |
<!--是否需要转换速度单位,转换完成后为:1b/s、1kb/s、1mb/s、1gb/s、1tb/s,如果不需要将返回byte长度--> |
||||||
<convertSpeed value="true"/> |
<convertSpeed value="true"/> |
||||||
|
|
||||||
<!--执行队列类型,见com.arialyy.aria.core.QueueMod,默认类型为wait--> |
<!--执行队列类型,见com.arialyy.aria.core.QueueMod,默认类型为wait--> |
||||||
<queueMod value="wait"/> |
<queueMod value="wait"/> |
||||||
|
|
||||||
<!--进度更新更新间隔,默认1000毫秒--> |
<!--进度更新更新间隔,默认1000毫秒--> |
||||||
<updateInterval value="1000"/> |
<updateInterval value="1000"/> |
||||||
|
|
||||||
</download> |
</download> |
||||||
|
|
||||||
<!--普通上传任务--> |
<!--普通上传任务--> |
||||||
<upload> |
<upload> |
||||||
<!--设置任务最大上传速度,0表示不限速,单位为:kb--> |
<!--设置任务最大上传速度,0表示不限速,单位为:kb--> |
||||||
<maxSpeed value="0"/> |
<maxSpeed value="0"/> |
||||||
|
|
||||||
<!--设置IO流读取时间,单位为毫秒,默认20000毫秒,该时间不能少于10000毫秒--> |
<!--设置IO流读取时间,单位为毫秒,默认20000毫秒,该时间不能少于10000毫秒--> |
||||||
<iOTimeOut value="10000"/> |
<iOTimeOut value="10000"/> |
||||||
|
|
||||||
<!--设置写文件buff大小,该数值大小不能小于2048,数值变小,速度会变慢--> |
<!--设置写文件buff大小,该数值大小不能小于2048,数值变小,速度会变慢--> |
||||||
<buffSize value="8192"/> |
<buffSize value="8192"/> |
||||||
|
|
||||||
<!--是否需要转换速度单位,转换完成后为:1b/s、1kb/s、1mb/s、1gb/s、1tb/s,如果不需要将返回byte长度--> |
<!--是否需要转换速度单位,转换完成后为:1b/s、1kb/s、1mb/s、1gb/s、1tb/s,如果不需要将返回byte长度--> |
||||||
<convertSpeed value="true"/> |
<convertSpeed value="true"/> |
||||||
|
|
||||||
<!--设置上传队列最大任务数, 默认为2--> |
<!--设置上传队列最大任务数, 默认为2--> |
||||||
<maxTaskNum value="2"/> |
<maxTaskNum value="2"/> |
||||||
|
|
||||||
<!--设置上传失败,重试次数,默认为10--> |
<!--设置上传失败,重试次数,默认为10--> |
||||||
<reTryNum value="3"/> |
<reTryNum value="3"/> |
||||||
|
|
||||||
<!--设置重试间隔,单位为毫秒--> |
<!--设置重试间隔,单位为毫秒--> |
||||||
<reTryInterval value="2000"/> |
<reTryInterval value="2000"/> |
||||||
|
|
||||||
<!--设置url连接超时时间,单位为毫秒,默认5000毫秒--> |
<!--设置url连接超时时间,单位为毫秒,默认5000毫秒--> |
||||||
<connectTimeOut value="5000"/> |
<connectTimeOut value="5000"/> |
||||||
|
|
||||||
<!--执行队列类型,见com.arialyy.aria.core.QueueMod,默认类型为wait--> |
<!--执行队列类型,见com.arialyy.aria.core.QueueMod,默认类型为wait--> |
||||||
<queueMod value="wait"/> |
<queueMod value="wait"/> |
||||||
|
|
||||||
<!--进度更新更新间隔,默认1000毫秒--> |
<!--进度更新更新间隔,默认1000毫秒--> |
||||||
<updateInterval value="1000"/> |
<updateInterval value="1000"/> |
||||||
|
|
||||||
</upload> |
</upload> |
||||||
|
|
||||||
<!-- 下载类组合任务 --> |
<!-- 下载类组合任务 --> |
||||||
<dGroup> |
<dGroup> |
||||||
|
|
||||||
<!--组合任务下载队列最大任务数, 默认为2--> |
<!--组合任务下载队列最大任务数, 默认为2--> |
||||||
<maxTaskNum value="1"/> |
<maxTaskNum value="1"/> |
||||||
|
|
||||||
<!--设置下载失败,重试次数,默认为10--> |
<!--设置下载失败,重试次数,默认为10--> |
||||||
<reTryNum value="1"/> |
<reTryNum value="1"/> |
||||||
|
|
||||||
<!--设置重试间隔,单位为毫秒,默认2000毫秒--> |
<!--设置重试间隔,单位为毫秒,默认2000毫秒--> |
||||||
<reTryInterval value="5000"/> |
<reTryInterval value="5000"/> |
||||||
|
|
||||||
<!--执行队列类型,见com.arialyy.aria.core.QueueMod,默认类型为wait--> |
<!--执行队列类型,见com.arialyy.aria.core.QueueMod,默认类型为wait--> |
||||||
<queueMod value="wait"/> |
<queueMod value="wait"/> |
||||||
|
|
||||||
<!--进度更新更新间隔,默认1000毫秒--> |
<!--进度更新更新间隔,默认1000毫秒--> |
||||||
<updateInterval value="1000"/> |
<updateInterval value="1000"/> |
||||||
|
|
||||||
|
|
||||||
<!-- =============================以下为子任务的配置====================================--> |
<!-- =============================以下为子任务的配置====================================--> |
||||||
|
|
||||||
<!--能同时下载的子任务最大任务数,默认3--> |
<!--能同时下载的子任务最大任务数,默认3--> |
||||||
<subMaxTaskNum value="1"/> |
<subMaxTaskNum value="1"/> |
||||||
|
|
||||||
<!--子任务下载失败时的重试次数,默认为5--> |
<!--子任务下载失败时的重试次数,默认为5--> |
||||||
<subReTryNum value="5"/> |
<subReTryNum value="5"/> |
||||||
|
|
||||||
<!--子任务下载失败时的重试间隔,单位为毫秒,默认2000毫秒--> |
<!--子任务下载失败时的重试间隔,单位为毫秒,默认2000毫秒--> |
||||||
<subReTryInterval value="5000"/> |
<subReTryInterval value="5000"/> |
||||||
|
|
||||||
<!--子任务url连接超时时间,单位为毫秒,默认5000毫秒--> |
<!--子任务url连接超时时间,单位为毫秒,默认5000毫秒--> |
||||||
<connectTimeOut value="5000"/> |
<connectTimeOut value="5000"/> |
||||||
|
|
||||||
<!--子任务IO流读取时间,单位为毫秒,默认20000毫秒,该时间不能少于10000毫秒--> |
<!--子任务IO流读取时间,单位为毫秒,默认20000毫秒,该时间不能少于10000毫秒--> |
||||||
<iOTimeOut value="10000"/> |
<iOTimeOut value="10000"/> |
||||||
|
|
||||||
<!--子任务写文件buff大小,该数值大小不能小于2048,数值变小,下载速度会变慢--> |
<!--子任务写文件buff大小,该数值大小不能小于2048,数值变小,下载速度会变慢--> |
||||||
<buffSize value="8192"/> |
<buffSize value="8192"/> |
||||||
|
|
||||||
<!--子任务 https ca 证书信息;path 为assets目录下的CA证书完整路径,name 为CA证书名--> |
<!--子任务 https ca 证书信息;path 为assets目录下的CA证书完整路径,name 为CA证书名--> |
||||||
<ca name="" path=""/> |
<ca name="" path=""/> |
||||||
|
|
||||||
<!--子任务是否需要转换速度单位,转换完成后为:1b/s、1kb/s、1mb/s、1gb/s、1tb/s,如果不需要将返回byte长度--> |
<!--子任务是否需要转换速度单位,转换完成后为:1b/s、1kb/s、1mb/s、1gb/s、1tb/s,如果不需要将返回byte长度--> |
||||||
<convertSpeed value="true"/> |
<convertSpeed value="true"/> |
||||||
|
|
||||||
<!--子任务的最大下载速度,0表示不限速,单位为:kb; --> |
<!--子任务的最大下载速度,0表示不限速,单位为:kb; --> |
||||||
<maxSpeed value="0"/> |
<maxSpeed value="0"/> |
||||||
|
|
||||||
</dGroup> |
</dGroup> |
||||||
</aria> |
</aria> |
@ -1,58 +1,58 @@ |
|||||||
// Top-level build file where you can add configuration options common to all sub-projects/modules. |
// Top-level build file where you can add configuration options common to all sub-projects/modules. |
||||||
buildscript { |
buildscript { |
||||||
ext.kotlin_version = '1.3.11' |
ext.kotlin_version = '1.3.11' |
||||||
repositories { |
repositories { |
||||||
jcenter() |
jcenter() |
||||||
mavenCentral() |
mavenCentral() |
||||||
google() |
google() |
||||||
maven { url 'https://jitpack.io' } |
maven { url 'https://jitpack.io' } |
||||||
} |
} |
||||||
dependencies { |
dependencies { |
||||||
// classpath 'com.android.tools.build:gradle:2.3.3' |
// classpath 'com.android.tools.build:gradle:2.3.3' |
||||||
classpath 'com.android.tools.build:gradle:3.3.2' |
classpath 'com.android.tools.build:gradle:3.3.2' |
||||||
classpath 'com.novoda:bintray-release:0.9' |
classpath 'com.novoda:bintray-release:0.9' |
||||||
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:${kotlin_version}" |
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:${kotlin_version}" |
||||||
// classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.7' |
// classpath 'com.jfrog.bintray.gradle:gradle-bintray-plugin:1.7' |
||||||
// classpath 'com.github.dcendents:android-maven-gradle-plugin:1.5' |
// classpath 'com.github.dcendents:android-maven-gradle-plugin:1.5' |
||||||
// NOTE: Do not place your application dependencies here; they belong |
// NOTE: Do not place your application dependencies here; they belong |
||||||
// in the individual module build.gradle files |
// in the individual module build.gradle files |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
allprojects { |
allprojects { |
||||||
repositories { |
repositories { |
||||||
jcenter() |
jcenter() |
||||||
mavenCentral() |
mavenCentral() |
||||||
google() |
google() |
||||||
maven { url 'https://jitpack.io' } |
maven { url 'https://jitpack.io' } |
||||||
} |
} |
||||||
|
|
||||||
tasks.withType(Javadoc) { |
tasks.withType(Javadoc) { |
||||||
options { |
options { |
||||||
encoding "UTF-8" |
encoding "UTF-8" |
||||||
charSet 'UTF-8' |
charSet 'UTF-8' |
||||||
links "http://docs.oracle.com/javase/7/docs/api" |
links "http://docs.oracle.com/javase/7/docs/api" |
||||||
} |
} |
||||||
} |
} |
||||||
} |
} |
||||||
|
|
||||||
task clean(type: Delete) { |
task clean(type: Delete) { |
||||||
delete rootProject.buildDir |
delete rootProject.buildDir |
||||||
} |
} |
||||||
|
|
||||||
ext { |
ext { |
||||||
userOrg = 'arialyy' |
userOrg = 'arialyy' |
||||||
groupId = 'com.arialyy.aria' |
groupId = 'com.arialyy.aria' |
||||||
publishVersion = '3.6.3' |
publishVersion = '3.6.4_dev_1' |
||||||
// publishVersion = '1.0.4' //FTP插件 |
// publishVersion = '1.0.4' //FTP插件 |
||||||
repoName='maven' |
repoName='maven' |
||||||
desc = 'android 下载框架' |
desc = 'android 下载框架' |
||||||
website = 'https://github.com/AriaLyy/Aria' |
website = 'https://github.com/AriaLyy/Aria' |
||||||
licences = ['Apache-2.0'] |
licences = ['Apache-2.0'] |
||||||
|
|
||||||
compileSdkVersion = 28 |
compileSdkVersion = 28 |
||||||
supportLibVersion = "28.0.0" |
supportLibVersion = "28.0.0" |
||||||
buildToolsVersion = "28.0.3" |
buildToolsVersion = "28.0.3" |
||||||
targetSdkVersion = 28 |
targetSdkVersion = 28 |
||||||
minSdkVersion = 15 |
minSdkVersion = 15 |
||||||
} |
} |
||||||
|
Loading…
Reference in new issue