• Post Reply Bookmark Topic Watch Topic
  • New Topic
programming forums Java Mobile Certification Databases Caching Books Engineering Micro Controllers OS Languages Paradigms IDEs Build Tools Frameworks Application Servers Open Source This Site Careers Other Pie Elite all forums
this forum made possible by our volunteer staff, including ...
Marshals:
  • Campbell Ritchie
  • Tim Cooke
  • paul wheaton
  • Jeanne Boyarsky
  • Ron McLeod
Sheriffs:
  • Paul Clapham
  • Liutauras Vilda
  • Devaka Cooray
Saloon Keepers:
  • Tim Holloway
  • Roland Mueller
Bartenders:

Trouble converting a Spring JDBC app to use Spring Hibernate

 
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Hi, I have a Spring application working with Spring JDBC and I'm trying to convert it to use Hibernate but I can't seem to get the Spring configuration right.

My application context file has the configuration for Hibernate connecting to a MySQL database. I want to use full annotations so my beans are not defined. Here is the config file:


Here is my data access class:



If I run the code like this I get the following error on the getCurrentSession() line:
No Hibernate Session bound to thread, and configuration does not allow creation of non-transactional one here

I've done much searching on the internet and trying various examples. I found suggestions adding the following property.
<prop key="hibernate.current_session_context_class">thread</prop>

When I do that I get the following error on the createQuery line:
createQuery is not valid without active transaction

Any suggestions as to what is wrong with my configuration?

Many Thanks,
Ray
 
ranger
Posts: 17347
11
Mac IntelliJ IDE Spring
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
No interface and therefore no transactions.

Transactions should belong set at the Use Case level so that Spring can better manage Connections, TransactionContext across a Use Case.

Anyway, I recommend creating an interface for your Repository and Service classes. Add @Transactional on your @Service classes and have your service class call the Repository.

However, you can still put @Transactional on your Repository, you just still need to create an interface for it and have your Repository implement it.

Also, I thought

<property name="packagesToScan" value="com.home.dvdtracker.domain" />

that property takes a List or an Array?

Thanks

Mark
 
Mark Spritzler
ranger
Posts: 17347
11
Mac IntelliJ IDE Spring
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I also recommend debugging your code through the debugger. Set a break point where you have a reference to the Repository. Look at the debugger for local variables and look at the repository. Is the type your Repository or is it a Proxy. It would be a Proxy if Transactionality was added to it.

Mark
 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
I've seen examples where the @Transactional annotation is in the DAO and I've seen it in the Service class. The Pro Spring 3 book that I have has it in the DAO class although it makes more sense to me to have it in the service. Ok, so I changed it to be in the service which does implement an interface. I also changed the packages to scan property to be:



This did not make a difference in the error message that I am getting.

I am using NetBeans and am not familiar with the debugger. I'll work on trying to get that hooked up and see what it can tell me.

Thank you for your post.
 
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
You do not need the .* on the packages to scan. This will scan sub packages.

Remove this property




You are overriding Spring which sets this to SpringSessionContext.class. If you want Spring to manage things you should not set that.

What Mark is explaining is by default Spring uses an interface based proxy. Therefore if you are going to use the @Transactional annotation and you want it to work properly you need to expose the method through an interface and access it through that interface. It is good programming style to code to interfaces anyway. You can have @Transactionals on the DAO and Service layer if you want.

That said if you want want class based proxies that is an option too but I would not worry about that just yet.

See this thread as well for a similar discussion in the ORM forum.
https://coderanch.com/t/590071/ORM/databases/org-hibernate-SessionException-Session-closed
 
Bill Gorder
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Sorry I responded without reading closely. That package scan is on AnnotationSessionFactoryBean that will not scan sub-packages. Use something like this.

 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Well, I tried to follow your reply and the information in the link that you provided. My error now is:



Here is what the application context file looks like now:



I now have @Transactional in my service class and it implements an interface. Here is what it looks like:



The error occurs in the DAO so I will post it here also:



Thank you for your help.

Ray
 
Bill Gorder
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Sorry I did not mean to confuse you with that other link. Do use the AnnotationSessionFactoryBean rather than the LocalSessionFactoryBean like you originally had if you intend to use Hibernate’s annotation support.

The DriverManagerDataSource is overly basic and worthless for anything other than testing. I would consider changing that to at least use apaches BasicDataSource. You might want to set the default auto commit to false on it as well.



The rest of your config looks OK. Do add an interface for your repository and call (and autowire) by the interface not the implementation. Please show us the code that calls your service. Is your service autowired in? How are you creating it? Make sure that everything is a Spring managed bean no uses of the word 'new'.

You might also try adding this to your hibernate properties, if the above suggestions don't help.

 
Bill Gorder
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Also I notice you are using MySQL make sure you are using InnoDB and use the more specific MySQLInnoDBDialect
 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thank you, but still no luck. I'm still getting the same error message:



My application context now looks like this:



As requested, I added an interface to the repository. Here is the full path of code. This is the Controller class. It has the service interface wired in.



Here is the service implementation class. It has the repository interface wired in.



Here is the repository implementation class.



Should the @Repository and @Service annotations reference the interface name or the implementation name?

It is throwing an exception on the line:


Can you tell what I have wrong?

Thanks,
Ray
 
Bill Gorder
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Odd maybe I am falling asleep at the keyboard but I am not seeing the problem. You can drop the proxy-target-class="true", with what you are doing that should not be necessary. How many contexts do you have can you post your web.xml?
 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Thank you for the reply. Here is my web.xml file:

 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Am I missing a Spring filter of some kind?

Thanks,
Ray
 
Bill Gorder
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Ok so you must have a dispatcher-servlet.xml as well what is in that?
 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Here is the dispatcher-servlet.xml file.

I tried to separate all of the DB related config into the applicationContext file. Maybe there is a conflict with this file someplace.

 
Bill Gorder
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Yup there is your problem. You will have 2 instances of your beans due to your component scanning. In your dispatcher-servlet.xml you should only be scanning the controllers only therefore remove all the component scans from dispatcher-servlet.xml except this one.




Remember that the dispatcher servlet has its own context. The scanning of services and repositories should be in the root context only. I am actually not even sure why you are scanning the domain package at all, seems to me that nothing that is going to be picked up on a component scan should be in that package.
 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Ok, I took out the component scan tags from the application context file. When I took all of the component scan tags out of the dispatcher servlet file except for the reference to the controller package I got the error:

I added the component scan for the service package to the dispatcher servlet and then I got the following error for the data access object

I added the component scan for the hibernate package to the dispatcher servlet and then I got the same error that I have been getting:

I also moved the component scan for the hibernate package to the application context and still got the No Hibernate Session bound error.

Thanks,
Ray
 
Bill Gorder
Bartender
Posts: 1682
7
Android Mac OS X IntelliJ IDE Spring Linux
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Oh yeah sorry about that

applicationContext.xml


dispatcher-servlet.xml



 
Ray Clark
Ranch Hand
Posts: 55
  • Mark post as helpful
  • send pies
    Number of slices to send:
    Optional 'thank-you' note:
  • Quote
  • Report post to moderator
Success.

I now am past my Hibernate configuration problem and can start debugging my data access code.

Thank you so much for your help and patience.

Ray
 
She'll be back. I'm just gonna wait here. With this tiny ad:
Smokeless wood heat with a rocket mass heater
https://woodheat.net
reply
    Bookmark Topic Watch Topic
  • New Topic