The EntitySpaces Community

Share and learn about the EntitySpaces Architecture.
Welcome to The EntitySpaces Community Sign in | Join | Help
in
Home Forums Photos

Detach- (and probably Attach-) Entity not 'working'

Last post 08-31-2008, 8:02 AM by Mike.Griffin. 19 replies.
Page 1 of 2 (20 items)   1 2 Next >
Sort Posts: Previous Next
  •  08-26-2008, 1:27 AM 10907

    Detach- (and probably Attach-) Entity not 'working'

    Hi,

    I have a EntityCollection which is bound to a GridView (and another component) through a BindingSource. I need to remove one entity from the collection and add it again so that the databound controls reflect changes in only that entity.

    • If I use DetachEntity(entity) on the Collection, it 'doesn't work'. The row is still visible in the Gridview. AttachEntity(entity) doesn't work either.. the extra row is not shown in the GridView.
    • If I use Remove(entity) on the BindingSource it 'doesn't work'. There is an error message saying the Row cannot be found in the RowCollection. Add(entity) does work, however I need to Remove it first, which didn't work...

    How can I remove an Entity from a Databound collection and keep it databound?

    code snippets (I only use one of the provided possiblities at once in the code below, just adding them together...):

    Code:
        Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
            'Removing Entity
            Dim p As BLL.EpPlan
            For Each p In theList
                If p.EppAutoKey.Equals(46951) Then
                    'Removing from Collection -> doesn't work
                    Me.theList.DetachEntity(p)
                    'Removing from BindingSource -> doesn't work
                    CType(DataGridView1.DataSource, BindingSource).Remove(p)
                    Exit For
                End If
            Next
        End Sub
    
        Private Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
            'Adding entity
            Dim p As New BLL.EpPlan
            p.LoadByPrimaryKey(46951)
            'Attaching Entity to Collection -> doesn't work
            Me.theList.AttachEntity(p)
            'Adding Entity to BindingSource -> does work
            CType(DataGridView1.DataSource, BindingSource).Add(p)
        End Sub
  •  08-26-2008, 3:54 AM 10908 in reply to 10907

    Re: Detach- (and probably Attach-) Entity not 'working'

    Hi

    I think it may be a problem with your Gridview not refreshing rather than Attach/Detach not working.  I've just mocked up a Winfom test with a datagridview bound to a bindingsource, the bindingsource having its datasource set to my entity collection.  I then added 2 buttons, one to attach a new entity, and the other to detach it.  Clicking the attach button results in the new entity showing immediately in the DGV, the detach immediately removes it from the DGV.

    Unfortunately I don't code webforms (yet) so can't offer any specific advice other than perform a refresh on your grid so that it reflects the current state of the datasource

    Cheers

    Martin

  •  08-26-2008, 4:20 AM 10910 in reply to 10908

    Re: Detach- (and probably Attach-) Entity not 'working'

    Lol strange,

    as you can see in my code example i also use a DataGridView. Is yours different than mine?

    The problem is that a refresh totally destroys the benefit of the control being databound. This makes all rows reload (and re-trigger all row_databound events in stead of only the one being attached...)

    1.) Are you DE-taching the entity the same way as i'm doing it in my example? Because attach also works for me, only detach doesn't seem to work...

    2.) Edit: I use a esEntityCollectionView(Of EntityCollection) to re-use the data and apply different views on the EntityCollection. If I detach/attach an Entity, the changes should be reflected by the esEntityCollectionView also right? Because this doesn't happen.. Smile

     

    A small code snippet, I hope this helps a bit...:

    Code:
    Public Class FormProduction
        Private _AllEpPlans As BLL.EpPlanCollection
    
        Private Sub FormProduction_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
            'Application initialization
            Common.LoadEntitySpacesFactory()
    
            'Form initialization
            Me._AllEpPlans = New BLL.EpPlanCollection
            Me._AllEpPlans.LoadAll()
        End Sub
    
        Private Function getBindingSourceFromView(ByVal Filter As String, ByVal OrderBy As String, Optional ByVal HandleChanges As Boolean = False) As BindingSource
            Dim v As New EntitySpaces.Core.esEntityCollectionView(Of BLL.EpPlanCollection)(Me._AllEpPlans)
            Dim bs As New BindingSource
    
            v.Filter = Filter
            v.Sort = OrderBy & " ASC"
            bs.DataSource = v
    
            AddHandler bs.ListChanged, AddressOf PlanCollection_Changed
            Return bs
        End Function
    
        Private Sub PlanCollection_Changed(ByVal sender As Object, ByVal e As EventArgs)
            MsgBox("list changed")
        End Sub
    
        Private Sub Button1_Click_1(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
            Dim strFilter as string = "EppParent Is Null"
            'Load Gantt
            Gantt1.Grid.RootNodes_DataSource = getBindingSourceFromView(strFilter, "Description")
            Gantt1.Grid.GridStructure.CollapseAll(True)
        End Sub
    
        Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
            'Detach Button
            Dim p As BLL.EpPlan
    
            For Each p In Me._AllEpPlans
                If p.EppAutoKey.Equals(44781) Then
                    Me._AllEpPlans.DetachEntity(p)
                End If
            Next
        End Sub
    
        Private Sub Button3_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button3.Click
            'Attach Button
            Dim p As New BLL.EpPlan
            p.LoadByPrimaryKey(44781)
            Me._AllEpPlans.AttachEntity(p)
        End Sub
    End Class
  •  08-26-2008, 5:04 AM 10911 in reply to 10910

    Re: Detach- (and probably Attach-) Entity not 'working'

    Hi

    I've just altered my code to look specifically at detaching only (i.e. not attaching something first) - setup as follows (Winform again)

    1. Bindingsource - datasource set to Northwind's "EmployeesCollection" (coll) - I use coll.LoadAll after my initialisation code

    2. DGV - datasource set to Bindingsource

    3. I run the following code in my "detach" button click event.

    Code:
    	Sub DetachEntityButtonClick(ByVal sender As Object, ByVal e As EventArgs)
    		Dim ent As Employees = CType(Me.bindingSource1.Current, employees)
    		
    		coll.DetachEntity(ent)
    	End Sub
    

    All works fine - changes are immediately visible in the DGV

    One thing I would say is that your code snippet modifies the collection that you're foreach-ing through - you shouldn't be doing this as it results in unexpected behaviour as you're removing one of the items in the collection you're 'walking' through.

    Hope that helps

    Martin

  •  08-26-2008, 5:31 AM 10914 in reply to 10911

    Re: Detach- (and probably Attach-) Entity not 'working'

    The Detaching was indeed not possible because it happened in the For Each loop, so now this works, however changes are still not reflected...

    The esEntityCollectionView(of EntityCollection) (which is used as datasource for the BindingSource) doesn't seem to notice that the underlying collection has changed...... So the BindingSource and thus the GridView aren't noticing the Entity being attached/detached....

    Is this feature missing? Or am I doing something wrong?

  •  08-26-2008, 6:16 AM 10915 in reply to 10914

    Re: Detach- (and probably Attach-) Entity not 'working'

    I think based on your last comment I know what the problem is. The esEntityCollectionView creates it's own DataView so that sorting and filtering are kept seperate from other views, however, the esEntityCollection is only catching events from the DataTable "DefaultView" which is not your view. Or stated this way, your Grid is bound to the esEntityCollectionView classes custom DataView but Attach/Detach aren't catching your custom DataView events. I will look at this and fix it. If you were just bound directly to a collection and not the esEntityCollectionView it would work. We are working hard on a really good maintenance release and I will look at this.
    EntitySpaces | Twitter | BLOG | Please honor our Software License
  •  08-26-2008, 6:29 AM 10917 in reply to 10915

    Re: Detach- (and probably Attach-) Entity not 'working'

    At this point I am really unable to bind to a collection because I need independent filtering on the same collection. The collection contains both Workorders and their Subtasks (both modelled as 'Plans' in a parent-child construction...)

    Do you have any e.t.a. on the release?

  •  08-26-2008, 6:53 AM 10918 in reply to 10917

    Re: Detach- (and probably Attach-) Entity not 'working'

    It will be no later than Sept 13, hopefully more like the 6th. I can't guarantee anything on the date. What I can do is push a beta up as soon as I fix it once David runs the unit tests, and that could be by this weekend perhaps.
    EntitySpaces | Twitter | BLOG | Please honor our Software License
  •  08-27-2008, 12:20 AM 10954 in reply to 10918

    Re: Detach- (and probably Attach-) Entity not 'working'

    Wow, that would be fantastic. I'll keep looking out for updates on this...
  •  08-27-2008, 4:36 PM 10981 in reply to 10954

    Re: Detach- (and probably Attach-) Entity not 'working'

    Bad news, I cannot reproduce this. I have two grids bound to different esEntityCollectionView objects and when I Detach and entity from the collection both grids reflect the change? I think you're going to have to send a sample.

    Here's my entire test

     

    Code:
    namespace EntitySpacesDemo
    {
    public partial class Views : Form
    {
    EmployeesCollection coll = new EmployeesCollection();

    esEntityCollectionView view1;
    esEntityCollectionView view2;

    public Views()
    {
    InitializeComponent();
    }

    private void Views_Load(object sender, EventArgs e)
    {
    coll.Query.es.Top = 5;
    coll.Query.Load();

    view1 = new esEntityCollectionView(coll);
    view2 = new esEntityCollectionView(coll);

    this.dataGridView1.DataSource = view1.LowLevelBind();
    this.dataGridView2.DataSource = view2.LowLevelBind();
    }

    private void btnD1_Click(object sender, EventArgs e)
    {
    coll.DetachEntity(coll[0]);
    }
    }
    }
     

    When I click on the button I remove an entity from the collection and it disappears from both Grids. I even tried the same thing using BindingSource's and it still works.


    EntitySpaces | Twitter | BLOG | Please honor our Software License
  •  08-28-2008, 1:38 AM 10992 in reply to 10981

    Re: Detach- (and probably Attach-) Entity not 'working'

    Hi Mike,

    I see I didn't use LowLevelBind(). The codefragment below doesn't work, but when I add the LowLevelBind it does!!!!!!!

    Code:
    Imports EntitySpaces.Interfaces
    
    
    Public Class Form2
        Private PlanCollection As BLL.EpPlanCollection
        Private Sub Form2_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
            esProviderFactory.Factory = New EntitySpaces.LoaderMT.esDataProviderFactory()
    
            'Load all plans, around 5000 records
            PlanCollection = New BLL.EpPlanCollection
            PlanCollection.LoadAll()
    
            Dim root As New EntitySpaces.Core.esEntityCollectionView(Of BLL.EpPlanCollection)(PlanCollection)
            Dim rootBs As New BindingSource
    
            'Filter view, just showing rootItems
            root.Filter = "Epp_Parent Is Null"
    
            'Set BindingSource datasource
            rootBs.DataSource = root
    
            'Set Gantt Datasource
            DataGridView1.DataSource = rootBs
        End Sub
    
    
        ''' <summary>
        ''' DETACH FUNCTION
        ''' </summary>
        ''' <remarks></remarks>
        Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
            Dim p As BLL.EpPlan
            Dim pToDetach As BLL.EpPlan
    
            For Each p In PlanCollection
                If p.EppAutoKey = 46951 Then
                    pToDetach = p
                End If
            Next
    
            If pToDetach IsNot Nothing Then
                Dim preCount As Integer
                Dim postCount As Integer
    
                preCount = PlanCollection.Count
                PlanCollection.DetachEntity(pToDetach)
                postCount = PlanCollection.Count
    
                MsgBox("Detached" & vbCrLf & "pre: " & preCount & vbCrLf & "post: " & postCount)
            End If
        End Sub
    
    
        ''' <summary>
        ''' ATTACH FUNCTION
        ''' </summary>    
        ''' <remarks></remarks>
        Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
            Dim p As New BLL.EpPlan
            Dim preCount As Integer
            Dim postCount As Integer
    
            p.LoadByPrimaryKey(46951)
    
            preCount = PlanCollection.Count
            PlanCollection.AttachEntity(p)
            postCount = PlanCollection.Count
    
            MsgBox("Attached" & vbCrLf & "pre: " & preCount & vbCrLf & "post: " & postCount)
        End Sub
    End Class

     

  •  08-28-2008, 2:21 AM 10995 in reply to 10992

    Re: Detach- (and probably Attach-) Entity not 'working'

    Darn,

    LowLevelBind does f*ck up a lot of my original application.... DBNull errors I was hoping never to face again....

     

    Is it true that the IPropertyDescriptor interface is not implemented anymore when using LowLevelBind? I have to pass the column names of StartDate and FinishDate as a string. With LowLevelBind it means that the column names match the database column fields (Start_Date and Finish_Date), but the component doesn't find the values.... If i do the bind on the view directly and if I pass StartDate and FinishDate (columnnames of EntitySpaces entity), then the values are found and the component loads normally....

  •  08-28-2008, 4:02 AM 10998 in reply to 10995

    Re: Detach- (and probably Attach-) Entity not 'working'

    I wasn't recommending LowLevelBind as a fix actually. I think you need to whip up a sample application and send it to me. We are quickly approaching the last ES2008 maintenance release this year and this fix might not make it unless we get a working sample. If you can generate one against northwind that would be great, we will need to be able to run it. Sad

    EntitySpaces | Twitter | BLOG | Please honor our Software License
  •  08-28-2008, 5:51 AM 11003 in reply to 10998

    Re: Detach- (and probably Attach-) Entity not 'working'

    Hi Mike

    Here's a simple test form that replicates this issue (running against Northwind)

    1) Create a Winform project - on the default form add 1 x datagridview (called DGV), 1 x BindingSource (called bs) and 1 x button (called DetachButton)

    2) Add the following code to the form:

    Code:
    imports BusinessObjects
    Imports EntitySpaces.Interfaces
    Imports EntitySpaces.Core
    imports System.ComponentModel
    
    Public Partial Class testform
    	
    	Private _coll As new EmployeesCollection
    	Private _collView as esEntityCollectionView(Of EmployeesCollection)
    
    	Public Sub New()
    		' The Me.InitializeComponent call is required for Windows Forms designer support.
    		Me.InitializeComponent()
    		
    		'
    		' TODO : Add constructor code after InitializeComponents
    		'
    	End Sub
    	
    	Sub TestformLoad(ByVal sender As Object, ByVal e As EventArgs)
    		esProviderFactory.Factory = New EntitySpaces.Loader.esDataProviderFactory()
    
    		_coll.LoadAll
    		_collView = new esEntityCollectionView(Of employeescollection)(_coll)
    
    		bs.DataSource = _collView '*** If you alter this to set the datasource to the collection (_coll) it works as expected
    		DGV.AutoGenerateColumns = True
    		DGV.DataSource = bs
    	End Sub
    	
    	Sub DetachButtonClick(ByVal sender As Object, ByVal e As EventArgs)
    		debug.Print("Before detach")
    		debug.Print("coll.Count = " + _coll.Count.ToString())
    		debug.Print("collView.Count = " + _collView.Count.ToString())
    		debug.Print("Bindingsource.Count = " + bs.Count.ToString())
    		debug.Print("*************")
    
    		Dim ent As Employees = CType(Me.bs.Current, employees)
    		_coll.DetachEntity(ent)
    		debug.Print("After detach")
    		debug.Print("coll.Count = " + _coll.Count.ToString())
    		debug.Print("collView.Count = " + _collView.Count.ToString())
    		debug.Print("Bindingsource.Count = " + bs.Count.ToString())
    		
    	End Sub
    End Class
    

    When you run this, you'll see that although the collection (and view against that collection) show the correct count after the entity is detached, the bindingsource still shows the count BEFORE the detach happened - even a call to BindingSource.ResetBindings doesn't sort this out I'm afraid.  If you alter the line with the asterisks so that the datasource of the bindingsource is set to the collection instead of the view of the collection, all works as expected and changes are reflected immediately.

    Hope this helps

    Martin

  •  08-28-2008, 6:15 AM 11004 in reply to 11003

    Re: Detach- (and probably Attach-) Entity not 'working'

    Hi

    Just had a quick play with this and have come up with the following (extremely kludgy) work-around.

    If you place the following code after the call to collection.Detach(entity) then it works fine - FYI I turned off event notification to prevent screen flutter when clearing/reseting the datasource

    Code:
    bs.RaiseListChangedEvents = false
    bs.DataSource = Nothing
    bs.DataSource = _collView
    bs.RaiseListChangedEvents = True
    bs.ResetBindings(false)

    Far from ideal I know, but a workaround nonetheless

    Cheers

    Martin

Page 1 of 2 (20 items)   1 2 Next >
View as RSS news feed in XML