Transaction Not working

Posts   
 
    
Sandumone1
User
Posts: 27
Joined: 28-Oct-2009
# Posted on: 03-Nov-2009 01:28:29   

Hi,

I had posted the issue in Architecture group and have not received any exact help.

Can somebody help me and let me know why transaction code is behaving wierd and not serving the porpose it is written for.

We are using selfservicing . SQL Server 2005 database.

the code written is very simple.

we generated the code using the SQL Server datbase . and we were trying to implement Transaction Feature using LLBLGen on the entities generated from database.

This is the first time we are trying the transaction piece as part of POC .

The Problem :

Transaction transactionManager = new Transaction(); Entity entity = new Entity(23);// 23 id i database entity.filedname = "xyz" // field to be updated transactionManager .Add(entity); entity.save(); //this saves everything and transaction.commit or rollback have no relevence.

transactionManager .Commit(); transactionManager .RollBack();

the above commit() and Rolback() methods are not wrking on the entity which is added to transaction.

behavior:

  1. Even if i comment the commit or rollback. the save happens.

When we add something to a transaction, we expect the commit() to be called for things in the transaction to be committed. the rollback should revert back the changes.

This is not happening. we are doing POC with LLBLgen and need to convinse our managers.

please help us out to understand the transaction part of LLBLgen . i did read the documents. but document says as i have written.

The exact code written is :

Database : SQL Server, But we tested on Oracle also and behavior is same. so i think its not Datbase issue.

The code giving issue :

public void UpdateCliamantTypeListInfo(UiClaimmstrVlntryAddrDTO dto) {

        string name = Guid.NewGuid().ToString();
        Transaction transactionManager = new Transaction(IsolationLevel.ReadCommitted, name);


        try
        {
            TClamMstrDTO clmMstDTO = new TClamMstrDTO();
            clmMstDTO.IsNew = dto.IsNew;
            //clmMstDTO.Clmid = dto.Clmid_;
            clmMstDTO.ClmType = dto.ClmType;
            clmMstDTO.ClmStus = dto.ClmStus;
            clmMstDTO.CrtdBy = " XXX ";
            clmMstDTO.CrtdDt = DateTime.Now;
            clmMstDTO.UpdtdBy = " XXX ";
            clmMstDTO.UpdtdDt = DateTime.Now;
            TClamMstrEntity clmMstrEnt = new TClamMstrEntity(clmMstDTO);


            transactionManager.Add(clmMstrEnt);             
            clmMstrEnt.Save();                              


            TClamAddrDTO clmAddrDTO = new TClamAddrDTO();
            clmAddrDTO.IsNew = dto.IsNew;
            clmAddrDTO.Clmid = clmMstrEnt.Clmid;
            clmAddrDTO.AddrLine1 = dto.AddrLine1;
            clmAddrDTO.AddrLine2 = dto.AddrLine2;
            clmAddrDTO.AddrType = dto.AddrType;
            clmAddrDTO.City = dto.City;
            clmAddrDTO.State = dto.State;
            clmAddrDTO.Zip = dto.Zip;
            clmAddrDTO.CrtdDt = DateTime.Now;
            clmAddrDTO.CrtdBy = "XXX";
            clmAddrDTO.UpdtdDt = DateTime.Now;
            clmAddrDTO.UpdtdBy = "XXX";

            TClamAddrEntity clmAddrEnt = new TClamAddrEntity(clmAddrDTO);
            transactionManager.Add(clmAddrEnt);
            clmAddrEnt.Save();


            TVlntryClmDTO objVlnDTO = new TVlntryClmDTO();
            objVlnDTO.IsNew = dto.IsNew;
            objVlnDTO.Clmid = clmMstrEnt.Clmid;
            objVlnDTO.ClmntFname = dto.ClmntFname;
            objVlnDTO.ClmntLname = dto.ClmntLname;
            objVlnDTO.ClmntSsn = dto.ClmntSsn;
            objVlnDTO.CrtdBy = " XXX ";
            objVlnDTO.CrtdDt = DateTime.Now;
            objVlnDTO.UpdtdBy = " XXX ";
            objVlnDTO.UpdtdDt = DateTime.Now;
            TVlntryClmEntity vlnEnt = new TVlntryClmEntity(objVlnDTO);

            transactionManager.Add(vlnEnt);

            vlnEnt.Save();          


            //transactionManager.Commit();



            //transactionManager.Rollback();

        }
        catch (Exception ex)
        {
            transactionManager.Rollback();
            ExceptionManager.HandleException(ex);
        }
        finally
        {
            transactionManager.Dispose();
        }

    }

