Skip to content

Commit

Permalink
downloader bug fixes
Browse files Browse the repository at this point in the history
  • Loading branch information
tonyofrancis committed Jul 1, 2018
1 parent 275648d commit 600825c
Show file tree
Hide file tree
Showing 8 changed files with 73 additions and 49 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ open class HttpUrlConnectionDownloader @JvmOverloads constructor(
override fun execute(request: Downloader.ServerRequest, interruptMonitor: InterruptMonitor?): Downloader.Response? {
val httpUrl = URL(request.url)
val client = httpUrl.openConnection() as HttpURLConnection
client.requestMethod = "GET"
client.requestMethod = request.requestMethod
client.readTimeout = connectionPrefs.readTimeout
client.connectTimeout = connectionPrefs.connectTimeout
client.useCaches = connectionPrefs.usesCache
Expand All @@ -58,6 +58,10 @@ open class HttpUrlConnectionDownloader @JvmOverloads constructor(
byteStream = client.inputStream
md5 = client.getHeaderField("Content-MD5") ?: ""
}
val responseHeaders = client.headerFields

val acceptsRanges = code == HttpURLConnection.HTTP_PARTIAL ||
responseHeaders["Accept-Ranges"]?.firstOrNull() == "bytes"

onServerResponse(request, Downloader.Response(
code = code,
Expand All @@ -66,7 +70,8 @@ open class HttpUrlConnectionDownloader @JvmOverloads constructor(
byteStream = null,
request = request,
md5 = md5,
responseHeaders = client.headerFields))
responseHeaders = responseHeaders,
acceptsRanges = acceptsRanges))

val response = Downloader.Response(
code = code,
Expand All @@ -75,7 +80,8 @@ open class HttpUrlConnectionDownloader @JvmOverloads constructor(
byteStream = byteStream,
request = request,
md5 = md5,
responseHeaders = client.headerFields)
responseHeaders = responseHeaders,
acceptsRanges = acceptsRanges)

connections[response] = client
return response
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ import com.tonyodev.fetch2.provider.NetworkInfoProvider
import com.tonyodev.fetch2.util.*
import com.tonyodev.fetch2core.*
import java.io.*
import java.net.HttpURLConnection
import java.util.concurrent.ExecutorService
import java.util.concurrent.Executors
import kotlin.math.ceil
Expand Down Expand Up @@ -79,12 +78,12 @@ class ParallelFileDownloaderImpl(private val initialDownload: Download,
override fun run() {
var openingResponse: Downloader.Response? = null
try {
val openingRequest = getRequestForDownload(initialDownload)
val openingRequest = getRequestForDownload(initialDownload, HEAD_REQUEST_METHOD)
openingResponse = downloader.execute(openingRequest, interruptMonitor)
if (!interrupted && !terminated && openingResponse?.isSuccessful == true) {
total = openingResponse.contentLength
if (total > 0) {
fileSlices = getFileSliceList(openingResponse.code, openingRequest)
fileSlices = getFileSliceList(openingResponse.acceptsRanges, openingRequest)
totalDownloadBlocks = fileSlices.size
try {
downloader.disconnect(openingResponse)
Expand Down Expand Up @@ -229,13 +228,13 @@ class ParallelFileDownloaderImpl(private val initialDownload: Download,
}
}

private fun getFileSliceList(openingResponseCode: Int, request: Downloader.ServerRequest): List<FileSlice> {
private fun getFileSliceList(acceptsRanges: Boolean, request: Downloader.ServerRequest): List<FileSlice> {
val file = getFile(downloadInfo.file)
if (!file.exists()) {
deleteAllTempFiles()
}
val previousSliceSize = getPreviousSliceCount(downloadInfo.id)
return if (openingResponseCode == HttpURLConnection.HTTP_PARTIAL) {
return if (acceptsRanges) {
val fileSliceInfo = getChuckInfo(request)
if (previousSliceSize != fileSliceInfo.slicingCount) {
deleteAllTempFiles()
Expand Down Expand Up @@ -285,19 +284,15 @@ class ParallelFileDownloaderImpl(private val initialDownload: Download,
private fun getPreviousSliceCount(id: Int): Int {
var sliceCount = -1
try {
if (!terminated && !interrupted) {
sliceCount = getSingleLineTextFromFile(getMetaFilePath(id))?.toInt() ?: -1
}
sliceCount = getSingleLineTextFromFile(getMetaFilePath(id))?.toInt() ?: -1
} catch (e: Exception) {
}
return sliceCount
}

private fun saveCurrentSliceCount(id: Int, SliceCount: Int) {
try {
if (!terminated && !interrupted) {
writeTextToFile(getMetaFilePath(id), SliceCount.toString())
}
writeTextToFile(getMetaFilePath(id), SliceCount.toString())
} catch (e: Exception) {
}
}
Expand Down Expand Up @@ -337,23 +332,19 @@ class ParallelFileDownloaderImpl(private val initialDownload: Download,

private fun deleteTempFile(id: Int, position: Int) {
try {
if (!interrupted && !terminated) {
val textFile = getFile(getDownloadedInfoFilePath(id, position))
if (textFile.exists()) {
textFile.delete()
}
val textFile = getFile(getDownloadedInfoFilePath(id, position))
if (textFile.exists()) {
textFile.delete()
}
} catch (e: Exception) {
}
}

private fun deleteMetaFile(id: Int) {
try {
if (!terminated && !interrupted) {
val textFile = getFile(getMetaFilePath(id))
if (textFile.exists()) {
textFile.delete()
}
val textFile = getFile(getMetaFilePath(id))
if (textFile.exists()) {
textFile.delete()
}
} catch (e: Exception) {
}
Expand All @@ -362,9 +353,7 @@ class ParallelFileDownloaderImpl(private val initialDownload: Download,
private fun getSavedDownloadedInfo(id: Int, position: Int): Long {
var downloaded = 0L
try {
if (!terminated && !interrupted) {
downloaded = getSingleLineTextFromFile(getDownloadedInfoFilePath(id, position))?.toLong() ?: 0L
}
downloaded = getSingleLineTextFromFile(getDownloadedInfoFilePath(id, position))?.toLong() ?: 0L
} catch (e: Exception) {
}
return downloaded
Expand Down Expand Up @@ -533,15 +522,9 @@ class ParallelFileDownloaderImpl(private val initialDownload: Download,
private fun deleteAllTempFiles() {
try {
for (fileSlice in fileSlices) {
if (!interrupted && !terminated) {
deleteTempFile(fileSlice.id, fileSlice.position)
} else {
break
}
}
if (!interrupted && !terminated) {
deleteMetaFile(downloadInfo.id)
deleteTempFile(fileSlice.id, fileSlice.position)
}
deleteMetaFile(downloadInfo.id)
} catch (e: Exception) {
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -302,7 +302,8 @@ class SequentialFileDownloaderImpl(private val initialDownload: Download,
headers = headers,
file = initialDownload.file,
tag = initialDownload.tag,
identifier = initialDownload.identifier)
identifier = initialDownload.identifier,
requestMethod = GET_REQUEST_METHOD)
}

private fun getAverageDownloadedBytesPerSecond(): Long {
Expand Down
12 changes: 9 additions & 3 deletions fetch2/src/main/java/com/tonyodev/fetch2/util/FetchUtils.kt
Original file line number Diff line number Diff line change
Expand Up @@ -6,9 +6,9 @@ import com.tonyodev.fetch2.Download
import com.tonyodev.fetch2core.Downloader
import com.tonyodev.fetch2.FetchConfiguration
import com.tonyodev.fetch2.Status
import com.tonyodev.fetch2core.GET_REQUEST_METHOD
import com.tonyodev.fetch2core.getFile


fun canPauseDownload(download: Download): Boolean {
return when (download.status) {
Status.DOWNLOADING,
Expand Down Expand Up @@ -43,9 +43,14 @@ fun canCancelDownload(download: Download): Boolean {
}
}

fun getRequestForDownload(download: Download, requestMethod: String = GET_REQUEST_METHOD): Downloader.ServerRequest {
return getRequestForDownload(download, -1, -1, requestMethod)
}

fun getRequestForDownload(download: Download,
rangeStart: Long = -1,
rangeEnd: Long = -1): Downloader.ServerRequest {
rangeEnd: Long = -1,
requestMethod: String = GET_REQUEST_METHOD): Downloader.ServerRequest {
val start = if (rangeStart == -1L) 0 else rangeStart
val end = if (rangeEnd == -1L) "" else rangeEnd.toString()
val headers = download.headers.toMutableMap()
Expand All @@ -56,7 +61,8 @@ fun getRequestForDownload(download: Download,
headers = headers,
file = download.file,
tag = download.tag,
identifier = download.identifier)
identifier = download.identifier,
requestMethod = requestMethod)
}

fun deleteRequestTempFiles(fileTempDir: String,
Expand Down
10 changes: 8 additions & 2 deletions fetch2core/src/main/java/com/tonyodev/fetch2core/Downloader.kt
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,10 @@ interface Downloader : Closeable {
val tag: String?,

/** The identifier associated with this request*/
val identifier: Long)
val identifier: Long,

/** Request Method. GET, HEAD or POST*/
val requestMethod: String)

/**
* A class that contains the server response information used by Fetch
Expand All @@ -168,7 +171,10 @@ interface Downloader : Closeable {
val md5: String,

/** Server Response Headers */
val responseHeaders: Map<String, List<String>>)
val responseHeaders: Map<String, List<String>>,

/** Details if the server accepts byte ranges*/
val acceptsRanges: Boolean)

/** File Downloading Type used to download each request.*/
enum class FileDownloaderType {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,12 @@ import java.util.concurrent.TimeUnit
import kotlin.math.abs
import kotlin.math.ceil

const val GET_REQUEST_METHOD = "GET"

const val HEAD_REQUEST_METHOD = "HEAD"

const val POST_REQUEST_METHOD = "POST"

fun calculateProgress(downloaded: Long, total: Long): Int {
return when {
total < 1 -> -1
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,23 +67,28 @@ open class FetchFileServerDownloader @JvmOverloads constructor(
val contentLength = serverResponse.contentLength
val inputStream = transporter.getInputStream()

val headerResponse = mutableMapOf<String, List<String>>()
val responseHeaders = mutableMapOf<String, List<String>>()
try {
val json = JSONObject(serverResponse.toJsonString)
json.keys().forEach {
headerResponse[it] = listOf(json.get(it).toString())
responseHeaders[it] = listOf(json.get(it).toString())
}
} catch (e: Exception) {

}

val acceptsRanges = code == HttpURLConnection.HTTP_PARTIAL ||
responseHeaders["Accept-Ranges"]?.firstOrNull() == "bytes"

onServerResponse(request, Downloader.Response(
code = code,
isSuccessful = isSuccessful,
contentLength = contentLength,
byteStream = null,
request = request,
md5 = serverResponse.md5,
responseHeaders = headerResponse))
responseHeaders = responseHeaders,
acceptsRanges = acceptsRanges))

val response = Downloader.Response(
code = code,
Expand All @@ -92,7 +97,8 @@ open class FetchFileServerDownloader @JvmOverloads constructor(
byteStream = inputStream,
request = request,
md5 = serverResponse.md5,
responseHeaders = headerResponse)
responseHeaders = responseHeaders,
acceptsRanges = acceptsRanges)

connections[response] = transporter
return response
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import okhttp3.Request
import okhttp3.Response
import java.io.InputStream
import java.io.OutputStream
import java.net.HttpURLConnection
import java.util.Collections
import java.util.concurrent.TimeUnit

Expand Down Expand Up @@ -43,6 +44,7 @@ open class OkHttpDownloader @JvmOverloads constructor(
override fun execute(request: Downloader.ServerRequest, interruptMonitor: InterruptMonitor?): Downloader.Response? {
val okHttpRequestBuilder = Request.Builder()
.url(request.url)
.method(request.requestMethod, null)

request.headers.entries.forEach {
okHttpRequestBuilder.addHeader(it.key, it.value)
Expand All @@ -52,26 +54,33 @@ open class OkHttpDownloader @JvmOverloads constructor(
val okHttpResponse = client.newCall(okHttpRequest).execute()
val code = okHttpResponse.code()
val success = okHttpResponse.isSuccessful
val contentLength = okHttpResponse.body()?.contentLength() ?: -1L
var contentLength = okHttpResponse.body()?.contentLength() ?: -1L
val byteStream: InputStream? = okHttpResponse.body()?.byteStream()
val md5 = okHttpResponse.header("Content-MD5") ?: ""
val responseHeaders = mutableMapOf<String, List<String>>()

val okResponseHeaders = okHttpResponse.headers()
for (i in 0 until okResponseHeaders.size()) {
val key = okResponseHeaders.name(i)
val values = okResponseHeaders.values(key)
responseHeaders[key] = values
}

if (contentLength < 1) {
contentLength = responseHeaders["Content-Length"]?.firstOrNull()?.toLong() ?: -1L
}

val acceptsRanges = code == HttpURLConnection.HTTP_PARTIAL ||
responseHeaders["Accept-Ranges"]?.firstOrNull() == "bytes"

onServerResponse(request, Downloader.Response(
code = code,
isSuccessful = success,
contentLength = contentLength,
byteStream = null,
request = request,
md5 = md5,
responseHeaders = responseHeaders))
responseHeaders = responseHeaders,
acceptsRanges = acceptsRanges))

val response = Downloader.Response(
code = code,
Expand All @@ -80,7 +89,8 @@ open class OkHttpDownloader @JvmOverloads constructor(
byteStream = byteStream,
request = request,
md5 = md5,
responseHeaders = responseHeaders)
responseHeaders = responseHeaders,
acceptsRanges = acceptsRanges)

connections[response] = okHttpResponse
return response
Expand Down

0 comments on commit 600825c

Please sign in to comment.