Re: Unexpected awakeFromInsertion() behaviour
Re: Unexpected awakeFromInsertion() behaviour
- Subject: Re: Unexpected awakeFromInsertion() behaviour
- From: Chuck Hill <email@hidden>
- Date: Thu, 10 Jan 2008 20:07:23 -0800
On Jan 10, 2008, at 8:04 PM, Mr. Pierre Frisch wrote:
Hi Chuck,
I am answering my own post.
:-)
I think the correct behavior is to call awakeFromInsertion() if we
have an object with EOTemporaryGlobalID and awakeFromFetch() if we
have a regular EOGlobalID.
I am not sure if either should be called, but I am not sure that they
should not be called either. Your proposal seems reasonable.
Chuck
On Jan 10, 2008, at 19:33, Mr. Pierre Frisch wrote:
--
Pierre Frisch
email@hidden
On Jan 10, 2008, at 18:37, Chuck Hill wrote:
On Jan 10, 2008, at 12:31 PM, Mr. Pierre Frisch wrote:
I am not entirely sure of what the behavior should be but after
the save the object is in the DB so this not a newly inserted
object anymore.
That is a good point. I'd guess if this is not a simple bug,
that someone was looking as insert as the opposite of delete when
reverting. But that is not quite true.
This is exactly how the code work by re-inserting the deleted
object and this is why the awakeFromInsertion() get called.
We do a deleteObject() and a revert() logically we should call
awakeFromFetch() as this would have reverted the object to its
fetched state (last snapshot), awakeFromInsertion() just does
not appears to make sense.
At first it made sense to me. In database terms, doing an insert
to revert a delete makes sense. But you are right, this is not
how EOF should revert.
If awakeFromFetch() changes any values after reverting, do these
get seen by the EC and saved to the DB? That is something to check.
As per the documentation revert() restore the last snapshot value
in the EO. It does not touch any other field i.e. the objects are
not recreated merely updated. What is the right behavior: do
nothing of call awakeFromFetch()? One way or another there may be
unintended repercussions. But any value initialized in
awakeFromFetch( will be save at the next DB save.
Chuck
On Jan 10, 2008, at 11:35, Chuck Hill wrote:
I will let Peter file the report. But while you are waiting...
What do you think is the correct behavior here? Should it not
call awakeFromInsertion again? Should it call it and undo any
changes? Should it call it and detect that the object has been
updated?
Calling revert() should, I think, return the contents of the EC
to the last state where there were no changes (after the
previous save if it has been saved, or will all local changes
undone). Calling awakeFromInsertion() does not seem compatible
with that.
Chuck
On Jan 10, 2008, at 11:30 AM, Mr. Pierre Frisch wrote:
Bug report please this needs to be fixed.
Pierre
--
Pierre Frisch
email@hidden
On Jan 10, 2008, at 11:04, Chuck Hill wrote:
That looks like a bug, the EC should either not be calling
awakeFromInsertion() or should be seeing the notifications
from the change in value. It makes sense to me for it to
call awakeFromInsertion() *BUT* this results in an object
state different from what was there before the changes being
reverted. That seems to be a very wrong result.
You will often see the method written as:
// in Order.java
public void awakeFromInsertion(EOEditingContext ec) {
super.awakeFromInsertion(ec);
if (statusMessage() == null) {
setStatusMessage("incomplete");
}
}
I don't do that myself (I probably should!), but I expect
this is done to handle the situation you are seeing.
Chuck
On Jan 9, 2008, at 3:37 PM, Peter Vandoros wrote:
Hi Chuck,
Chuck Hill wrote:
Hi Peter,
On Jan 9, 2008, at 2:49 PM, Peter Vandoros wrote:
Chuck Hill wrote:
On Jan 8, 2008, at 9:23 PM, Peter Vandoros wrote:
I came across an interesting behaviour today with
awakeFromInsertion() that i did not expect and I hope
someone could shed some light.
What happens is that awakeFromInsertion() is not only
called when the EO is "created" but also when reverting
the editing context after having deleted an EO (which
hasn't yet been saved). That is, if you delete an EO and
revert() instead of saveChanges(), that EO's
awakeFromInsertion() method is called again.
The documentation states:
"Overridden by subclasses to perform additional
initialization on the receiver upon its being inserted
into ec. This is commonly used to assign default values
or record the time of insertion. ...."
I originally took this to mean that it is only called
when the EO is _created_. Technically speaking, the
documentation states that it is called when the EO is
_inserted_ into the editing context which does not
necessarily mean when the EO is _created_.
Does this mean that I need to go through all my EO's
that use this method for some initialisation and take
this scenario into account or is this a bug with WO?
I am using WO 5.2.4.
Is this what you are talking about?
com.webobjects.eocontrol.EOEditingContext ec =
newEditingContext();
ec.lock();
Order o = new Order();
ec.insertObject(o);
ec.deleteObject(o);
ec.revert();
ec.unlock();
I log a stack trace from Order.awakeFromInsertion. I do
not get a call to awakeFromInsertion when the ec is
reverted in WO 5.3.3.
Log out a stack trace from awakeFromInsertion and see
what it says for the second call:
public void awakeFromInsertion(EOEditingContext ec)
{
NSLog.out.appendln(new RuntimeException("backtrace"));
super.awakeFromInsertion(ec);
. . .
I'd be interested to see it.
That is not exactly what i am talking about.
The code below demonstrates what i am talking about.
EOEditingContext ec = new EOEditingContext();
ec.lock();
try {
Order order = (Order) EOUtilities.createAndInsertInstance
( ec, "Order" );
// set order properties so it can be saved successfully
ec.saveChanges();
ec.deleteObject( order);
NSLog.out.appendln("should see awakeFromInsertion call
now...");
ec.revert();
NSLog.out.appendln("did you see the awakeFromInsertion
call?");
}
catch (Exception e) {
System.err.println("Error with test");
e.printStackTrace();
}
finally {
ec.unlock();
}
The stack trace (the interesting part) that i get when
this happens is:
java.lang.RuntimeException: backtrace
at com.etechgroup.test.eo.Order.awakeFromInsertion
(Order.java:44)
at
com.webobjects.eocontrol.EOEditingContext.insertObjectWithGlo
balID(EOEditingContext.java:2851)
at com.webobjects.eocontrol.EOEditingContext.insertObject
(EOEditingContext.java:2871)
at com.webobjects.eocontrol.EOEditingContext.revert
(EOEditingContext.java:4570)
It looks as though the editing context re-inserts a
deleted EO if that EO is not newly created and you revert.
Of course it does! deleteObject makes the object not
exist. Reverting that makes it exist again. So it is
newly created and get awoken again. Revert is more like
undo than "forget what I just changed".
ec.deleteObject(order);
ec.saveChanges();
ec.undo();
ec.saveChanges();
I am not sure of the exact calls, but it is possible to
reverse changes committed to the database. Or it was at
one time, I have seen this happen due to a bug processing
delete rules. Much fun debugging that one.
I can imagine :-)
I'm glad i cleared this up and gave other people on this
list a heads up about this behaviour. At least now I know
about this and have worked around it by creating a new
method in my generic record super class awakeFromCreate()
which is called by awakeFromInsertion() only if the EO is
newly created. This way, it does what i thought
awakeFromInsertion() does and what i was using it for.
On a side note, i also noticed that if the default values
that are set in awakeFromInsertion() differ from the
committed value, EOF does not pick up that change leaving
that EO/EditingContext in an invalid state. This is actually
what bit me yesterday and lead me to investigate this
behaviour.
This one _may_ be a bug. I can report it if you think it is
a bug.
For example:
// in Order.java
public void awakeFromInsertion(EOEditingContext ec) {
super.awakeFromInsertion(ec);
setStatusMessage("incomplete");
}
// in SomeTestFile.java
EOEditingContext ec = new EOEditingContext();
ec.lock();
try {
Order order = (Order) EOUtilities.createAndInsertInstance
( ec, "Order" );
order.setStatusMessage("complete");
ec.saveChanges();
ec.deleteObject( order );
System.out.println("should see awakeFromInsertion call
now...");
ec.revert();
System.out.println("did you see the awakeFromInsertion call?");
// the stateMessage should be 'complete' but you will see
that it is 'incomplete'
NSLog.out.appendln("order.statusMessage should be
'complete', but it is: " + order.statusMessage());
// the editing context also does not show any changes
NSLog.out.appendln("ec.hasChanges: " + ec.hasChanges());
NSLog.out.appendln("ec.insertedObjects: " +
ec.insertedObjects().count());
NSLog.out.appendln("ec.updatedObjects: " + ec.updatedObjects
().count());
NSLog.out.appendln("ec.deletedObjects: " + ec.deletedObjects
().count());
}
catch (Exception e) {
System.err.println("Error with test");
e.printStackTrace();
}
finally {
ec.unlock();
}
As always Chuck, your help is much appreciated.
Thanks
--
Peter Vandoros
Software Engineer
Etech Group Pty Ltd
Level 3/21 Victoria St
Melbourne VIC 3000
Australia
Ph: +61 3 9639 9677
Fax: +61 3 9639 9577
----------------------------------
IMPORTANT: This e-mail message and any attachments are
confidential and may be privileged. If received in error,
please reply to this message and destroy all copies and any
attachments. You should check this message and any
attachments for viruses or defects. Our liability is limited
to resupplying any affected message or attachments. For more
information about Etech Group, please visit us at http://
www.etechgroup.com.au.
--
Practical WebObjects - for developers who want to increase
their overall knowledge of WebObjects or who are trying to
solve specific problems.
http://www.global-village.net/products/practical_webobjects
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Webobjects-dev mailing list (Webobjects-
email@hidden)
Help/Unsubscribe/Update your Subscription:
40apple.com
This email sent to email@hidden
--
Practical WebObjects - for developers who want to increase
their overall knowledge of WebObjects or who are trying to
solve specific problems.
http://www.global-village.net/products/practical_webobjects
--
Practical WebObjects - for developers who want to increase their
overall knowledge of WebObjects or who are trying to solve
specific problems.
http://www.global-village.net/products/practical_webobjects
--
Practical WebObjects - for developers who want to increase their
overall knowledge of WebObjects or who are trying to solve specific
problems.
http://www.global-village.net/products/practical_webobjects
_______________________________________________
Do not post admin requests to the list. They will be ignored.
Webobjects-dev mailing list (email@hidden)
Help/Unsubscribe/Update your Subscription:
This email sent to email@hidden