Database Session storage "lost" after some minutes

Description

https://dev.lucee.org/t/session-storage-memory-vs-dsn/10742

https://dev.lucee.org/t/lucee-session-expires-after-10-minutes-using-docker-and-nginx/12879

 

Summary / how to reproduce:

  1. Enable / setup datasource for session storage

  2. Login or save values in session

  3. wait at least 5 or 10 minutes

  4. except: values in session; result: empty session

The values are still in the database.

Environment

any 5.x version

tested with mysql / mariadb

tested with ubuntu lts +apache / docker + nginx

Attachments

2
  • 07 Mar 2024, 06:58 pm
  • 15 Dec 2023, 12:25 pm

relates to

Activity

Show:

Leon Miller-Out 15 March 2024 at 19:03

Yes, I think that would do the trick, !

In the meantime, I think this workaround will be effective:

function OnRequestEnd() { // Touch all objects in the session to ensure that they are persisted to the database session store. // This works around the problem described in https://luceeserver.atlassian.net/browse/LDEV-4670 // (where changes to in-session components' scopes are lost when falling back to the database). session.KeyList().each((key) => { session[key] = session[key]; }); }

Zac Spitzer 15 March 2024 at 18:51

Leon Miller-Out 15 March 2024 at 18:48

I’ve developed a better understanding of this issue. The problem in my app is occurring because we use components in the session, and their state changes are never persisted to the database when sessionCluster = false. This is the responsible code, I believe:

https://github.com/lucee/Lucee/blob/6.1/core/src/main/java/lucee/runtime/type/scope/storage/IKStorageScopeSupport.java#L609-L632

Lucee has no way to determine which session items have changed unless they’ve been assigned (e.g. session.foo = ‘bar'). I don’t know whether it’s possible for Lucee to test whether a component has been changed since it was last stored. It would have to compare at least the variables and this scopes of the two versions. Another possible approach would be fully store components each time the database-stored session is touched.

What I really want is an in-between setting for sessionCluster, where the whole session is written to the database after each request (like sessionCluster = true, but is only read when there’s no session in memory (like sessionCluster = false). This would enable clustering that worked well with sticky sessions for optimal performance.

In my assessment, sessionCluster = false is not an option for apps that store mutable components in the session, because the mutations will not be written to the database.

Leon Miller-Out 14 March 2024 at 17:46

Haha my workaround doesn’t work. The database version of the components in the session still retain their pre-authentication state. Back to the JS setInterval workaround to keep sessions in-memory. Sigh.

Leon Miller-Out 14 March 2024 at 17:36

I believe my session issues are due to the oddities of how this application manages authentication using the internal state of components stored in the session. With sessionCluster = false, the database-stored session sometimes holds a stale, pre-authentication state. When that is reloaded (due to the session having expired from the short-term memory cache), the user is back to their pre-authentication state, and isn’t logged in.

I think I have a workaround for this, which just involves writing a timestamp to the session during each request. That seems to trigger an update of the database store at some point during the request.

I suspect that somewhere in Lucee there’s a shallow check of “has the in-memory session changed?” that determines whether the database-stored session should be updated. We were only making deep changes that wouldn’t trigger that check. I haven’t been able to figure out where in the code that happens. I understand that doing a deep comparison of an arbitrary set of objects is difficult (if not impossible) and expensive. Maybe the best we can do is to update the documentation about sessionCluster with some caveats and possible workarounds.

Details

Assignee

Reporter

Priority

New Issue warning screen

Before you create a new Issue, please post to the mailing list first https://dev.lucee.org

Once the issue has been verified, one of the Lucee team will ask you to file an issue

Affects versions

Created 14 August 2023 at 07:12
Updated 26 March 2025 at 06:42

Flag notifications