Note :

We commented the commit transaction, but still the Save above for the entities is working. Are we doing anything wrong

We tried Rollback , but still nothing is rolling back.

If code written is correct. Could it be because of the transaction code generated otr any other reason.

please suggest.

daelmo avatar
daelmo
Support Team
Posts: 8245
Joined: 28-Nov-2005
# Posted on: 03-Nov-2009 06:05:16   

I think your code is not that trivial and POC. Please explain these lines:

clmMstDTO.IsNew = dto.IsNew;
...

TClamMstrEntity clmMstrEnt = new TClamMstrEntity(clmMstDTO);
...

Something in your custom code may be doing something weird in the transaction behavior. At least that is what I guess.

Also please post more information so we could try to reproduce your problem (runtime library version, generated sql, etc.): http://llblgen.com/tinyforum/Messages.aspx?ThreadID=7725

David Elizondo | LLBLGen Support Team
Otis avatar
Otis
LLBLGen Pro Team
Posts: 39862
Joined: 17-Aug-2003
# Posted on: 03-Nov-2009 10:00:23   

Also keep in mind that Save() will save, regardless of what the transaction is doing. Commit and Rollback just finalize and rollback the ADO.NET transaction started by the constructor call of Transaction.

As you seem to have added custom code to the generated classes (As you pass in a DTO to the ctor), did you also add custom code to the save code?

Frans Bouma | Lead developer LLBLGen Pro
Sandumone1
User
Posts: 27
Joined: 28-Oct-2009
# Posted on: 03-Nov-2009 18:55:15   

Otis,

  If you are telling that Save() will anyway Save. I could not understand the answer.

If i Save() and i dont call any commit() method. You are saying that it will save to the database. But, if i have not committed i dont want that in the database in any case.

I think what i am thinking is correct. So, Save() will anyway Save doenst make sense for me.

If Save() will anyway Save. What significance these Commit() has in LLBLgen Pro Transaction.

We need to be 100% sure before we buy LLBLGen as our project is a big one and will span for almost 5 years time. so need to be very sure with every feature of LLBLgen .

**Do you guys have any kind of Telephonic help where you can take us through the features of LLBLgen and answer our questions . I need this now as we are in process of deciding the framework and LLBLgen is fron runner at this moment. I want to understand every aspect and make sure i can present LLBLgen in the high level meetings.

so, please suggest what we can do. I can call you if you can share your number .**

daelmo avatar
daelmo
Support Team
Posts: 8245
Joined: 28-Nov-2005
# Posted on: 04-Nov-2009 03:26:53   

Sandumone1 wrote:

Otis,

  If you are telling that Save() will anyway Save. I could not understand the answer.

If i Save() and i dont call any commit() method. You are saying that it will save to the database. But, if i have not committed i dont want that in the database in any case.

I think what i am thinking is correct. So, Save() will anyway Save doenst make sense for me.

If Save() will anyway Save. What significance these Commit() has in LLBLgen Pro Transaction.

This is normal for ADO.Net transactions. The commands (insert, update, delete, select, etc.) are sent to the server. The atomic process is complete when you Commit or Rollback. Take a look at these MS links: http://msdn.microsoft.com/en-us/library/777e5ebh.aspx http://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqltransaction.aspx

Sandumone1 wrote:

We need to be 100% sure before we buy LLBLGen as our project is a big one and will span for almost 5 years time. so need to be very sure with every feature of LLBLgen .

That's ok. We want to help you. However you need to understand the nature of the transactions (see the docs). Also please the code we ask you. I suspect you have custom code something or maybe you modified the generated code. (see my previous post).

Sandumone1 wrote:

