#RequestScoped in Quarkus having same hashcode for all request bean - spring

I have used #RequestScoped with quarkus framework. My requirement is for every request new object must be created. But Whenever I have checked the hashcode for all bean for all request then it was same. Means as per my understanding if the first request is there it will create one bean which having some hashcode ,whenever second request will come it will create another bean with different hashcode .But in reality it was same hashcode. Can any one help me to know reason behind it ?

#RequestScoped beans, as well as all other normal-scoped beans, are not injected directly. Instead, a so called client proxy is injected. This client proxy, on each method invocation, looks up the correct instance (in this case, an instance belonging to the "current" request) and forwards the method invocation to it.
So, what you're observing is totally expected. There's one instance of the client proxy, but that doesn't mean there is not a dedicated instance for each request.
There's one twist to it. I said that all methods are forwarded to the correct instance, so you might expect that hash codes would be different for different requests. That isn't the case, though, because the CDI spec says:
The behavior of all methods declared by java.lang.Object, except for toString(), is undefined for a client proxy. Portable applications should not invoke any method declared by java.lang.Object, except for toString(), on a client proxy.
So no, hash codes don't have to be different. If you really want to prove that each request gets a different instance, generate a unique ID in the constructor of the bean class, and expose it though some method.

Related

Kotlin instance variable is null when accessed by Spring proxied class

