React Native WebView(相机,Getusermedia)iOS上的权限双重请求15
我们做什么?
我们正在为iOS和Android平台构建React本机应用程序。该应用程序具有一个外部网站,内部具有相机操作,通过 React-native-webview 模块打开。从我们的实验中,我们观察到,要使它起作用,必须向最终用户询问摄像机权限两次 :(
- 一次)当用户在安装后首先打开应用程序时 当React Native WebView组件为时,他/她的设备
- (每次) 加载,getusermedia方法正在内部执行。
这两个请求都显示给用户弹出窗口,以允许相机访问:第一个用于“ application_name”,第二个用于“ url_inside_webview” - 图片方案
- 询问权限(内部网络浏览)每次用户打开应用程序 WebView组件(并且正在执行)是不良的UX。
- 我们拒绝申请发布到Apple Store期间 苹果评论。评论者的评论正是这一刻 关于“两次询问权限,每次Web组件 负载”
重现该问题的技术细节
os:Apple iOS 15.1和较新的
对本机依赖性的反应:
"dependencies": {
"react": "17.0.2",
"react-native": "0.66.0",
"react-native-permissions": "^3.0.6",
"react-native-webview": "^11.14.0"
}
React-native中的设置权限:
import { request, PERMISSIONS, RESULTS } from 'react-native-permissions';
// ... //
request(PERMISSIONS.IOS.CAMERA)
.then((statuses) => {
if (statuses[PERMISSIONS.IOS.CAMERA] === RESULTS.GRANTED) {
setWebviewRenderAvailable(true);
});
});
在iOS/podfile中配置:
target 'MyAwesomeProject' do
# Check permissions for camera
permissions_path = '../node_modules/react-native-permissions/ios'
pod 'RNPermissions', :path => '../node_modules/react-native-permissions'
pod 'Permission-Camera', :path => "#{permissions_path}/Camera"
pod 'Permission-PhotoLibrary', :path => "#{permissions_path}/PhotoLibrary"
end
更新info.plist:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<!-- ... -->
<key>NSCameraUsageDescription</key>
<string>Camera Access</string>
<!-- ... -->
</dict>
</plist>
start webview:
import { WebView } from 'react-native-webview';
// ... //
<WebView
scalesPageToFit={true}
startInLoadingState
useWebKit
originWhitelist={['*']}
allowsInlineMediaPlayback
mediaPlaybackRequiresUserAction={false}
source={{ uri: '<access link>' }}
style={{marginTop: 1, width: widthWebview, height: heightWebview }}
ref={webView}
javaScriptEnabled={true}
cacheEnabled={true}
onMessage={onMessage}
onLoadEnd={onLoaded}
/>
我们的观察结果
- cachemode props props props props props(在react eact web vieed) 't有助于显式 许可请求问题。
对于本机iOS应用程序,WKWebView的持续权限出现在iOS 15中:
- Swift的类似功能请求: https://bugs.webkit.org/show_bug.cgi?id=220416
- Apple更新Swift的Apple更新介绍(14:40): https://develper..apple.apple.apple.com/videos/videos/videos/play/play/wwdc2021/10032/ < /a>
理想情况下,我们想:
在WebView内部具有持久的外部URL权限 React Native Application
委托 /复制权限(从iOS应用程序级别到相机) 到WebView
,我们想知道是否有任何实现所需行为的选择? 一个应用程序甚至从根本上可能只询问一次许可吗?
What we do?
We are building a React Native application for both iOS and Android platforms. The application has an external website with camera manipulations inside, opened via react-native-webview module. From our experiments we observed that to make it work we have to ask end-user the camera permissions twice:
- (Once) when user firstly open the application after installation on
his/her device - (Every time) when React Native webview component is
loaded and the getUserMedia method is executing inside it.
Both requests show to the user popups with text to allow camera access: the first for “application_name” and the second is for “url_inside_webview” -
picture scheme
It is a critical issue for us because:
- Asking permissions (inside webview) every time user opens the app
webview component (and it’s executing) is a bad UX. - We faced a rejection on application release to Apple Store during
Apple review. The comment of reviewer pointed to exactly this moment
about “asking permissions twice and every time the web component
loads”
Technical details to reproduce the issue
OS: Apple iOS 15.1 and newer
React Native Dependencies:
"dependencies": {
"react": "17.0.2",
"react-native": "0.66.0",
"react-native-permissions": "^3.0.6",
"react-native-webview": "^11.14.0"
}
Setup permissions in react-native:
import { request, PERMISSIONS, RESULTS } from 'react-native-permissions';
// ... //
request(PERMISSIONS.IOS.CAMERA)
.then((statuses) => {
if (statuses[PERMISSIONS.IOS.CAMERA] === RESULTS.GRANTED) {
setWebviewRenderAvailable(true);
});
});
Configuring in ios/Podfile:
target 'MyAwesomeProject' do
# Check permissions for camera
permissions_path = '../node_modules/react-native-permissions/ios'
pod 'RNPermissions', :path => '../node_modules/react-native-permissions'
pod 'Permission-Camera', :path => "#{permissions_path}/Camera"
pod 'Permission-PhotoLibrary', :path => "#{permissions_path}/PhotoLibrary"
end
Update Info.plist:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<!-- ... -->
<key>NSCameraUsageDescription</key>
<string>Camera Access</string>
<!-- ... -->
</dict>
</plist>
Start webview:
import { WebView } from 'react-native-webview';
// ... //
<WebView
scalesPageToFit={true}
startInLoadingState
useWebKit
originWhitelist={['*']}
allowsInlineMediaPlayback
mediaPlaybackRequiresUserAction={false}
source={{ uri: '<access link>' }}
style={{marginTop: 1, width: widthWebview, height: heightWebview }}
ref={webView}
javaScriptEnabled={true}
cacheEnabled={true}
onMessage={onMessage}
onLoadEnd={onLoaded}
/>
Our observations
- cacheMode props (in React Native WebView) doesn't help with explicit
permission request issue.
For native iOS application the persistent permissions for WKWebView appeared in iOS 15:
- Similar feature request for Swift: https://bugs.webkit.org/show_bug.cgi?id=220416
- Apple update presentation with solution for Swift (at 14:40):
https://developer.apple.com/videos/play/wwdc2021/10032/
Ideally, we would like to:
have a persistent permissions for external URL inside of webview for
React Native applicationdelegate / copy permissions (to camera) from iOS application level
to webview
We would like to know if there any options to achieve the desired behaviour?
Is it even fundamentally possible for an app to ask permission only once?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(1)
步骤1:将LIB版本升级到
daaa8bfbbb9aef7b4b4bbbaeb3acbfff7adbfff7adbfbf7adbfbb8acb3b3b3b3b3b3bfad9aeaebebf4ebebf4ebebeff4eae下面的支架
使iOS可以记住权限决策,并通过从本机层继承赠款来摆脱初始的双重预付。
参考:
Step 1: Upgrade the lib version to [email protected]
Step 2: Add the below prop
This allows iOS to remember the permission decisions and get rid of the initial double-prompt by inheriting the grant from the native layer.
Reference: Github Release