How to delete DownloadManager cache folder? - android

I'm looking to delete file(s) at /data/user/0/com.android.providers.downloads/cache programmatically but do not seem to have access to it. I have signature level app permission and can do adb root and su in the shell but Runtime.getRuntime().exec(su) receives a Permission denied exception. When I try to do File file = new File(path) and check if it exists, it returns false. The permissions for the cache folder are drwxrwx--x.
How can I delete file(s) from the DownloadManager cache directory?
Update
The best way seems to be to use DownloadManager remove(downloadId) which removes it from the cache folder. It is not well documented that it does that though.

The best way seems to be DownloadManager remove(downloadId) when you have it available. It actually removes the file with a message Deleting /data/data/com.android.providers.downloads/cache/binary.apk via provider delete
If you want the list of downloadIds to remove the whole cache, the programmer might need to use DownloadManager Query and filter by status complete to get all of them to remove.

Related

Downloaded files get deleted automatically

In my app, there are a few files that users can download. The files get downloaded via the android download manager. But, since a few weeks now, hundreds of users have been complaining that their files automatically keep deleting every 8-12 days, without them even uninstalling the app. (There might be many more users who haven't bothered to complain about the same.)
Now, there could be a number of user-specific reasons why that would happen on a few devices. But considering the huge number of users, it seems that I might have been doing something wrong.
Why would the system/download manager delete the files automatically? Is there a way to inform the system or the download manager to not delete certain files? Or should I just settle with renaming the files after downloading, so as to unlink them from the download manager, and hope that the problem gets solved with just that?
Edit:
Here's the code that I use to download the files:
DownloadManager.Request request = new DownloadManager.Request(Uri.parse(trackLink));
request.setTitle(trackTitle);
request.setDestinationInExternalPublicDir("Tracks", trackTitle + ".mp3");
request.setVisibleInDownloadsUi(false);
DownloadManager manager = (DownloadManager) getSystemService(Context.DOWNLOAD_SERVICE);
manager.enqueue(request);
I also came across this issue. Looking at the source for DownloadIdleService it appears that if the download are set to not be visible in the UI they're deleted after 7 days as they're considered "stale".
Here's the javadoc fromDownloadIdleService:
/**
* Remove stale downloads that third-party apps probably forgot about. We
* only consider non-visible downloads that haven't been touched in over a
* week.
*/
https://android.googlesource.com/platform/packages/providers/DownloadProvider/+/master/src/com/android/providers/downloads/DownloadIdleService.java#110
There is a bigger problem starting in Android Q where value set by setVisibleInDownloadsUi is ignored and it is false by default. The files will be deleted after a week. You can test it by: download file, change date in calendar by 2 months for example, call this in terminal:
adb shell cmd jobscheduler run -f com.android.providers.downloads -100
It starts job from DownloadIdleService where old and forbidden files are deleted. You can see in logcat (set no filter) that DownloadManager try to delete your files.
To prevent from that you can:
download files to Environment#getExternalStoragePublicDirectory(String) with Environment#DIRECTORY_DOWNLOADS) - this is the only path starting in Android Q where downloads are visible and should not be deleted
change file name after downloading (in DownloadedReceiver for example)
It was too big for a comment to I'm just putting it as an answer.
I don't have any clue yet why the files are missing or getting deleted over a period of time - which a bit strange. But I had to do something similar and never experienced something like this. So I though I might share what I have done in that case.
I preferred to keep the downloaded files in the internal storage which the application holds rather than keeping it in the external storage. For example, the file path where I used to save the downloaded files is something like...
/data/data/" + "com.example.myapplication" + "/musicfiles/
So what I did right after downloading is telling the media scanner about the new file so that it is immediately available to the user. So as I was downloading the file using an AsyncTask I had to run the scanner in the onPostExecute method like this after a successful download.
protected void onPostExecute() {
if(downloadCompletedSuccessfully) {
MediaScannerConnection.scanFile(context,
new String[]{file.toString()}, null,
new MediaScannerConnection.OnScanCompletedListener() {
public void onScanCompleted(String path, Uri uri) {
Log.i("ExternalStorage", "Scanned " + path + ":");
Log.i("ExternalStorage", "-> uri=" + uri);
}
});
}
}
So in your case, I think its not might be the issue that the Download button is not visible due to the unavailability of the file downloaded. It might happen if the media scanner fails to find the file in the file system as well. So you might consider giving it a try.
I don't know if clean master or some softwares like that cleans junk files every now and then if they are in external storage. You might consider investigate those as well.

Trigger the rescan of MediaStore programmatically

Notice that the newly added photos(copied over using "adb push" into Pictures folder) are not included in the MediaStore Content Provider. Is there a way to trigger the rescan programmatically?
Already tried:
sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE,Uri.parse(Environment.getExternalStorageDirectory().getPath())));
and
sendBroadcast(new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE,Uri.parse(Environment.getExternalStorageDirectory().getPath() + "/Pictures")));
which seem not work.
The broadcast Intent.ACTION_MEDIA_MOUNTED cannot be used after Android 4.4.
(1) Other than using MediaScannerWrapper to scan files myself, is there other way to programmatically trigger the rescan?
(2) Under what circumstances will the rescan happen in Android?
Already tried
You are passing a directory, not a file.
is there other way to programatically trigger the rescan?
Use MediaScannerConnection and its scanFile() method. This too requires a file AFAIK.