I have a service class that is being proxied by Spring, like so:
#Service
#Transactional
open class MyService { ... }
If I remove the open modifier, Spring complains that it needs to proxy the class to apply the #Transactional annotation tweaks.
However, this is causing issues when calling a function on the proxied service, which attempts to access a variable:
#Service
#Transactional
open class MyService {
protected val internalVariable = ...
fun doWork() {
internalVariable.execute() // NullPointerException
}
}
The internalVariable is assigned as part of its declaration, does not have any annotations (like #Autowired, etc.), and works fine when I remove the #Transactional annotation and the requirement for Spring to proxy the class.
Why is this variable null when Spring is proxying/subclassing my service class?
I hit a similar issue and the above comments by Rafal G & Craig Otis helped me-- so I'd like to propose that the following write up be accepted as an answer (or the comments above be changed to an answer and they be accepted).
The solution: open the method/field.
(I hit a similar case where it was a closed method that caused the problem. But whether it is a field/method the solution is the same, and I think the general cause is the same...)
Explanation:
Why this is the solution is more complicated and definitely has to do with Spring AOP, final fields/methods, CGLIB proxies, and how Spring+CGLIB attempts to deal with final methods (or fields).
Spring uses proxies to represent certain objects to handle certain concerns dealt with by Aspect Oriented Programming. This happens with services & controllers (especially when #Transactional or other advice is given that requires AOP solutions).
So a Proxy/Wrapper is needed with these beans, and Spring has 2 choices-- but only CGLIB is available when the parent class is not an interface.
When using CGLIB to proxy classes Spring will create a subclass called
something like myService$EnhancerByCGLIB. This enhanced class will
override some if not all of your business methods to apply
cross-cutting concerns around your actual code.
Here comes the real surprise. This extra subclass does not call super
methods of the base class. Instead it creates second instance of
myService and delegates to it. This means you have two objects now:
your real object and CGLIB enhanced object pointing to (wrapping) it.
From: spring singleton bean fields are not populated
Referenced By: Spring AOP CGLIB proxy's field is null
In Kotlin, classes & methods are final unless explicitly opened.
The magic of how Spring/CGLib when & how chooses to wrap a Bean in an EnhancerByCGLIB with a target delegate (so that it can use finalized methods/fields) I don't know. For my case, however the debugger showed me the 2 different structures. When the parent methods are open, it does not create a delegate (using subclassing instead) and works without NPE. However, when a particular methods is closed then for that closed method Spring/CGLIB uses a wrapped object with delegation to a properly initialized target delegate. For some reason, the actual invocation of the method is done with the context being the wrapper with its uninitialized field values (NULLs), causing NPE. (Had the method on the actual target/delegate been called, there should not have been a problem).
Craig was able to solve the problem by opening the property (not the method)-- which I suspect had a similar effect of allowing Spring/CGLib to either not use a delegate, or to somehow use the delegate correctly.

Creating Spring Beans with arguments only known at runtime

I have a class that requires parameters provided by the user at runtime. I do this because I like the idea of ensuring the object is always in a valid, ready to use state. However I do not know the parameter values until the user has started using the application which is causing problems with Spring IoC as everything is instantiated at start up.
I think I can work around it this with #Configuration, .getBean calls with arguments, and #Lazy annotations however it feels like I'm kluging (eg. .getBean calls are discouraged)
Is there a nicer way to handle this? I'm thinking I should just lump it and move to having a constructor with no parameters and force a setter method call with the parameters but then I'll have an object sitting around that's in an invalid state.

UnderStanding of #Controller #Service #Repository

I have a doubt regarding dependency injection,Suppose my controller ,service,dao all are singleton so usually when we create the controller we inject the service as a instance variable of that class, but according to the singleton pattern if our controller is stateless then only we would not face any concurrency issue but here We are declaring the service dependency so it should not be stateless so we have to take care of synchronization?
Please clear this doubt as I am beginner so I hope its natural to have this doubt in mind,I don't know if I am thinking totally wrong.Please help.
All beans in Spring are Singleton by default. This includes any #Controller, #Service, #Repository and others, as well as any xml defined bean.
You could read this and this
From Java basic variable tutorial:
Local Variables Similar to how an object stores its state in fields, a
method will often store its temporary state in local variables. The
syntax for declaring a local variable is similar to declaring a field
(for example, int count = 0;). There is no special keyword designating
a variable as local; that determination comes entirely from the
location in which the variable is declared — which is between the
opening and closing braces of a method. As such, local variables are
only visible to the methods in which they are declared; they are not
accessible from the rest of the class.
If your service and controller are stateless, it's ok to inject one to another.
You should not declare any variable which keeps a state in these classes. final variables are ok.
If all operations are defined in methods and they don't use any variables of the classes, dependency injection that you're doing is totally safe.
That's why you need to use #Autowired when you declare a dependent service. Effectively handing the initialization process to the Spring framework instead of instantiating it yourself. Since Spring only has stateless beans, you're injecting one stateless singleton to another stateless singleton, so there's no need to manage thread manually.

getting bean id of target class in advice

I have a few classes that interact with databases (more than one). Some classes are reused so for example "obs.table1" is used to interact with table1 in database "obs" while "ref.table1" is used to interact with table1 in database "ref". These databases are at different URLs and each gets its own connection pool, etc... obs.table1 and ref.table1 are both instances of MyTable1Class, defined in beans file.
I have a pointcut that intercepts calls to methods annotated with #Transactional or with a custom annotation #MyTablesAnnotation and have it set so those calls will all get routed into a #Around advice.
This all works and the flow through the advice is correct.
What I am trying to add is reporting on what is going on in there. Currently I can tell where in there I am, but I can't tell if it was obs.table1 or ref.table1 object that got me there.
Is there a way to extract the bean id of the object on whose method the advice was invoked on?
ProceedingJoinPoint that is passed to the method the only thing I do with it is call a .proceed on it and the rest is just various checks and catches. I see that I can get either the target class or proxy class out of it, but... not sure how to go from there to knowing what the bean id was.
Is it possible?
Firstly it is not recommended to depend on bean id as it creates tight coupling with framework.
To quote from docs Note that it is not usually recommended that an object depend on its bean name, as this represents a potentially brittle dependence on external configuration, as well as a possibly unnecessary dependence on a Spring API.
Now to answer your question yes it is possible to fetch the name of bean via org.springframework.beans.factory.BeanNameAware.
The class for which you require the bean name should implement it and spring will auto-magically inject the name of the bean. However there is a gotcha which you should be aware and is mentioned in docs here

Regarding Instance in Spring mvc web application development

I am new to spring mvc web development. I have one query.
Suppose we are having different service classes. So do we have one instance of those classes per request OR only single instance of that class gets create. Actually i want to use instance variables , so with each request new instance will get created or it will be like singleton type of behavior. Hopefully i am able to explain my question.
you can have either, the default is a singleton - one instance. But this can be changed using bean scope.
obligatory link to offical docs correct chapter
(personally never needed to use anything other singleton)
If you have not defined any scope explicitly, it will be singleton by default, singleton means there will be one object per spring container, for your context, one object for all your request threads. In case of singleton scope, be cautious while using member variables, because thread safety comes into picture.
If you are modifying state of a member variable inside your singleton scoped bean, you need to write thread safe code because multiple threads are accessing your member variable and a race condition may occur.
Moreover, you can define other scopes too using #Scope at the class level(i.e above #Component) or at method level above #Bean annotations.
Generally, we keep using the default scope (i.e singleton scope), this way spring container also does not waste time in creating the new object of the bean asked for, though it would be a little overhead creating an object on each request thread.
If you want a new object on every bean injection, you can have prototype scope for that bean.

Resources