feat(iOS): Add callback for webViewWebContentProcessDidTerminate (#774)

* Add callback for WKWebView's onContentProcessDidTerminate

* Add platform information to docs

* Add new WebViewTerminatedEvent type
This commit is contained in:
Samuel Sieg 2019-09-23 10:20:12 +02:00 committed by Thibault Malbranche
parent 9c7bf57a9b
commit a76811da93
5 changed files with 68 additions and 0 deletions

View File

@ -17,6 +17,7 @@ This document lays out the current public properties and methods for the React N
- [`onHttpError`](Reference.md#onhttperror)
- [`onMessage`](Reference.md#onmessage)
- [`onNavigationStateChange`](Reference.md#onnavigationstatechange)
- [`onContentProcessDidTerminate`](Reference.md#oncontentprocessdidterminate)
- [`originWhitelist`](Reference.md#originwhitelist)
- [`renderError`](Reference.md#rendererror)
- [`renderLoading`](Reference.md#renderloading)
@ -433,6 +434,40 @@ Note that this method will not be invoked on hash URL changes (e.g. from `https:
---
### `onContentProcessDidTerminate`
Function that is invoked when the `WebView` content process is terminated.
| Type | Required | Platform |
| -------- | -------- | ------------- |
| function | No | iOS WKWebView |
Example:
```jsx
<WebView
source={{ uri: 'https://facebook.github.io/react-native' }}
onContentProcessDidTerminate={syntheticEvent => {
const { nativeEvent } = syntheticEvent;
console.warn('Content process terminated, reloading', nativeEvent);
this.refs.webview.reload()
}}
/>
```
Function passed to onContentProcessDidTerminate is called with a SyntheticEvent wrapping a nativeEvent with these properties:
```
canGoBack
canGoForward
loading
target
title
url
```
---
### `originWhitelist`
List of origin strings to allow being navigated to. The strings allow wildcards and get matched against _just_ the origin (not the full URL). If the user taps to navigate to a new page but the new page is not in this whitelist, the URL will be handled by the OS. The default whitelisted origins are "http://*" and "https://*".

View File

@ -37,6 +37,7 @@ static NSDictionary* customCertificatesForHost;
@property (nonatomic, copy) RCTDirectEventBlock onHttpError;
@property (nonatomic, copy) RCTDirectEventBlock onMessage;
@property (nonatomic, copy) RCTDirectEventBlock onScroll;
@property (nonatomic, copy) RCTDirectEventBlock onContentProcessDidTerminate;
@property (nonatomic, copy) WKWebView *webView;
@end
@ -833,6 +834,19 @@ static NSDictionary* customCertificatesForHost;
decisionHandler(WKNavigationResponsePolicyAllow);
}
/**
* Called when the web views content process is terminated.
* @see https://developer.apple.com/documentation/webkit/wknavigationdelegate/1455639-webviewwebcontentprocessdidtermi?language=objc
*/
- (void)webViewWebContentProcessDidTerminate:(WKWebView *)webView
{
RCTLogWarn(@"Webview Process Terminated");
if (_onContentProcessDidTerminate) {
NSMutableDictionary<NSString *, id> *event = [self baseEvent];
_onContentProcessDidTerminate(event);
}
}
/**
* Decides whether to allow or cancel a navigation after its response is known.
* @see https://developer.apple.com/documentation/webkit/wknavigationdelegate/1455643-webview?language=objc

View File

@ -49,6 +49,7 @@ RCT_EXPORT_VIEW_PROPERTY(onLoadingError, RCTDirectEventBlock)
RCT_EXPORT_VIEW_PROPERTY(onLoadingProgress, RCTDirectEventBlock)
RCT_EXPORT_VIEW_PROPERTY(onHttpError, RCTDirectEventBlock)
RCT_EXPORT_VIEW_PROPERTY(onShouldStartLoadWithRequest, RCTDirectEventBlock)
RCT_EXPORT_VIEW_PROPERTY(onContentProcessDidTerminate, RCTDirectEventBlock)
RCT_EXPORT_VIEW_PROPERTY(injectedJavaScript, NSString)
RCT_EXPORT_VIEW_PROPERTY(javaScriptEnabled, BOOL)
RCT_EXPORT_VIEW_PROPERTY(allowsInlineMediaPlayback, BOOL)

View File

@ -22,6 +22,7 @@ import {
WebViewMessageEvent,
WebViewNavigationEvent,
WebViewProgressEvent,
WebViewTerminatedEvent,
IOSWebViewProps,
DecelerationRateConstant,
NativeWebViewIOS,
@ -255,6 +256,13 @@ class WebView extends React.Component<IOSWebViewProps, State> {
viewManager.startLoadWithResult(!!shouldStart, lockIdentifier);
};
onContentProcessDidTerminate = (event: WebViewTerminatedEvent) => {
const { onContentProcessDidTerminate } = this.props;
if (onContentProcessDidTerminate) {
onContentProcessDidTerminate(event);
}
};
componentDidUpdate(prevProps: IOSWebViewProps) {
this.showRedboxOnPropChanges(prevProps, 'allowsInlineMediaPlayback');
this.showRedboxOnPropChanges(prevProps, 'incognito');
@ -333,6 +341,7 @@ class WebView extends React.Component<IOSWebViewProps, State> {
onMessage={this.onMessage}
onScroll={this.props.onScroll}
onShouldStartLoadWithRequest={onShouldStartLoadWithRequest}
onContentProcessDidTerminate={this.onContentProcessDidTerminate}
ref={this.webViewRef}
// TODO: find a better way to type this.
source={resolveAssetSource(this.props.source as ImageSourcePropType)}

View File

@ -126,6 +126,8 @@ export type WebViewMessageEvent = NativeSyntheticEvent<WebViewMessage>;
export type WebViewErrorEvent = NativeSyntheticEvent<WebViewError>;
export type WebViewTerminatedEvent = NativeSyntheticEvent<WebViewNativeEvent>;
export type WebViewHttpErrorEvent = NativeSyntheticEvent<WebViewHttpError>;
export type DataDetectorTypes =
@ -269,6 +271,7 @@ export interface IOSNativeWebViewProps extends CommonNativeWebViewProps {
pagingEnabled?: boolean;
scrollEnabled?: boolean;
useSharedProcessPool?: boolean;
onContentProcessDidTerminate: (event: WebViewTerminatedEvent) => void;
}
export interface IOSWebViewProps extends WebViewSharedProps {
@ -442,6 +445,12 @@ export interface IOSWebViewProps extends WebViewSharedProps {
* @platform ios
*/
allowingReadAccessToURL?: string;
/**
* Function that is invoked when the WebKit WebView content process gets terminated.
* @platform ios
*/
onContentProcessDidTerminate: (event: WebViewTerminatedEvent) => void;
}
export interface AndroidWebViewProps extends WebViewSharedProps {