[b]Do you guys have any kind of Telephonic help where you can take us through the features of LLBLgen and answer our questions . I need this now as we are in process of deciding the framework and LLBLgen is fron runner at this moment. I want to understand every aspect and make sure i can present LLBLgen in the high level meetings.

Sorry, there's no phone support. IMHO, if you read the docs, take a look at some examples and ask your questions in the forums should be enough. You also can buy Consultancy.

David Elizondo | LLBLGen Support Team
Otis avatar
Otis
LLBLGen Pro Team
Posts: 39862
Joined: 17-Aug-2003
# Posted on: 04-Nov-2009 09:47:11   

To elaborate why there's no phone support: LLBLGen Pro is about code, and communicating code snippets, error descriptions and stacktraces for example is hard over the phone. We monitor these forums on a regular basis several times a day, and even during weekends, which means you'll get a respons within 12 hours in workdays and 24 hours in weekends and we strive to fix issues (bugs) within 24 hours as well. No worry, we're here to help, however please help us help you too wink (by answering our questions if we have them wink )

Frans Bouma | Lead developer LLBLGen Pro
Sandumone1
User
Posts: 27
Joined: 28-Oct-2009
# Posted on: 05-Nov-2009 01:15:12   

Daelmo,

   I agree that the atomic operations are happening. But when we add the entities to transaction , the save should be sustained when we call commit. But in this case, even if i dont call commit, the save is permanent. i hope you got what i am pointing at. In ADO.Net the behavior is like this.

SqlConnection myConnection = new SqlConnection("Data Source=GDB14166001529\EDDDATABASE;Initial Catalog=Logging;User Id=sa;Password=sandu1990;"); myConnection.Open();

        // Start a local transaction.
        SqlTransaction myTrans = myConnection.BeginTransaction();

        // Enlist the command in the current transaction.
        SqlCommand myCommand = myConnection.CreateCommand();
        myCommand.Transaction = myTrans;

        try
        {
            myCommand.CommandText = "Insert into Category (CategoryName) VALUES ('santhosh16')";
            myCommand.ExecuteNonQuery();
            myCommand.CommandText = "Insert into Category (CategoryName) VALUES ('balaji16')";
            myCommand.ExecuteNonQuery();
        ** myTrans.Commit();**              Console.WriteLine("Both records are written to database.");
        }
        catch (Exception e)
        {
            try
            {
               myTrans.Rollback();
            }
            catch (SqlException ex)
            {
                if (myTrans.Connection != null)
                {
                    Console.WriteLine("An exception of type " + ex.GetType() +
                                      " was encountered while attempting to roll back the transaction.");
                }
            }

            Console.WriteLine("An exception of type " + e.GetType() +
                              "was encountered while inserting the data.");
            Console.WriteLine("Neither record was written to database.");
        }
        finally
        {
            myConnection.Close();
        }

In the above code , if Commit ( which is in Bold) is commented, Nothing is saved to the database.

This is the scenario i am trying to replicate using LLBLgen Transaction.

qn 1. If i do some operations and dont call Commit() method ,will the actions be save din DB or not? In normal ADO.Net its not saved, What happens in LLBLGen Transaction.

My Answer : It will not save if commit is not called.

OUtput for me: it is saving inspite of not calling transaction.Commit().

So, Daelmo , i dont think its a normal operation. Its having some problem.

Please let me know how LLBLgen behaves for thsi scenario and if it behaves as i am getting the output, its fine. if not what could be the reason for thsi behavior.

I have posted the code directly in earlier posts .

please suggest.

Sandumone1
User
Posts: 27
Joined: 28-Oct-2009
# Posted on: 05-Nov-2009 01:20:11   

Reagrding the custom code,

We have entities generated , which have constructor which takes DTOS as argument and converts them to entities.

here is the custom code in each entity.cs file.

So, every entity in our project has this method which accepts the DTO and converts it to Entity.

