Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Entity Framework 1to1 relationship via association table not working in EDMX

I have the following tables in SQL Server database enter image description here

Which has a 1-1 association table (FooBar) which has unique indexes on corresponding FooId, BarId, and the primary key is (FooId, BarId).

To be clear FooBar does not allow any FooId (due to unique constraint) to be in the table more than once neither can any BarId (due to unique constraint) be in the table more than once. This is what makes it a 1-1 associative table.

I want to have this association table instead of 1-1 relationship between Foo and Bar because in my real world scenario, Bar will have other relationships to different unrelated tables and I will want similar association tables (as opposed to adding new FK columns to Bar for each new table)

Which I then bring these tables into my EDMX designer. The relationship is brought in as a Many to Many instead of One to One. enter image description here

Which of course isn't what I want. I can manually change the model to a 1-1 relationship. enter image description here

But then I get an error (in the designer). enter image description here

Is this a bug or is it not possible to create a 1-1 association in this manner in EF?

like image 499
Jim Avatar asked Feb 17 '15 16:02

Jim


People also ask

How to create one to one relationship in Entity Framework?

One to One relationship in Entity Framework. Let us take the example of an Employee and Employee Address domain models and create a One to One relationship between them. In a One to one relationship PrimaryKey of Primary table (employeeID of employee table) is both Primary key and Foreign key in the dependent table (EmployeeAddress).

What is an association in edmx?

In the .edmx file, an Association element defines a relationship between two entity types. An association must specify the entity types that are involved in the relationship and the possible number of entity types at each end of the relationship, which is known as the multiplicity.

How do I access the entity type in an association?

At run time, entity type instances at one end of an association can be accessed through navigation properties or foreign keys (if you choose to expose foreign keys in your entities). With foreign keys exposed, the relationship between the entities is managed with a ReferentialConstraint element (a child element of the Association element).

How to create one to one relationship with employeeaddress in EF Core?

The EmployeeAddress class uses the EmployeeID as both Primary key & Foreign Key. The Convention requires us to have either Id property or EmployeeAddressID Property in the EmployeeAddress class So by Adding the public int id { get; set; } we are able to trick EF Core to create the one to one relationship for us


2 Answers

It is a "bug" with the entire EF design: Entity Framework 4-6.1x Only Honors Multiplicity on Primary Keys.

Thus even though we know (and the RA models) that it is a 1-1 relationship due to a Candidate Key Constraint, EF does not and will not like it. Tough luck.

The "solutions" include:

  1. Changing the model to something EF understands (EF understands Code First, not RA). Granted this may indicate an "issue" with the selected RA model, but such is orthogonal to the question ..

  2. Live with the incorrectly generated multiplicity rules and "use with care"; the dirty work can be wrapped, but has to be added manually outside of the auto-generated model.

  3. .. Hmm, others?

Shameless plug to unresolved questions deal with the same core lack-of feature:

  • How to get EF6 to honor Unique Constraint (on FK) in Association/Relationship multiplicity?

  • How to add an EF6 Association to a Candidate Key / Unique Key which is not the Primary Key?

like image 85
user2864740 Avatar answered Sep 23 '22 01:09

user2864740


The relationship you've shown in your first graphic is not a 1to1 relationship as far as EF is concerned.

It's a many to many relationship between Foo and Bar

Think about it this way:

Possible combinations with the following Foo and Bar values

Foo
1
2
3

Bar
1
2
3

FooBar
1, 1
1, 2
1, 3
2, 1
2, 2
2, 3
3, 1
3, 2
3, 3

Your FooBar table is a composite key, meaning it's a combination of the Foo and Bar values making up the key - not a 1 to 1 relationship

to define a 1 to 1 relationship between Foo and Bar, your schema should look something more like this:

Foo
FooId PK

Bar
FooId PK FK to Foo.FooId

the FooBar table is not needed for a 1to1 relationship between foo and bar.

As you stated in your question/comments - yes you put a unique constraint on the individual parts of your composite key, but EF doesn't take into account unique constraints for your model when determining a relationship. If you want a 1to1 relationship, you should create a 1to1 model, rather than mocking a 1to1 relationship via unique constraints.

like image 36
Kritner Avatar answered Sep 22 '22 01:09

Kritner