You are viewing a plain text version of this content. The canonical link for it is here.
Posted to users@tomee.apache.org by James Green <ja...@gmail.com> on 2013/06/26 12:58:24 UTC
OpenJPA and ConcurrentHashMap
Hi,
We're observing some stack traces which I was not expecting.
Caused by: <openjpa-2.2.0-r422266:1244990 fatal internal error>
org.apache.openjpa.util.InternalException: Multiple concurrent threads
attempted to access a single broker. By default brokers are not thread
safe; if you require and/or intend a broker to be accessed by more than one
thread, set the openjpa.Multithreaded property to true to override the
default behavior.
at
org.apache.openjpa.kernel.BrokerImpl.endOperation(BrokerImpl.java:1956)
at
org.apache.openjpa.kernel.BrokerImpl.isActive(BrokerImpl.java:1904)
at
org.apache.openjpa.kernel.StateManagerImpl.beforeAccessField(StateManagerImpl.java:1610)
at
org.apache.openjpa.kernel.StateManagerImpl.accessingField(StateManagerImpl.java:1598)
Our application has a component that routinely reads @Entity instances from
a database table and puts them into a cache.
The cache component (an EJB) accepts these instances and places them into a
ConcurrentHashMap for instance retrieval by other processes.
Other components then have this cache instance injected into them and
perform a get on it to read values and do read-only work.
When the component that reads the entities from the database and puts them
all into the cache (overwriting any previous entries) runs, and other
components are also running, we can see the above stack trace and a
rollback occurs.
Can someone help me understand what is happening and how to re-work the
architecture to avoid this?
Thanks,
James
Re: OpenJPA and ConcurrentHashMap
Posted by Romain Manni-Bucau <rm...@gmail.com>.
that's what i'd do (cloneable or not, this signature is not so friendly
IIRC)
*Romain Manni-Bucau*
*Twitter: @rmannibucau <https://twitter.com/rmannibucau>*
*Blog: **http://rmannibucau.wordpress.com/*<http://rmannibucau.wordpress.com/>
*LinkedIn: **http://fr.linkedin.com/in/rmannibucau*
*Github: https://github.com/rmannibucau*
2013/6/26 James Green <ja...@gmail.com>
> So quick fix is to add Cloneable to the entity and call it when receiving
> instances into the map.
>
> Longer term fix is to replace ConcurrentHashMap with JPA access.
>
> Correct?
>
>
> On 26 June 2013 14:23, Romain Manni-Bucau <rm...@gmail.com> wrote:
>
> > Hi,
> >
> > first using the L2 cache should help then if you really want a "manual"
> > caching just recreate entities to cache (bean copy ;) and store the copy.
> > It will not be a real entity (jpa) anymore and it will work
> >
> > *Romain Manni-Bucau*
> > *Twitter: @rmannibucau <https://twitter.com/rmannibucau>*
> > *Blog: **http://rmannibucau.wordpress.com/*<
> > http://rmannibucau.wordpress.com/>
> > *LinkedIn: **http://fr.linkedin.com/in/rmannibucau*
> > *Github: https://github.com/rmannibucau*
> >
> >
> >
> > 2013/6/26 James Green <ja...@gmail.com>
> >
> > > Yeah although I didn't have JPA in my mind when I wrote it so the idea
> > they
> > > were "managed" didn't come into it. I guess that's the cause - the
> > > EntityManager from a past invocation has references to them and as it
> > > reloads them into the cache something, somewhere, is going bang.
> > >
> > > The rationale behind this cache is relatively simple. We have an
> existing
> > > PHP/MySQL service that gets hammered when API requests are made because
> > > each involves database queries for account information. To avoid this
> > > occurring in this new Java Enterprise service I wanted to maintain a
> > cache
> > > of accounts across many invocations, reloading that cache from the
> > database
> > > periodically.
> > >
> > > It could be that this cache is utterly redundant but back at the start
> I
> > > was not familiar with the connection pooling or JPA caching available
> so
> > I
> > > probably re-invented the wheel. If this is the case I can write out the
> > > cache and plumb in the persistence context.
> > >
> > > If the custom cache is however a good thing[tm] then an explanation of
> > > what's happening would be good to see.
> > >
> > > Thanks,
> > >
> > > James
> > >
> > >
> > > On 26 June 2013 12:30, Romain Manni-Bucau <rm...@gmail.com>
> wrote:
> > >
> > > > Hi
> > > >
> > > > Do you cache managed entities? If so maybe use dto
> > > > Le 26 juin 2013 12:58, "James Green" <ja...@gmail.com> a
> > écrit
> > > :
> > > >
> > > > > Hi,
> > > > >
> > > > > We're observing some stack traces which I was not expecting.
> > > > >
> > > > > Caused by: <openjpa-2.2.0-r422266:1244990 fatal internal error>
> > > > > org.apache.openjpa.util.InternalException: Multiple concurrent
> > threads
> > > > > attempted to access a single broker. By default brokers are not
> > thread
> > > > > safe; if you require and/or intend a broker to be accessed by more
> > than
> > > > one
> > > > > thread, set the openjpa.Multithreaded property to true to override
> > the
> > > > > default behavior.
> > > > > at
> > > > >
> > org.apache.openjpa.kernel.BrokerImpl.endOperation(BrokerImpl.java:1956)
> > > > > at
> > > > > org.apache.openjpa.kernel.BrokerImpl.isActive(BrokerImpl.java:1904)
> > > > > at
> > > > >
> > > > >
> > > >
> > >
> >
> org.apache.openjpa.kernel.StateManagerImpl.beforeAccessField(StateManagerImpl.java:1610)
> > > > > at
> > > > >
> > > > >
> > > >
> > >
> >
> org.apache.openjpa.kernel.StateManagerImpl.accessingField(StateManagerImpl.java:1598)
> > > > >
> > > > > Our application has a component that routinely reads @Entity
> > instances
> > > > from
> > > > > a database table and puts them into a cache.
> > > > >
> > > > > The cache component (an EJB) accepts these instances and places
> them
> > > > into a
> > > > > ConcurrentHashMap for instance retrieval by other processes.
> > > > >
> > > > > Other components then have this cache instance injected into them
> and
> > > > > perform a get on it to read values and do read-only work.
> > > > >
> > > > > When the component that reads the entities from the database and
> puts
> > > > them
> > > > > all into the cache (overwriting any previous entries) runs, and
> other
> > > > > components are also running, we can see the above stack trace and a
> > > > > rollback occurs.
> > > > >
> > > > > Can someone help me understand what is happening and how to re-work
> > the
> > > > > architecture to avoid this?
> > > > >
> > > > > Thanks,
> > > > >
> > > > > James
> > > > >
> > > >
> > >
> >
>
Re: OpenJPA and ConcurrentHashMap
Posted by James Green <ja...@gmail.com>.
So quick fix is to add Cloneable to the entity and call it when receiving
instances into the map.
Longer term fix is to replace ConcurrentHashMap with JPA access.
Correct?
On 26 June 2013 14:23, Romain Manni-Bucau <rm...@gmail.com> wrote:
> Hi,
>
> first using the L2 cache should help then if you really want a "manual"
> caching just recreate entities to cache (bean copy ;) and store the copy.
> It will not be a real entity (jpa) anymore and it will work
>
> *Romain Manni-Bucau*
> *Twitter: @rmannibucau <https://twitter.com/rmannibucau>*
> *Blog: **http://rmannibucau.wordpress.com/*<
> http://rmannibucau.wordpress.com/>
> *LinkedIn: **http://fr.linkedin.com/in/rmannibucau*
> *Github: https://github.com/rmannibucau*
>
>
>
> 2013/6/26 James Green <ja...@gmail.com>
>
> > Yeah although I didn't have JPA in my mind when I wrote it so the idea
> they
> > were "managed" didn't come into it. I guess that's the cause - the
> > EntityManager from a past invocation has references to them and as it
> > reloads them into the cache something, somewhere, is going bang.
> >
> > The rationale behind this cache is relatively simple. We have an existing
> > PHP/MySQL service that gets hammered when API requests are made because
> > each involves database queries for account information. To avoid this
> > occurring in this new Java Enterprise service I wanted to maintain a
> cache
> > of accounts across many invocations, reloading that cache from the
> database
> > periodically.
> >
> > It could be that this cache is utterly redundant but back at the start I
> > was not familiar with the connection pooling or JPA caching available so
> I
> > probably re-invented the wheel. If this is the case I can write out the
> > cache and plumb in the persistence context.
> >
> > If the custom cache is however a good thing[tm] then an explanation of
> > what's happening would be good to see.
> >
> > Thanks,
> >
> > James
> >
> >
> > On 26 June 2013 12:30, Romain Manni-Bucau <rm...@gmail.com> wrote:
> >
> > > Hi
> > >
> > > Do you cache managed entities? If so maybe use dto
> > > Le 26 juin 2013 12:58, "James Green" <ja...@gmail.com> a
> écrit
> > :
> > >
> > > > Hi,
> > > >
> > > > We're observing some stack traces which I was not expecting.
> > > >
> > > > Caused by: <openjpa-2.2.0-r422266:1244990 fatal internal error>
> > > > org.apache.openjpa.util.InternalException: Multiple concurrent
> threads
> > > > attempted to access a single broker. By default brokers are not
> thread
> > > > safe; if you require and/or intend a broker to be accessed by more
> than
> > > one
> > > > thread, set the openjpa.Multithreaded property to true to override
> the
> > > > default behavior.
> > > > at
> > > >
> org.apache.openjpa.kernel.BrokerImpl.endOperation(BrokerImpl.java:1956)
> > > > at
> > > > org.apache.openjpa.kernel.BrokerImpl.isActive(BrokerImpl.java:1904)
> > > > at
> > > >
> > > >
> > >
> >
> org.apache.openjpa.kernel.StateManagerImpl.beforeAccessField(StateManagerImpl.java:1610)
> > > > at
> > > >
> > > >
> > >
> >
> org.apache.openjpa.kernel.StateManagerImpl.accessingField(StateManagerImpl.java:1598)
> > > >
> > > > Our application has a component that routinely reads @Entity
> instances
> > > from
> > > > a database table and puts them into a cache.
> > > >
> > > > The cache component (an EJB) accepts these instances and places them
> > > into a
> > > > ConcurrentHashMap for instance retrieval by other processes.
> > > >
> > > > Other components then have this cache instance injected into them and
> > > > perform a get on it to read values and do read-only work.
> > > >
> > > > When the component that reads the entities from the database and puts
> > > them
> > > > all into the cache (overwriting any previous entries) runs, and other
> > > > components are also running, we can see the above stack trace and a
> > > > rollback occurs.
> > > >
> > > > Can someone help me understand what is happening and how to re-work
> the
> > > > architecture to avoid this?
> > > >
> > > > Thanks,
> > > >
> > > > James
> > > >
> > >
> >
>
Re: OpenJPA and ConcurrentHashMap
Posted by Romain Manni-Bucau <rm...@gmail.com>.
Hi,
first using the L2 cache should help then if you really want a "manual"
caching just recreate entities to cache (bean copy ;) and store the copy.
It will not be a real entity (jpa) anymore and it will work
*Romain Manni-Bucau*
*Twitter: @rmannibucau <https://twitter.com/rmannibucau>*
*Blog: **http://rmannibucau.wordpress.com/*<http://rmannibucau.wordpress.com/>
*LinkedIn: **http://fr.linkedin.com/in/rmannibucau*
*Github: https://github.com/rmannibucau*
2013/6/26 James Green <ja...@gmail.com>
> Yeah although I didn't have JPA in my mind when I wrote it so the idea they
> were "managed" didn't come into it. I guess that's the cause - the
> EntityManager from a past invocation has references to them and as it
> reloads them into the cache something, somewhere, is going bang.
>
> The rationale behind this cache is relatively simple. We have an existing
> PHP/MySQL service that gets hammered when API requests are made because
> each involves database queries for account information. To avoid this
> occurring in this new Java Enterprise service I wanted to maintain a cache
> of accounts across many invocations, reloading that cache from the database
> periodically.
>
> It could be that this cache is utterly redundant but back at the start I
> was not familiar with the connection pooling or JPA caching available so I
> probably re-invented the wheel. If this is the case I can write out the
> cache and plumb in the persistence context.
>
> If the custom cache is however a good thing[tm] then an explanation of
> what's happening would be good to see.
>
> Thanks,
>
> James
>
>
> On 26 June 2013 12:30, Romain Manni-Bucau <rm...@gmail.com> wrote:
>
> > Hi
> >
> > Do you cache managed entities? If so maybe use dto
> > Le 26 juin 2013 12:58, "James Green" <ja...@gmail.com> a écrit
> :
> >
> > > Hi,
> > >
> > > We're observing some stack traces which I was not expecting.
> > >
> > > Caused by: <openjpa-2.2.0-r422266:1244990 fatal internal error>
> > > org.apache.openjpa.util.InternalException: Multiple concurrent threads
> > > attempted to access a single broker. By default brokers are not thread
> > > safe; if you require and/or intend a broker to be accessed by more than
> > one
> > > thread, set the openjpa.Multithreaded property to true to override the
> > > default behavior.
> > > at
> > > org.apache.openjpa.kernel.BrokerImpl.endOperation(BrokerImpl.java:1956)
> > > at
> > > org.apache.openjpa.kernel.BrokerImpl.isActive(BrokerImpl.java:1904)
> > > at
> > >
> > >
> >
> org.apache.openjpa.kernel.StateManagerImpl.beforeAccessField(StateManagerImpl.java:1610)
> > > at
> > >
> > >
> >
> org.apache.openjpa.kernel.StateManagerImpl.accessingField(StateManagerImpl.java:1598)
> > >
> > > Our application has a component that routinely reads @Entity instances
> > from
> > > a database table and puts them into a cache.
> > >
> > > The cache component (an EJB) accepts these instances and places them
> > into a
> > > ConcurrentHashMap for instance retrieval by other processes.
> > >
> > > Other components then have this cache instance injected into them and
> > > perform a get on it to read values and do read-only work.
> > >
> > > When the component that reads the entities from the database and puts
> > them
> > > all into the cache (overwriting any previous entries) runs, and other
> > > components are also running, we can see the above stack trace and a
> > > rollback occurs.
> > >
> > > Can someone help me understand what is happening and how to re-work the
> > > architecture to avoid this?
> > >
> > > Thanks,
> > >
> > > James
> > >
> >
>
Re: OpenJPA and ConcurrentHashMap
Posted by James Green <ja...@gmail.com>.
Yeah although I didn't have JPA in my mind when I wrote it so the idea they
were "managed" didn't come into it. I guess that's the cause - the
EntityManager from a past invocation has references to them and as it
reloads them into the cache something, somewhere, is going bang.
The rationale behind this cache is relatively simple. We have an existing
PHP/MySQL service that gets hammered when API requests are made because
each involves database queries for account information. To avoid this
occurring in this new Java Enterprise service I wanted to maintain a cache
of accounts across many invocations, reloading that cache from the database
periodically.
It could be that this cache is utterly redundant but back at the start I
was not familiar with the connection pooling or JPA caching available so I
probably re-invented the wheel. If this is the case I can write out the
cache and plumb in the persistence context.
If the custom cache is however a good thing[tm] then an explanation of
what's happening would be good to see.
Thanks,
James
On 26 June 2013 12:30, Romain Manni-Bucau <rm...@gmail.com> wrote:
> Hi
>
> Do you cache managed entities? If so maybe use dto
> Le 26 juin 2013 12:58, "James Green" <ja...@gmail.com> a écrit :
>
> > Hi,
> >
> > We're observing some stack traces which I was not expecting.
> >
> > Caused by: <openjpa-2.2.0-r422266:1244990 fatal internal error>
> > org.apache.openjpa.util.InternalException: Multiple concurrent threads
> > attempted to access a single broker. By default brokers are not thread
> > safe; if you require and/or intend a broker to be accessed by more than
> one
> > thread, set the openjpa.Multithreaded property to true to override the
> > default behavior.
> > at
> > org.apache.openjpa.kernel.BrokerImpl.endOperation(BrokerImpl.java:1956)
> > at
> > org.apache.openjpa.kernel.BrokerImpl.isActive(BrokerImpl.java:1904)
> > at
> >
> >
> org.apache.openjpa.kernel.StateManagerImpl.beforeAccessField(StateManagerImpl.java:1610)
> > at
> >
> >
> org.apache.openjpa.kernel.StateManagerImpl.accessingField(StateManagerImpl.java:1598)
> >
> > Our application has a component that routinely reads @Entity instances
> from
> > a database table and puts them into a cache.
> >
> > The cache component (an EJB) accepts these instances and places them
> into a
> > ConcurrentHashMap for instance retrieval by other processes.
> >
> > Other components then have this cache instance injected into them and
> > perform a get on it to read values and do read-only work.
> >
> > When the component that reads the entities from the database and puts
> them
> > all into the cache (overwriting any previous entries) runs, and other
> > components are also running, we can see the above stack trace and a
> > rollback occurs.
> >
> > Can someone help me understand what is happening and how to re-work the
> > architecture to avoid this?
> >
> > Thanks,
> >
> > James
> >
>
Re: OpenJPA and ConcurrentHashMap
Posted by Romain Manni-Bucau <rm...@gmail.com>.
Hi
Do you cache managed entities? If so maybe use dto
Le 26 juin 2013 12:58, "James Green" <ja...@gmail.com> a écrit :
> Hi,
>
> We're observing some stack traces which I was not expecting.
>
> Caused by: <openjpa-2.2.0-r422266:1244990 fatal internal error>
> org.apache.openjpa.util.InternalException: Multiple concurrent threads
> attempted to access a single broker. By default brokers are not thread
> safe; if you require and/or intend a broker to be accessed by more than one
> thread, set the openjpa.Multithreaded property to true to override the
> default behavior.
> at
> org.apache.openjpa.kernel.BrokerImpl.endOperation(BrokerImpl.java:1956)
> at
> org.apache.openjpa.kernel.BrokerImpl.isActive(BrokerImpl.java:1904)
> at
>
> org.apache.openjpa.kernel.StateManagerImpl.beforeAccessField(StateManagerImpl.java:1610)
> at
>
> org.apache.openjpa.kernel.StateManagerImpl.accessingField(StateManagerImpl.java:1598)
>
> Our application has a component that routinely reads @Entity instances from
> a database table and puts them into a cache.
>
> The cache component (an EJB) accepts these instances and places them into a
> ConcurrentHashMap for instance retrieval by other processes.
>
> Other components then have this cache instance injected into them and
> perform a get on it to read values and do read-only work.
>
> When the component that reads the entities from the database and puts them
> all into the cache (overwriting any previous entries) runs, and other
> components are also running, we can see the above stack trace and a
> rollback occurs.
>
> Can someone help me understand what is happening and how to re-work the
> architecture to avoid this?
>
> Thanks,
>
> James
>