From 6003b560ae1a0f704dd66d3c638d9ff1fe8e568f Mon Sep 17 00:00:00 2001 From: Lyubo Marinov Date: Tue, 15 Aug 2017 17:21:58 -0500 Subject: [PATCH] [RN] Fix opening the same URL multiple times Deep/universal linking now utilizes loadURL (when possible). But loadURL is imperative in the native source code while its JavaScript counterpart i.e. React App Component prop url is declarative. So there's the following bug: open a URL, leave the conference (by tapping the hangup button, for example), and then opening the same URL actually leaves you on the Welcome page (if enabled; otherwise, a black screen). The implementation has a flow though: opening the same URL twice in a row without an intervening leave will leave the first opening and join the new opening. Which can be improved by not leaving and joining if the conference is joined, joining, an not leaving. But that can be done separately as an improvement independent of the current implementation details. --- ios/sdk/src/JitsiMeetView.m | 12 ++++++++++++ react/features/app/components/AbstractApp.js | 10 +++++++++- 2 files changed, 21 insertions(+), 1 deletion(-) diff --git a/ios/sdk/src/JitsiMeetView.m b/ios/sdk/src/JitsiMeetView.m index 2b3afebe9..0e0985da8 100644 --- a/ios/sdk/src/JitsiMeetView.m +++ b/ios/sdk/src/JitsiMeetView.m @@ -15,6 +15,7 @@ */ #import +#include #import #import @@ -239,6 +240,17 @@ static NSMapTable *views; props[@"url"] = urlObject; } + // XXX The method loadURLObject: is supposed to be imperative i.e. a second + // invocation with one and the same URL is expected to join the respective + // conference again if the first invocation was followed by leaving the + // conference. However, React and, respectively, + // appProperties/initialProperties are declarative expressions i.e. one and + // the same URL will not trigger componentWillReceiveProps in the JavaScript + // source code. The workaround implemented bellow introduces imperativeness + // in React Component props by defining a unique value per loadURLObject: + // invocation. + props[@"timestamp"] = @(mach_absolute_time()); + if (rootView) { // Update props with the new URL. rootView.appProperties = props; diff --git a/react/features/app/components/AbstractApp.js b/react/features/app/components/AbstractApp.js index 41a56c09e..222392a03 100644 --- a/react/features/app/components/AbstractApp.js +++ b/react/features/app/components/AbstractApp.js @@ -47,6 +47,10 @@ export class AbstractApp extends Component { */ store: PropTypes.object, + // XXX Refer to the implementation of loadURLObject: in + // ios/sdk/src/JitsiMeetView.m for further information. + timestamp: PropTypes.any, + /** * The URL, if any, with which the app was launched. */ @@ -143,7 +147,11 @@ export class AbstractApp extends Component { let { url } = nextProps; url = toURLString(url); - if (toURLString(this.props.url) !== url) { + if (toURLString(this.props.url) !== url + + // XXX Refer to the implementation of loadURLObject: in + // ios/sdk/src/JitsiMeetView.m for further information. + || this.props.timestamp !== nextProps.timestamp) { this._openURL(url || this._getDefaultURL()); } }