Recently Nuxeo has been updated internally to provide much better concurrency support when dealing with CoreSession, which is the main object through which developers manipulate documents. Along the way, some simplified APIs have been introduced to acquire and manage CoreSession objects, taking advantage of some Java 7 features.

Based on these updates, here is how you should now get a new CoreSession:

try (CoreSession session = CoreInstance.openCoreSession(repositoryName)) {
// do something with session, including session.save()
}

This is using the Java 7 try-with-resource pattern, so you don't have to explicitly do session.close(); - the try block does that for you. The above is equivalent to the following, which would have been used in Java 6 (but as Nuxeo only support Java 7 and above, the try-with-resource pattern is simpler and safer, as there's no risk of forgetting to call close in a finally block):

CoreSession session = CoreInstance.openCoreSession(repositoryName)
try {
// do something with session, including session.save()
} finally {
session.close();
}

Keep in mind however that in most cases in Nuxeo a CoreSession is already available to you, and you don't need to open one by hand.

Here are five ways to get a Nuxeo Platform CoreSession:

  1. When writing an Automation operation, the CoreSession can be injected with:
    @Context
    protected CoreSession session;
  2. When writing a Seam bean, the CoreSession can be injected with:
    @In(create = true, required = false)
    protected transient CoreSession documentManager;
  3. When writing a WebEngine module, the CoreSession is available from the ctx field using:
    CoreSession session = ctx.getCoreSession();
    
  4. When writing a pure JAX-RS resource, you can do:
    CoreSession session = WebEngine.getActiveContext().getCoreSession();
    
  5. If you already have a DocumentModel doc, it's linked to a CoreSession, so you can always do:
    CoreSession session = doc.getCoreSession();

    In all these cases, you're accessing a CoreSession object that has already been allocated by the framework, and the framework is responsible for closing it, so you must not call close() on it.

Internally, this streamlining of CoreSession acquisition has enabled us to change the internals of the CoreSession.

A CoreSession is now thread-safe, because we're now using a thread-local to manage the way the CoreSession is holding onto its internal Session object, which is the link to data storage. This is important in particular for our usage of the Seam framework, where a long-lived CoreSession is allocated for the duration of the conversation.

A CoreSession can also be used in a second transaction after you commit the first transaction that used it, if you're using manual transaction start/commit.

All these changes are geared toward minimizing the number of surprises for the developer, and we hope that this goal has been attained.