Asymmetry in SessionFactory.Evict()

35 views
Skip to first unread message

Huge

unread,
Aug 3, 2010, 6:28:57 PM8/3/10
to nhusers
I am really puzzled why there is a method to remove an object from the
2nd level cache - SessionFactory.Evict(object) but there is no
function to put an object directly into the 2nd level cache, e.g. a
SessionFactory.Add(object).

Background: I receive Entities from a P2P network connection that, by
definition, are supposed to be the most up-to-date objects. These
should be taken as the new master copy of the entity. So, they should
replace any object in the 2nd level cache which has the same key. I
currently am able to take the old object out of the 2nd level cache by
using SessionFactory.Evict(object) but I have no API to get the object
in.

It's really baffling to me why NHib would implement the functionality
to take an object out of 2nd level cache but not bother to implement a
way to put an object in!?

I do not want to make a round trip to the database to select the
updated object again. The P2P connection has supplied the new object
and our rules say that the network-received object is the master, no
ifs, ands, or buts.

Thanks for your help.
Hugh

Diego Mijelshon

unread,
Aug 4, 2010, 11:19:41 AM8/4/10
to nhu...@googlegroups.com
The NH cache is for objects retrieved by NH. If you are getting it from other source, you can cache it yourself using the same underlying cache (syscache, memcached, etc)
 
    Diego



--
You received this message because you are subscribed to the Google Groups "nhusers" group.
To post to this group, send email to nhu...@googlegroups.com.
To unsubscribe from this group, send email to nhusers+u...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/nhusers?hl=en.


Huge

unread,
Aug 4, 2010, 6:38:18 PM8/4/10
to nhusers
"The NH cache is for objects retrieved by NH"

I understand that. What confuses me is that somebody wrote an API to
take things out of that cache without writing an API to put things
into it.

Why allow the ability to take something out of that cache? Somebody
had justification for writing such a function back in the day.

So, isn't that same justification viable for a reason to be able to
stuff something into that cache? Even better yet a
SessionFactory.Replace(object) would be perfect, because I just need
to take the new copy of Object A and overwrite the old Object A and
have that new Object A be the master.


"If you are getting it from other source, you can cache it yourself
using the same underlying cache (syscache, memcached, etc)"

I'm not sure what you mean. Are you saying there is a way to stuff an
object into the L2 cache? If so, how do I get at the SessionFactory's
underlying memory structure that is used to implement that cache? Or,
are you saying that I should implement my own cache, separate from
SessionFactory? In that case, what good would it do, because
SessionFactory wouldn't be aware that I have a separate cache where it
could find objects instead of selecting them.

Diego Mijelshon

unread,
Aug 4, 2010, 6:49:19 PM8/4/10
to nhu...@googlegroups.com
NHibernate is like a screwdriver. All your emails today can be reduced to "why is it so hard to hammer nails with it?"

    Diego


Fabio Maulo

unread,
Aug 4, 2010, 10:45:44 PM8/4/10
to nhu...@googlegroups.com
Man!... too many words and few facts!
be Nike!

--
You received this message because you are subscribed to the Google Groups "nhusers" group.
To post to this group, send email to nhu...@googlegroups.com.
To unsubscribe from this group, send email to nhusers+u...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/nhusers?hl=en.




--
Fabio Maulo

Frans Bouma

unread,
Aug 5, 2010, 3:21:55 AM8/5/10
to nhu...@googlegroups.com
Apparently no-one else is mature enough to answer this guy's questions, so
let me give it a try.

> "The NH cache is for objects retrieved by NH"
>
> I understand that. What confuses me is that somebody wrote an API to take
> things out of that cache without writing an API to put things into it.
>
> Why allow the ability to take something out of that cache? Somebody had
> justification for writing such a function back in the day.

The caching mechanism is in the o/r mapper, it's FOR the o/r mapper,
when it materializes entity class instances with the data from the db. So
objects end up in the cache because the o/r mapper decided to do so.

It can be you need to remove an object from the cache, because you
removed it from the db using other means, e.g. a trigger, a separate process
on another machine, you name it. This way you can, in case of emergency,
remove it. I think that's the reason behind this method but we can only
guess, we didn't write the method. I agree that it's not a shiny example of
proper design, but NHibernate has plenty of that kind of hodgepodge stuff,
added during the years, as it's a framework which exists for a long time
(and inherited it from the Java version)

> So, isn't that same justification viable for a reason to be able to stuff
> something into that cache? Even better yet a
> SessionFactory.Replace(object) would be perfect, because I just need to
take
> the new copy of Object A and overwrite the old Object A and have that new
> Object A be the master.

that would mean you'd place yourself on the seat of the o/r mapper
which decides when to keep objects in the cache. That's not your job, leave
that to the o/r mapper. If you want to use a cache for your objects, use ...
a cache :) The l2 cache here is out of reach so use another one.

