I'm loading my spring configuration file in web.xml file. The spring file contains many beans. How can I get the bean name in my class. Is their any way to get the bean name without providing the path name.
web.xml
<context-param>
<param-name>configDir</param-name>
<param-value>D:/akatte/config</param-value>
</context-param>
<context-param>
<param-name>springConfig</param-name>
<param-value>spring-config.xml</param-value>
</context-param>
spring-config.xml
<bean id="foNasShare" class="com.katte.galaxe.FoNas">
<property name="fname" value="arvind"/>
<property name="lname" value="katte"/>
</bean>
Pojo class
FoNas.java
class FoNas
{
//getter and setter
}
Now tell me how can I access the bean name (context.getBean("foNasShare")) in my class. spring-config.xml file is already loaded in web.xml, i don't want to load the xml file one more time. The problem is spring bean is loading but the value of the getter and setter are setting to null.
Related
This question already has answers here:
Spring JSF integration: how to inject a Spring component/service in JSF managed bean?
(4 answers)
Closed 6 years ago.
I have a webmodule with JSF 2 end Spring 4.3. In a backing bean I use #Autowired for DI of a service of a JAR. In EAR module there are WAR, JAR with #Service Spring and JAR with Spring configuration file.
Below a web.xml snippet:
<context-param>
<param-name>locatorFactorySelector</param-name>
<param-value>classpath:beanRefContext.xml</param-value>
</context-param>
<context-param>
<param-name>parentContextKey</param-name>
<param-value>sharedContext</param-value>
</context-param>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath:applicationContext.xml</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<listener>
<listener-class>org.springframework.web.context.request.RequestContextListener</listener-class>
</listener>
applicationContext.xml:
<context:annotation-config />
<context:spring-configured />
<!-- package of #Service class in jar module in EAR-- >
<context:component-scan base-package="com.ipdb.service" />
beanRefContext.xml:
<bean id="sharedContext" class="org.springframework.context.support.ClassPathXmlApplicationContext"> <constructor-arg>
<list>
<value>spring-ctx.xml</value>
</list>
</constructor-arg> </bean>
When I Use #Autowired(required=null) in a Backing Bean the value is null (there is not any exception). My JSF bean
#Component
#ManagedBean
#ViewScoped
public class PortfolioController {
#Autowired(required = true)
private PortfolioService portfolioService;
...
Can you help me, please.
PortfolioController is considered a JSF context bean adding #Component to #ManagedBean is totally wrong you can't mark same class as bean in two different contexts (JSF and Spring ).
Two solutions either make PortfolioController a spring bean thus remove the #ManagedBean and #ViewScoped or inject PortfolioController via JSF injection annotation #ManagedProperty
#ManagedProperty("#{portfolioService}")
private PortfolioService portfolioService;
if the applicationContext.xml is in your jar dependency, then you need to add asterisk after classpath:
<param-name>contextConfigLocation</param-name>
<param-value>classpath*:applicationContext.xml</param-value>
</context-param>
With the asterisk spring search files applicationContext.xml anywhere in the classpath not only the current project.
I have configured spring jpa with annotation driven. I would expect the following code to persist the changes to the database upon method exist.
#Transactional
public Foo changeValue(int id){
final Foo foo = fooRepository.findOne(id);
if(foo != null){
foo.setValue("new value");
//fooRepository.save(foo);
}
}
FooRepository is a JPARepository and the foo object is getting fetched so it is managed. Based on what I read about #Transactional I would expect that even without the fooRepository.save(foo) call the changes in foo's value column in the database would be persisted upon method exist. However, this only happens if I uncomment the call to fooRepository.save(foo)
No exceptions are thrown and the configuration for the jpa datasource is as below.
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
...
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager"
p:entityManagerFactory-ref="entityManagerFactory" />
<tx:annotation-driven transaction-manager="transactionManager" />
<context:component-scan
base-package="com.example.package.data" />
<jpa:repositories
base-package="com.example.package.data.repository"
entity-manager-factory-ref="entityManagerFactory"
transaction-manager-ref="transactionManager" />
Any ideas?
Update
I do have a ContextLoaderListener and a DispatcherServlet but I do not have component scan for both.
<servlet>
<servlet-name>appServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/appServlet/servlet-context.xml</param-value>
</init-param>
</servlet>
....
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
Update
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/spring/root-context.xml</param-value>
</context-param>
And there I do
<context:component-scan base-package="com.example.package">
<context:exclude-filter type="regex"
expression="com.example.package.data.*" />
<context:exclude-filter type="regex"
expression="com.example.package.web.controller.*" />
<context:exclude-filter type="regex"
expression="com.example.package.web.service.*" />
</context:component-scan>
And in servlet-context
<context:component-scan base-package="com.example.package.web" />
Your general approach is correct. The changes should get saved and committed on exit of the method. While this approach works great when it works it is a bitch to debug.
Your configuration looks ok to me, so I would double check, that you actually have Spring Beans at your disposal and not some instance that you created simply by calling the constructor.
To verify this, just put a breakpoint at the code point where the annotated method gets called. The bean with the annotated method should NOT by of the class you wrote, but some ProxySomething class.
This article also provides some pointers what might be wrong with your setup.
If you have both a ContextLoaderListener and DispatcherServlet they both load a configuration file.
Judging from your configuration the services are loaded by the DispatcherServlet and your <tx:annotation-driven /> is loaded by the ContextLoaderListener. They both create an ApplicationContext and as AOP is only applied to the beans in the same context your services will not be transactional (Transaction management is done by using AOP).
As a rule of thumb your ContextLoaderListener should contain all shared or global resources (like services, daos, datasources etc.) whereas your DispatcherServlet should only contain web related beans like controllers, view resolvers etc.
I am trying to understand a web system using spring and I can not debug it.
Now I am confused by the order of the XML initialization.
Support I have an web.xml which is like this:
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>
classpath*:/com/pathA/**/applicationContext*.xml,classpath*:/com/pathB/**/applicationContext*.xml
</param-value>
</context-param>
and in /com/pathA I have some xml files that define some beans with the same name.
In /com/pathB I also have some xml files that define beans with the same name as in com/pathA's xml file.
I know that spring framework will use the last bean definition by default.But I can't
find the order of the xml files initialization.
Here is the beans' definition:
/com/pathA/applicationContextOne.xml
<bean name="/testBean" class="com.TestActionOne">
</bean>
/com/pathA/applicationContextTwo.xml
<bean name="/testBean" class="com.TestActionTwo">
</bean>
/com/pathB/applicationContextThree.xml
<bean name="/testBean" class="com.TestActionThree">
</bean>
can anyone can tell me the initialization order of the differnet xml files in /com/pathA/
and the initialization order of the xml files between com/pathA/ and com/pathB?
I have written some samples in local pc (Windows and AIX)to simulate the initialization order and I found the result below.
1.the initialization order of files in different path depends on the order written in
classpath*:/com/pathA/*/applicationContext.xml
on my question, the [applicationContext*.xml] files in pathA will be initialized first and then in pathB.
2.the initialization order of files in the same path is the order of the file name
for example,if in pathA there are [applicatinContextOne.xml] and [applicationContextTwo.xml],then [applicatinContextOne.xml] will be initialized first and then [applicationContextTwo.xml].
I tried this under both Windows and AIX, and it returns the same result.
Hope this will be helpful.
I have a UserDetailsService class annotated with #Service. I also have DAO classes annonated which are autowiring and working fine within my controllers.
The problem is when I want to wire up the UserDetailsService bean within my security-context.xml. Spring is unable to find the bean. Is it because my component-scan is in my controllers.xml file and out of the scope of my security configuration?
xml config file layout as so :
web.xml :
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>
/WEB-INF/spring/root-context.xml
/WEB-INF/spring/appServlet/security-context.xml
</param-value>
</context-param>
servlet-context.xml :
...
<beans:import resource="controllers.xml" />
...
Yes, you'll need to add the component scan to both contexts, it's not enough to do it in just one.
I find myself using two identical beans in my applicationContext.xml and my applicationContext-test.xml. I'd like my test context to be able to inherit from my app context, to avoid repeating myself.
I've seen plenty of material indicating that you can declare a parent application context and reference beans from that context, but I can't find a useful example. Can anyone help?
Update
As some background info, my normal application context is being loaded in web.xml:
<context-param>
<description>Application Contexts for Spring</description>
<param-name>contextConfigLocation</param-name>
<param-value>/WEB-INF/classes/applicationContext.xml</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
My test application context is loaded in my unit tests:
#RunWith(SpringJUnit4ClassRunner.class)
#ContextConfiguration(locations = "/applicationContext-test.xml")
So let's say I have a bean in my regular context:
<bean name="someBean" class="com.foo.MyClass" />
Then, in my test application context, I'd like to refer to this bean. How do I do it?
Update
Per skaffman's suggestion, I've moved the bean into a SharedBeans.xml file and imported it into my applicationContext.xml. However, this causes a SAXParser exception:
org.springframework.beans.factory.parsing.BeanDefinitionParsingException: Configuration problem: Failed to import bean definitions from URL location [classpath:SharedBeans.xml]
Offending resource: ServletContext resource [/WEB-INF/classes/applicationContext.xml]; nested exception is org.springframework.beans.factory.xml.XmlBeanDefinitionStoreException: Line 1 in XML document from class path resource [SharedBeans.xml] is invalid; nested exception is org.xml.sax.SAXParseException: cvc-elt.1: Cannot find the declaration of element 'bean'.
at org.springframework.beans.factory.parsing.FailFastProblemReporter.error(FailFastProblemReporter.java:68)
I can't be sure what I'm doing wrong. The bean was working fine in my context file, and all I did was cut and paste into the new file. Here are the contents of SharedBeans.xml in its entirety:
<bean name="properties" class="com.foo.Properties">
<constructor-arg><value>${module.name}</value></constructor-arg>
<constructor-arg><value>${businessUnit}</value></constructor-arg>
<constructor-arg><value>${product}</value></constructor-arg>
<constructor-arg><value>${env}</value></constructor-arg>
<constructor-arg><value>${machineName}</value></constructor-arg>
<constructor-arg><value>${collectionSet.company}</value></constructor-arg>
<constructor-arg><value>${route.tag}</value></constructor-arg>
<constructor-arg><value>${timeout}</value></constructor-arg>
</bean>
This doesn't strike me as a particularly good use-case for a parent context, which is useful mainly to set up a hierarchy (e.g. one root webapp context, multiple child servlet contexts).
For your situation, it's going to be simpler and easier to understand if you just extract the common bean definitions into a separate file, and then <import> them into each context file that needs it. You could do this with parent-child contexts, but it's going to be harder to understand, unnecessarily so.
OK, so an example, put your shared bean definition into a file called shared-beans.xml, and put it (for now) at the top-level of your classpath, containing:
<bean name="someBean" class="com.foo.MyClass" />
Then, inside applicationContext-test.xml and /WEB-INF/classes/applicationContext.xml, add the following:
<import resource="classpath:/shared-beans.xml" />
All of the bean definitions in shared-beans.xml will now be imported into each app context. You don't get a third app-context by doing this, you just import the bean definitions from another file.
You can move your common declaration to the separate XML file and place it in classpath (for easy access from test). Then you can do the following:
<context-param>
<description>Application Contexts for Spring</description>
<param-name>contextConfigLocation</param-name>
<param-value>
/WEB-INF/classes/applicationContext.xml
classpath:/common-beans.xml
</param-value>
</context-param>
.
#RunWith(SpringJUnit4ClassRunner.class)
#ContextConfiguration(
locations = {"/applicationContext-test.xml", "common-beans.xml"})
You can also include common-beans.xml from both contexts using <import>, as suggested by skaffman.