Remove entities and remove relationships on Entity framework - entity-framework

I´m using EF databaseFrist and creating a model, now having a problem trying to understand how to delete an entity or a relationship.
Lest say a have and Table "A" and a Table "B", and a "a_b" table that relates A and B by id (many to many), a_b only has id_A and id_B, so there is no entity a_b created on the model. A has a list<B> and B has a list<A>, i need to know how can i perform the next functions:
-Remove all B entities related to A, it means delete the rows of B.
-Remove only the relationships of A to B, so all entities still exist on DB but they are dissociated.
-Delete A and remove all B related as well (remove entities from DB).
-Delete A and preserve all B entities.
-How will it change if a_b has any other property so it becomes an entity
thanks for your time.
pd: I´m using Lambda syntax.

You can tell EF on DB First model creation to expose all primary and foreign-key properties in the entities. What it means to you is that you can query separately by querying for child objects to a parent by using the foreign-key property of the child object linked to the parent object's primary key. You can delete each child object to the parent by the child's primary-key property value to remove the relationship between parent and child. You can delete the parent if no child object is linked to the parent. That's if one is doing things normally in a deletion process using EF where one takes complete control of the deletion process.
So, you can kind of do something like that.

Related

Establishing One-to-One Relationship in Entity Framework

When working with a one-to-one relationship at the database level, we (I?) often end up implementing what is actually a one-to-many relationship.
For example:
CREATE TABLE master (masterId INT PRIMARY KEY)
and
CREATE TABLE child (
childId INT PRIMARY KEY,
masterId INT,
CONSTRAINT child_master_fk FOREIGN KEY (masterId) REFERENCES master (masterId))
While a single child can only reference a single master, there is nothing preventing multiple childs from referencing the same master, resulting in a one-to-many relationship.
When generating an entity data model from such a database set-up, this gets reflected with the fact that the master entity will contain a reference to the child entity, but the child entity will have a master entity collection.
Since I logically see the relationship as one-to-one, I never expect the child's master collection to contain more than one element; thus, I'd like the child entity to have a single master reference instead of a collection.
What is the correct way of accomplishing this? Creating a two-way foreign key constraint at the database level? Tweaking the generated model?
Tweak the model. Add a singular reference property that returns the single instance and just ignore the collection property. Then set the singular property to be ignored by EF in your mapping configuration.
It isn't what I'd call elegant, but such sacrifices often have to be made when using EF with a pre-existing database.

Entity Framework inheritance moving a foreign key to a child in TPH

I'm using table per hierarchy inheritance within my enitity model and I have a parent table that contains relationships to other tables via foreign keys.
My parent table (Product) has a FK relationship to another table which in EF resolves to a Navigation Property. I can easily move that navigation property to my child table (Fragrance) and delete it from the parent which is great. However I also want to move the foreign key property (FragranceId) to the child but I can't work out how to do this because the FK relationship requires that my parent table has that property.
The diagram below illustrates how far I've got, basically what I'm trying to do is move the FragranceId into the Perfume entity.
It seems like this should be possible but since Perfume is not a table it can't take on the database relationship and while that relationship exists between Fragrance and Property I can't remove FragranceId from Product.
Moving the FragranceId leads to an EF error 'there is no property with the name FragranceId defined in the type referred by Role Product.
The relationship between Fragrance and Perfume is 1 to 1.
Any help would be awesome. Thanks.
So it turns out the answer is pretty simple I just needed to delete the database foreign key relationship from my entity model and I could move the FragranceId to the perfume entity.
I then needed to manually remove all reference to the FK from the edmx file's XML to resolve error 3015 and finally re-map the FragranceId to fix error 3004.

EF anonymous object query returns null collections instead of empty ones

