-
Notifications
You must be signed in to change notification settings - Fork 2.7k
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
Add support for single non no-arg constructor injection without @Inject #548
Conversation
Basically when the bean has a single constructor that contain arguments, then the @Inject annotation is not necessary, since the injection point can be safely deduced. This is analogous to what Spring DI does
b9b9b12
to
46cfe9a
Compare
So this is definitely against the spec. On the other hand, we don't run TCK and not even try to be fully spec-compliant. It really depends on how useful you guys think this "feature" is. @emmanuelbernard @stuartwdouglas @FroMage @Sanne and others? |
Not my area of expertise, but out of curiosity: by "against the spec" you mean the spec doesn't mention anything like this, or is it explicitly prohibiting such a thing to work? In the second case, might be good to know why they did that.. might have good reasons? (Other than that doubt I personally like it!) |
@Sanne http://docs.jboss.org/cdi/spec/2.0/cdi-spec.html#instantiation and http://docs.jboss.org/cdi/spec/2.0/cdi-spec.html#declaring_bean_constructor. So stricly speaking the constructor should not be found. But I don't think there is a tck test that would fail... @manovotn @antoinesd Your opinion? |
This is definitely against CDI spec so the real question here is how much you want this implementation to pretend it's CDI compliant and how much you want to step away and say you are creating a different (C)DI implementation. Settings that aside, I think this is more of a syntactic sugar rather then anything else. Bean with just one constructor cannot be a CDI bean anyway, as you need a no-args one by definition, so I think it should work. |
Hm, I disagree. A bean with non-normal scope can either have no-args constructor or a constructor with |
Sorry, I wasn't clear. In my previous comment I meant that a class that has only once constructor and that one is parameterized. |
My reading of the spec is that it describes one way which is expected to work. The language is open-ended, it doesn't preclude you to offer additional ways of constructing such beans. As long as you don't violate the definition:
I'd argue you'd still be allowed to call this a CDI implementation (if not for missing other things..) |
@Sanne this part of spec http://docs.jboss.org/cdi/spec/2.0/cdi-spec.html#what_classes_are_beans states that:
|
@manovotn good catch. That section is indeed more restrictive |
If the change makes sense, let's push for a change in the spec. |
I know that I use the respective Spring capability whenever the opportunity arises :P, so from my point of view it makes a lot of sense |
I think we should include it and try and change the spec. |
Yea, we can make a proposal for sure. I'll put up an issue tomorrow |
FYI, created CDI-742. Feel free to add any remarks and notes. |
So do we merge this in the meantime or wait? |
+1 to merge |
I'd say merge, one might grow a beard before there is next CDI release ;-) |
@geoand Ok, so we agreed that this "feature" should be merged. Now let's polish the code a little ;-) |
@mkouba Of course! What sort of polish do you have in mind? |
// if the class has a single non no-arg constructor that is not annotated with @Inject, | ||
// the class is not a non-static inner or and it not a superclass of of a bean | ||
// we consider that constructor as an injection | ||
if (injections.isEmpty() && isFirstLevel) { |
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.
The injections
list contains all injection points found, i.e. injections.isEmpty()
returns false if any injection point (field, method) is found. If you add @Inject Head head2
field to your test it fails.
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.
That's a very interesting case I hadn't thought of :).
I will see how it can be fixed
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.
I would just check isFirstLevel
first and then proceed if there is no injection for which Injection.isConstructor()
returns true ;-)
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.
That's what I'm thinking as well, but I'm trying to think if it would fail in any case - but probably not :)
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.
Fixed. Should I also rebase onto the current master?
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.
Unless there are conflicts it should not really matter
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.
No conflicts, so I'll leave as is then
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.
@mkouba Tests passed with the latest fix. Is there anything else you would like to see?
@geoand Thanks for your contribution ;-) |
@mkouba You are most welcome! |
Basically when the bean has a single constructor that contain arguments,
then the @Inject annotation is not necessary, since the injection point
can be safely deduced.
This is analogous to what Spring DI does since Spring 4.3