ExecuteDelete from Entity Framework 7.0 throws System.InvalidOperationException - c#

I have 3 classes in my DB. Human, Car and Address.
Human class has navigation properties to Car and Address and also foreign keys to the Car and Address tables (CarId and AddressId).
Car and Address classes have only navigation properties. Car has property of type Human? and Address has property of type ICollection? .
I try to use ExecuteDelete for all addresses and i got an exception when i try to use ExecuteDelete :
dbContext.Set.ExecuteDelete();
I attached
to the post.
If i understand right, i need to remove navigation property Humans from Address entity before ExecuteDelete . But how i can do it and also in generic way...
I don't have any Humans in Human table. By the way what is there a way to do cascade delete with ExecuteDelele method.
Any help to understand what i'm doing wrong will be appreciated.
Thank you.
I tried to use Where and Select without any special success...

Related

EF6 Code First : Entity with multiple relationships

I am creating a new database using EF code-first which contain the following classes:
Address, Contact, Account, Customer (a sub-class of Account), and SalesOrder.
The Address class is the one giving me problems at the moment, it can have no foreign key because it can be linked to any of the other five classes (with more to come), and each of the other classes can have one or more navigation properties pointing back to it.
The navigation properties should look as follows:
Contact.AddressId?
Contact.Address
Account.AddressId?
Account.Address
Customer.DeliveryAddresses
SalesOrder.InvoiceAddressId
SalesOrder.InvoiceAddress
SalesOrder.DeliveryAddressId?
SalesOrder.DeliveryAddress
It should be possible for these classes to share the same Address record, e.g. an Account has an Address, this can also be linked to a SalesOrder, a different Address, linked to the Customer, could be linked to another SalesOrder. All Addresses linked to Accounts and Customers should be unique, but other classes should be able to share links to these Addresses.
I have tried setting it up with all the possible fluent configurations I can think of, with my DbContext having a DbSet property and without (ultimately I don't think it should have it's own DbSet property, as the Addresses should only be accessible from the various root objects, but if that's the only way to get it to work I'm happy to manage the inserts/deletes myself).
I tried making all the navigation properties nullable (ideally SalesOrder.InvoiceAddressId should not be nullable), and also had to remove the Customer.DeliveryAddresses Many-to-Many mapping at one point because that was confusing the issue.
I get various errors depending on how I have it set up, either Multiplicity conflicts due to non-nullable fields, or Cascade on Delete errors when I have no DbSet property and I try and let EF handle the inserts and deletes.
I also end up with unwanted null rows when I do have a DbSet property set. e.g:
add three Address records to the DbSet (Address(1), Address(2), Address(3),
add two Accounts to the DbSet (Account(1) & Account(2)),
add multiple SalesOrders,
set Account(1).AddressId = 1
set Account(2).AddressId = 2,
set SalesOrder(n).InvoiceAddressId = 1,
set SalesOrder(n).DeliveryAddressId = 3
This will correctly create the Address records, but the related keys will only be set correctly if the various Id foreign-key properties are used, rather than the navigation property, and even if the Id properties are used the foreign keys all look correct, but orphaned records for each SalesOrder (or two per order if both navigation properties are used) end up in my Address table with all their fields bar Id set to NULL.
The only thing I can think of that I haven't tried would be to create multiple sub-classes of Address and use each one with it's related class (e.g. SalesOrderDeliveryAddress), but that doesn't seem ideal. I'd rather not do that unless I have to.
Is what I'm looking for possible to set up in EF, or is there some other way to go about doing it?
Thanks,
David
There are several issues making this confusing. To start with I would switch off the default cascade on delete to get rid of multiple cascade paths and come back to that later.
Then read about adding disconnected trees, foreign keys and navigation properties here: http://msdn.microsoft.com/en-us/magazine/dn166926.aspx
Then I would set up the entities you way you want them and repost a more specific issue. (You have tried lots of stuff so it's hard to work out what happens when here)
Once you've got adding and updating working you can come back and work out where you can put in cascade delete and where it needs to be manual

Modelling polymorphic associations database-first vs code-first

We have a database in which one table contains records that can be child to several other tables. It has a "soft" foreign key consisting of the owner's Id and a table name. This (anti) pattern is know as "polymorphic associations". We know it's not the best database design ever and we will change it in due time, but not in the near future. Let me show a simplified example:
Both Event, Person, and Product have records in Comment. As you see, there are no hard FK constraints.
In Entity Framework it is possible to support this model by sublassing Comment into EventComment etc. and let Event have an EventComments collection, etc.:
The subclasses and the associations are added manually after generating the basic model from the database. OwnerCode is the discriminator in this TPH model. Please note that Event, Person, and Product are completely different entities. It does not make sense to have a common base class for them.
This is database-first. Our real-life model works like this, no problem.
OK. Now we want to move to code-first. So I started out reverse-engineering the database into a code first model (EF Power Tools) and went on creating the subclasses and mapping the associations and inheritance. Tried to connect to the model in Linqpad. That's when the trouble started.
When trying to execute a query with this model it throws an InvalidOperationExeception
The foreign key component 'OwnerId' is not a declared property on type 'EventComment'. Verify that it has not been explicitly excluded from the model and that it is a valid primitive property.
This happens when I have bidirectional associations and OwnerId is mapped as a property in Comment. The mapping in my EventMap class (EntityTypeConfiguration<Event>) looks like this:
this.HasMany(x => x.Comments).WithRequired(c => c.Event)
.HasForeignKey(c => c.OwnerId);
So I tried to map the association without OwnerId in the model:
this.HasMany(x => x.Comments).WithRequired().Map(m => m.MapKey("OwnerId"));
This throws a MetaDataException
Schema specified is not valid. Errors:
(10,6) : error 0019: Each property name in a type must be unique. Property name 'OwnerId' was already defined.
(11,6) : error 0019: Each property name in a type must be unique. Property name 'OwnerId' was already defined.
If I remove two of the three entity-comment associations it is OK, but of course that's not a cure.
Some further details:
It is possible to create a working DbContext model ("code second") from the edmx by adding a DbContext generator item. (this would be a work-around for the time being).
When I export the working code-first model (with one association) to edmx (EdmxWriter) the association appears to be in the storage model, whereas in the original edmx they are part of the conceptual model.
So, how can I create this model code-first? I think the key is how to instruct code-first to map the associations in the conceptual model, not the storage model.
I personally stick with Database first when using EF on any schema that is this level of complexity. I have had issues with complex schemas in regards to code first. Maybe the newer versions are a little better, but worrying how to try and code complex relationships seems less straight forward then allowing the engine to generate it for you. Also when a relationship gets this complex I tend to avoid trying to generate it with EF and try and use stored procedures for easier troubleshooting of performance bottlenecks that can arise.

Problem mapping multiple relations using Entity Framework code-first

Scenario
I have a model that has the following setup:
A member can be member of multiple memberlists. A memberlist can have multiple members. I also defined that a memberlist can have a seperate set of optional members. Basically I have a double n-m relationship between member and memberlist. What's more, a memberlist is always owned by a member, the one person that created the memberlist that is.
Problem
Entity framework code-first is unable to map this relationship correctly eventhough I tell it how to map the relationships. I get the following error when I try to use the DbContext the first time
Schema specified is not valid. Errors:
(32,6) : error 0040: Type MemberList_Members is not defined in namespace NerdCooking.Models (Alias=Self).
(33,6) : error 0040: Type MemberList_OptionalMembers is not defined in namespace NerdCooking.Models (Alias=Self).
What I have tried
The first attempt to use the model in the scenario fails, because it's clear EF doesn't know how to map the n-m relationships. So I told the framework explicitly how to fix the situation.
// Map the relation between members of a memberlist and the memberlist
// to a Membership table
modelBuilder.Entity<MemberList>().HasMany(memberList => memberList.Members)
.WithMany(member => member.MemberLists)
.Map(mapping => mapping.MapLeftKey("MemberId")
.MapRightKey("MemberListId").ToTable("Membership"));
// Map the relation between optional members of a memberlist and the memberlist
// to a separate table
modelBuilder.Entity<MemberList>().HasMany(memberList => memberList.OptionalMembers)
.WithMany(member => member.MemberLists)
.Map(mapping => mapping.MapLeftKey("MemberId")
.MapRightKey("MemberListId").ToTable("OptionalMembership"));
// Map the relationship between the owner and the memberlist
modelBuilder.Entity<MemberList>().HasRequired(memberList => memberList.Owner)
.WithMany(member => member.MemberLists).WillCascadeOnDelete(true);
My question
Is this scenario possible with Entity framework 4.1 code-first? And if so, what's the best way to fix the mapping issue I'm experiencing?
I can always change the model so that it features a Membership entity that links a member to a memberlist. It makes the whole thing a bit more explicit and I can then add a property to that entity to mark it as optional.
I think however that this is a scenario that should have worked, so I hope someone did this before and knows what the trick is to get it working correctly.
All your mappings contain .WithMany(member => member.MemberLists). That is incorrect. You need separate navigation property for each relation = you can use each navigation property only for one relation mapping.

EF4 Self referencing with association 0..1 -> 1

There's a lot of reading on self referencing problems, but I can't seem to find an answer to my question.
Say I have a Human(A), and I want A to have a partner, another Human(B). Naturally, it means that B has a partner in human A. How would you solve this? Ideally, I should only have to do:
humanA.Partner = humanB;
and humanB would automatically get humanA as a partner.
I would have thought I could create a Human enity, and add an Association, something like:
End1 Entity:Human, Multiplicity:0..1, Navigation Property:Partner
End2 Entity:Human, Multiplicity:0..1
So, each human has zero or one Partner which is a human.
Thanks for your time.
1:0..1 mapping is possible only when entities "share" primary key. It means when the related's entity FK is also its PK. So self referencing 1:0..1 cannot exist. I think you can't even map it in database directly.

Fluent Nhibernate - Mapping two entities to same table

I'm trying to map two domain entities to the same table. We're doing a smart entity for our domain model, so we have the concept of an Editable Address and a readonly Address. I have both mapped using Classmaps, and everything seems to go fine until we try to export the schema using the SchemaExport class from NHibernate. It errors out saying the table already exists.
I assume it's something simple that I'm just not seeing.
Any ideas?
Thanks
Update
There are a couple of other things I didn't mention which I should have. I appreicate those that answered so far, but they don't work for us.
One is that we have a single address table, not include the columns in whatever entities have an address.
The other is that we can't use a common base class. For editable objects, we have a super class which adds validation behaviors to the subclasses. The readonly objects don't need this behavior though and should not have these behaviors.
I have considered an interface, but then I believe I end up in a situtation where you can cast a readonly object to this interface and then changes its values (since presumably NHibernate would use said interface to hydrate the object).
So if there's another way to acomplish this, or if mapping via an interface won't have the problem I described, please let me know. I'm still learning NHibernate.
Thanks again!
you can Exclude the readonly class from schemaexport:
public class ReadonlyAdressMap : ClassMap<ReadonlyAdress>
{
ReadonlyAdressMap()
{
Schemaaction.None();
[...]
}
}
Create one base abstract class entity which you will later extend to the Editable Address and the ReadOnly Address.

Categories

Resources