Expand my Community achievements bar.

SOLVED

How to avoid concurrent use of sessions?

Avatar

Level 3

 

I utilize a session to copy images from one folder to another, and at the same time there is workflow which is triggered whenever any node is created under that folder.

One of the workflow's process steps uses a session to edit a property of the newly generated node, which raises the following warning:

 

06.04.2023 13:54:16.472 *WARN* [Apache Sling Resource Resolver Finalizer Thread] org.apache.jackrabbit.oak.jcr.delegate.SessionDelegate Attempted to perform logout while thread JobHandler: /var/workflow/instances/server2/2023-04-06/torrid-amplience-update-asset_692:/content/dam/torrid/pdp-assets/402/250/40225019/40225019_av1.jpg/jcr:content/renditions/original was concurrently writing to this session. Blocked until the other thread finished using this session. Please review your code to avoid concurrent use of a session.

 

Any assistance with this matter would be greatly appreciated.

 

Thanks,

Nandan

1 Accepted Solution

Avatar

Correct answer by
Level 4

In Apache Sling, it's important to avoid concurrent use of a session to prevent data corruption and other issues. There are two main ways to do this: using separate sessions for different threads or processes, or using locks to prevent concurrent modification of the same node.

To use separate sessions, create a new session for each thread or process instead of using the same session across multiple threads or processes. This ensures that each thread or process has its own session to work with, avoiding concurrent use of a single session. It's important to properly close sessions once they're no longer needed to avoid resource leaks.

To use locks, you can use the javax.jcr.lock.LockManager interface provided by the JCR API. Locking a node prevents other threads or processes from modifying it while it's being modified by another thread or process. You can use either a shared lock, which allows multiple threads or processes to read the node but prevents them from modifying it, or an exclusive lock, which prevents all other threads or processes from accessing the node.

It's important to release locks once they're no longer needed to avoid deadlocks. You can do this by unlocking the node using the same LockManager instance that was used to lock it.

View solution in original post

5 Replies

Avatar

Correct answer by
Level 4

In Apache Sling, it's important to avoid concurrent use of a session to prevent data corruption and other issues. There are two main ways to do this: using separate sessions for different threads or processes, or using locks to prevent concurrent modification of the same node.

To use separate sessions, create a new session for each thread or process instead of using the same session across multiple threads or processes. This ensures that each thread or process has its own session to work with, avoiding concurrent use of a single session. It's important to properly close sessions once they're no longer needed to avoid resource leaks.

To use locks, you can use the javax.jcr.lock.LockManager interface provided by the JCR API. Locking a node prevents other threads or processes from modifying it while it's being modified by another thread or process. You can use either a shared lock, which allows multiple threads or processes to read the node but prevents them from modifying it, or an exclusive lock, which prevents all other threads or processes from accessing the node.

It's important to release locks once they're no longer needed to avoid deadlocks. You can do this by unlocking the node using the same LockManager instance that was used to lock it.

Avatar

Level 3

Thank you for your reply @Monendra_Singh ,

I am using separate sessions for different process but will try using locks.

Avatar

Community Advisor

Hi @nandan123 ,

You mentioned that you are using different session. How are you getting these session ?

Below best practices we can use to resolve this issue.

  1. As we know, Instead of using a session object directly, Use the ResourceResolverFactory to obtain a ResourceResolver object. ResourceResolverFactory provides a thread-safe way to create and manage ResourceResolver objects.
  2. Always close the ResourceResolver using the ResourceResolver.close() method when it is no longer needed. This method ensures that all the resources associated with the ResourceResolver are released.

Along with this try using LockManager as suggested by@Monendra_Singh

Regards

Shiv

 

Shiv Prakash

Avatar

Employee Advisor

Hi,

 

The warning message indicates that the session used by the workflow process step is being used concurrently with another thread that is writing to the same session. This can lead to inconsistent behavior and is not recommended.

To avoid concurrent use of the session, you can try the following options:

  1. Use separate sessions: Use separate sessions for the code that copies the images and the workflow process step. This way, each thread will have its own session and there won't be any conflicts.

  2. Use the session within the workflow process step only: Move the code that edits the property of the newly generated node to the workflow process step. This way, the session will only be used by the workflow process step and there won't be any conflicts with other threads.

  3. Use the Sling Resource Resolver API: Instead of using the session, you can use the Sling Resource Resolver API to modify the properties of the newly generated node. This API is thread-safe and can be used concurrently by multiple threads without any issues.

In general, it's recommended to avoid using sessions concurrently in AEM, as it can lead to unpredictable behavior and issues like the one you are experiencing.

Avatar

Employee Advisor

Next to all the other more generic responses:
* The code in the thread JobHandler: /var/workflow/instances/server2/2023-04-06/torrid-amplience-update-asset_692:/content/dam/torrid/pdp-assets/402/250/40225019/40225019_av1.jpg/jcr:content/renditions/original is using a session.
* In parallel the "ResourceResolver finalizer thread" (which closes all abandoned ResourceResolvers, which have not been properly closed) tries to close the ResourceResolver, which wraps that session.

 

That is an interesting combination, because

* there is a ResourceResolver leak,

* and these leaking ResourceResolvers are used in that JobHandler.

My recommendation: Check the code behind the workflow "torrid-amplience-update-asset" for the proper use of Resource resolvers.