Deleting files from applications data folder

I have a tablet where I need to execute a service from a binary file which will continually receive data from a chip and store the various data files in the "/data/data/com.example.binary/received/" folder. I also have a FileObserver set up on that folder to perform an action on the files that are created and once the Close event is given by the FileObserver I an trying to delete the file. This is what I have an issue with. I can delete the files if it is in the "/data/data/com.example.binary/" folder but if its in the "/data/data/com.example.binary/received/" folder I cant delete it. Seems to be some android permission issue. Is there any way around this?.
So far I have tried and failed by
1) trying to execute the "rm /data/data/com.example.binary/received/file1.xy"
2) trying file.delete()
FYI - I have the Read and Write Permissions. And all file handles to the file are closed, that's when the file's Close event is fired by the FileObserver.
I can delete the files from ADB using the "rm file1.xy"
And the binary file is from our client and i cannot change the location where it creates the output files.xy . . it will always be in the received folder. So any suggestions?
PS: /data/data folder is the location where all the installed apps get stored in my tablet.

programmatically erase android browser cache, history, etc. with root

I have an android tablet that is locked down (users will only be able to use standard issue android browser), so all the temporary internet stuff should be in the same place.
Assuming I am able to root the device sometime here soon, I would like to be able to wipe out (1) cookies,(2) temp internet files,(3) history,(4) form data,(5) location access info,(6) passwords, (7) cache.
I think I can knock out most of these by erasing:
/data/data/com.android.browser/cache
The cookies appear to be in a database. I'm not sure if I can just delete it
/data/data/com.android.browser/databases/webview.db
And then I think I can just delete these files to erase location information:
/data/data/com.google.android.location/files/wifi
/data/data/com.google.android.location/files/cell
Will that take care of everything?
What am I leaving out?
Is it safe to just erase that database? Does anyone know?
how about something as simple as
adb shell pm clear com.android.browser
from command line ?
This API is deprecated in Android Marshmallow. If you build using API 23 it wont work any more.
You can delete them #micahhoover,
You can delete complete com.android.browser sub directories, every time you relaunch browser, all the sub folders gets created.
To delete android browser History(Default)
in your Activity.java file add the follwing code
Browser.clearHistory(getContentResolver());
In your manifest add
<uses-permission android:name="com.android.browser.permission.WRITE_HISTORY_BOOKMARKS"/>
<uses-permission android:name="com.android.browser.permission.READ_HISTORY_BOOKMARKS"/>

Shared folder implementation

I need to make a shared folder in android.
I want to be able to:
1) create a folder on the device(sdcard/SharedFolder). ;
2) create a folder on the server. ;
3) copy some files to that folder. ;
4) seamlessly synchronize those files with my Android(and vice-versa). ;
The idea is to make an ftp connection to the ftp server(local filzila server at first) and
compare my local files list to his remote files list(by means of comparing timestamps or any other way).
Then my application would decide which files are the most updated and will copy them(from device to server or from the server to the device).
So i have 3 issues which i wanted to talk about:
I.Currently i made my application be a Broadcast-Receiver which is being called by the Alarm-Manager repeatedly(with the inexact method) and run on its own process.
Upon receiving a broadcast i connect to the server and make the above.
currently the broadcast-receiver is set from some Activity(enable/disable buttons and thats it.)
What will happen to my Broadcast-Receiver after killing the Activity which set him? I understood that at some point the system will delete him from the Alarm-Manager too? How should i handle this? I want the program to run without the user handling it... hence after restart of the device and etc i don't want him to re-enable my program.
II. How would you suggest to handle the files compare between the folders? i would like to support copy, delete, edit on those files hence the most suitable version of a file should be on both the server and device after the sync.
i thought about making some manifest file in each folder and save in it data on the file like:
-who change it last and when
-how much readers does this file have(can it be done as a service of the phone? some event of opening a file or a folder?)
and etc.
III.
Any suggestions will be appreciated!
ADB provides a shell interface where you can issue commands shell commands. See http://developer.android.com/guide/developing/tools/adb.html#shellcommands
You can also use the sync command provided with ADB. Open a prompt and issue 'adb help' to see more.

Categories

Resources