-
-
Notifications
You must be signed in to change notification settings - Fork 111
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
feat(auto-update): make bundle rollback more robust #502
Comments
Hello thanks for the feedback, we just released a new Android version who use WorkerManager. |
Hi, thanks for the response! About In solution 1, I indeed mean JS in the app. Just like we can list bundles, get the current bundle info or reset to a different bundle. It would be useful if we can mark a bundle as faulty (BundleStatus = 'error'). For solution 2, yes it would be very nice to have that possibility. App launch is a perfect moment to switch to a new bundle. Backgrounding is not so much. But I understand that it might be a difficult change for you. So to sum up, if we can have a JS plugin method where we can change the status of a Bundle to "error", that would at least allow us to run our own recovery logic without waiting for |
To make a bit of context, you are the only one reporting this, so there is a chance it's more a misuse than a real issue :) We can still have the set error method, but I think in your use case this is not the problem. It will be useful for manual mode. |
Just without looking at the code, I don't really see why |
Right, so currently we call I sort of believe that the fix for the timeout could be as simple as doing if (!isForeground()) {
this.checkAppReady();
} in the I sort of believe that currently, we call Or perhaps I am misreading the code. I am going to check. |
It does, in fact, at least on Android, trigger |
iOS does the same. @riderx, please let me know if you would like to see a flag to make this |
The problem is realod can be called also by JS and then it need to start the check . |
Yeah, that is why I suggested making this a flag. By default, we would keep the current behavior as is, while users who experience this timeout would be able to set the flag that disables |
Yea, before that i want to be able to reproduce as we never saw that happening in any of other users or any of our test, the only time i saw timeout was when our method was called after http request or others stuff who take time. |
The main magic is here: |
@hakant can you provide a reproduction? |
Hey @riderx and @WcaleNieWolny, thanks for thinking along! Our understanding of the purpose of We want to call I stumbled upon something the other day, maybe we can use that as an easy reproduction. One of our developers was working on an animation for the landing page and he introduced this piece of code to smoothen the animation:
It turned out requestAnimationFrame calls are paused in browsers when they're not in the foreground.
So if my So overall point is, how the JS code executes in foreground vs background can be very different in terms of timing and behaviour. So treating them to the same Last but not least, I understand that refreshing the bundle in the background sounds logical as user is not using the app. But quick background foreground operations lead to bad experience because user's journey gets broken. If I could configure turning off bundle updates during backgrounding, I would do that in my project. But as @WcaleNieWolny mentioned, if we can turn off checking app ready in background that also solves this issue. @riderx, what are your thoughts on when |
You can, please check the setMultiDelay call. |
I was hoping the same and tried that. But this only helps with delaying. When the delay is over, update takes place with the same rules. Later I noticed the docs is clear about that:
|
@hakant yes we totally recommend to be the first line in your JS. |
@riderx that settles things then for In that case the solution 1 that I proposed in the original issue would still be useful for us to handle critical issues in our bundles. Let's say we executed So, a plugin method to set the status of a bundle to 'error' in this case. Does that make sense and doable for you ? |
@hakant do you use capgo cloud? |
The idea of allowing the plugin to reject an auto update on its own is something we could consider I think. It does, however, require some planing to ensure that this plays well with both manual mode and auto update |
@WcaleNieWolny we're running our own backend and testing this solution at the moment. Auto updates are enabled on the plugin side. A manual bundle reset doesn't play nicely with auto updates as it will continuously find the new version and try to update. Not sure what happens with 'error' bundles in manual mode. |
If the bundle is marked errored it will stop update it |
@riderx do you think we should maintain a separate list of 'banned' versions? If, for example, the user bans the |
We have already something with the errored version, i wonder what happen in manual mode if you try to add again a version present it auto remove? |
Imho, manual mode should allow setting a bundle that was earlier marked as 'error'. Folks might be using this in their bundle testing process (we do). We let testers download any bundle they want and test it within an app shell. On prod scenarios devs can list bundles and check their statuses and do what's necessary ? On the other hand it makes sense that auto updates don't download and set those error bundles anymore. My 2 cents if that makes sense.. |
iOS will not care and always try redownload, even in manual mode. However, it also will leak the preferences ( |
At some point, we need to clean this system up. We keep adding new features that make the bundle info storage more and more complex. Multiple service-like components of the updater plugin interact with one another in unpredictable ways. |
@riderx @WcaleNieWolny we spoke about a whole bunch of stuff in this issue 😄. Shall I create a new focused issue about the item below ? I was going to suggest closing this one but I see @WcaleNieWolny started linking it to other places. What do you folks prefer ?
|
Correct, i close this one, and made one for the feature requested. |
Feature Request
Description
In
auto-update
scenarios, new bundles are often set while the app is running in the background. During this time, the JavaScript execution of the webview is usually deprioritized by the mobile operating system due to backgrounding. This leads to slow or delayed JavaScript execution, which in turn necessitates higherappReadyTimeout
configurations (typically 10–20 seconds).The issue with prolonged
appReadyTimeout
durations is that, if a bundle contains a bug causing a critical crash, recovery takes too long. In real-world usage, most users won’t wait 10–20 seconds staring at a white screen. Instead, they are likely to kill the app and give up, meaning recovery might never occur.I propose two solutions to address this problem:
appReadyTimeout
. Resetting is already possible, but without marking the current bundle as erroneous it doesn't seem very useful as it locks up in a cycle ofupdate
->fail
->reset
.appReadyTimeout
durations.Platform(s)
iOS & Android
Preferred Solution
Both solutions 1 and 2 would be generally useful. If I had to prioritize, solution 1 would likely be sufficient. However, I’m uncertain if updating the bundle while the app (and therefore the webview) is in the background introduces other edge case consequences. For instance, if the webview receives no execution time, it might lead to false rollbacks.
Alternatives
An alternative would be to abandon
auto-updates
altogether and implement a custom manual update logic. However, this approach would sacrifice theauto-update
feature's implicit disaster recovery benefit thanks to its native implementation, which is independent of JavaScript execution in the bundle. Losing this feature would be unfortunate.Additional Context
Here’s some additional context: we’re aiming to move
notifyAppReady
to the end of the critical application load path, covering bundle startup and the display of the first screen. This process should take no more than 3–5 seconds. However, when the app is in the background, the mobile operating system may arbitrarily freeze JavaScript execution in the webview depending on device activity. This forces us to increase the timeout, ultimately reducing the effectiveness of recovery mechanisms.Curious about your thoughts and whether there are any other solutions we might have missed in our analysis. Thank you!
The text was updated successfully, but these errors were encountered: