Ben,
Actually I was thinking about what I wrote below and think maybe the
PROPER solution is to have Stripes FIXED to enforce the ordering of
classes in "Interceptor.Classes" w.r.t. "initialization" (in addition to
the ordering already enforced for "execution").
Would this be difficult to fix considering the ordering is already
handled for execution????
I have a test bed ready to go :-) AND clearly this would be the "right"
solution and I think an important more general fix for Stripes for other
future scenarios as Developers leverage interceptors more and more this
will become a necessity vs. a nice to have I suspect.
Thanks,
--Nikolaos
P.S. If you can point me to the code that does the initialization I can
take a look to see what I can provide....
Nikolaos Giannopoulos wrote:
Aaron / Frank,
While I realize I don't have to use Stripersist... I am quite happy
with it... and instead of chucking it and doing some things by hand I
am trying to figure out how I can make things work. I mean it is
providing some benefit (we have MANY Entities and MANY DAOs) and while
I agree that the EntityManagerFactory is something it indirectly
leverages I would hope to find a way to make Stripersist work in this
case... which I think is important.
With that said I have clearly identified the problem by running all
sorts of tests and debugging things.
The Stripersist interceptor never gets a chance to initialize itself
prior to the Spring interceptor no matter how I configure the web.xml
and the ordering of Interceptor.classes appears to only apply to
"execution" strictly - not in addition "initialization" - as some have
suggested.
Why is this a problem... because of the way Stripersist is coded...
Spring ends up calling my @PostConstruct which in turn calls:
protected List<T> load(String persistenceUnitName) {
return
Stripersist.getEntityManager(persistenceUnitName).createQuery("from "
+ this.entityClass.getName()).getResultList();
Which in turn calls:
public static EntityManager getEntityManager(String persistenceUnit) {
EntityManagerFactory factory =
getEntityManagerFactory(persistenceUnit);
Which in turn calls:
public static EntityManagerFactory getEntityManagerFactory(String
persistenceUnit) {
return entityManagerFactories.get(persistenceUnit); // [1]
and herein lies the problem... if Stripersist init() has not been
called then the following static attribute is NULL
static private Map<String, EntityManagerFactory>
entityManagerFactories;
It is the lack of initialization of this attribute using information
obtained by reading the persistence.xml, calling the Persistence
class, etc... that is the problem.
And to prove that... if we do the following in our @PostConstruct:
Stripersist s = new Stripersist();
s.init(StripesFilter.getConfiguration());
List<Modality> modalityList = this.modalityDao.findAll();
this.modalityCache = new ModalityCache();
this.modalityCache.init(modalityList);
Stripersist spits up 2 exceptions about being accessed outside any
request but now that the static attributes are initialized things work
from here. Of course defensively placing this code that spews 2
exceptions in each service bean is not acceptable but it proves the point.
Stripersist interceptor needs to be initialized BEFORE Spring
interceptor and Stripes does NOT seem to offer a configurable way to
force this.
Does anyone know how I can create a wrapper to dynamically:
--> Init and wire up Stripersist interceptor...
followed by....
--> Init and wire up Spring interceptor
I figure if I create a simple wrapper to force the ordering we should
be in business.
--Nikolaos
Aaron Porter wrote:
Hi Nikolaos,
What Frank is saying is you don't have to go through Stripersist to get
an EntityManager. The main purpose of Stripersist is to provide the
Formatter/TypeConverter for Stripes to handle entities. It also provides
a little security by beginning a transaction so that you must explicity
commit for changes to occur.
I don't use Spring but I'm sure there is some way to get an
EntityManager from Spring without going through Stripersist.
Aaron
On 05/27/2010 09:35 AM, Nikolaos Giannopoulos wrote:
Frank,
Comments in-line below...
Frank Pavageau wrote:
On Thu, May 27, 2010 at 5:23 PM, Nikolaos Giannopoulos
<nikol...@brightminds.org> wrote:
public class BaseActionBean implements ActionBean {
@SpringBean protected ModalityDao modalityDao;
...
@Repository("modalityDao")
public class ModalityDaoImpl extends BaseDaoImpl<Modality, Integer>
implements ModalityDao {
public List<Modality> findAll() {
return (this.load()); // [2]
}
@PostConstruct
private void init() {
this.findAll(); // [1]
}
<snip>
The problem is that you have objects instanciated by the 2 frameworks
with independent lifecycles :
- Spring instanciates the DAO at context initialization (triggered by
the listener)
- Stripes instanciates the Stripersist interceptor at filter
initialization, and the Spring context knows nothing about it
Sure. I get that.
You don't really need to use the Stripersist interceptor in your
BaseDaoImpl, you just want the EntityManagerFactory injected directly
instead. Stripersist also gets it from the Spring context anyway
(AFAIR, we use our own TypeConverter with a similar mechanism).
Sorry. Now you lost me :-) Sounds great but what "exactly" are you
suggesting?
Much appreciated!
--Nikolaos
------------------------------------------------------------------------------
_______________________________________________
Stripes-users mailing list
Stripes-users@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/stripes-users