> "If you are getting it from other source, you can cache it yourself using
> the same underlying cache (syscache, memcached, etc)"
>
> I'm not sure what you mean. Are you saying there is a way to stuff an
> object into the L2 cache? If so, how do I get at the SessionFactory's
> underlying memory structure that is used to implement that cache? Or, are
> you saying that I should implement my own cache, separate from
> SessionFactory? In that case, what good would it do, because
SessionFactory
> wouldn't be aware that I have a separate cache where it could find objects
> instead of selecting them.

the underlying caching system used for l2 caching is the one you can
add the object to yourself, that's what was meant.

FB

>
> Thanks for your help.
> Hugh
>

Fabio Maulo

unread,
Aug 5, 2010, 6:50:45 AM8/5/10
to nhu...@googlegroups.com
On Thu, Aug 5, 2010 at 4:21 AM, Frans Bouma <fr...@sd.nl> wrote:
Apparently no-one else is mature enough to answer this guy's questions, so
let me give it a try.

Thanks you for your professional and mature support.

--
Fabio Maulo

Frans Bouma

unread,
Aug 5, 2010, 7:12:02 AM8/5/10
to nhu...@googlegroups.com

No offence Fabio, but:


> Man!... too many words and few facts!
> be Nike!

and (Diego)


> NHibernate is like a screwdriver. All your emails today can be reduced to
"why is it so hard > to hammer nails with it?"

why bother replying then? It's really easy: why reply to the person
with the question with answers like the ones above? If the user asks a
question not worth answering, why not simply ignore it? This happens on this
mailinglist anyway.

It's very easy to help users AND be nice. They _care_ about your
work otherwise they'd dump it and move to something else.

FB


Fabio Maulo

unread,
Aug 5, 2010, 7:26:12 AM8/5/10
to nhu...@googlegroups.com
On Thu, Aug 5, 2010 at 8:12 AM, Frans Bouma <fr...@sd.nl> wrote:
       No offence Fabio, but:


Don't worry. You can give some discomfort but to offend me you have an hard work to do.

--
Fabio Maulo

Diego Mijelshon

unread,
Aug 5, 2010, 9:40:59 AM8/5/10
to nhu...@googlegroups.com
On Thu, Aug 5, 2010 at 08:12, Frans Bouma <fr...@sd.nl> wrote:
> On Thu, Aug 5, 2010 at 4:21 AM, Frans Bouma <fr...@sd.nl> wrote:> NHibernate is like a screwdriver. All your emails today can be reduced to
"why is it so hard > to hammer nails with it?"

       why bother replying then? It's really easy: why reply to the person
with the question with answers like the ones above? If the user asks a
question not worth answering, why not simply ignore it? This happens on this
mailinglist anyway.

I did try to explain it at first. But when somebody that clearly has not given the NH architecture a try keeps going about how it should all be different, and complaining that it's broken... it's frustrating.
When I started with NH, the first thing I did was RTFM. Then I made lots of mistakes, but instead of blaming them on the framework not doing whatever I thought it should be doing, I learned to work with it.
"Select is not broken". In the few cases that I found stuff that was, indeed, broken, I opened Jira issues, with patches when I knew how to create them.
 
       It's very easy to help users AND be nice. They _care_ about your
work otherwise they'd dump it and move to something else.
 
You _know_ I'm just another enthusiastic user and member of this community, willing to help anyone with legitimate concerns about using NHibernate. Of the hundreds of emails I've sent on the list, a small percentage is "not nice", and it's directed at those users who _don't_ seem to care about our work.
As others have pointed out, the person originating this thread expects NHibernate to be something that it isn't. So he probably shouldn't use it, at least for that project.

   Diego

Frans Bouma

unread,
Aug 5, 2010, 10:29:08 AM8/5/10
to nhu...@googlegroups.com
Fair enough

FB

Huge

unread,
Aug 5, 2010, 11:18:59 AM8/5/10
to nhusers
Thank you, one and all, for the good insight. I'm new to NHibernate
and I might have dumb questions or perhaps be too wordy. You can say
whatever you want about me, I also have a thick skin, like Fabio said,
you will have a very hard time to offend me :)

So, please if you could just clarify a little more, that would be
great. What did you mean by:

"the underlying caching system used for l2 caching is the one you can
add the object to yourself, that's what was meant."

Great so it does sound like there's a way to add an object received
via network connection into the L2 cache, by accessing "the underlying
system". But in some ways that last statement contradicted your
previous few which said that was the ORM's job. If you could just
provide a link or two that might demonstrate how to do add an object
to that myself, I think that would solve my original need.

Thanks again, H

Tim Hoolihan

unread,
Aug 5, 2010, 11:32:02 AM8/5/10
to nhusers
The discussion seems to be missing a fundamental point of L2 cache.
If you get an object, or collection of objects via NHibernate with L2
cache, you don't know or care if the object is coming from the cache
or the database. The assumption is, that if you do not hit the
database that you are getting an up-to-date object that is or will be
committed to the db at the appropriate time. That is an implicit
contract in the nature of caching an ORM.

