How to create a ReadOnlyListBase object as a GrandChild

How to create a ReadOnlyListBase object as a GrandChild

Old forum URL: forums.lhotka.net/forums/t/8292.aspx


zhengokusa posted on Wednesday, January 06, 2010

I have a parent object as ReadOnlyListBase called ROLicensedPropertyRootList, and it contains many ReadOnlyBase objects called ROLicensedProperty. In each ROLicensedProperty object it contains another ReadOnlyListBase object called ROLicensedAssetsList then in this object it contains many ReadOnlyBase called ROLicensedAsset.

So in my parent dataportal I do a database call and it will return two Results.

------------------------------------------------------------------------------

1000 Alabama A&M University                1000  Acme Licensing Agency
1001 University of Arkansas at Pine Bluff  1000  Acme Licensing Agency
1002 Troy University                                1000  Acme Licensing Agency

-----------------------------------------------------------------------------

1004 1000 PrimaryLogo Primary Logo         1                     Current  1
1005 1000 SecondaryLogo Secondary Logo 1                    Current  1
1006 1000 PrimaryLogoStiches Primary Logo Stiches          Current  2
1007 1000 SecondaryLogoStiches Secondary Logo Stiches  Current  2
1009 1001 PrimaryLogo Primary Logo 1                              Current  1
1010 1001 SecondaryLogo Secondary Logo 1                     Current  1
1011 1001 PrimaryLogoStiches Primary Logo Stiches           Current 2
1012 1001 SecondaryLogoStiches Secondary Logo Stiches  Current  2

-----------------------------------------------------------------------------

The code in parent ReadOnlyListBase is:

 private void DataPortal_Fetch(SingleCriteria<ROLicensedPropertyRootList, int> criteria)
        {
            RaiseListChangedEvents = false;
            IsReadOnly = false;
            using (SqlConnection connection = new SqlConnection(DataConnection.ConnectionString))
            {
                connection.Open();
                using (SqlCommand command = new SqlCommand("sp_ROLicensedPropertyRootList_Get", connection))
                {
                    command.CommandType = System.Data.CommandType.StoredProcedure;
                    command.Parameters.Add(new SqlParameter("@manfacID", criteria.Value));
                    using (Csla.Data.SafeDataReader reader = new Csla.Data.SafeDataReader(command.ExecuteReader()))
                    {
                        while (reader.Read())
                        {
                            Add(ROLicensedProperty.GetReadOnly(reader));
                        }
                        reader.NextResult();
                        int propID = 0;
                        while (reader.Read())
                        {
                            propID = reader.GetInt32("PROP_ID");
                            foreach (ROLicensedProperty aProperty in this)
                            {
                                if (aProperty.PropID == propID)
                                {
                                   //Not sure how to do here. I cannot simply Add it like I did in Editable List because it is ReadOnly List Object. So How could I do it here?

                                     aProperty.LicensedAssetList.Add(ROLicensedAsset.GetROLicensedAsset(reader));
                                }
                               
                            }
                        }
                        reader.NextResult();
                    }
                }
                connection.Close();
            }
            IsReadOnly = true;
            RaiseListChangedEvents = true;
        }

 So the second result which is a collection of all assets, and based on the PropID it will try to added to the ROLicensedAssetsList object which is a child of  a ROLicensedProperty object

I did something similar with editable object it works. However, when I try to do it on ReadOnly objects. it gives me error. I think the key is on how my ROLicensedAssetsList was created. What is the Template for doing ReadOnlyListBase as a GrandChild ?

Thanks,

 

 

William replied on Wednesday, January 06, 2010

To my understanding, ReadOnlyBase and ReadOnlyListBase do not explicitly differentiate parent/child relationship in code as they fetch and hold unmodifiable objects in memory.

In your parent data access code, instead of calling the public Add() method from your read-only child list, you should invoke the corresponding internal factory method or Fetch() method from the list instead. Based on common practices, ReadOnlyListBase has an internal IsReadOnly property, which is set to true by default. Thus, your code in Fetch() will need to turn this flag to false, load/add the list objects, then turn it back to true before the function returns.

Hope this helps.

zhengokusa replied on Thursday, January 07, 2010

I understand I have to use a factory method instead of Add(), however, in my case I don't know to

to do a factory method fetch to consume the data like the following code

using (SqlCommand command = new SqlCommand("sp_ROLicensedPropertyRootList_Get", connection))
                {
                    command.CommandType = System.Data.CommandType.StoredProcedure;
                    command.Parameters.Add(new SqlParameter("@manfacID", criteria.Value));
                    using (Csla.Data.SafeDataReader reader = new Csla.Data.SafeDataReader(command.ExecuteReader()))
                    {
                        while (reader.Read())
                        {
                            Add(ROLicensedProperty.GetReadOnly(reader));
                        }
                        reader.NextResult();
                        int propID = 0;
                        while (reader.Read())
                        {
                            propID = reader.GetInt32("PROP_ID");
                            foreach (ROLicensedProperty aProperty in this)
                            {
                                if (aProperty.PropID == propID)
                                {
                                    //I can do this on Editable object just by do a Add() operation. however I cannot do it here because it is
                                    //a Readonlylist object. My question is how to create a ROLicensedAssetsList object
                                    //that accept this kind of operation.

                                    aProperty.LicensedAssetList ????????? what to do here?                                  }
                            }
                        }
                        reader.NextResult();
                    }
                }

zhengokusa replied on Friday, January 08, 2010

Just want to share the information with you all

I got help from Sergey

That's what he wrote to me

Instead of calling LicensedAssetList.Add create a custom method in that list that would set IsReadOnly to false, add new items, then turn readonly to true again.

THanks.

Thanks to Sergey .

Copyright (c) Marimer LLC