Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Make transactions usable with raw MongoDB client / collection interfaces #27311

Open
languitar opened this issue Aug 16, 2022 · 7 comments
Open
Labels
area/mongodb kind/enhancement New feature or request

Comments

@languitar
Copy link
Contributor

languitar commented Aug 16, 2022

Description

The transaction support for MongoDB currently only works when using Panache entities directly. Sometimes, though, it is necessary to resort to the raw operations provided by MongoCollection etc. Such manual operations currently run outside a potentially active transaction because the session containing this transaction is not accessible for user code. The MongoDB Java driver requires to explicitly pass this session into operations for being performed inside transactions.

It would be nice if there either was a way to

  • access (or newly create) a session with ongoing transaction for use with operations provided by MongoCollection, or
  • to have the transaction automatically passed into the raw Java driver operations without manual actions being needed by the user code

This request is the result of #27289

Implementation ideas

From my perspective it would probably best if transaction handling based on @Transactional and other mechanisms was handled automatically by MongoClient, MongoDatabase and MongoCollection, potentially through a Quarkus-specific facade. The MongoDB driver provides for most operations two method signatures, one with a client session passed in via the first parameter, and one without that parameter. If an ongoing transaction was not handled automatically this would often result in client code like the following needed to handle the different signatures:

ClientSession session = Somewhere.getMongoDbTransaction()
if (session == null) {
    res = collection.findOneAndUpdate(query, mutation)
} else {
    res = collection.findOneAndUpdate(session, query, mutation)
}
@languitar languitar added the kind/enhancement New feature or request label Aug 16, 2022
@loicmathieu
Copy link
Contributor

potentially through a Quarkus-specific facade.

this will be a lot of work as the transactonal facade will need to be kepts in line with the underlying MongoDB 'raw' facilities.

However, two implementations could be eaisy to create:

  • Panache.getMongoSession()
  • Having a way to inject a request scoped objet that can obtains the session (like a specific QuarkusMongoSession on which you can call .getSession())

They may be more questions to ask so we may want to think a little more about this.

@languitar
Copy link
Contributor Author

Injection sounds cleaner to me than random static methods with magic implementations that get back into the concrete context of the running request. I'm also a bit confused why QuarkusTransaction is static and not something to inject along these lines.

@languitar
Copy link
Contributor Author

languitar commented Aug 16, 2022

Not having a facade is definitely OK at the moment. It could be added later by providing other accessor methods on the repository or active record without breaking compatibility.

@languitar languitar changed the title Make transactions usable with raw client / collection interfaces Make transactions usable with raw MongoDB client / collection interfaces Aug 16, 2022
@quarkus-bot
Copy link

quarkus-bot bot commented Aug 22, 2022

/cc @evanchooly, @loicmathieu

@loicmathieu
Copy link
Contributor

@languitar currently, the ClientSession is created lazilly at first use and registered inside the transaction manager. Then we reuse the existing transaction interceptors.
So it may be hard to provide a way to inject it as a request scoped bean.
But allowing to statically get it from an helper method (that will also create it) is not very complex so you could write someting like : Panache.getClientSession().

See this draft PR: #30115

@felixng313
Copy link

I'm looking forward to this feature.

@felixng313
Copy link

felixng313 commented Feb 14, 2024

The MongoCollection only accepts com.mongodb.client.ClientSession, but the new function Panache.getSession() is returning com.mongodb.session.ClientSession. Any advice for this case?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area/mongodb kind/enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

4 participants