Read/Write access to 'Documents' folder for all Android versions? - java

I'm currently using Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOCUMENTS) as a path. I have requested android.permission.WRITE_EXTERNAL_STORAGE. I am targeting SDK 30. I have had success reading and writing a file on Android 8 and Android 11, but not Android 10. Adding android:ignore="ScopedStorage" and android:requestLegacyExternalStorage="true" to my AndroidManifest.xml didn't work.
Reading through the official docs, it's very confusing. I tried an alternative approach with an ACTION_OPEN_DOCUMENT_TREE indent, but all I could navigate was the Downloads folder. I couldn't get to the Documents folder.
There are multiple questions on here that are similar, but don't quite get to the nub of the matter for me. Can anyone please share some light on how to do something as basic as simple file access to the Documents folder?

Actually, the problem was that on this particular Android 10 device there was no "Documents" folder. Manually creating one fixed it. So the real gotcha is that Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOCUMENTS) sometimes doesn't give you a "Documents" directory depending on the device.
However, I'm not convinced this is the correct way to do this with Android 11 (even though it's currently working for me).

Related

Java - Download from OneDrive public folder

I have a link for OneDrive. The format is https://onedrive.live.com/?cid=XXXXXXXXXXXXXXXX&id=XXXXXXXXXXXXXXXX%XXXXX
The link is public, it's not mine and new files is often added in it. My question is simple. What is the best way in Java to list all the file/folder from this link and to download a file ?
I tried HtmlUnit but it give a big javascript error.
Since the link is public, do I really need to use a OneDrive SDK ? I really don't know how to proccess with OneDrive... Thank's for any help
https://github.com/isac322/OneDrive-SDK-java This SDK will help you get the path and download the folder.

Is it possible to programmatically access Download folder on Android Q (SDK >= 29)?

I want to list all files .txt in the Download folder and then allow the user to pick one and read its content. My minSdkVersion is 16, but I came across this problem because my Android is Q (29).
What I tried:
Apparently Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS) would solve it for SDK <= 29. However, I didn't test it because I would first like to check out a solution for Android Q.
getExternalStoragePublicDirectory says:
When an app targets Build.VERSION_CODES.Q, the path returned from this method is no longer directly accessible to apps. Apps can continue to access content stored on shared/external storage by migrating to alternatives such as Context#getExternalFilesDir(String), MediaStore, or Intent#ACTION_OPEN_DOCUMENT.
So:
getExternalFilesDir returns /storage/emulated/0/Android/data/com.mypackage/files/Download. This path is not useful, I expected it to return /storage/emulated/0/Download, which is where the downloaded files are.
I didn't manage to do something with MediaStore.Downloads. I checked the documentation and it says "In particular, if your app wants to access a file within the MediaStore.Downloads collection that your app didn't create, you must use the Storage Access Framework.". So, I assume it won't work for me.
In my concept, Intent and Storage Access Framework would need the user to navigate through directories and files using a File Manager, which is not what I want here.
In short:
Is it possible to list the .txt downloaded files programmatically in Android Q (SDK >= 29)? If so, how?
Is it possible to list the .txt downloaded files programmatically in Android Q (SDK >= 29)?
Not ones created by other apps, which would appear to be your intention.
The closest is if you use ACTION_OPEN_DOCUMENT_TREE and ask the user to open the Downloads/ tree on external storage... and you cannot do that on Android R (at least through DP1).

java.lang.IllegalStateException: Not one of standard directories [duplicate]

Android Api 29 has big changes regarding files and folders.
I have not found a way so far to create a folder in the internal storage that is public visible.
Every folder I create can be seen by my app only.
I write an app that creates data files that shall be picked up by other apps, for instance the Total Commander to copy them to a destination.
Everything worked fine until I activated Api 29. Some of my clients DO use pixel phones and they use Android 10.
How can I create a folder and files in Android 10 that are public?
This has been deprecated:
Environment.getExternalStorageDirectory();
Environment.getExternalStoragePublicDirectory(type);
and when I use
File root = context.getExternalFilesDir(null);
The created files can only be seen by my app.
How can I achieve the behavior that was valid before Android 10?
Thanks in advance.
when I use File root = context.getExternalFilesDir(null); The created files can only be seen by my app
They can be seen by any app that uses the Storage Access Framework (e.g., ACTION_OPEN_DOCUMENT), if the user chooses the document that you place in that directory.
I write an app that creates data files that shall be picked up by other apps
Other apps have no access to external or removable storage on Android 10, except in the limited directories like getExternalFilesDir() or via non-filesystem means (ACTION_OPEN_DOCUMENT, MediaStore).
How can I create a folder and files in Android 10 that are public?
Use getExternalFilesDir() and related methods on Context. Or, use ACTION_CREATE_DOCUMENT or ACTION_OPEN_DOCUMENT_TREE and use the Storage Access Framework. In either case, the resulting documents can be used by other apps that also use the Storage Access Framework.
Starting from Android 10, you should use SAF, and let user choose the directory using ACTION_OPEN_DOCUMENT_TREE.
If you need a simple example. You can find it here
Alternatively, you could use requestLegacyExternalStorage = true in manifest when your app is not newly released. But, this is something that should not be used for future release, as this is a short-term solution provided by Google.
Note: In future releases of Android, user will not be able to pick the whole external file directory and Downloads directory, so unfortunately, keep in mind that we are not going to have access to these as well! For more information you can click here

Detect the source of apk download

I have an apk file present in 2 standalone servers both of which have separate download links.
I would like to know if it is possible to detect from which link the apk was downloaded after the app was installed and opened.
The download is via browser and the one of the requirements is that the build has to remain the same.
If you are just installing your APK as a link directly on a file server, and the APKs are exactly the same, then no, there is no way to do this.
Here are some work-arounds:
Google Play provides a way for you to do this, but they are doing this through broadcasting an intent to the application after it has been successfully installed. You could release the APKs through Google Play privately through the beta / alpha channel, and take advantage of this feature perhaps. You'd not be able to use a private file server though.
You could create your own application that downloads and installs
the APKs and mimics Google Play's functionality which I described
above. This would probably be ridiculous for you to do, and I don't recommend it.
You could differentiate the APKs in some way. You could keep the content exactly the same, but configure some fields in the build logic through Gradle using the buildConfigField. You could also do split apks, use flavors, or a number of other different creative solutions if you wish.
So if for some reason the above suggestions don't meet your requirements, another solution that would be extremely hacky would be to use different APK file names. The browser would download the APK to the download folder, and you could probably look at the Android downloads folder after opening the app and look at the file name. This would not be reliable in any way though, as users could easily delete the file before actually opening your app, or there could be old downloads also. You'd have to look for base file names, and identify the most recent file based on creation date.

How to use Google Cloud storage to upload image file?

These couple day I have been trying to upload images to the Google cloud using Java. However, I did found some source codes around but amazingly, none of them come with the handy lib jar files. I am trying to search for the required jar file but still can not found them all. Here, I am asking, does any one have the sample code that I just directly run? The change of the settings is a necessary but definitely not for libs.
All you need is Java Client for Google Cloud Storage
Howto you will find here: Getting Started

Categories