net.wicp.tams.common.http.download.Download Maven / Gradle / Ivy
package net.wicp.tams.common.http.download;
import java.io.IOException;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.concurrent.CountDownLatch;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.impl.conn.PoolingHttpClientConnectionManager;
import lombok.extern.slf4j.Slf4j;
import net.wicp.tams.common.apiext.IOUtil;
import net.wicp.tams.common.apiext.StringUtil;
import net.wicp.tams.common.thread.ThreadPool;
/***
* 多线程下载
*
* @author andy.zhou
*
*/
@Slf4j
public class Download {
private final String url;
private final long fileSize;
private final String dirPath;
private final String fileName;
private final String fileNameRemote;
private final String filePath;
private CloseableHttpClient httpClient;
/**
*
* 每个线程下载的字节数
*/
private long unitSize = 2 * 1024 * 1024;
public Download(String url, long fileSize, String dirPath, String fileName)
throws IOException {
this.url = url;
this.fileSize = fileSize < 0 ? getRemoteFileSize(url) : fileSize;
this.fileNameRemote = StringUtil.getFileName(url);
this.fileName = StringUtil.isNull(fileName) ? this.fileNameRemote
: fileName;
this.dirPath = dirPath;
this.filePath = IOUtil.mergeFolderAndFilePath(dirPath, this.fileName);
PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager();
cm.setMaxTotal(100);
this.httpClient = HttpClients.custom().setConnectionManager(cm).build();// HttpConnPool.getInstance().getClient();
}
public Download(String url, String dirPath) throws IOException {
this(url, -1, dirPath, null);
}
public String download() throws IOException {
IOUtil.createFile(filePath, fileSize);
Long threadCount = (fileSize / unitSize)
+ (fileSize % unitSize != 0 ? 1 : 0);
long offset = 0;
CountDownLatch end = new CountDownLatch(threadCount.intValue());
if (fileSize <= unitSize) {// 如果远程文件尺寸小于等于unitSize
DownloadThread downloadThread = new DownloadThread(url, filePath,
offset, fileSize, end, httpClient);
ThreadPool.getDefaultPool().submit(downloadThread);
} else {// 如果远程文件尺寸大于unitSize
for (int i = 1; i < threadCount; i++) {
DownloadThread downloadThread = new DownloadThread(url,
filePath, offset, unitSize, end, httpClient);
ThreadPool.getDefaultPool().submit(downloadThread);
offset = offset + unitSize;
}
if (fileSize % unitSize != 0) {// 如果不能整除,则需要再创建一个线程下载剩余字节
DownloadThread downloadThread = new DownloadThread(url,
filePath, offset, fileSize - unitSize
* (threadCount - 1), end, httpClient);
ThreadPool.getDefaultPool().submit(downloadThread);
}
}
try {
end.await();
} catch (InterruptedException e) {
log.error("DownLoadManager exception msg:{}",
org.apache.commons.lang3.exception.ExceptionUtils
.getStackTrace(e));
e.printStackTrace();
}
log.info("下载完成!{} ", filePath);
return filePath;
}
/**
*
* 获取远程文件尺寸
*/
private long getRemoteFileSize(String remoteFileUrl) throws IOException {
long fileSize = 0;
HttpURLConnection httpConnection = (HttpURLConnection) new URL(
remoteFileUrl).openConnection();
httpConnection.setRequestMethod("HEAD");
int responseCode = httpConnection.getResponseCode();
if (responseCode >= 400) {
log.debug("Web服务器响应错误!");
return 0;
}
String sHeader;
for (int i = 1;; i++) {
sHeader = httpConnection.getHeaderFieldKey(i);
if (sHeader != null && sHeader.equals("Content-Length")) {
System.out.println("文件大小ContentLength:"
+ httpConnection.getContentLength());
fileSize = Long.parseLong(httpConnection
.getHeaderField(sHeader));
break;
}
}
return fileSize;
}
}