Instantiating domain object and factory object with spring container - java

our application is using Spring container and Spring AOP.We need to Instantiate all the object from Spring Container,so that Spring AOP work with whole application
Is there any way where we can Instantiate domain object,factory method from spring container.we dont want to use AspectJ
<bean id="ExBean" factory-bean="ExFactoryBean" factory-method="getObj">
<constructor-arg ref="runtimeBean"/>
<constructor-arg value="Add"/>
</bean>
I want to select interface implementing class at runtime and that class should be instantiated from Spring. we have use factory method for creating the class,but classes bean instantiation at runtime is not happening yet

Yes you can configure spring to instantiate object from factory method
<bean id="exampleBean"
class="examples.ExampleBean2"
factory-method="createInstance"/>
3.2.3.2.2. Instantiation using a static factory method

There are two options to make objects managed by spring:
let spring instantiate them
use apsectj weaving
No other way.

Related

Bean definition for using a class with static methods in Spring Controller class

I have a TestUtil class that I need to use in almost each of my other classes in a Spring MVC web application.
In my application context, I have done the following bean definitions:
<bean id="masterbo" class="com.bo.master.MasterBO">
<property name="masterdao" ref="masterdao"></property>
<property name="testutil" ref="testutil"></property>
</bean>
<bean id="masterdao" parent="daoSupport" class="com.dao.master.MasterDAO"></bean>
<bean id="testutil" class="com.util.TestUtil"></bean>
I have autowired the TestUtil class in MasterBO and simply used the testutil.someMethod() call.
Using this I am able to use the static method from TestUtil in MasterBO. Now, I would like to do the same in the MasterController. Similar bean definition is not working in that case
Can anyone guide me regarding the bean definition that needs to be done?
EDIT: Calling static methods directly is working on Tomcat. Facing this issue on WildFly and JBoss, which supposedly require proper bean definition.
SOLVED: It seems there was an incorrect ParseException being used in the Util which was conflicting with WildFly
You don't need to instantiate a bean to call a static method, just call the method directly by the class itself: TestUtil.someMethod().

Refrence Spring Beans Generated From an Interface in XML Bean Definition

I have some code that generates a class from an interface. I need to reference that interface in a Spring XML configuration. Is there a Spring 3 annotations I can use on the interface such that I can reference the generated implementation using <constructor-arg ref="myBeanInterface"/>?
I can reference it using <constructor-arg value="com.mysite.myBeanInterface"/>, however I want to refrence a bean name instead of an explicit class.
Details: The beans are generated by an extension of AbstractFactoryBean. I do not have access to the bean generating code.
Use the name of your factory bean. If you have something like:
<bean id="myBean class="MyBeanInterfaceFactoryBean>
...
</bean>
Then to inject the bean that was generated by the factory bean, just use myBean.

ways to inject a object of a class in spring controller?

I need to inject a object of a java class in spring controller through applicaionContext.xml. My controller will be ,
#Controller
public class SpringController{
private MyClass obj;
}
I know I can do it with #Autowired annotation.
Is this really good to create a object for a controller through applicaionContext.xml ? Also can I inject a object of a class in controller using the <property> tag inside a <bean> tag ?
Is this really possible ? or please forgive me if it is a stupid question.
I need to know the possible ways for how to inject a object of a class in Spring controller ?
You can of course use #Autowired annotation to autowire the relationships, which can reduce the need to define the properties and constructor arguments for the controller in your applicationContext.xml file. And also to add a dependency to a class, you don't need to modify the configuration files.
But it has some disadvantages too, like if you use #Autowired, there will not be any explicit documentation for the wiring details between Spring managed beans. And to know the relationships between the beans, you have to go through your managed beans. But, if you use configuration files to define the relationships, the relationship details can be found in one place.
You can inject an object of a class into your controller through your applicaionContext.xml as below:
Constructor based injection:
#Controller
public class SpringController{
private MyClass obj;
public SpringController(MyClass obj){
this.obj=obj;
}
}
<bean id="myClassImpl" class="x.y.z.MyClassImpl"></bean>
<bean id="springController" class="x.y.z.web.controllers.SpringController">
<constructor-arg ref="myClassImpl"></constructor-arg>
</bean>
Setter based injection:
#Controller
public class SpringController{
private MyClass obj;
public void setObj(MyClass obj){
this.obj=obj;
}
public MyClass getObj(){
return obj;
}
}
<bean id="myClassImpl" class="x.y.z.MyClassImpl"></bean>
<bean id="springController" class="x.y.z.web.controllers.SpringController">
<property name="obj" ref="myClassImpl"></property>
</bean>
If you want to inject an object in a controller and you particularly want to you use xml,then instead of component scanning of Controller you should create a bean of the controller class of singleton scope in the application context.
Your controller class need not be annotated with #Controller.
you then have to you extend some Controller also like AbstractCommandController, AbstractController, AbstractFormController, AbstractWizardFormController, BaseCommandController, CancellableFormController, MultiActionController SimpleFormController, UrlFilenameViewController
Now to inject a particular object you can use Either Constructor and Setter based injection.
or you can use Autowring by name or type to auto inject the object.
Make sure that you have also declared the bean of that object also in Application Context.
After a DispatcherServlet has received a request and has done its work to resolve locales, themes and suchlike, it then tries to resolve a Controller, using a HandlerMapping. When a Controller has been found to handle the request, the handleRequest method of the located Controller will be invoked; the located Controller is then responsible for handling the actual request and - if applicable - returning an appropriate ModelAndView.
Thats it.
Actually, injection with xml and annotation is same behind the scene. Xml is old fashion while annotations are newer.
Basically, there are 2 types of injection types.
byName
Autowiring by property name. Spring container looks at the properties
of the beans on which autowire attribute is set to byName in the XML
configuration file. It then tries to match and wire its properties
with the beans defined by the same names in the configuration file.
You can give explicit names to beans both with xml and annotation.
#Service("BeanName")
#Component("BeanName")
#Controller("BeanName")
<bean name="BeanName" class="someclass"></bean>
and inject beans by using #Qualifier annotation.
#Autowired
#Qualifier("BeanName")
and with xml
<bean id="MyBean2" class="MyBean2 class">
<property name="Property of MyBean2 which refers to injecting bean" ref="BeanName" />
</bean>
byType
Autowiring by property datatype. Spring container looks at the
properties of the beans on which autowire attribute is set to byType
in the XML configuration file. It then tries to match and wire a
property if its type matches with exactly one of the beans name in
configuration file. If more than one such beans exists, a fatal
exception is thrown.
Default auto wiring mode is byType, so spring will look for matching type in auto wiring. However, older versions of Spring has default behavior none on injection. If you want to inject byType using xml, you should tell spring contaioner explicitly.
For example MyBean2 has a reference to MyBean, by setting autowired attribute to byType it handles injection automatically.
<bean id="MyBean" class="MyBean class">
<property name="Property of MyBean2 which refers to injecting bean" ref="BeanName" />
</bean>
<bean id="MyBean2" class="MyBean2 class"
autowire="byType">
</bean>
It also depends on where the injection take place in your code. There are 2 types, setter getter injection and constructor injection.
Note : There is no difference in #Controller since they are already in spring context.
See also
Spring Beans Auto wiring
I ran into such problem. I was getting "Ambiguous mapping found". (I use xml configuration as well and i am injecting a bean into my controller)
Then looking at my console i realized that my controller was being instantiated twice.
In more detailed look i noticed that my annotation
#Controller(value = "aController")
(Note value = "aController")
was different from my xml configuration where i was instatiating the same controller with different bean id
<bean id="aControleRRRRR" class="package.ControllerClassName"
p:property-ref="beanToInject" />
(Note id="aControleRRRRR")
So in conclusion your #Controller name (value = "aController") needs to be exactly the same as the name you give in the XML configuration (id="aControleRRRRR"), so that Spring can manage to distinct that they refer to the same bean (instance)
Hope this helps

