I am working on a multi-threaded Spring Boot/JPA/Hibernate project started by someone else. They have created 10 DAO classes and each one looks something like this:
#Repository
public class FirstDAO
{
#PersistenceContext
private EntityManager entityManager;
...
}
I am working on learning JPA & Hibernate, so I know the entity managers can persist different versions of the same data.
When we have that many DAO classes, are there other pitfalls we need to worry about? Thx!
Edit:
Since I am pretty new with JPA and multi-threading, I am mostly just nervous.
But a question I have is: if you want more than one #Repository for a database then do you have to create an interface that has the #PersistenceContext and then you implement the interface multiple times?
Related
Currently spring data has multiple db support (mysql, cassandra, mongo.. very big list), however i want to add my custom repository from the scratch like adding custom db support in spring data. I don't want to extend any existing repositories, instead I want to create a parallel repository strutcutre for my custom datasource. Looking at current implementation it looks like tedious task. It would be a great if someone could help me with minimal requirement to do this.
You could create a repository annotated bean where you would inject EntityManager or the proper bean that is acting like that, depending on database type that you are using.
#Repository
public class MyCustomRepositoryImpl implements MyCustomRepository {
#Autowired
private EntityManager entityManager;
//the methods that you are going to create.
}
For more details see:
https://docs.spring.io/spring-data/data-commons/docs/1.6.1.RELEASE/reference/html/repositories.html
Chapter: 1.3 Custom implementations for Spring Data repositories
My application is based on Spring Boot, Hibernate, MySQL using Spring Data JPA to stitch them.
Use case is to use slave db node for doing heavy read operations so as to avoid all traffic being served from master mysql node. One way of achieving this is to have multiple Entity Managers pointing to separate data sources(one to master and other to slave node). This way has been explained quite well in below SO questions and blogs.
Spring Boot, Spring Data JPA with multiple DataSources
https://scattercode.co.uk/2016/01/05/multiple-databases-with-spring-boot-and-spring-data-jpa/
Where I am stuck is to understand if there is a way I can inject different entity managers for different use cases in my Repository Annotated Interface.
The only way I see it can be done is extending repository with a custom implementation which gives uses custom entity manager annotated with relevant persistenceContext like below.
public interface CustomerRepository extends JpaRepository<Customer, Integer>, MyCustomCustomerRepository{
}
public class MyCustomCustomerRepositoryImpl implements MyCustomCustomerRepository {
#PersistenceContext(unitName = "entityManagerFactoryTwo")
EntityManager entityManager;
}
I would like to avoid doing this custom implementation. Any help around solving this use case(which I feel should be very common) would be appreciated.
NOTE: Entities are same in both databases so giving separate packages for entity scanning and similar solutions might not work.
Here is a nice sample you can use:
dynamic-datasource-routing-with-spring.
Inside you can find an AbstractRoutingDatasource + an interceptor for a custom annotation that wires the service method to a required database.
However you can just use datasource switch explicitly.
Below is the pull request that shows the diff and how I made it work with most configurations annotation driven instead of xml. It is based on cra6's answer above. i.e. using spring's RoutingDataSource capability.
https://github.com/himanshuvirmani/rest-webservice-sample/pull/1/files
I have experience building applications on the Spring Framework primarily. I was wondering if there was anything similar to the Spring Data API (to support a Data Access Layer) in the JEE6 space?
I know I can wire in an entity manager like:
#PersistenceContext
EntityManager em;
Ideally I would like to avoid writing reams of boiler plate JPA code on Data Access beans, is an API similar to SpringJPA which can help cut down on the amount of boilerplate code such as findAll(), findByX() etc. For example, with SpringJPA I can define a bean as:
#Repository
public interface FooRepository
extends JpaRepository<Foo, String>
{
}
Whereas in vanilla JEE6 I would need a
a FooRepository interface with methods Foo findOne(Long), List<Foo> findAll()
a FooRepositoryImpl which implements the interface and interacts with the EntityManager
Spring Data JPA ships with a CDI extension to simply #Inject a repository into your CDI managed bean. See the reference documentation for details. The approach still requires Spring JARs on the classpath but no container being bootstrapped. This functionality is also available for MongoDB repositories.
I have a question about spring + hibernate
I always use hibernate for my develeppoment, I generate images of the tables and the class DAO
then at logic metier I make simple calls to these methods dao ....
for exemple UserDao=new UserDao () then userdao.persist() ...
Now I have intgret spring, and I do not yet understand ..
1
what is the plus made by him knowing that he is also making calls
has dao Service (the writings that manually) it does not generate the
class dao with hibernate
2
is that with spring I would not worry about manage session for
example open session, close session commit() ...
thank you in advance I would like to have an idea Ccool:
At its core, Spring is a dependency injection framework. This means that instead of doing
public class MyService
private MyDao dao;
public MyService() {
dao = new MyDao();
}
}
You can do
public class MyService
private MyDao dao;
#Autowired
public MyService(MyDao dao) {
this.dao = dao;
}
}
And Spring will automatically call the constructor and inject an instance of MyDao. The main benefit is that the code is easily unit-testable.
On top of that, it allows injecting proxies instead of the actual implementations directly. These proxies will indeed handle the transaction management for you, and more (exception translation, security checks, etc.).
So instead of explicitely opening, committing and rollbacking transactions, you would simply annotate a service method with #Transactional, and Spring would open, commit/rollback the transaction. And the transaction context would automatically propagate to the nested service calls.
This short answer is only to give you an idea. To learn more, read about dependency injection, and read the Spring documentation.
Use Spring annotations like #Service for service classes, #Repository for Dao classes and #Controller for action controllers. Use of #Transactional on service class or methods is suffice to carry out transactions.
I am using the spring mvc3 in my applicatio,and in the dao layer I want to use jdbctemplate,however I do not know where to add the dao,in the controller?
For example:
#Controller
public class UserController{
private UserDao udao;
public String list(Model model){
udao=new UserDaoImple();
List<User> users=udao.list();
model.addAttrubut('users',users);
return "list";
}
}
The above code is just an example,I want to know where to create the userdao?
Also,since I want to use the jdbctemplate,and it is recommended that the jdbctemplate is created only once for one datasourece,so how to make all the daos use the same jdbctemplate?
You could use Spring IOC (dependency injection) to inject the DAO like this
#Autowired
UserDao userdao;
or you could use the repository pattern, and create a central point for all the DAOs so you just go to the repository and ask for the DAO you need.
for that you would have to create singleton class that has all instances of all DAOs and when asked give give an instance to your class, so you don't need to instantiate the Dao just do a
Repo.getUserDaoInstance();
In my opinion, go for the Spring approach you will learn a very useful skill and it's a lot easier to maintain when you know what you are doing.