MPR Flow/Vaadin 7 deadlock issue?

I am running my Vaadin7 app under MPR and when I logout ( which includes closing sessions, etc, using Vaadin 7 API ),
I am getting the following exception: ERROR com.vaadin.flow.server.DefaultErrorHandler - java.lang.IllegalStateException: Can't access session while another session is locked by the same thread. This restriction is intended to help avoid deadlocks.

I imagine flow cleans up something under the hood that Vaadin 7 did not, or they are stepping on each other, or something. Not sure if this is important, but just before the above error, I get a framework warning:

[WARNING]
 /framework/
java.lang.NullPointerException
	at com.vaadin.mpr.core.MprServletService.getFlowSession(MprServletService.java:184)
	...

To the best of my knowledge, the errors are not related, but maybe they are.

Here is my “logout code”:

	public void userLoggedOut(final UserLoggedOutEvent event) {
		// When the user logs out, current VaadinSession gets closed and the
		// page gets reloaded on the login screen. Do notice the this doesn't
		// invalidate the current HttpSession.
		if( VaadinSession.getCurrent() instanceof VaadinSession )
			VaadinSession.getCurrent().close();
		
		if( Page.getCurrent() instanceof Page )
			Page.getCurrent().reload();

		...

		if( Page.getCurrent() instanceof Page )
		{
			String uriFragment = Page.getCurrent().getUriFragment();

			if( uriFragment != null && !uriFragment.trim().isEmpty() )
			{
				Page.getCurrent().setUriFragment("", false );
			}
		}
	}

What is super interesting is that change

		if( VaadinSession.getCurrent() instanceof VaadinSession )
			VaadinSession.getCurrent().close();

to

//		if( VaadinSession.getCurrent() instanceof VaadinSession )
//			VaadinSession.getCurrent().close();

I don’t get the two exceptions I mentioned. I actually cannot remember why I used “close” in the first place, but I do remember I did it on purpose. Maybe that messes something up in MPR?

It is recommended to invalidate the session via Flow instead, see:

https://vaadin.com/docs/v13/mpr/configuration/session.html

Thanks. Conceptually, what is the difference between VaadinSession.getCurrent().getSession().invalidate(); and VaadinSession.getCurrent().close();, and when should each be used? I was using “close” instead of “invalidate” in Vaadin 7 for some reason, which currently I cannot remember. I know what the API definition is of each, and it seems to me that “close” is more delayed then “invalidate”, and higher level. Just asking when each is used, I guess.

Thanks.

VaadinSession.close will only close the VaadinSession, whereas VaadinSession.getCurrent().getSession() will return the wrapped top-level HTTP session (or Portlet) session, which is the one that you probably want to close. The only scenario I can think of where you wouldn’t want to close the HTTP / Portlet session would be some kind of composed view that has multiple smaller UIs / portlets where you can log out of one but not all of them.

I keep getting “session already invalidated” when I call VaadinSession.getCurrent().getSession().invalidate();. So far I am only able to test it in Eclipse. When I debug it using Jetty, I don’t have this issue. But when I run it in Tomcat 8.5, it gets this issue. Any ideas?

Not really, sorry.

This might be related to a bug that has been fixed but not yet released. We plan to release versions 1.1.2, 1.2.1 and 2.0.0 quite soon and all those versions should include the fix.

Not ideal, but I got around the “session already invalidated” with VaadinSession.getCurrent().getSession().invalidate(); and related pieces of logic with try…catch. Still bugs me it happens, so if anyone has ideas on what I am truly doing wrong, do tell me. But for those in the same situation as me, this works. Sort of an obvious solution, really, just seems wrong.

Not sure what fixed it, but it was probably one of the two following things:

  1. Upgrading to 13.0.9
  2. Moving “invalidate” to as late in possible in my userLoggedOut method.