If you insert into that cache manually from some other source, you
completely violate that contract. There is no guarantee that the next
person fetching an object (or collection) will get data that is up-to-
date and will be (or already is) persisted in the database.

You are bypassing the mechanism which NHibernate tracks what in the
cache needs flushed to the DB, and thus breaking the entire point of
having the cache.

Why not just fetch and update the object in question with the data you
received from some other source, and the cache (and eventually the db)
will be up to date. Data coming in from some other source should be
treated just like any other disconnected object, and there is tons of
documentation about dealing with this in NHibernate.

Or am I missing something about your request?

Huge

unread,
Aug 5, 2010, 12:07:05 PM8/5/10
to nhusers
Thanks Tim.

"Why not just fetch and update the object in question with the data
you
received from some other source, and the cache (and eventually the
db)
will be up to date."

I guess my point is, that when I receive the object via the Network,
it was because somebody else on the Network has already just recently
committed that object to the database, and I'm being notified of that
fact.

Imagine a Doctor's office with 20 people running the software
connected via P2P. One person saves an object and notifies all the
other ones of that fact via the Network. What I'm trying to avoid is
then all 20 workstations going and selecting that object out of the
database. They just got it off the network, so all the data the
client needs, it already has.

It seems to me the better approach would be to receive the object off
the network, and have it "absorb" into my system completely, and not
have to make another trip from each client to the database in order to
verify the correctness of the object. Just treat it as the "gospel"
master object and replace any other previous version of that object
with the one received off the network.

Why does it seem like people want to challenge everything I'm doing,
instead of considering the possibility I might have a good idea or a
unique need?

"If you insert into that cache manually from some other source, you
completely violate that contract."

What I'm saying is that by providing a SessionFactory.Evict() method,
hasn't this "contract" essentially been violated already? And if it
has, then why not enjoy this and expand on it to let it be a 2 way
street?

H

Greg Young

unread,
Aug 5, 2010, 12:15:52 PM8/5/10
to nhu...@googlegroups.com
If you are sending around notifications why do you need to update the cache?

Wouldn't the cache (assuming distributed here) have already been
updated when user 4 saved to the db and published the notification?

Greg

--
Les erreurs de grammaire et de syntaxe ont été incluses pour m'assurer
de votre attention

Huge

unread,
Aug 5, 2010, 12:32:38 PM8/5/10
to nhusers
Greg, thanks for your reply.
Each client runs NHibernate and has their own Cache that becomes out
of date when another client modifies an object.
Due to the fact that workstations running our software must never,
ever be able to be offline, we are forbidden from using a SaaS
architecture for Data Access, thus the P2P network and the rich client
model.
H
> > For more options, visit this group athttp://groups.google.com/group/nhusers?hl=en.

Tim Hoolihan

unread,
Aug 5, 2010, 1:10:50 PM8/5/10
to nhusers

On Aug 5, 12:32 pm, Huge <hughb...@gmail.com> wrote:
...
> Due to the fact that workstations running our software must never,
> ever be able to be offline, we are forbidden from using a SaaS
> architecture for Data Access, thus the P2P network and the rich client
> model.

Your argument of preventing an offline mode based on the location of
nhibernate holds no water. In either model (centralized app server
that exposes data through web services or nhibernate on the client),
if I pull the network cable, you can no longer fetch new data or
update anything with that app. That is not an offline app. Offline
apps have to have the ability to cache data, go offline, update the
data, and then synchronize at some later point.

Regardless, if you have an app that does not have exclusive write to
the database, then 2nd level caching is not a great idea anyway.
You'll spend more time and effort notifying of dirty caches than is
worth it. By not using 2nd level cache, you'll have less problems
with stale data and don't have to implement so much messaging.

To your point of assuming that your case isn't special, pay attention
to the mailing list (or any other mailing list). 99/100 times when
people think they have a unique problem that hasn't been solved, they
are wrong. Especially when the framework is as old as nhibernate.
Unique cases happen, but they are a rare exception. Yours seems to be
a unique case, but only because you are trying to use L2 cache for an
architecture it wasn't meant for.

Greg Young

unread,
Aug 5, 2010, 1:13:56 PM8/5/10
to nhu...@googlegroups.com
exactly, if you want true occasionally connected the architecture
would be a p2p pub/sub with local data storages.

> --
> You received this message because you are subscribed to the Google Groups "nhusers" group.
> To post to this group, send email to nhu...@googlegroups.com.
> To unsubscribe from this group, send email to nhusers+u...@googlegroups.com.
> For more options, visit this group at http://groups.google.com/group/nhusers?hl=en.
>
>

--

Reply all
Reply to author
Forward
0 new messages