Getting the entity manager - spring

i'm using spring data jpa but i want execute some costume query so how can i get the entity manager in my java classes to make entityManager.createQuery(..)
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="persistenceUnitName" value="persistenceYous" />
<property name="dataSource" ref="dataSource" />
<property name="packagesToScan" value="persistence" />
<property name="jpaVendorAdapter" ref="jpaVendorAdapter" />
</bean>

You can obtain your EntityManager as in any other spring application:
public class ProductDaoImpl implements ProductDao {
private EntityManager em;
#PersistenceContext
public void setEntityManager(EntityManager em) {
this.em = em;
}
public Collection loadProductsByCategory(String category) {
em. ....
....
}
}
See: http://docs.spring.io/spring/docs/4.0.0.RELEASE/spring-framework-reference/html/orm.html#orm-jpa-straight

In your applicationContext.xml, check that you have the following:
<context:annotation-config />
That will add support for several annotations, such as #PersistenceContext, that injects an EntityManager. So in your Spring-managed beans, you can do:
public class MyClass {
private EntityManager entityManager;
#PersistenceContext
public void setEntityManager(EntityManager em) {
this.entityManager = em
}
public void myMethod() {
Query q = entityManager.createQuery(...);
// ...
}
}
If you want to add suport for just #PersistenceContext, and not the other annotations that <context:annotation-config /> supports, you would delete that from the applicationContext.xml and add the specific BeanPostProcessor:
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" scope="singleton">
<!-- Optional configuration of PersistenceAnnotationBeanPostProcessor, for advanced use cases -->
</bean>

Firstly follow this link to get the steps required to implement..
check this link
In second step he uses #Autowired private JdbcOperations operations;
But that doesn't work for me, so i used the following code.. Which worked for me.
#Component
public class MayorRepositoryImpl extends JdbcDaoSupport implements MayorRepositoryCustom {
#Override
public List<Employee> getUsers(String role) {
return getJdbcTemplate().query("Write your custom query",new RowMapper<Employee>(){
#Override
public Employee mapRow(ResultSet rs, int rownumber) throws SQLException {
// Mapping each row and adding to list and returning the list
Employee employeeBean=new Employee();
employeeBean.setId(rs.getInt("id"));
employeeBean.setEmployeeNumber(rs.getString("employeeNumber"));
employeeBean.setName(rs.getString("name"));
employeeBean.setWorkEmailAddress(rs.getString("workEmailAddress"));
employeeBean.setPersonalEmailAddress(rs.getString("personalEmailAddress"));
return employeeBean;
}
});
}
}
This is perfectly working for me..
If you find any difficulty let me know to help you.
Cheers

Related

Spring not roll back transaction if exception throws in the application

