Downloader.cancelDownload() instead of using external Thread logic
This is needed so that downloads can be canceled from within an IntentService. Since the Downloader classes do not have any Thread logic in them, they shouldn't use Thread logic within them anyway. This also removes the unused argument to AsyncDownloader.attemptCancel().
This commit is contained in:
parent
74274d21b4
commit
591b23b5ab
@ -556,7 +556,7 @@ public class AppDetails extends AppCompatActivity implements ProgressListener, A
|
||||
@Override
|
||||
protected void onDestroy() {
|
||||
if (downloadHandler != null && !inProcessOfChangingConfiguration) {
|
||||
downloadHandler.cancel(false);
|
||||
downloadHandler.cancel();
|
||||
cleanUpFinishedDownload();
|
||||
}
|
||||
inProcessOfChangingConfiguration = false;
|
||||
@ -1553,7 +1553,7 @@ public class AppDetails extends AppCompatActivity implements ProgressListener, A
|
||||
return;
|
||||
}
|
||||
|
||||
activity.downloadHandler.cancel(true);
|
||||
activity.downloadHandler.cancel();
|
||||
activity.cleanUpFinishedDownload();
|
||||
setProgressVisible(false);
|
||||
updateViews();
|
||||
|
@ -253,12 +253,10 @@ public class ApkDownloader implements AsyncDownloader.Listener {
|
||||
/**
|
||||
* Attempts to cancel the download (if in progress) and also removes the progress
|
||||
* listener
|
||||
*
|
||||
* @param userRequested - true if the user requested the cancel (via button click), otherwise false.
|
||||
*/
|
||||
public void cancel(boolean userRequested) {
|
||||
public void cancel() {
|
||||
if (dlWrapper != null) {
|
||||
dlWrapper.attemptCancel(userRequested);
|
||||
dlWrapper.attemptCancel();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -43,9 +43,9 @@ class AsyncDownloadWrapper extends Handler implements AsyncDownloader {
|
||||
downloadThread.start();
|
||||
}
|
||||
|
||||
public void attemptCancel(boolean userRequested) {
|
||||
if (downloadThread != null) {
|
||||
downloadThread.interrupt();
|
||||
public void attemptCancel() {
|
||||
if (downloader != null) {
|
||||
downloader.cancelDownload();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -16,6 +16,6 @@ public interface AsyncDownloader {
|
||||
|
||||
void download();
|
||||
|
||||
void attemptCancel(boolean userRequested);
|
||||
void attemptCancel();
|
||||
|
||||
}
|
||||
|
@ -23,6 +23,8 @@ public abstract class Downloader {
|
||||
public static final String EXTRA_BYTES_READ = "extraBytesRead";
|
||||
public static final String EXTRA_TOTAL_BYTES = "extraTotalBytes";
|
||||
|
||||
private volatile boolean cancelled = false;
|
||||
|
||||
private final OutputStream outputStream;
|
||||
|
||||
private final File outputFile;
|
||||
@ -124,12 +126,19 @@ public abstract class Downloader {
|
||||
* @throws InterruptedException
|
||||
*/
|
||||
private void throwExceptionIfInterrupted() throws InterruptedException {
|
||||
if (Thread.interrupted()) {
|
||||
if (cancelled) {
|
||||
Utils.debugLog(TAG, "Received interrupt, cancelling download");
|
||||
throw new InterruptedException();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Cancel a running download, triggering an {@link InterruptedException}
|
||||
*/
|
||||
public void cancelDownload() {
|
||||
cancelled = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* This copies the downloaded data from the InputStream to the OutputStream,
|
||||
* keeping track of the number of bytes that have flowed through for the
|
||||
|
@ -6,8 +6,11 @@ import org.junit.Test;
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.net.URL;
|
||||
import java.util.concurrent.CountDownLatch;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
|
||||
import static org.junit.Assert.assertTrue;
|
||||
import static org.junit.Assert.fail;
|
||||
|
||||
public class HttpDownloaderTest {
|
||||
|
||||
@ -56,4 +59,38 @@ public class HttpDownloaderTest {
|
||||
assertTrue(receivedProgress);
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void downloadThenCancel() throws IOException, InterruptedException {
|
||||
final CountDownLatch latch = new CountDownLatch(5);
|
||||
URL url = new URL("https://f-droid.org/repo/index.jar");
|
||||
File destFile = File.createTempFile("dl-", "");
|
||||
destFile.deleteOnExit(); // this probably does nothing, but maybe...
|
||||
final HttpDownloader httpDownloader = new HttpDownloader(url, destFile, null);
|
||||
httpDownloader.setListener(new Downloader.DownloaderProgressListener() {
|
||||
@Override
|
||||
public void sendProgress(URL sourceUrl, int bytesRead, int totalBytes) {
|
||||
System.out.println("DownloaderProgressListener.sendProgress " + bytesRead + " / " + totalBytes);
|
||||
receivedProgress = true;
|
||||
latch.countDown();
|
||||
}
|
||||
});
|
||||
new Thread(){
|
||||
@Override
|
||||
public void run() {
|
||||
try {
|
||||
httpDownloader.download();
|
||||
fail();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
fail();
|
||||
} catch (InterruptedException e) {
|
||||
// success!
|
||||
}
|
||||
}
|
||||
}.start();
|
||||
latch.await(100, TimeUnit.SECONDS); // either 5 progress reports or 100 seconds
|
||||
httpDownloader.cancelDownload();
|
||||
assertTrue(receivedProgress);
|
||||
}
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user