-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 4 posts ] 
Author Message
 Post subject: Transactions with entities in a datagrid
PostPosted: Sat Jun 25, 2005 12:17 pm 
Hi,

I am getting entities from the DB using a HQL query. This returns an IList. I am wrapping each entity in a helper class and each instance is stored in a new IList. This is set as the datasource of a datalist. This is all fine and works well.

I have the datalist setup so that it allows in place editing. Now I did have it so that when the user clicks update the primaryID for the list item was used to re-lookup the entity from the database set the changed fields and then persist. This works as such but does not give me the use of transactions for a particular use case I have giving me, I believe it is called, a lost update.

I need the entity that is originally given to the datalist and to update that as I will contain the version column which would render it dirty when it updates.

I have tried without luck to retrieve the entites from a datalist but it seems to be a one way street. (e.Item.DataItem is something I tried which returns a null). I have also thought about saving the collection to session state but then the app will not know when to get new data or how to deal with someone who just closes their browser.

I have even tried saving the version field to the datalist and used it to construct a new instance of the object with the primary key and version number intact but hibernate complains about having two entities with the same ID loaded in the same session (presumably the other is somewhere in the datalist!)

Is there any pointers how I can deal with this?


Top
  
 
 Post subject:
PostPosted: Mon Jun 27, 2005 9:31 am 
Expert
Expert

Joined: Fri May 13, 2005 5:56 pm
Posts: 308
Location: Santa Barbara, California, USA
Quote:
I have tried without luck to retrieve the entites from a datalist but it seems to be a one way street. (e.Item.DataItem is something I tried which returns a null).


this is not entirely true in my experience. there might be some problems in your code around this. you might want to tyr using the event argument to find the name of the form controls within the grid row. i have some code that does exactly what you are looking at:

Code:
private void AnswerSet_EditCommand(object source, DataGridCommandEventArgs e)
{
   this.MyDataGrid.EditItemIndex = e.Item.ItemIndex;
   this.MyDataGrid.DataSource = this._question.AnswerSet;
   this.MyDataGrid.DataBind();
}

private void AnswerSet_UpdateCommand(object source, DataGridCommandEventArgs e)
{
   TextBox displayOrder = (TextBox) e.Item.FindControl("DisplayOrder");
   TextBox answerText = (TextBox) e.Item.FindControl("Text");
   TextBox scoreValue = (TextBox) e.Item.FindControl("ScoreValue");

   // apply values to my object within the AnswerSet collection
   // ...

   // call the update
   base.DomainManager.UpdateObject(this._question);

   this.MyDataGrid.EditItemIndex = -1;
   this.MyDataGrid.DataSource = this._question.AnswerSet;
   this.MyDataGrid.DataBind();
}


Top
 Profile  
 
 Post subject:
PostPosted: Mon Jun 27, 2005 11:58 am 
Newbie

Joined: Mon Jun 27, 2005 11:49 am
Posts: 7
Location: Norwich, UK
Hi devonl,

Thanks for the reply. Nearly a carbon-copy of the code I have! :D

Code:
public void OnUpdate(object source, DataListCommandEventArgs e)
      {
         /* Get the updated values from the form */
         int vehicleID = Convert.ToInt32(vehiclesDataList.DataKeys[e.Item.ItemIndex].ToString());

         /* check date given is valid otherwise use todays date */
         DateTime date;
         string dateString = DataValidation.ValidateDate(((TextBox)(e.Item.FindControl("txtDate"))).Text);
         if (dateString != null)
         {   
            date = Convert.ToDateTime(dateString);
         }
         else
         {
            date = DateTime.Now;
         }

         /* check price is valid otherwise set to 0 - maybe change this? */
         decimal price;
         string priceString = DataValidation.ValidatePrice(((TextBox) e.Item.FindControl("txtPrice")).Text);
         if(priceString != null)
         {
            price = Convert.ToDecimal(priceString);
         }
         else
         {
            price = 0;
         }
         
         /* Get the other fields */
         string manufacturer = ((TextBox) e.Item.FindControl("txtManufacturer")).Text;
         string model = ((TextBox) e.Item.FindControl("txtModel")).Text;
         string regNumber = ((TextBox) e.Item.FindControl("txtRegNumber")).Text;
         
         string stockNumber = ((TextBox) e.Item.FindControl("txtStockNumber")).Text;
         string orderNumber = ((TextBox) e.Item.FindControl("txtOrderNumber")).Text;
         bool cancelled = ((CheckBox) e.Item.FindControl("chkIsCancelled")).Checked;
         bool readyToInvoice = ((CheckBox) e.Item.FindControl("chkIsReadyToInvoice")).Checked;

         int driverID = Convert.ToInt32(((DropDownList) e.Item.FindControl("lstDriver")).SelectedValue);
         int transporterID = Convert.ToInt32(((DropDownList) e.Item.FindControl("lstTransporter")).SelectedValue);
         int version = Convert.ToInt32(((Label) e.Item.FindControl("version")).Text);

         /* Get the session */
         ISession session = SessionHandler.CurrentSession;
         
         /* Get the selected driver & transporter */
         Driver driver = DataAccessLayer.GetDriverByID(driverID, session);
         Transporter transporter = DataAccessLayer.GetTransporterByID(transporterID, session);
         
         Vehicle vehicle = new Vehicle();
         vehicle.ID = vehicleID;
         vehicle.Version = version;

         /* Update vehicle fields here */
         // chopped for brevity

         if(vehicle.IsCancelled)
         {
            /* Delete the vehicle */
            SessionHandler.DeleteObject(vehicle);
         }
         else
         {
            /* Update vehicle */
            SessionHandler.UpdateObject(vehicle);
         }

         /* Unset edit row */
         this.vehiclesDataList.EditItemIndex = -1;
         BindGrid();
      }


This is throwing the following error:
Code:
another object with the same id was already associated with the session: [Vehicle#11]


In your code how is "this._question" set and where is it stored? If in session how does your code know to go to the database for a new version?

I will take another look at my code to work out why the DataItem property is not returning anything. It can't all be null as I am getting the values from the controls ok just need to get my business object back!


Top
 Profile  
 
 Post subject:
PostPosted: Tue Jun 28, 2005 10:01 am 
Newbie

Joined: Mon Jun 27, 2005 11:49 am
Posts: 7
Location: Norwich, UK
I'm managed to sort this for the moment by putting the Entity into session state if the update event is fired and then get it back when updating the entity which now works as I hoped.

A few problems with this approach: Stale data, and if a user goes away. However this is not much of a problem at all as this is an internal app with few users.


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 4 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.