Saving M:N relation

Posts   
 
    
Fanaticit
User
Posts: 4
Joined: 09-Oct-2007
# Posted on: 09-Oct-2007 17:21:16   

I wanted to find out if there was a clean way to save the parent object and have it save the children in the following structure:

Person -> PersonAddress -> Address

Here is the sample code.

            DataAccessAdapter adapter = new DataAccessAdapter(connectionString);
            PersonEntity person = new PersonEntity(4);

            PrefetchPath2 prePath = new PrefetchPath2((int)EntityType.PersonEntity);
            prePath.Add(PersonEntity.PrefetchPathAddressCollectionViaPersonAddress);
            
            adapter.FetchEntity(person, prePath);
            person.AddressCollectionViaPersonAddress.IsReadOnly = false;

            // add an address
            AddressEntity address = new AddressEntity();
            address = person.AddressCollectionViaPersonAddress.AddNew();
            address.AddressTypeId = 1;
            address.Line1 = "Bla";
            address.Line2 = "Bla";
            address.Line3 = "Bla";

            adapter.SaveEntity(person, true, true);

If I SaveEntityCollection it saves the new Address but not the PersonAddress?

goose avatar
goose
User
Posts: 392
Joined: 06-Aug-2007
# Posted on: 09-Oct-2007 19:08:30   
adapter.SaveEntity(person, true, true);

When you do this, it will recursively save their children entities. It will also internally create a transaction so if something goes wrong it will reverse the whole graph.

If I SaveEntityCollection it saves the new Address but not the PersonAddress?

If you only save the children Collection, it will only save the itself and the children's belonging to this collection, in this case the Address Collection is the last branch of the tree.

Fanaticit
User
Posts: 4
Joined: 09-Oct-2007
# Posted on: 10-Oct-2007 11:22:32   

Hi Goose

This is why I asked the question, because it does not save them. The line of code:

 adapter.SaveEntity(person, true, true)

saves any changes to the person entity, but does not save the changes to PersonAddress and Address.

This is the problem I am having...

I am looking for a nice easy way like this line to save the changes to the child table and the gran-child table.

Walaa avatar
Walaa
Support Team
Posts: 14995
Joined: 21-Aug-2005
# Posted on: 10-Oct-2007 11:40:50   

address = person.AddressCollectionViaPersonAddress.AddNew();

You can't save an m:n entity that way, Since PersonAddress should be saved too, and this can't be done implecitly, since the intermediate table might have more fields than just a couple of FKs to the joined tables.

Please consult the manual for the How do I add an entity A to an entity B's collection of A's if A and B have an m:n relation ?, under "Tutorials and examples -> How do I ... ?"

Fanaticit
User
Posts: 4
Joined: 09-Oct-2007
# Posted on: 12-Oct-2007 15:36:17   

OK. thank-you. I am happy now that I know there is no other way.

I have got something that does this the long way, but can't seem to find what you are talking about in any of the help files that I have. "How do I add an entity A to an entity B's collection of A's if A and B have an m:n relation ?"

Where do I find that manual, or could you just paste the example in the forum?

Walaa avatar
Walaa
Support Team
Posts: 14995
Joined: 21-Aug-2005
# Posted on: 12-Oct-2007 16:05:13   

The manual I'm talking about is the LLBLGen Pro Documentation file.

Here you are:

How do I add an entity A to an entity B's collection of A's if A and B have an m:n relation ?

Say you want to add an Employee to a Department and Employee and Department have an m:n relation. This means that there is an intermediate entity DepartmentEmployees which defines the m:n relation with a foreign key to both Employee and Department. Employee has a collection Departments which results in all Department entities the Employee works for and Department has a collection Employees which results in all Employees working for the Department. In LLBLGen Pro, m:n relations are read-only, therefore, to add an Employee to a Department, you've to use the following steps. The example uses department and employee which are filled in DepartmentEntity and EmployeeEntity instances. You can also use new entities, this doesn't matter.

// Adapter // C# DepartmentEmployees newDepEmp = new DepartmentEmployees(); newDepEmp.Employee = employee; newDepEmp.Department = department; // the 3 entities are now linked. We can now save recursively any of the three (doesn't matter) // to save the relation in the database. adapter.SaveEntity(employee);

Keep in mind that the m:n relation is then saved in the database, but the situation in memory isn't updated, i.e.: employee.Departments doesn't contain 'department'. This is by design, as the m:n relation is based on a 3rd entity, which can be altered by any thread in the system, making the m:n relation, which is a result of the values of the intermediate entity, a 'view' of a situation at a given point in time.