I have bean like this :
<bean id="myBean" class="com.mypackage.MyClass" scope="session">
</bean>
here is the class declaration :
MyClass extends MySuperClass implements MyInterface<A>
MySuperClass extends GenericClass<A>
Later I try to do this :
applicationContext.getBean("myBean", GenericClass.class);
And I get this error :
org.springframework.beans.factory.BeanNotOfRequiredTypeException: Bean named 'myBean' must be of type [com.mypackage.GenericClass], but was actually of type [com.sun.proxy.$Proxy118]
I solved it by adding :
<aop:scoped-proxy />
inside my bean declaration but I like to understand what I am doing and in this case I don't.
Could you explain me why I am getting this exception and why adding <aop:scoped-proxy /> solved it ?
thanks !
By adding <aop:scoped-proxy/> I believe you are telling Spring to use a smart object proxy rather than just a plain JDK interface proxy. Basically your proxy object is backed by your actual object so that when you pass it around it looks just like your regular object. It sounds like a compromise between using AspectJ loadtime weaving and plain JDK proxies. Have a read of what the equivalent annotation does here
EDIT 1: Actually it looks like using CGLib (AspectJ) based proxies is the default option there. Thats probably what fixed your problem.
Related
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().
I am working on an application where I have two classes both implementing a common interface. So in time of bean declaration, I am going to mark one of them primary in my app-context.xml file. I can achieve this by simply declaring the primary bean like this:
<bean id="oracleImpl" class="com.me.dao.OracleImpl" primary="true">
</bean>
Now I don't want to hard code which of the beans is going to be the primary bean, rather want to read the true/false value from a properties file. So I went like this:
<context:property-placeholder location="classpath:jdbc.properties"/>
<bean id="oracleImpl" class="com.me.dao.OracleImpl" primary="${oracle.primary}">
</bean>
<bean id="pgsqlImpl" class="com.me.dao.PgsqlImpl" primary="${pgsql.primary}">
</bean>
The values of oracle.primary and pgsql.primary are defined in the file jdbc.properties along with other jdbc (non-boolean) properties.
But it doesn't work and says, "'${oracle.primary}' is not a valid value for 'boolean'"
I have a feeling it is something to do with the xsd validators. Browsing through this site and google gave me this much idea, but got no real solution. Can any body help?
This will not work.
As of 3.2.5.RELEASE only the following bean definition elemets support property placeholder:
parent name
bean class name
factory bean name
factory method name
scope
property values
indexed constructor arguments
generic constructor arguments
See the BeanDefinitionVisitor's visitBeanDefinition method for the details. This method is used by the PlaceholderConfigurerSupport.
I would recommend you to create a feature request in the spring issue management system.
PS: if you create an issue please add a comment to the issues url.
I have a system where I have an enum of Shops for example. These shows each have their own ShopCommand property (some of which share the same type of command class). from a method in the command class I then want to call send on a Spring Integration gateway. Where I'm confused is how to actually insantiate this gateway in spring. Ideally what I want is to construct the enum via XML configuration with command property being created also in spring, which has the property outGateway set via Spring. I'm not sure if I've made myself very clear with this descrition, if clarification is needed then just ask!
I think this is what you are asking for:
Say I have an enum for ShopType
public enum ShopType {
GROCERY, DEPARTMENT, MALL;
}
Then I have some Store bean that I want to setup via spring configuration. You can instantiate and use the enum like this:
<bean id="DEPTARTMENT_STORE" class="my.package.ShopType" factory-method="valueOf">
<constructor-arg value="DEPARTMENT"/>
</bean>
<bean id="searsStore" class="my.package.Store">
<property name="shopType" ref="DEPTARTMENT_STORE"/>
</bean>
The factory-method points to a static method that is used to create the object. So you can use the enum's method "valueOf" as a factory method.
I would like to get inner bean by it's name. Is it possible with Spring API?
Right now I'm using such Spring 2.5 API
ConfigurableApplicationContext.getBean(String paramString)
Example of XML:
<bean id="parent" parent="t_Parent">
<property name="items">
<bean id="child" parent="t_Child">
<property name="ABC" value="test"/>
</bean>
</property>
</bean>
I would like to get inner (t_Child) bean by id "child". E.g. ConfigurableApplicationContext.getBean("child"). Spring can't find such bean (because it's inner). At the same time .getBean("parent") works fine.
Any thoughts?
You can't.
From the docs:
A element inside the or elements is used to define a so-called inner bean. An inner bean definition does not need to have any id or name defined, and it is best not to even specify any id or name value because the id or name value simply will be ignored by the container.
If you need it like that, define it as a regular bean.
You can't, but you can create you inner bean outside (so it's no longer an inner bean...) and then reference it inside the property:
<bean id="child" parent="t_Child">
<property name="ABC" value="test"/>
</bean>
<bean id="parent" parent="t_Parent">
<property name="items" ref="child"/>
</bean>
Apart from the other (mostly valid) answers and solutions, I guess the spring way would be to use the BeanWrapper interface:
final BeanWrapper bw =
new BeanWrapperImpl(applicationContext.getBean("parent"));
Object innerBean = bw.getPropertyValue("child");
But I guess that implies that there must be a getter for the property (not only a setter).
Reference:
BeanWrapper (javadoc, 2.5 version)
Bean manipulation and the BeanWrapper (reference, 2.5 version)
If you move up to Spring 3.x, you should be able to do this with the Spring Expression Language. There are examples of directly referencing a bean property from another property (like in link text). The code to do this from Java would be somewhat similar, although I can't find an exact example of this scenario.
However, I would say that if you're trying to use "getBean()", you're doing something wrong. You could just as easily use the SpEL in your context to define a bean or a bean property that references that inner bean.
I read about Compound property names in the "The Spring Framework (2.5) - Reference Documentation - chapter 3.3.2.7"
Can i use the same concept to set values of properties? Can i use a compound string as a value expression?
<bean id="service1" class="a.b.c.Service1Impl" scope="prototype">
<property name="service2" ref="service2"/>
<property name="service2.user" value="this-service1-instance.user"/>
</bean>
<bean id="service2" class="a.b.c.Service2Impl" scope="prototype">
...
</bean>
User is a property of a.b.c.Service1Impl which is not in control of Spring. I want to forward this property to a.b.c.Service2Impl.
Rather than use a plain old factory bean, rather use a factory method to create the bean of the property and then inject that result...
iow
in your case, it would look something like this...
<!-- the bean to be created via the factory bean -->
<bean id="exampleBean"
factory-bean="serviceLocator"
factory-method="createInstance"/>
So the bean of id is created by calling createInstance on bean serviceLocator.
Now spring does not support nested properties out of the box, though you could look at creating a custom editors which might provide that support - possible but tricky. Possibly not worth the effort.
One mechanism you could look at using is nesting using the factory-bean factory-method technique...
Something like:
<bean id="c" class="C" />
<bean id="b" factory-bean="c" factory-method="getB"/>
<bean id="a" factory-bean="b" factory-method="getA"/>
This will effectively expose: a.b.c where C has a method getB and A has a method getB
I had to do something similar, and I'm afraid it's not possible. I had to write a [FactoryBean][1] to expose the property.
It would look something like this:
public class UserFactory implements BeanFactory {
private Service2 service2;
// ... setter and getter for service2
public Object getObject() {
return getService2().getUser();
}
public Class getObjectType() {
return User.class;
}
public boolean isSingleton() {
// Since it's a prototype in your case
return false;
}
}
Come to think of it, in your case, you'd probably define the factory itself as a prototype, in which case your isSingleton() may return true, you'll need to play around with this a little bit.
Spring's XML wiring syntax supports lists, maps and properties objects, and you can create other 'data' objects via property editors.
Edit: (Oh I see what you are asking.) I think that the answer is no. I don't recall having seen any mention of calling getters on a bean or non-bean object in the Spring documentation, let alone a syntax for doing this in the wiring file. It tends to go against the grain. Spring wiring is declarative, and calling a getter would lead to patterns that are bordering on procedural.