spring 3: inject a dependency from a library?

I am developing a project and using 3rd party libraries. Let's say I use a library which gives me the object ExtObj. In my project I have a class MyObj, which uses ExtObj. How can I configure spring 3 to inject ExtObj in MyObj?
I tried to research the topic on the internet, but I didn't find a straight answer. I would like to use xml configuration and maybe (?) #Autowired, not #EJB or #Inject
Thanks in advance!
UPDATE
my guess was:
<bean id="myObj" value="me.MyObj">
<property name="extObj" value=" ... ??? ...">
</bean>
So, I don't know what I should put into value. I guess that's where the reference to the external object goes. But spring can only reference objects that have been already defined/configured in spring. So:
<bean id="extObj" value="ext.lib.ExtObj">
<bean id="myObj" value="me.MyObj">
<property name="extObj" value="extObj">
</bean>
Is that configuration right?
First you need to define a bean for your ExtObj in your application context (an xml file or a #Configuration class). Eg. if ExtObj has a constructor taking a String you can define the bean this way:
<bean id="extObj" class="ext.lib.ExtObj">
<constructor-arg value="SomeString"/>
</bean>
To define MyObj you can use constructor injection:
<bean id="myObj" class="me.MyObj">
<constructor-arg ref="extObj"/>
</bean>
or setter injection:
<bean name="myObj" class="me.MyObj">
<property name="extObj" ref="extObj"/>
</beans>
If you use setter injection then MyObj needs to have a setter setExtObj. If you use constructor injection MyObj needs to have a constructor taking an instance of the ExtObj class.
Of course you can inject a 3rd party library, as long as it has constructors that Spring can access.
You can use either XML or annotations - your choice.
You need to ask Spring to instantiate the instance(s) of the library class and then inject that into your objects that need them.
You do this every time you create a Spring data source that uses a JDBC driver. That's a 3rd party library.

Ability to create bean template in Spring

Lets say I have a situation like this:
<bean id="sample" class="ComlicatedClass" scope="prototype">
<property name="someProperty" value="${propertyValue}"/>
</bean>
I want to be able to create the bean programatically and provide value for propertyValue at runtime (pseudocode ahead):
appContext.getBean("sample", "propertyValue" => "value")
In a way, I want to create "bean template" rather than full defined bean. Is that possible in any way in spring?
EDIT:
The value for propertyValue is known at runtime! There is no way to define it as another bean.
why don't you just do
Sample sample = appContext.getBean("sample");
sample.setSomeProperty(appContext.getBean("someOtherBean"));
Have you looked at the Prototype scope?
The non-singleton, prototype scope of bean deployment results in the creation of a new bean instance every time a request for that specific bean is made. That is, the bean is injected into another bean or you request it through a getBean() method call on the container. As a rule, use the prototype scope for all stateful beans and the singleton scope for stateless beans.
There is also the #Scope annotation if you are using the Java based container configuration.

Categories