I developed the application using spring transactions and insert records in the table.
I'm explicitly throwing the exception in DAO class but spring is inserting the record into the table rather than roll back the transaction.
I have created the two applications as below . In Case 1 record is inserted into table even though exception is thrown . But In Case 2 no record is inserted and spring roll back the transaction successfully. Can you explain me the difference between these two applications.
Case 1:
Item.java
public class Item {
int itemNo;
String itemName;
String itemType;
String itemSize;
public int getItemNo() {
return itemNo;
}
public void setItemNo(int itemNo) {
this.itemNo = itemNo;
}
public String getItemName() {
return itemName;
}
public void setItemName(String itemName) {
this.itemName = itemName;
}
public String getItemType() {
return itemType;
}
public void setItemType(String itemType) {
this.itemType = itemType;
}
public String getItemSize() {
return itemSize;
}
public void setItemSize(String itemSize) {
this.itemSize = itemSize;
}
}
ItemDao
#Service
public class ItemDao {
#Autowired
JdbcTemplate jdbcTemplate ;
void insert(Item item){
jdbcTemplate.update("insert into item_test(itemno, itemtype,itemsize,itemname) values (?,?,?,?)", new Object[]{item.getItemNo(),item.getItemType(),item.getItemSize(),item.getItemName()});
int a=2/0;
}
}
ItemService.java
#Service
public class ItemService {
#Autowired
ItemDao itemDao;
#Transactional
public void insert(Item item){
try{
itemDao.insert(item);
}
catch(Exception e){
e.printStackTrace();
}
}
}
Test.java
public class Test {
public static void main(String[] args) {
// TODO Auto-generated method stub
ApplicationContext ct = new ClassPathXmlApplicationContext("spring.xml");
ItemService itemService = ct.getBean("itemService", ItemService.class);
Item item = new Item();
item.setItemNo(1234);
item.setItemName("sofa");
item.setItemSize("4");
item.setItemType("furniture");
itemService.insert(item);
}
}
spring.xml
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans" xmlns:context="http://www.springframework.org/schema/context" xmlns:tx="http://www.springframework.org/schema/tx" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context.xsd http://www.springframework.org/schema/tx http://www.springframework.org/schema/tx/spring-tx.xsd">
<!-- Enable Annotation based Declarative Transaction Management -->
<tx:annotation-driven proxy-target-class="true" transaction-manager="transactionManager" />
<context:component-scan base-package="com.spring.springtransaction" />
<!-- Creating TransactionManager Bean, since JDBC we are creating of type
DataSourceTransactionManager -->
<bean id="transactionManager" class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSource" />
</bean>
<!-- MySQL DB DataSource -->
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName" value="oracle.jdbc.OracleDriver" />
<property name="url" value="jdbc:oracle:thin:#locahost:1521:xe)))" />
<property name="username" value="system" />
<property name="password" value="system" />
</bean>
<bean id="jdbcTemplate" class="org.springframework.jdbc.core.JdbcTemplate">
<property name="dataSource" ref="dataSource" />
</bean>
<bean id="itemService" class="com.spring.springtransaction.ItemService" />
</beans>
Case 2:
ItemService.java
#Service
public class ItemService {
#Autowired
ItemDao itemDao;
#Autowired
ItemManger itemManger;
#Transactional
public void insert(Item item){
try{
itemManger.insert(item);
}
catch(Exception e){
e.printStackTrace();
}
}
}
ItemManger.java
#Service
public class ItemManger {
#Autowired
ItemDao itemDao;
#Transactional
public void insert(Item item){
itemDao.insert(item);
}
}
ItemDao.java
#Service
public class ItemDao {
#Autowired
JdbcTemplate jdbcTemplate ;
void insert(Item item){
jdbcTemplate.update("insert into item_test(itemno, itemtype,itemsize,itemname) values (?,?,?,?)", new Object[]{item.getItemNo(),item.getItemType(),item.getItemSize(),item.getItemName()});
int a=2/0;
}
}
Annotate you ItemDao as #Repository instead of #Service
You should execute unit test with spring Transactional context instead of main , for example using TestNG:
#ContextConfiguration(classes = {ConfigurationClass.class})
#ActiveProfiles({"test"})
public class TestItemDAO extends AbstractTransactionalTestNGSpringContextTests {
#Autowired
private ItemDao dao;
#Test
public void testItemDao() {
dao.insert(item);
}
}
Remove the try block, you are trying to handle the exception so this is reason why RollbackException is not cutting the transaction stream.

Spring #Autowire retuning null while creating an object

