Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[Permissions] Clean-up Camera and Media permissions for Android 13 and up #133

Merged
merged 7 commits into from
Sep 4, 2023

Conversation

thomashorta
Copy link
Contributor

@thomashorta thomashorta commented Aug 29, 2023

Part of wordpress-mobile/WordPress-Android#19016
Companion PR: wordpress-mobile/WordPress-Android#19103

This PR groups some changes related to Camera, Media, and Storage permissions on recent Android versions. The fixes made here were needed because the methods here were grouping some unrelated permissions, which causes client apps (tested on WordPress/Jetpack) to request unnecessary permissions in specific flows.

This is particularly more of an issue for Android 14 more stricter permission model for media reading, which changes how the user can give access to media, and partial access as well.

Notable changes

Note: The client app I used for testing and checking these was the WP-Android app, but it should be the same for all client apps using this library.

Remove getLastRecordedVideoUri

This method is only being used to get the last recorded video right after requesting for ACTION_VIDEO_CAPTURE, but that's not the correct way of getting the video that was recorded as a result of the video capture request intent. Also, with Android 14, the user can provide partial access to selected media files, so this method will no longer work in that scenario, since when the user selects that option they won't have given permission to this freshly taken video.

When using ACTION_VIDEO_CAPTURE without passing an EXTRA_OUTPUT the Uri of the video comes back in the onActivityResult result intent data field. Also, that Uri already has the proper access permissions for the requester, which makes it suitable for use with Android 14. In any case, the file permission is given by the Camera application so it's good to keep an eye on possible issues on Android 14 with Camera apps from lesser-known manufacturers, which could have incorrect implementation.

Reference:
https://developer.android.com/reference/android/provider/MediaStore#ACTION_VIDEO_CAPTURE

getCameraAndStoragePermissions should only match the CAMERA permission on Android 13 and up

Based on the history and the PR that introduced the other READ_MEDIA_* permissions to the return of the getCameraAndStoragePermissions method, this was added because of how getLastRecordedVideoUri was working, which queried media from the device after the user recorded a video, which is not needed and was removed (see point above).

Because of that removal, the client app doesn't really need MEDIA permissions for using ACTION_*_CAPTURE intents, since there are other ways of getting the picture/video when the CAMERA is started from those intents, so the client apps just need to implement the proper way (note: PR for WP-Android with that implementation will be open soon).

References:

checkAndRequestStoragePermission change to checkAndRequestFileDownloadPermission

The checkAndRequestStoragePermission was a bit too generic and was used throughout the WP-Android client app for several different flows, most of which didn't even require storage permissions, such as sharing media from other apps, dropping media into Aztec Editor when in Split Screen, and even File Download in most recent Android versions.

The name was changed to checkAndRequestFileDownloadPermission and should now only be used by the client app when doing some sort of File Download, which requires writing to the shared "destination" for downloads (provided by DownloadManager.Request#setDestinationInExternalPublicDir).

WP-Android already uses the method mentioned and as the documentation says, no permissions are required for writing to that directory on Android Q (SDK 29) and up, so getFileDownloadPermission method was updated to provide the proper list of permissions based on SDK level.

Reference:
https://developer.android.com/reference/android/app/DownloadManager.Request#setDestinationInExternalPublicDir(java.lang.String,%20java.lang.String)

Testing

WIP

Note: I tested all changes and made the appropriate updates to WordPress-Android code to make proper use of the permissions and this lib, and I should have PRs for it on that repository soon, but right now there's no way of easily testing the changes of this PR.

Reviews

@irfano I am adding you as you were the last one to make some changes regarding Android 13 media/Camera permissions so you probably have some context already. I suggest waiting until I have the companion PRs ready on the WordPress repo, so it's easier to test and make sense of all of that.

@RenanLukas I'm adding you as usual. 😅

Thomas Horta added 6 commits August 25, 2023 11:11
This method is only being used to get the last recorded video right after
requesting for `ACTION_VIDEO_CAPTURE`, but that's not the correct way of getting
the video that was recorded as a result of the video capture request intent.
Also, with Android 14, the user can provide partial access to selected media
files, so this method will no longer work in that scenario, as if the user
selected that option it won't have given permission to this freshly taken video.

When using `ACTION_VIDEO_CAPTURE` without passing an EXTRA_OUTPUT the Uri of the
video comes back in the `onActivityResult` result intent `data` field. Also,
that Uri already has the proper access permissions for the requester, which
makes it suitable for use with Android 14. In any case, the file permission is
given by the Camera application so it's good to keep an eye on possible issues
on Android 14 with Camera apps from lesser known manufactures, which could have
incorrect implementation.

Reference:
https://developer.android.com/reference/android/provider/MediaStore#ACTION_VIDEO_CAPTURE
Storage permissions are very specific to each context and situation, having them
in this shared library under such a generic term is misleading as it was being
used in several places (at least on WordPress-Android) that didn't even need
storage permissions for working.
Copy link

@RenanLukas RenanLukas left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the PR, @thomashorta. Code LGTM and the implementation was tested using the WP client PR. The concerns about specific Android versions I've mentioned in the client PR should have nothing to do with the way we're handling permissions (and most likely are related to emulator limitations).

Is it worth to make an internal announcement of these changes in case another product is currently using the functions that were modified?

@irfano
Copy link
Member

irfano commented Sep 4, 2023

Is it worth to make an internal announcement of these changes in case another product is currently using the functions that were modified?

Only WPAndroid and FluxC are using this library. The change doesn't affect FluxC, and wordpress-mobile/WordPress-Android#19103 has already handled the change in WPAndroid. So, it looks safe to merge without an extra announcement.

Copy link
Member

@irfano irfano left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I tested the change via wordpress-mobile/WordPress-Android#19103. LGTM! 👍🏻

@irfano irfano merged commit e539743 into trunk Sep 4, 2023
8 checks passed
@irfano irfano deleted the fix/camera-permission-video branch September 4, 2023 17:53
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Android 13 Android 13 Migration Android 14 Updates to comply with Android 14 changes. Tech Debt
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants