StrataFrame Forum

Modify/update same row more than two times from BO on transaction not update it from 2nd time hereinafter

http://forum.strataframe.net/Topic31946.aspx

By Fabian R Silva, - - 3/21/2013

Hello, 
problem is that when loop the 2nd time, Save(lOnTr, sTrKEy) not do nothing because isDirty() is false... (1st time work ok)

how I can update a 2nd time the same table "Counter" on a transaction?
I need this because this will lock the number on MyTabkecounter an allow to use it in AnotherTable on a transaction without fear of that this number can be repeated



MyTableCounter
------------------------------
Id   |   Number
-----------------------------
1      5
2      99
3      999

dsk = "myDB"
lOnTr = true
sTrKey = "aTrKey"

BusinessLayer.TransactionBegin(dsk, trKey, IsolationLevel.ReadCommitted);
MyTableCounter.FillByPrimaryKey(1);
for(lnk=0;lnk<=5;lnk++)
{
   MyTableCounter.Number += 1;
   MyTableCounter.Save(lOnTr, sTrKey); --> this doesn't execute from 2nd time

   AnotherTable.NewRow();
        AnotherTable.MyTableCounterId = MyTableCounterId.Id;
   AnotherTable.Number = MyTable.Number;
   AnotherTable.Date = DateTime.Now.Date;
   AnotherTable.Save(lOnTr, sTrKey);
}

MyTableCounter.FillByPrimaryKey(2);
for(lnk=0;lnk<=5;lnk++)
{
   MyTableCounter.Number += 1;
   MyTableCounter.Save(lOnTr, sTrKey); --> this doesn't execute

   AnotherTable.NewRow();
   AnotherTable.Number = MyTable.Number;
   AnotherTable.Date = DateTime.Now.Date;
   AnotherTable.Save(lOnTr, sTrKey);
}



BusinessLayer.TransactionCommit(dsk, sTrKey);
By StrataFrame Team - 3/22/2013

There is a way to do this, but purists would frown upon it Smile  Since you're saving the same record over and over again instead of creating a new record, we need to tell the MyTableCounter business object that it isn't really "saved."  The flag that is preventing it from saving after the first time is an internal field called _IsSavedOnTransaction.  You need to use Reflection to set that field back to False each time before you try to save the MyTableCounter business object.  I say purists would hate it because they say you should never tamper with something using Reflection.  In this case, it works just fine.




using System.Reflection;

...

//-- Get a reference to the FieldInfo of the field we need to set
FieldInfo isSavedOnTransactionField = MyTableCounter.GetType().GetField("_IsSavedOnTransaction", BindingFlags.NonPublic | BindingFlags.Instance);

...

//-- In your loop before you save the BO
isSavedOnTransactionField.SetValue(MyTableCounter, false);
By Fabian R Silva, - - 3/22/2013

thanks you for the response

Today I ended up doing a process to control it "manually" before save the BO with transaction... 

the resumed process that I ended up doing was;

- make a temp MyTableCounterDTO that stores info about what it have to save (using MyAnotherTable to fill it)
- fill all records that will be needed to update of MyTableCounter on 1 roundtrip (I created a base fillbyPks methods that receive an List<Int> that ended doing "select * from MyTableCounter where id in (X,Y,Z))
- store on MyTablecounterDTO LastNumber = MyTableCounter.Number, and a "RequiredNumbers" that stores how much times it need to be increased (in the example increase Number 5 times for id 1 and 2, then I fill those two Pks)
- increase number of id on all neded records from MyTableCounter (1 and 2 in this case with number+5) and save it (it locks each row on MyTableCounter)
- use MyTableCounterDTO to set all the AnotherTable.Number
- Save AnotherTable (s) with MyTableCounter numbers

It worked ok but required too much work to make what I thinked that have to be a easy step.

I not sure if saving a 2nd time the same row/record from same bo and transaction is allowed by sql server on isolation level "read commited"
I thinked that it was the normal behavior of Strataframe when save on transaction that if I save a bo, change it and save again it have to save

I will check your mentioned "trick" and will see if that work without problems. thank you so much for your response.
By Andrew Harper - 6/30/2016

Hi Ben,

I am facing the same situation as described in this post.

Within  a transaction I do the following

1. Save BoOrderMaster to insert a new OrderMaster record with a boOrderMaster.Status ='T' 
2. Save BoOrderLines to insert the orderlines
3. Set  boOrderMaster.Status ='U'
4. Save BoOrderMaster
5. commit 

Step 4 is not updating the database

As per your previous suggestion I have tried the inserting following code prior to Step 4 

Dim isSavedOnTransactionField As FieldInfo
isSavedOnTransactionField = boOrderMaster.GetType().GetField("_IsSavedOnTransaction", BindingFlags.NonPublic Or BindingFlags.Instance)        
isSavedOnTransactionField.SetValue(boOrderMaster, False)  

The   isSavedOnTransactionField.SetValue(boOrderMaster, False) statement throws an error.

I have been able to get around the problem in this instance by performing steps 3 and 4 after the commit but am wondering if am missing something here and/or if the suggested work around using reflection is still valid and has been tested.

TIA Andy