I have an Android app that downloads hundreds of files from the Internet. After downloading, some files turn out to be 0-bytes. The application tries to detect such cases and delete such files after downloading, but sometimes it fails. The problem is more common on Android 4.x devices.
Here is the method that performs the download. I get the number of bytes actually read from inputStream.read(buffer) .
public class Utils { public static class DownloadFileData { int nTotalSize; int nDownloadedSize; } public interface ProgressCallback { void onProgress(long nCurrent, long nMax); } public static boolean downloadFile(String sFileURL, File whereToSave, DownloadFileData fileData, ProgressCallback progressCallback) { InputStream inputStream = null; FileOutputStream fileOutput = null; try { URL url = new URL(sFileURL); URLConnection connection = url.openConnection();
Here is a piece of code that handles downloads. Since sometimes the number of bytes read is incorrect (this is> 0, and the real file is 0 bytes in size), I check the size of the downloaded file using outputFile.length() . But this again gives a value> 0, although the file is really 0 bytes. I also tried to simply create a new file and read its size using recheckSizeFile.length() . However, the size is defined as> 0, while it is really 0 bytes.
Utils.DownloadFileData fileData = new Utils.DownloadFileData(); boolean bDownloadedSuccessully = Utils.downloadFile(app.sCurrenltyDownloadedFile, outputFile, fileData, new Utils.ProgressCallback() { ... // progress bar is updated here }); if (bDownloadedSuccessully) { boolean bIsGarbage = false; File recheckSizeFile = new File(sFullPath); long nDownloadedFileSize = Math.min(recheckSizeFile.length(), Math.min(outputFile.length(), fileData.nDownloadedSize)); // if the file is 0bytes, it garbage if (0 == nDownloadedFileSize) { bIsGarbage = true; } // if this is a video and if of suspiciously small size, it's // garbage, too else if (Utils.isStringEndingWith(app.sCurrenltyDownloadedFile, App.VIDEO_FILE_EXTENSIONS) && nDownloadedFileSize < Constants.MIN_NON_GARBAGE_VIDEO_FILE_SIZE) { bIsGarbage = true; } if (bIsGarbage) { ++app.nFilesGarbage; app.updateLastMessageInDownloadLog("File is fake, deleting: " + app.sCurrenltyDownloadedFile); // delete the garbage file if (null != outputFile) { if (!outputFile.delete()) { Log.e("MyService", "Failed to delete garbage file " + app.sCurrenltyDownloadedFile); } } } else { ... // process the normally downloaded file }
I'm not sure, but I think there is an error in Android with the file size to read. Has anyone seen a similar problem? Or am I maybe something is wrong here? Thanks!
EDIT: how do I determine that files are 0-byte: all files that are downloaded go through the procedures described. When I then look at the download folder with a file browser (Ghost Commander), some of the files (for example, 10%) will be 0-byte. They cannot be played by the video player (displayed as a βbroken fileβ icon).