Closed mvysny closed 5 years ago
Run the app and press F5. The app shows the text This is instance no 1
; view's constructor increases the integer. I expect that F5 would not re-create the view, and thus after F5 the text should still read This is instance no 1
. However, currently the constructor is re-run and the text will read This is instance no 2
.
The issue is even worse if the view's attach listener shows a Window
. Those windows then start to multiply as the user presses F5 (since the UI preserves the prior windows).
I tested this, and your finding is correct. This is clearly a regression from that fix.
I believe that the patch will not work in all cases. Please consider the following scenario:
oldNavigationState
is null
oldNavigationState
is set to current navigator state which is ""
. The navigation is not performed (this is proper behavior)Navigator
to navigate to MyView
. oldNavigationState
is still ""
since doRefresh()
was not called.oldNavigationState
is ""
but the current navigator state comes from browser's URL which is my-view
, and alas the view is reinstantiated.To fix this, we probably need to remember the oldNavigationState
in the Navigator
(it would be the currentNavigationState
for which the View is instantiated). Then, we only navigate in doRefresh()
if the current view's currentNavigationState
is different than the browser's URL. The Navigator needs to keep track to currentNavigationState
as it performs navigation and view instantiation.
When F5 is pressed in a browser with Vaadin app having
@PreserveOnRefresh
on the UI, I expect that the UI including any of the child components will not be re-created on server-side. However, starting with Vaadin 8.7.0-8.8.2 as a result of https://github.com/vaadin/framework/issues/11416 theUI.doRefresh()
callsnavigator.navigateTo()
to the current URL, which re-creates the view. The issue is demonstrated in the example app attached.