I am new to this Spring and trying to learn it.
I am using basic auth jersey and using spring to inject my db props and instantiate the class. However I am getting null pointer exception when I try this with a REST call using postman.
Below is code snippet
AppContx.xml
<context:annotation-config />
<context:component-scan base-package="com.rest" />
<bean id="userDao" class="com.rest.dao.UserDao">
<property name="dataSource" ref="ds" />
</bean>
<bean id="ds" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiName" value="java:comp/env/jdbc/Weber" />
<property name="resourceRef" value="true" />
</bean>
Filter
#Provider
public class AuthenticationFilter implements ContainerRequestFilter {
/*ApplicationContext ctx = new ClassPathXmlApplicationContext("applicationContext.xml");
IuserDao userDao = (IuserDao) ctx.getBean("userDao");*/
#Autowired
UserDao userDao;
public void setUserDao(UserDao userDao) {
this.userDao = userDao;
}
public UserDao getUserDao() {
return userDao;
}
if (userDao.getUSerForAuthentication(password, username) == 1) {
String userRole = "ADMIN";
if (rolesSet.contains(userRole)) {
isAllowed = true;
}
DAO
#Autowired
private DataSource dataSource;
public void setDataSource(DataSource dataSource) {
this.dataSource = dataSource;
}
I am successfully able to inject DB properties to my data source using #Autowired but I am unable to instantiate the UserDao in my Filter class.
Thank You
Mark

Spring autowiring not working, getting `applicationDao` as null

Below are my classes and xml:
#Component
#Service("ApplicationService")
public class ApplicationServiceImpl implements ApplicationService{
public ApplicationDao getApplicationDao() {
return applicationDao;
}
public void setApplicationDao(ApplicationDao applicationDao) {
this.applicationDao = applicationDao;
}
#Autowired
private ApplicationDao applicationDao;
// some methods..
}
#Service
public interface ApplicationService {
// methods...
}
#Component
#Repository("ApplicationDao")
public class ApplicationDaoImpl implements ApplicationDao {
#Autowired
private SessionFactory sessionFactory;
public SessionFactory getSessionFactory() {
return sessionFactory;
}
public void setSessionFactory(SessionFactory sessionFactory) {
this.sessionFactory = sessionFactory;
}
// other methods...
}
public interface ApplicationDao {
// methods...
}
xml file:
<bean id="transactionManager"
class="org.springframework.orm.hibernate4.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory" />
</bean>
<tx:annotation-driven/>
<context:component-scan base-package="com" />
<bean id="sessionFactory" class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
<!-- <property name="dataSource" ref="dataSource" /> -->
<property name="configLocation">
<value>classpath:hibernate.cfg.xml</value>
</property>
</bean>
<bean id="ApplicationDao" class="com.dao.impl.ApplicationDaoImpl"/>
<bean id="ApplicationService" class="com.service.impl.ApplicationServiceImpl"/>
Here autowiring is not working.in ApplicationServiceImpl, I am getting applicationDao as null. Have not tested sessionFactory in ApplicationDaoImpl.
I know that if I am using #Component then bean declaration in xmnl is not required.
You should not instantiate service like that..
At the time of application loading, spring container will create all instances defined in spring.xml or annotated classes and it's dependencies..
So you have to access them with the following example code..
ApplicationContext applicationContext = ApplicationContextProvider.getApplicationContext();
ApplicationService applicationService = (ApplicationService) applicationContext.getBean("ApplicationService");
Since ApplicationService is having property that is ApplicationServiceDAOImpl, it's already been created by spring container and will return you..
But in case of directly instantiating manually by you, you are just creating instance of ApplicationService but not for ApplicationServiceDAOImpl.. so it obviously returns null
I'm currently using this approach only to access beans or services..
update for comment
public class ApplicationContextProvider implements ApplicationContextAware {
private static ApplicationContext applicationContext;
#Override
public void setApplicationContext(ApplicationContext arg0)
throws BeansException {
applicationContext = arg0;
}
public static ApplicationContext getApplicationContext() {
return applicationContext;
}
}
Hope it helps,
try a change like this:
import org.springframework.beans.factory.annotation.Qualifier;
#Autowired
#Qualifier("ApplicationDao")
private ApplicationDao applicationDao;
this give spring a hint.
If you are using annotations in your application, you should denote it using a tag :
<mvc:annotation-driven />
Add this line in application context xml above component scan tag.
Also, if you are using annotations, remove ApplicationDao and ApplicationService bean declarations from xml.
And don't mark you service and dao classes with both #Component and #Service or #Repository annotations. No need to mark them #Component there. Remove it.

JPA - Entities are not stored in database

I am facing a problem, when I tried to insert a data into Database through JPA (#persistanceContex)
Observations
Not getting any errors;
Record is not storing into database (save)
When I tried with listAll() ; it retrieving the data from database
Domain
#Entity
public class Test {
#Id
private int id;
#Column(name="full_name")
private String fullName;
#Column(name="mobile_number")
private int mobileNumber;
.....
}
DAO Class
#Repository("testDAO")
#Transactional
public class TestDAO {
private EntityManager entityManager;
#PersistenceContext(unitName="CRUD_Test_Annotation")
public void setEntityManager(EntityManager entityManager) {
this.entityManager = entityManager;
}
public void save(Test test){
entityManager.persist(test);
}
}
Service
#Service("testService")
#Transactional
public class TestService {
private static final Logger logger = LoggerFactory.getLogger(TestService.class);
#Autowired(required=true)
private TestDAO testDAO;
public void save(Test test){
logger.info("TestService::save()");
testDAO.save(test);
}
public void list(){
testDAO.getAll();
}
}
Controller
#RequestMapping(value = "/add", method = RequestMethod.GET)
public String add(Locale locale, Model model) {
Test test = new Test();
test.setId(xx);
test.setFullName("xxxxx");
test.setMobileNumber(yyyyyy);
testService.save(test);
return "home";
}
application-context.xml
<tx:annotation-driven transaction-manager="transactionManager" />
<!-- Declare a JPA entityManagerFactory-->
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="persistenceXmlLocation" value="classpath*:META-INF/persistence.xml"></property>
<property name="persistenceUnitName" value="CRUD_Test_Annotation" />
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="showSql" value="true" />
</bean>
</property>
</bean>
<!-- Declare a transaction manager-->
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory" />
</bean>
First of all, you don't need two transaction boundaries, I suggest you remove #Transactional from your DAO and keep the one in your service.
Start by verifying that spring-transaction has initiated a transaction: Use the debugger and stop the application after the transaction boundary, for instance in your TestService.save-method. If transactions are running, you will see org.springframework.transaction.interceptor.TransactionInterceptor#invoke in the call stack. If you don't see the TransactionInterceptor, then that's your problem. Post your persistence.xml file if transactions are running.

Create spring beans, based on a comma-separated list of classes

Is there a way in Spring to create a collection, or array, of beans, based on a comma-separated list of classes. For example:
package mypackage;
public class Bla {
private Set<MyBean> beans;
public void setBeans(Set<MyBean> beans) {
this.beans = beans;
}
}
With the application context:
<bean id="bla" class="mypackage.Bla">
<property name="beans">
<set>
<bean class="mypackage.Bean1, mypackage.Bean2" />
</set>
</property>
</bean>
Preferably the beans are all initialized and wired from the context, leaving the code as simplistic as possible, is this possible?
Use a combination of ApplicationContextAware and ApplicationListener:
public class BeanInitializer implements ApplicationContextAware, ApplicationListener<ContextRefreshedEvent> {
private ApplicationContext context;
private List<Class<?>> beanClasses;
public void onApplicationEvent(final ContextRefreshedEvent event) {
final AutowireCapableBeanFactory beanFactory = this.context.getAutowireCapableBeanFactory();
for (final Class<?> beanClass : this.beanClasses) {
beanFactory.autowire(beanClass, AutowireCapableBeanFactory.AUTOWIRE_BY_TYPE, true);
}
}
public void setApplicationContext(final ApplicationContext context) throws BeansException {
this.context = context;
}
public void setBeanClasses(final List<Class<?>> beanClasses) {
this.beanClasses = beanClasses;
}
}
in your spring config, do this:
<bean class="com.yourcompany.BeanInitializer">
<property name="beanClasses">
<list>
<value>com.yourcompany.Type1</value>
<value>com.yourcompany.Type2</value>
<value>com.yourcompany.Type3</value>
</list>
</property>
</bean>
Edited: Actually, if you want comma separated, it will probably be more like this:
<bean class="com.yourcompany.BeanInitializer">
<property name="beanClasses"
value="com.yourcompany.Type1,com.yourcompany.Type2,com.yourcompany.Type3" />
</bean>
I don't know if there is a built-in property editor that converts a comma delimited string to a list of classes but if not you can either create one yourself or change your setter method to accept a string and parse the string yourself

Resources