I'm using this trick to perform conditional Include's with EF. http://blogs.msdn.com/b/alexj/archive/2009/10/13/tip-37-how-to-do-a-conditional-include.aspx
The problem I'm having is that any collections that don't have records, are null, and not empty. This is causing headaches cos I have to check each collection before I can loop through it in my mvc view, otherwise i get a null reference exception.
For example, the StudentModules collection will be null. How can I turn it into an empty list in my query? ie without having to loop through it all and checking.
I can put a constructor in the poco to initialize the list, which fixes it, but the this collection is a virtual member in the poco (based on an EF video!) - surely this is not the way to go?
var query = from module in db.Modules
where module.Id == id
select new
{
module,
QualificationModules = from qualificationModule in module.QualificationModules
where qualificationModule.IsDeleted == false
select new
{
qualificationModule,
qualificationModule.Qualification,
StudentModules = from studentModule in qualificationModule.StudentModules
where studentModule.IsDeleted == false
select new
{
studentModule,
studentModule.Student
}
},
Assessments = (from assessment in module.Assessments
where assessment.IsDeleted == false
select new
{
assessment,
assessment.AssessmentType
}
)
};
var modules = query.AsEnumerable().Select(x => x.module);
return modules.ToList().First();
Relationship fixup runs when an entity gets attached to a context - either manually by calling Attach or when the entity is materialized as a result of a query (your case).
It is based on foreign keys of an entity and works in both directions:
If the context already contains an entity A with a foreign key f to entity B and an entity B is being attached to the context that has a primary key with the same value f as the foreign key in A (i.e. the two entities are related by an FK relationship) then Entity Framework will do the following:
If A has a navigation reference property to B it will assign the attached entity B to this property.
If B has a navigation reference property to A (one-to-one relationship) it will assign A to this property.
If B has a navigation collection property to A (one-to-many relationship) it will add A to this collection in the attached entity B. If the collection is null it will instantiate the collection before adding.
If an entity B is being attached to the context that has a foreign key f to an entity A that the context already contains and that has f as primary key EF will set the navigation properties based on the same rules like above.
As a side note: The fact that relationship fixup is based on foreign keys (they are always loaded when you query an entity, no matter if the FK is exposed as property in the model class or not) is also the reason why relationship fixup does not apply to and does not work for many-to-many relationships because the two entities of a many-to-many relationship don't have a foreign key.
Now, if there are no related StudentModules in your case there is no StudentModule entity that gets loaded into the context and there is nothing what EF could target for a fixup. Keep in mind that the fixup algorithm is not related to a particular query and does not only fix relationships between entities that this query would materialize but it will consider all entities for fixup that the context already contains, no matter how they came into the context. If you would want that collections get instantiated as empty collections EF had run through all attached parent entities of StudentModules and just create an empty collection. It makes no sense to do this during fixup instead of creating empty collections up-front before entities get attached to a context.
I can put a constructor in the poco to initialize the list, which
fixes it, but the this collection is a virtual member in the poco
(based on an EF video!) - surely this is not the way to go?
In my opinion it is the best solution if you don't want to have null collections in your model class instances. It doesn't matter if the collection is declared as virtual (to enable lazy loading) or not. A collection type does not have a derived proxy type, only the instances that get added to the collection are derived proxies. In both case you can just use StudentModules = new HashSet<StudentModule>(); (or List if you prefer).

How to use DBContext.Add/Attach (using EF CodeFirst 4.1) with nested opbjects

Problem: When adding an object "Order" to my dbcontext, all nested objects of the order gets "readded" to the database, though the nested objects is static data and only a reference shoudl be added in the database.
Example:
The database holds 0 orders, and 3 items.
I add one order with 2 items.
Now the database hold 1 order, and 5 items. The two items in the order has been "readded" to the database, even though the items had the right primary keys before db.SaveChanges().
I realize that i may be able to attach the existing items to the dbcontext before saving changes, but is that really the only way to go? Can't EF figure out that to item already exists when the primary key matches an existing item?
Does anyone know if this is different in the new version of EF CodeFirst?
No EF cannot figure if entities are existing one or new one - both Add and Attach commands are graph oriented operations. You call them on one entity in the graph and they traverse all relations (and their relations and so on) and perform the operation for them as well.
You must figure correct state of each entity in the graph for example by using:
dbContext.Orders.Add(newOrder);
foreach(var item in newOrder.Items) {
dbContext.Entry(item).State = EntityState.Unchanged;
}
dbContext.SaveChanges();
You can use the reverse operation by calling Attach(newOrder) and set the order to Added state. The main difference will come with independent associations (for example many-to-many relations). The first approach will correctly add new relation between order and each item whereas second will not unless you manually set each relation to Added state (and changing state for relations is more complex).

Coredata relationship entity creation

I have a question about the coredata relationship.
Essentially, if I have 1 entity called i.e parent and the other entity which it has a relationship with is children and it is inverse.
If I create the parent entity, will it create the children entity as well? I 've set the "parentchildrenrelationship" to optional but it looks like every time I create the parent entity, it creates the children entity.
Is that something normal ? Thanks
It is not normal. Are you sure you're not creating the children entity otherwise? Just because you create one entity does not mean it creates the entities that it is referencing.
Core Data should not automatically create entities to fulfill relationships, especially if the relationship is optional. The value of children should either be nil (for a one-to-one relationship) or an empty NSSet or NSArray (for a one-to-many relationship, depending on ordering) for a newly created parent entity.