Re: Reusing tapestry hibernate session in a thread
Sorry, it was a newbie mistake... I simplified my test and found that even a simple call to a service (no extra threads involved) was not being persisted, and the cause was the lack of adviseTransactions() method in the module. @Match("MyService") public static void adviseTransactions(HibernateTransactionAdvisor advisor, MethodAdviceReceiver receiver) { advisor.addTransactionCommitAdvice(receiver); } Thanks for your help -- View this message in context: http://tapestry.1045711.n5.nabble.com/Reusing-tapestry-hibernate-session-in-a-thread-tp5438833p5521766.html Sent from the Tapestry - User mailing list archive at Nabble.com. - To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org
Re: Reusing tapestry hibernate session in a thread
You will have to call commit directly, or via HibernateSessionManager. Have a look at how CommitAfterWorker uses HibernateSessionManager. You need to do the same within your thread. On 28/02/2012 10:11 PM, fmaylinch wrote: Howard, I tried the ptm.run(...) idiom you posted and I found that the changes are not committed. How can I commit the changes I perform inside that thread? I suppose I can't add @CommitAfter to the method that starts the thread because that method will probably end before the thread. But I tried putting it on the Runnable run() method (which is called by the ptm), and that doesn't commit changes either. -- View this message in context: http://tapestry.1045711.n5.nabble.com/Reusing-tapestry-hibernate-session-in-a-thread-tp5438833p5521521.html Sent from the Tapestry - User mailing list archive at Nabble.com. - To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org - To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org
Re: Reusing tapestry hibernate session in a thread
Howard, I tried the ptm.run(...) idiom you posted and I found that the changes are not committed. How can I commit the changes I perform inside that thread? I suppose I can't add @CommitAfter to the method that starts the thread because that method will probably end before the thread. But I tried putting it on the Runnable run() method (which is called by the ptm), and that doesn't commit changes either. -- View this message in context: http://tapestry.1045711.n5.nabble.com/Reusing-tapestry-hibernate-session-in-a-thread-tp5438833p5521521.html Sent from the Tapestry - User mailing list archive at Nabble.com. - To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org
Re: Reusing tapestry hibernate session in a thread
Ok, I didn't know that one, thanks. But what about injecting the Dao (service) outside of the thread and using it inside and outside of the thread? Surely the same dao object will be used in both cases, and therefore the same session (since it is injected per thread the first time, not the second ? Therefore what I'm doing above is wrong and I should acquire the Dao within the context of the thread? And if thats the case I will need to grab a reference to the Registry outside of the thread and then use it to give me a Dao inside the thread? Thanks, Paul. On 28/02/2012 5:47 AM, Howard Lewis Ship wrote: Using PerthreadManager.run() is more convenient. i.e. new Thread("MyThread") { public void run() { ptm.run(new Runnable() { public void run() { List stuff = dao.getSomething(); doSomethingWithIt(stuff); } }); }; If I was doing this a lot, I'd create a service or base class to make it more concise. On Mon, Feb 27, 2012 at 2:29 AM, Greg Pagendam-Turner wrote: Thanks for your thoughts Paul Regards, Greg On 27/02/2012, at 4:37 PM, Paul Stanton wrote: Hi Greg, The following seems to work, although I'm not entirely sure if it should !! If the tapestry IOC geniuses agree, it is quite elegant and you can @Inject Session within your DaoImpl. Basically, injecting the PerthreadManager allows you to tell tapestry-ioc that your thread is complete. This will perform all the necessary cleanup. You only need to do this when you create your own threads obviously. I'm just not sure if its the best idea to inject the Dao at the top level, since the object (and possibly session) would be re-used in both contexts. public class MyPage { @Inject private PerthreadManager ptm; @Inject private Dao dao; void setupRender() { dao.getSomething(); new Thread("MyThread") { @Override public void run() { try { List stuff = dao.getSomething(); doSomethingWithIt(stuff); } finally { ptm.cleanup(); } } }.start(); } } Can someone who knows please confirm or correct this theory please!! Thanks, Paul. On 29/01/2012 4:23 PM, Greg Pagendam-Turner wrote: In answer to my own question: Inject HibernateSessionSource and call its create() method to get a new session. public synchronized void execute(String url, String subject, SendEmail sendEmail, HibernateSessionSource sessionSource) { // For each mailout fetch url and send mailout logger.debug("BulkEmailerImpl.execute was called "); Session session = sessionSource.create(); userDAO = new UserDAOImpl(session); I just need to find a better way of instantiating the DAO. Regards, Greg ---- Original Message -------- Subject: Reusing tapestry hibernate session in a thread Date: Sun, 29 Jan 2012 11:28:41 +1000 From: Greg Pagendam-Turner Organization: Liftyourgame To: Tapestry users scheduled thread Hi, I have a batch job that sends email to users based on a query in my database. AppModule starts it up like so in a: @Startup public static void scheduleJobs(PeriodicExecutor executor, final BulkEmailer emailer, @Value("${liftyourgame.url}") String urlIn, @Value("${liftyourgame.subject}") String subjectIn, final SendEmail sendEmail ) { final String url = urlIn; final String subject = subjectIn; executor.addJob(new CronSchedule("0 0/5 * * * ?"), "BulkEmailer", new Runnable() { public void run() { emailer.execute(url + "/liftyourgame/", subject, sendEmail); } }); } In order to query the database the thread needs a hibernate session of its own as hibernate sessions are per thread. Currently it creates a session and DAO like so: public synchronized void execute(String url, String subject, SendEmail sendEmail) { // For each mailout fetch url and send mailout if (factory == null) { Configuration cfg = new Configuration(); factory = cfg.configure().buildSessionFactory(); } Session session = factory.openSession(); userDAO = new UserDAOImpl(session); / This means I need to add all of my entities in hibernate.cfg.xml: Tapestry doesn't seem to need these mappings for my web application as tapestry-hibernate seems to scan all classes in the entities package. Is there some way I could use tapestry-hibernate to setup a session for my thread? Regards, Greg
Re: Reusing tapestry hibernate session in a thread
Using PerthreadManager.run() is more convenient. i.e. new Thread("MyThread") { public void run() { ptm.run(new Runnable() { public void run() { List stuff = dao.getSomething(); doSomethingWithIt(stuff); } }); }; If I was doing this a lot, I'd create a service or base class to make it more concise. On Mon, Feb 27, 2012 at 2:29 AM, Greg Pagendam-Turner wrote: > Thanks for your thoughts Paul > > > Regards, > > Greg > > > On 27/02/2012, at 4:37 PM, Paul Stanton wrote: > >> Hi Greg, >> >> The following seems to work, although I'm not entirely sure if it should !! >> >> If the tapestry IOC geniuses agree, it is quite elegant and you can @Inject >> Session within your DaoImpl. >> >> Basically, injecting the PerthreadManager allows you to tell tapestry-ioc >> that your thread is complete. This will perform all the necessary cleanup. >> You only need to do this when you create your own threads obviously. >> >> I'm just not sure if its the best idea to inject the Dao at the top level, >> since the object (and possibly session) would be re-used in both contexts. >> >> public class MyPage { >> @Inject >> private PerthreadManager ptm; >> @Inject >> private Dao dao; >> >> void setupRender() { >> dao.getSomething(); >> >> new Thread("MyThread") { >> @Override >> public void run() { >> try { >> List stuff = dao.getSomething(); >> doSomethingWithIt(stuff); >> } >> finally { >> ptm.cleanup(); >> } >> } >> }.start(); >> } >> } >> >> Can someone who knows please confirm or correct this theory please!! >> >> Thanks, Paul. >> >> On 29/01/2012 4:23 PM, Greg Pagendam-Turner wrote: >>> In answer to my own question: >>> >>> Inject HibernateSessionSource and call its create() method to get a new >>> session. >>> >>> public synchronized void execute(String url, String subject, SendEmail >>> sendEmail, HibernateSessionSource sessionSource) { >>> // For each mailout fetch url and send mailout >>> logger.debug("BulkEmailerImpl.execute was called >>> "); >>> >>> Session session = sessionSource.create(); >>> userDAO = new UserDAOImpl(session); >>> >>> >>> I just need to find a better way of instantiating the DAO. >>> >>> Regards, >>> >>> Greg >>> >>> Original Message >>> Subject: Reusing tapestry hibernate session in a thread >>> Date: Sun, 29 Jan 2012 11:28:41 +1000 >>> From: Greg Pagendam-Turner >>> Organization: Liftyourgame >>> To: Tapestry users scheduled thread >>> >>> >>> >>> Hi, >>> >>> I have a batch job that sends email to users based on a query in my >>> database. >>> >>> AppModule starts it up like so in a: >>> >>> @Startup >>> public static void scheduleJobs(PeriodicExecutor executor, final >>> BulkEmailer emailer, >>> @Value("${liftyourgame.url}") >>> String urlIn, >>> @Value("${liftyourgame.subject}") >>> String subjectIn, >>> final SendEmail sendEmail >>> ) { >>> final String url = urlIn; >>> final String subject = subjectIn; >>> executor.addJob(new CronSchedule("0 0/5 * * * ?"), >>> "BulkEmailer", >>> new Runnable() { >>> public void run() { >>> emailer.execute(url + "/liftyourgame/", subject, >>> sendEmail); >>> } >>> }); >>> } >>> >>> In order to query the database the thread needs a hibernate session of >>> its own as hibernate sessions are per thread. >>> >>> Currently it creates a session and DAO like so: >>> >>> public synchronized void execute(String url, String subject, >>> SendEmail sendEmail) { >>> // For each mailout fetch url and send mailout >>> >&g
Re: Reusing tapestry hibernate session in a thread
Thanks for your thoughts Paul Regards, Greg On 27/02/2012, at 4:37 PM, Paul Stanton wrote: > Hi Greg, > > The following seems to work, although I'm not entirely sure if it should !! > > If the tapestry IOC geniuses agree, it is quite elegant and you can @Inject > Session within your DaoImpl. > > Basically, injecting the PerthreadManager allows you to tell tapestry-ioc > that your thread is complete. This will perform all the necessary cleanup. > You only need to do this when you create your own threads obviously. > > I'm just not sure if its the best idea to inject the Dao at the top level, > since the object (and possibly session) would be re-used in both contexts. > > public class MyPage { >@Inject >private PerthreadManager ptm; >@Inject >private Dao dao; > >void setupRender() { >dao.getSomething(); > >new Thread("MyThread") { >@Override >public void run() { >try { >List stuff = dao.getSomething(); >doSomethingWithIt(stuff); >} >finally { >ptm.cleanup(); >} >} >}.start(); >} > } > > Can someone who knows please confirm or correct this theory please!! > > Thanks, Paul. > > On 29/01/2012 4:23 PM, Greg Pagendam-Turner wrote: >> In answer to my own question: >> >> Inject HibernateSessionSource and call its create() method to get a new >> session. >> >>public synchronized void execute(String url, String subject, SendEmail >> sendEmail, HibernateSessionSource sessionSource) { >>// For each mailout fetch url and send mailout >>logger.debug("BulkEmailerImpl.execute was called >> "); >> >>Session session = sessionSource.create(); >> userDAO = new UserDAOImpl(session); >> >> >> I just need to find a better way of instantiating the DAO. >> >> Regards, >> >> Greg >> >> Original Message >> Subject: Reusing tapestry hibernate session in a thread >> Date: Sun, 29 Jan 2012 11:28:41 +1000 >> From: Greg Pagendam-Turner >> Organization: Liftyourgame >> To: Tapestry users scheduled thread >> >> >> >> Hi, >> >> I have a batch job that sends email to users based on a query in my >> database. >> >> AppModule starts it up like so in a: >> >>@Startup >>public static void scheduleJobs(PeriodicExecutor executor, final >> BulkEmailer emailer, >>@Value("${liftyourgame.url}") >> String urlIn, >>@Value("${liftyourgame.subject}") >> String subjectIn, >>final SendEmail sendEmail >>) { >>final String url = urlIn; >>final String subject = subjectIn; >>executor.addJob(new CronSchedule("0 0/5 * * * ?"), >> "BulkEmailer", >> new Runnable() { >> public void run() { >> emailer.execute(url + "/liftyourgame/", subject, >> sendEmail); >> } >> }); >>} >> >> In order to query the database the thread needs a hibernate session of >> its own as hibernate sessions are per thread. >> >> Currently it creates a session and DAO like so: >> >>public synchronized void execute(String url, String subject, >> SendEmail sendEmail) { >>// For each mailout fetch url and send mailout >> >>if (factory == null) { >>Configuration cfg = new Configuration(); >>factory = cfg.configure().buildSessionFactory(); >>} >> >>Session session = factory.openSession(); >>userDAO = new UserDAOImpl(session); >> >> >> / >> >> This means I need to add all of my entities in hibernate.cfg.xml: >> >> >> >> >> >> >> >> >> >> >> >> Tapestry doesn't seem to need these mappings for my web application as >> tapestry-hibernate seems to scan all classes in the entities package. >> >> Is there some way I could use tapestry-hibernate to setup a session for >> my thread? >> >> >> Regards, >> >> Greg >> >> >> - To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org
Re: Reusing tapestry hibernate session in a thread
Hi Greg, The following seems to work, although I'm not entirely sure if it should !! If the tapestry IOC geniuses agree, it is quite elegant and you can @Inject Session within your DaoImpl. Basically, injecting the PerthreadManager allows you to tell tapestry-ioc that your thread is complete. This will perform all the necessary cleanup. You only need to do this when you create your own threads obviously. I'm just not sure if its the best idea to inject the Dao at the top level, since the object (and possibly session) would be re-used in both contexts. public class MyPage { @Inject private PerthreadManager ptm; @Inject private Dao dao; void setupRender() { dao.getSomething(); new Thread("MyThread") { @Override public void run() { try { List stuff = dao.getSomething(); doSomethingWithIt(stuff); } finally { ptm.cleanup(); } } }.start(); } } Can someone who knows please confirm or correct this theory please!! Thanks, Paul. On 29/01/2012 4:23 PM, Greg Pagendam-Turner wrote: In answer to my own question: Inject HibernateSessionSource and call its create() method to get a new session. public synchronized void execute(String url, String subject, SendEmail sendEmail, HibernateSessionSource sessionSource) { // For each mailout fetch url and send mailout logger.debug("BulkEmailerImpl.execute was called "); Session session = sessionSource.create(); userDAO = new UserDAOImpl(session); I just need to find a better way of instantiating the DAO. Regards, Greg Original Message Subject: Reusing tapestry hibernate session in a thread Date: Sun, 29 Jan 2012 11:28:41 +1000 From: Greg Pagendam-Turner Organization: Liftyourgame To: Tapestry users scheduled thread Hi, I have a batch job that sends email to users based on a query in my database. AppModule starts it up like so in a: @Startup public static void scheduleJobs(PeriodicExecutor executor, final BulkEmailer emailer, @Value("${liftyourgame.url}") String urlIn, @Value("${liftyourgame.subject}") String subjectIn, final SendEmail sendEmail ) { final String url = urlIn; final String subject = subjectIn; executor.addJob(new CronSchedule("0 0/5 * * * ?"), "BulkEmailer", new Runnable() { public void run() { emailer.execute(url + "/liftyourgame/", subject, sendEmail); } }); } In order to query the database the thread needs a hibernate session of its own as hibernate sessions are per thread. Currently it creates a session and DAO like so: public synchronized void execute(String url, String subject, SendEmail sendEmail) { // For each mailout fetch url and send mailout if (factory == null) { Configuration cfg = new Configuration(); factory = cfg.configure().buildSessionFactory(); } Session session = factory.openSession(); userDAO = new UserDAOImpl(session); / This means I need to add all of my entities in hibernate.cfg.xml: Tapestry doesn't seem to need these mappings for my web application as tapestry-hibernate seems to scan all classes in the entities package. Is there some way I could use tapestry-hibernate to setup a session for my thread? Regards, Greg - To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org
Re: Reusing tapestry hibernate session in a thread
In answer to my own question: Inject HibernateSessionSource and call its create() method to get a new session. public synchronized void execute(String url, String subject, SendEmail sendEmail, HibernateSessionSource sessionSource) { // For each mailout fetch url and send mailout logger.debug("BulkEmailerImpl.execute was called "); Session session = sessionSource.create(); userDAO = new UserDAOImpl(session); I just need to find a better way of instantiating the DAO. Regards, Greg Original Message Subject: Reusing tapestry hibernate session in a thread Date: Sun, 29 Jan 2012 11:28:41 +1000 From: Greg Pagendam-Turner Organization: Liftyourgame To: Tapestry users scheduled thread Hi, I have a batch job that sends email to users based on a query in my database. AppModule starts it up like so in a: @Startup public static void scheduleJobs(PeriodicExecutor executor, final BulkEmailer emailer, @Value("${liftyourgame.url}") String urlIn, @Value("${liftyourgame.subject}") String subjectIn, final SendEmail sendEmail ) { final String url = urlIn; final String subject = subjectIn; executor.addJob(new CronSchedule("0 0/5 * * * ?"), "BulkEmailer", new Runnable() { public void run() { emailer.execute(url + "/liftyourgame/", subject, sendEmail); } }); } In order to query the database the thread needs a hibernate session of its own as hibernate sessions are per thread. Currently it creates a session and DAO like so: public synchronized void execute(String url, String subject, SendEmail sendEmail) { // For each mailout fetch url and send mailout if (factory == null) { Configuration cfg = new Configuration(); factory = cfg.configure().buildSessionFactory(); } Session session = factory.openSession(); userDAO = new UserDAOImpl(session); / This means I need to add all of my entities in hibernate.cfg.xml: Tapestry doesn't seem to need these mappings for my web application as tapestry-hibernate seems to scan all classes in the entities package. Is there some way I could use tapestry-hibernate to setup a session for my thread? Regards, Greg
Reusing tapestry hibernate session in a thread
Hi, I have a batch job that sends email to users based on a query in my database. AppModule starts it up like so in a: @Startup public static void scheduleJobs(PeriodicExecutor executor, final BulkEmailer emailer, @Value("${liftyourgame.url}") String urlIn, @Value("${liftyourgame.subject}") String subjectIn, final SendEmail sendEmail ) { final String url = urlIn; final String subject = subjectIn; executor.addJob(new CronSchedule("0 0/5 * * * ?"), "BulkEmailer", new Runnable() { public void run() { emailer.execute(url + "/liftyourgame/", subject, sendEmail); } }); } In order to query the database the thread needs a hibernate session of its own as hibernate sessions are per thread. Currently it creates a session and DAO like so: public synchronized void execute(String url, String subject, SendEmail sendEmail) { // For each mailout fetch url and send mailout if (factory == null) { Configuration cfg = new Configuration(); factory = cfg.configure().buildSessionFactory(); } Session session = factory.openSession(); userDAO = new UserDAOImpl(session); / This means I need to add all of my entities in hibernate.cfg.xml: Tapestry doesn't seem to need these mappings for my web application as tapestry-hibernate seems to scan all classes in the entities package. Is there some way I could use tapestry-hibernate to setup a session for my thread? Regards, Greg - To unsubscribe, e-mail: users-unsubscr...@tapestry.apache.org For additional commands, e-mail: users-h...@tapestry.apache.org