Rolling back twice

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
8 messages Options
Reply | Threaded
Open this post in threaded view
|

Rolling back twice

jtuchel
Hi there,

Before I build some strancge workaround, I thought I'd ask a question on this group:

In my Seaside Application on VAST (still using an ancient GLORP version) I see the following behaviour:

If I edit an object in a Component once an do a rollbackTransaction, the object gets refreshed automagically.
If I edit it again and do another rollbackTransaction, the changes made in the Seaside App do not get saved to the DB, but the object in memory is not refresh'ed again. So it looks as if the transaction got committed. In a new GLORP session, the values are still the old ones.

All is well if I refresh: all touched objects after a rollback.

So MY THEORY of what happens is this: the first rollback works because there is a registered copy of the original in the currentUOW. After the first rollback, the currentUOW and its undoMap are cleaned and therefor the original values aren't copied back into the object, because the object is not registered with the UOW any more.

Is that roughly what's going on?

If so, is there anything else I can do other than doing a rollback/refresh by hand (there's always the danger of me forgetting an object), something like rollbackAndContinue (comparable to commitAndContinue)? Or should I always register: all possible transacted objects that get handed into a Seaside Component, or is it sufficient to register the "root" object with the transaction. The way I read register:, an already registered (and previously saved) object doesn't hurt because it won't be re-registered.

How do people solve this?
Always register their objects on opening a Component (same problem goes for GUIs)?
Always refresh objects after a rollback?
Something copletely different that I missed until now?

Joachim

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.
Reply | Threaded
Open this post in threaded view
|

Aw: Rolling back twice

jtuchel
There's one little question for extra points here:

in search for a place in our web framework where I could register: the "main" object to be handled in a component, I came to the problem that some of our components handle a "model object" that is not to be persisted in the DB and therefor not an instance of one of the classes that the GLORP descriptor describes.

Now in order to avoid problems, I would first check with the descriptor that an object is really to be handled by GLORP, but I was just wondering if that shouldn't be done by ObjectTransaction>>#register: anyways. It sure sounds cool that GLORP can (theoretically) rollback any object, but on the other hand it is likely the user will get an exception at #commit time if an object is not in the descriptor system...

Or maybe the check I'm asking for is in current versions of GLORP anyways?

Joachim

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.
Reply | Threaded
Open this post in threaded view
|

Re: Rolling back twice

Alan Knight-2
In reply to this post by jtuchel
There is an API saveAndContinue on GlorpSession. It sounds like what you want is a rollbackAndContinue, implemented the same way. I think just removing the line about deleted objects and changing the commit to a rollback would be enough.



[hidden email]
May 11, 2011 7:48 AM


Hi there,

Before I build some strancge workaround, I thought I'd ask a question on this group:

In my Seaside Application on VAST (still using an ancient GLORP version) I see the following behaviour:

If I edit an object in a Component once an do a rollbackTransaction, the object gets refreshed automagically.
If I edit it again and do another rollbackTransaction, the changes made in the Seaside App do not get saved to the DB, but the object in memory is not refresh'ed again. So it looks as if the transaction got committed. In a new GLORP session, the values are still the old ones.

All is well if I refresh: all touched objects after a rollback.

So MY THEORY of what happens is this: the first rollback works because there is a registered copy of the original in the currentUOW. After the first rollback, the currentUOW and its undoMap are cleaned and therefor the original values aren't copied back into the object, because the object is not registered with the UOW any more.

Is that roughly what's going on?

If so, is there anything else I can do other than doing a rollback/refresh by hand (there's always the danger of me forgetting an object), something like rollbackAndContinue (comparable to commitAndContinue)? Or should I always register: all possible transacted objects that get handed into a Seaside Component, or is it sufficient to register the "root" object with the transaction. The way I read register:, an already registered (and previously saved) object doesn't hurt because it won't be re-registered.

How do people solve this?
Always register their objects on opening a Component (same problem goes for GUIs)?
Always refresh objects after a rollback?
Something copletely different that I missed until now?

Joachim
--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.

--
Alan Knight [|], Engineering Manager, Cincom Smalltalk
[hidden email]
[hidden email]
http://www.cincomsmalltalk.com

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.
Reply | Threaded
Open this post in threaded view
|

Aw: Re: Rolling back twice

jtuchel
Alan,

that's exactly what I was looking for: rollbackAndConitnue. Looking at #commitUnitOfWorkAndContinue, the implementation would be straghtforward:

rollbackUnitOfWorkAndContinue
    | registeredObjects |   
    currentUnitOfWork isNil ifTrue: [^self error: 'Not in unit of work'].
    registeredObjects := currentUnitOfWork registeredObjects.
"    currentUnitOfWork deletedObjects do: [:each | registeredObjects remove: each]."
    self rollbackUnitOfWork.
    self beginUnitOfWork.
    self registerAll: registeredObjects.

This would surely be safe for changed objects and I guess also for to-be-deleted objects that simply won't be deleted now that we rollback.
But what to do with objects that were registered as new? They should be removed from the collection for re-registration, shouldn't they?

So do you think replacing the line I commented out above with the following would be safe?

currentUnitOfWork newObjects do: [:each | registeredObjects remove: each].

Or am I on the wrong track?

Do you think adding rollbackAndContinue to an official GLORP version makes sense?

Joachim

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.
Reply | Threaded
Open this post in threaded view
|

Aw: Re: Rolling back twice

jtuchel
Okay, I tried it and slo far it seems to work nicely.

Here's what I added to GlorpSession:

rollbackAndContinue
    "A shorter synonym"
    ^self rollbackUnitOfWorkAndContinue.

rollbackUnitOfWorkAndContinue
    "Rollback the current unit of work, but then keep going with the same set of registered objects, with their state updated to reflect current values."

    | registeredObjects |  
    currentUnitOfWork isNil ifTrue: [^self error: 'Not in unit of work'].
    registeredObjects := currentUnitOfWork registeredObjects.
    currentUnitOfWork newObjects do: [:each | registeredObjects remove: each].
    self rollbackUnitOfWork.
    self beginUnitOfWork.
    self registerAll: registeredObjects.

So far, it seems I have no troubles and have no need to re-register or refresh objects after a rollback, since the re-registering is done in rollbackUnitOtWorkAndContinue.

Since I am neither using a current version of GLORP, nor have a current version of VW at my fingertips, I cannot publish any changes to Glorp anywhere. But they're probably in a good place on this list if anybody wants to harvest the code into a new release.

Thanks, Alan, for your hints. Please feel free to tell me if my thinking about new objects is wrong (since I am not completely sure).

Joachim

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.
Reply | Threaded
Open this post in threaded view
|

Re: Aw: Re: Rolling back twice

Alan Knight-2
In reply to this post by jtuchel
Yes, I think that's exactly right. I'll see about adding that to the current versions.



[hidden email]
May 11, 2011 9:00 AM


Alan,

that's exactly what I was looking for: rollbackAndConitnue. Looking at #commitUnitOfWorkAndContinue, the implementation would be straghtforward:

rollbackUnitOfWorkAndContinue
    | registeredObjects |   
    currentUnitOfWork isNil ifTrue: [^self error: 'Not in unit of work'].
    registeredObjects := currentUnitOfWork registeredObjects.
"    currentUnitOfWork deletedObjects do: [:each | registeredObjects remove: each]."
    self rollbackUnitOfWork.
    self beginUnitOfWork.
    self registerAll: registeredObjects.

This would surely be safe for changed objects and I guess also for to-be-deleted objects that simply won't be deleted now that we rollback.
But what to do with objects that were registered as new? They should be removed from the collection for re-registration, shouldn't they?

So do you think replacing the line I commented out above with the following would be safe?

currentUnitOfWork newObjects do: [:each | registeredObjects remove: each].

Or am I on the wrong track?

Do you think adding rollbackAndContinue to an official GLORP version makes sense?

Joachim


[hidden email]
May 11, 2011 8:20 AM


There is an API saveAndContinue on GlorpSession. It sounds like what you want is a rollbackAndContinue, implemented the same way. I think just removing the line about deleted objects and changing the commit to a rollback would be enough.



--
Alan Knight [|], Engineering Manager, Cincom Smalltalk
[hidden email]
[hidden email]
http://www.cincomsmalltalk.com

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.
Reply | Threaded
Open this post in threaded view
|

Re: Aw: Rolling back twice

Alan Knight-2
In reply to this post by jtuchel
It doesn't exist. Right now I think that what will happen is if you register an object without a descriptor and commit it will just do nothing. So it will roll it back if it's registered at the top level. It also uses having a descriptor or not as a basis for where to stop in a transitive closure. So if you register an object with a descriptor that has referenced objects without, then it will not dive down into those objects. Whether that's actually the most desirable semantics is an interesting question.



[hidden email]
May 11, 2011 8:04 AM


There's one little question for extra points here:

in search for a place in our web framework where I could register: the "main" object to be handled in a component, I came to the problem that some of our components handle a "model object" that is not to be persisted in the DB and therefor not an instance of one of the classes that the GLORP descriptor describes.

Now in order to avoid problems, I would first check with the descriptor that an object is really to be handled by GLORP, but I was just wondering if that shouldn't be done by ObjectTransaction>>#register: anyways. It sure sounds cool that GLORP can (theoretically) rollback any object, but on the other hand it is likely the user will get an exception at #commit time if an object is not in the descriptor system...

Or maybe the check I'm asking for is in current versions of GLORP anyways?

Joachim
--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.


[hidden email]
May 11, 2011 7:48 AM


Hi there,

Before I build some strancge workaround, I thought I'd ask a question on this group:

In my Seaside Application on VAST (still using an ancient GLORP version) I see the following behaviour:

If I edit an object in a Component once an do a rollbackTransaction, the object gets refreshed automagically.
If I edit it again and do another rollbackTransaction, the changes made in the Seaside App do not get saved to the DB, but the object in memory is not refresh'ed again. So it looks as if the transaction got committed. In a new GLORP session, the values are still the old ones.

All is well if I refresh: all touched objects after a rollback.

So MY THEORY of what happens is this: the first rollback works because there is a registered copy of the original in the currentUOW. After the first rollback, the currentUOW and its undoMap are cleaned and therefor the original values aren't copied back into the object, because the object is not registered with the UOW any more.

Is that roughly what's going on?

If so, is there anything else I can do other than doing a rollback/refresh by hand (there's always the danger of me forgetting an object), something like rollbackAndContinue (comparable to commitAndContinue)? Or should I always register: all possible transacted objects that get handed into a Seaside Component, or is it sufficient to register the "root" object with the transaction. The way I read register:, an already registered (and previously saved) object doesn't hurt because it won't be re-registered.

How do people solve this?
Always register their objects on opening a Component (same problem goes for GUIs)?
Always refresh objects after a rollback?
Something copletely different that I missed until now?

Joachim
--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.

--
Alan Knight [|], Engineering Manager, Cincom Smalltalk
[hidden email]
[hidden email]
http://www.cincomsmalltalk.com

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.
Reply | Threaded
Open this post in threaded view
|

Aw: Re: Aw: Re: Rolling back twice

jtuchel
In reply to this post by Alan Knight-2
Hi Alan,

thanks for commenting and looking into this. I am quite happy with the changes I made, have seen no problems so far.

Also the fact that registering an object without a descriptor doesn't hurt is helpful, because registering an object every time a GUI or Web page uses it ("just in case") won't do no harm.

So far I must say I really like GLORP, even the old version I am on. Instantiations announced to update to a newer version with the next VAST release. I hope the binding stuff will then be working as well, so that we can use stored procedures and view. But for now, we can live without them.
So I'll probably soon be able to ask questions based on a somewhat recent version ;-)

Joachim

--
You received this message because you are subscribed to the Google Groups "glorp-group" group.
To post to this group, send email to [hidden email].
To unsubscribe from this group, send email to [hidden email].
For more options, visit this group at http://groups.google.com/group/glorp-group?hl=en.