public Entity(UiFlowMachineDTO dto) { InitClassEmpty(null); IsNew = dto.IsNew; Fields[(int)UiFlowMachineFieldIndex.MachId].ForcedCurrentValueWrite(dto.MachId); StartState = dto.StartState; MachNa = dto.MachNa; Props = dto.Props; Inherit = dto.Inherit; Gui = dto.Gui; CreateDt = dto.CreateDt; CreateUser = dto.CreateUser; MdfctnDt = dto.MdfctnDt; MdfctnUser = dto.MdfctnUser; UpdateNu = dto.UpdateNu; if (dto.UiFlowState != null) { foreach (UiFlowStateDTO dtoItem in dto.UiFlowState) { (new UiFlowStateEntity(dtoItem)).UiFlowMachine = this; } }

        foreach (EntityField field in Fields)
        {
            field.IsChanged = true;
        }
    }

Does it have anything to do with Transaction probblem. Please suggest.

If i want to test Transaction feature of LLBLgen , how should i generate the code .

I mean which template i should use which will not have any customised code.

Please suggest and i can generate the code using basic template (generic one) and test it.

Please tell me which template i should use as we have templates hsihc do some chnages to the generated code.

Thansk

Sandumone1
User
Posts: 27
Joined: 28-Oct-2009
# Posted on: 05-Nov-2009 01:25:55   

This is normal for ADO.Net transactions. The commands (insert, update, delete, select, etc.) are sent to the server. The atomic process is complete when you Commit or Rollback. Take a look at these MS links: http://msdn.microsoft.com/en-us/library/777e5ebh.aspx http://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqltransaction.aspx

For this,

We should call Commit(), But LLBLgen save method is saving everything permanently even without Commit().

Walaa avatar
Walaa
Support Team
Posts: 14993
Joined: 21-Aug-2005
# Posted on: 05-Nov-2009 10:29:01   

LLBLGen Pro handles Transactions like ADO.NET would do.

What Frans, mesnt earlier is that when you call Save the corresponding command (INSERT or UPDATE) is sent to the database, and if this is within a Transaction, then it won't be permenant unless a Commit is also sent.

The code snippet in the docs is enough to test this.

Sandumone1
User
Posts: 27
Joined: 28-Oct-2009
# Posted on: 05-Nov-2009 18:26:12   

Walla,

thanks for the reply. Your code in the docs works fine for me. But when i remove Commit(), then also its committing. Do you have reason for that??

If i call rollback also its committing.

so, in short when i do what you say in docs...its behaving properly.

But when i remove Commit(), It saves When i rollback instaead of Commit() , then also it saves().

Any suggestions.

MTrinder
User
Posts: 1461
Joined: 08-Oct-2008
# Posted on: 05-Nov-2009 21:39:26   

I think we have got to the point where you need to send us a repro solution. We need a db script to create the needed tables, and enough code (that builds...!) as either a sample winforms or console app to allow us to reproduce the issue at our end.

This will allow us to investigate your issue properly.

Thanks

Matt

Walaa avatar
Walaa
Support Team
Posts: 14993
Joined: 21-Aug-2005
# Posted on: 06-Nov-2009 09:09:15   

Using the same code in the docs and running it against Northwind. When I comment out the Commit code, it never saves anything to the database.

Something somewhere is auto-commiting your transactions.

I too, think that you should send us a repro test solution, better to be on Northwind using the docs code.

Otis avatar
Otis
LLBLGen Pro Team
Posts: 39862
Joined: 17-Aug-2003
# Posted on: 06-Nov-2009 10:39:58   

@Walaa, did you change anything?

ADO.NET transactions: If you start a transaction it will sent a BEGIN TRANS name; statement. Then, if you save anything, you'll see normal INSERT / UPDATE statements being executed, these are normal, as they're inside the database transaction started.

When you then call Commit, the ado.net object will sent a COMMIT TRANS; command and this will finalize the changes made since BEGIN TRANS name at the db level. If you call Rollback, it will sent ROLLBACK TRANS; and all changes made since BEGIN TRANS name; will be rolled back.

So between the start of the transaction (in llblgen pro, the creation of the Transaction object!) and Commit/Rollback, all changes made are visible and live, as that's how sqlserver works.

If you never call Rollback nor commit on the transaction, the changes will also be there, as the transaction is still open! The changes will rollback when the transaction object is disposed, which can take some time, e.g. when the garbage collector runs if you don't dispose it yourself.

Frans Bouma | Lead developer LLBLGen Pro