-
Notifications
You must be signed in to change notification settings - Fork 30
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
allow disambiguating annotation on resource accessor methods #474
base: main
Are you sure you want to change the base?
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is an interesting approach, but I think it goes too far because these annotations enable you to obtain any DataSource/EntityManager, not just the one that is backing the repository. It isn't the place of Jakarta Data to provide access to other resources apart from maybe the one that it is using, which we already have via the resource accessor method pattern. I don't think we need to provide anything else here. @Resource
and @PersistenceContext
already exist in Jakarta EE and can be used to obtain resources in the ways in which they are already standardized to do so.
But what I'm saying here is that the annotation would determine the resource that backs the repository. i.e. the repository implementation itself would use those annotations to look up its datasource, or entity manager, or whatever. |
The issue is that currently, if I have, say, two persistence units in my EE application, we have no clear way to tell a repository which one to use. |
Once we are changing this part. As a reader, it sounds weird. I prefer to cover the Jakarta Persistence in a single place and not broad in the spec. |
@otaviojava I'm not sure what you mean. None of that section is specific to Jakarta Persistence or to relational databases. Mongo DB or whatever has some sort of native "connection" or "session" type. JDBC is just an example. |
Oh I see what you are trying to do here.
|
OK, yeah, I forgot about that when I was looking at #264, but the thing is that the |
(And I don't think it would be correct to just stick the CDI qualifiers on the repository itself.) |
How important is it to be able to obtain the resource via qualifiers? The |
Well it's something we (JPA) have been getting pressure from Jakarta EE folks and some individuals about so apparently it matters to some people. I think there's a desire to unify everything around a CDI-based approach and deemphasize the more "legacy" JNDI stuff. And I'm not going to argue against that. |
Is it a "have to have" 🤷♂️ well, for me personally, no, I guess?? |
It sounds like it's part of the CDI-centric push from Jakarta EE platform, which I agree in general is a good direction. But I don't think some of the specs we might utilize are far enough along with it for us to figure out what the best approach will be for Jakarta Data. For example, I don't see a spec-defined solution yet for a CDI alternative to resource references to JDBC DataSource. I would rather wait for these other specifications and Jakarta EE to get further along with a clearer picture of where it all ends up and then have Jakarta Data tie into that, especially when the approaches we currently would have with qualifiers are a bit awkward and not intuitive. I would propose that we go with what is currently in the spec here for 1.0 and assign this issue to Future, where we can revisit when there is better direction. |
Just to be clear, this has been available and well-defined since CDI 1.0. The way to do it is to write: @Produces @Resource(lookup="java:global/env/jdbc/CustomerDatasource")
@CustomerDatabase DataSource customerDatabase; or: @Produces @PersistenceContext(unitName="CustomerDatabase")
@CustomerDatabase EntityManager customerDatabasePersistenceContext; anywhere that CDI will look. And then inject with This is currently in section 9.7.1 of the CDI 4 spec, but it's been there forever. I'm pointing this out because some people don't seem to be aware that it exists, or for some reason view it as some sort of "workaround". |
OK, so look, how about we close issue #264, since I think that the issue description is a bit outdated/confusing/not-quite-right, and I will open a new issue specifically describing the problem with CDI qualifiers, and laying out what I see as the range of possible solutions. (There aren't really many options, since interfaces are a bit limited in terms of places you can but an annotation.) |
I'm one of the people that thought of that as a workaround. I didn't realize that was the intended solution. |
I mean, to me it's a great solution. I find it more natural to write the mapping from a string-based name to a typesafe annotation in Java, than to write annotations in, say |
I've done more investigation of this proposal and even got some of it sort of working, although this has also raised more concerns because I don't see it working in all cases. First, some background. We currently let the user configure either a persistence unit reference or a data source resource reference, as you can do with One problem is how to supply that to the Jakarta Persistence provider. Even if the Data CDI extension is running at a point where it has access to do CDI.current().select(DataSource.class, qualifierAnnos), this doesn't help us any because Jakarta Persistence config doesn't accept DataSource instances. It takes JNDI names to resource references. At this point, I can locate the producer definition, grab the Another problem I worry about is CDI scopes. In this case of the hacky approach I described above, I swizzled it back to JNDI and the scope doesn't even apply. That seems wrong. If taking another approach, maybe with obtaining the EntityManager/EntityManagerFactory rather than DataSource, do we need to be concerned with it going out of scope and the Jakarta Data provider/Jakarta Persistence provider still trying to use it across the application? Maybe the users needs to always need to specify Another issue is with obtaining EntityManager. I like how the existing approach can give you an EntityManagerFactory, not EntityManager. In the future I see this being quite useful if a Jakarta Data provider wants to in turn request a specific type of EntityManager from the Jakarta Persistence provider. I'm imagining a emf.getStatelessEntityManager method or something to that effect. If, on the other hand, we have a model where the user, via their repository, supplies the EntityManager and not the EntityManagerFactory, then the Jakarta Data provider is stuck with whatever sort of EntityManager the user's gave it. To summarize, the proposed approach has some aspects that might be workable, but introduces complexity and unanswered questions. We shouldn't add it in version 1.0. Maybe there are ways we can improve on it and/or be able to resolve some of the issues related to it, and if so, maybe it will be something we can add later on. |
@njr-11 I don't quite understand what you're trying to do here. Are you trying to obtain a With respect to CDI qualifiers:
|
That is to say: @Repository
interface DocumentRepo {
@DocumentDatabase
EntityManager entityManager()
} Would by implemented by a class like this, say: class DocumentRepo_ implements DocumentRepo {
private final EntityManager entityManager;
@Inject
DocumentRepo_(@DocumentDatabase EntityManager entityManager) {
this.entityManager = entityManager;
}
@Override
EntityManager entityManager() { return entityManager; }
} Or whatever. There's lot of possible variations on this. Anyway the point is I don't see what a repository based on JPA would be messing around with the |
One of the scenarios I was looking it is when a user writes a repository resource accessor/supplier method to produce a DataSource, associating that repository to a Jakarta Data provider that is backed by Jakarta Persistence. I noted that we can already handle the equivalent with |
I suppose you're doing it by passing the datasource name via config property I believe that it's possible to directly pass an instance of Quote from the JPA spec: The following additional standard properties are defined by this specification for the configuration of the entity manager factory: |
So the current proposal is that the |
Nice - I should try out "jakarta.persistence.dataSource" and see how that works. That would reduce the issues with DataSource to being more similar to those with EntityManager, where I'm wondering what if it goes out of scope? |
UPDATE: this is now issue #476.
Here's a proposal that in my opinion solves #264, as well as providing an alternative to "configuration" as envisaged in issue #22.What do ya'll think of this approach?