Someone know how to add a another datasource in hibernate configuration and how to configure Spring to that datasource its autoinject in my respective DAO?
This is my code with one datasource, that run perfectly, but i don't know how add another datasource. I want to add another data source that is a database with different tables than the actual database.
HIBERNATE CONF
<bean id="dataSource" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<property name="driverClassName">
<value>com.mysql.jdbc.Driver</value>
</property>
<property name="url" value="jdbc:mysql://localhost/personal"/>
<property name="username" value="root"/>
<property name="password" value="mysql"/>
</bean>
<bean id="sessionFactory" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
<property name="dataSource">
<ref local="dataSource"/>
</property>
<property name="packagesToScan">
<list>
<value>com.app.personal.model</value>
</list>
</property>
<property name="hibernateProperties">
<props>
<prop key="hibernate.dialect">org.hibernate.dialect.MySQLDialect</prop>
<prop key="hibernate.show_sql">false</prop>
</props>
</property>
</bean>
<tx:annotation-driven/>
<bean id="transactionManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory">
<ref local="sessionFactory"/>
</property>
</bean>
DAO EXAMPLE
@Repository
public class ModuloDAOHibernate extends HibernateTemplate implements ModuloDAO {
@Autowired
public ModuloDAOHibernate(SessionFactory sessionFactory) {
super(sessionFactory);
}
public List<Modulo> getAllGrupoModuloDAO() {
Criteria criteriaList = this.getSession().createCriteria(Modulo.class);
criteriaList.addOrder(Order.asc("orden"));
return criteriaList.list();
}
In hibernate we can interact with multiple databases within the same application. All we need is to create two different session factories; one to interact with each database.
To communicate with another database server, you need another hibernate configuration file similar to hibernate. cfg. xml. For example, let's say we have a MySQL database server and a Microsoft SQL database server that will be used in an application.
Usually one session factory should be created for one database. When you have multiple databases in your application you should create multiple SessionFactory object. SessionFactory sc=cfg.
Multiple Databases in Spring BootSpring Boot can simplify the configuration above. Now we have defined the data source properties inside persistence-multiple-db-boot. properties according to the Boot autoconfiguration convention.
I assume you have a set of DAOs that should use dataSource1
and appropriate sessionFactory1
, while others should use different dataSouce2
and sessionFactory2
based on dataSource2
. Of course you need to declare your second dataSource
and other beans: simply copy the configuration you already have and change bean ids so they won't collide. Everything should be mirrored except <tx:annotation-driven/>
:
<bean id="dataSource1" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<!-- ... -->
</bean>
<bean id="sessionFactory1" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
<property name="dataSource" ref="dataSource1"/>
<!-- ... -->
</bean>
<bean id="transactionManager1" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory1"/>
<!-- ... -->
</bean>
<bean id="dataSource2" class="org.springframework.jdbc.datasource.DriverManagerDataSource">
<!-- ... -->
</bean>
<bean id="sessionFactory2" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean">
<property name="dataSource" ref="dataSource2"/>
<!-- ... -->
</bean>
<bean id="transactionManager2" class="org.springframework.orm.hibernate3.HibernateTransactionManager">
<property name="sessionFactory" ref="sessionFactory2"/>
<!-- ... -->
</bean>
<tx:annotation-driven transaction-manager="transactionManager1"/>
And here comes the real problem: you now have two transaction managers bound to different session factories, which in turns are routed to different data sources. But @Transactional
annotations will always use only one transaction manager - the one named transactionManager
by default (note I explicitly pointed transactionManager1
. This means that DAOs using second data source will participate in transactions started within first data source - this is obviously not what intended.
There are some workaround to this, like explicitly defining transaction manager name in @Transactional
annotation (never tried it) or using TransactionTemplate
, but as you can see problem should be well thought.
As for autowiring - if you autowire by name, name your fields the same as session factories or data sources ids and it should work - but is your smallest problem actually.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With