Hi there folks, I'm hoping someone can give me a nudge in the right direction here!
Basically I have a list of "order detail" lines (orderline) that are held in a BusinessListBase (orderlinelist) which is in turn a property of my Order Header (orderheader). Now when I call the save on my order header I also want to save the order detail lines that have changed - that was straightforward enough by calling the fieldmanager.updatechildren method in the orderheader save method.
Unfortunately though the logic of the data that I'm working with has been changed so that there is now a requirement that an order cannot contain zero detail lines and an edit is performed by deleting the original line and adding a new one. What this means is that I have to ensure that new detail lines are added before old detail lines are removed.
In a nutshell, I need to save the "IsNew" children before I save the "IsDeleted" children. I thought I could just grab a collection of the added and deleted children and loop through them in the Orderheader save method and call their individual save methods but I'm getting the "Can not directly save a child object" warning. I'm still on the learning curve for CSLA (3.62 in this project) and it's been going well so far but I'm not exactly sure where to target my attention for a solution to this.
I also hope that this question makes a measure of sense to those reading it.
Thanks in advance for your time :)
CSLA does indeed deal with children by first deleting and then inserting, this is the behaviour coded into the ChildDataPortal. If you want to take full control of the save behaviour then perhaps not using the ChildDataPortal is the answer. By not using the ChildDataPortal I mean don't call DataPortal.CreateChild<T> or DataPortal.FetchChild<T>. Use DataPortal.Create<T> etc instead.
The ChildDataPortal automatically calls MarkAsChild on your business object which in turn stops you from calling save directly. The DataPortal doesn't call MarkAsChild which means you can call Save unrestricted.
Ultimately this does mean that you won't be able to use the FieldManager.UpdateChildren method and that you'll have to hand code the cascading calls.
Hope this helps, dude.
Alas it is as I feared...I have to do some work :(
Cheers mate, I'd pretty much ruled out any easy way of doing it but I was hoping I'd missed something. My original plan was to call the fieldmanager.update in a Do while IsDirty loop but in the delete methods of the children do an early exit if the parent collection still contained "isnew" items so that they retained their "IsDirty" status, in this way I was hoping that the inserts would be dealt with and then the deletes but it's not a very elegant solution.
...but it's not a very elegant solution.
No kidding; I feel sick just thinking about it.
You could to the solution you have proposed and instead of calling ChildObject.Save() call DataPortal.UpdateChild(OrderLine, paramaters) within the OrderHeader class.
The other solution is to override Child_Update(Paramaters) within the OrderLineList Class and then do the specific logic that you want to do within there; then your order class can continue to just call FieldManager.UpdateChildren(). Within there you will have access to the deleted items and the standard items and there you could then do the new items first, update exisiting records and delete items from deletedList. When you actually want to do the update, do a DataPortal.UpdateChild(OrderLine,paramaters).
Using the ChildDataPortal is still a valid option for you!
Of course! That'd work perfectly.
Yup, they both work but of the two this is the neatest - when I get five minutes I'm going to go back and redo it - thanks Marjon :)
Copyright (c) Marimer LLC