Reputation: 747
I have a React webapp running inside a webview in a React Native app. The React Native side injects javascript to set window.postMessage
like so:
<WebView
injectedJavaScriptBeforeContentLoaded={`
(function() {
window.postMessage = function(data) {
window.ReactNativeWebView.postMessage(data);
};
})()
window.isInApp=true;
true;`
}
/>
Then, I call window.postMessage()
in the React webapp to make the React Native app react to certain button presses:
<Button
onClick={() => {
if (window.isInApp) window.postMessage();
else navigate("/my-trips");
}}
>
Exit
</Button>;
(I know that postMessage()
is supposed to require arguments, but) This works everywhere in my React webapp, except for one particular page. At first, I get the error
Script error.
As well as
A cross-origin error was thrown. React doesn't have access to the actual error object in development.
So, to see the error, I wrapped the function call in a try-catch block, then displayed the error in an alert
:
<Button
onClick={() => {
try {
if (window.isInApp) window.postMessage();
else navigate("/my-trips");
} catch (e) {
alert(e);
}
}}
>
Exit
</Button>;
Running on an Android Samsung A54, I get this:
TypeError: Cannot read properties of undefined (reading postMessage)
And on an iOS iPhone 8, I get this:
TypeError: undefined is not an object (evaluating 'window.ReactNativeWeb-View.postMessage')
So then, I added some if conditionals to ensure window was not undefined, and also displayed window
in some alert
s before and after calling window.postMessage()
:
<Button
onClick={() => {
try {
alert(`window: ${window}
window.postMessage: ${window.postMessage}`)
if (window && window.postMessage && window.isInApp) window.postMessage();
else navigate("/my-trips");
} catch (e) {
alert(`${e}
window: ${window}
window.postMessage: ${window.postMessage}`);
}
}}
>
Exit
</Button>;
However, I get the exact same error message, which claims that window
is undefined, even though I check that it isn't undefined before AND after calling window.postMessage()
. I also tried using window.postMessage(true, "*")
just so I didn't have no arguments, but to no avail. I also don't see anything different about this particular page that can be remotely related to making window
have an ephemeral superstate of existence. It's almost an exact replica of another page where the same thing works.
How is this possible? Why does it seem like window
is only undefined when I call window.postMessage()
, but is not undefined in the if
checks and the alert
dialogues? Almost like some double-slit-experiment-electrons behaviour type shit? Wtf is this?
(I know I should make a minimal reproducible example but that's gonna take a lot of time I don't have to spare at the moment. Hoping that maybe someone knows the explanation/fix before I resort to that.)
Upvotes: 0
Views: 338