Entity Framework 4 Code First demonstrates how to declare a one-to-one connection (POCO)

c# ef-code-first entity-framework one-to-one poco

Question

Using Entity Framework 4 Code First (POCO), how do you define a one-to-one relationship?

I discovered this inquiry (one-to-one relationships in Entity Framework 4), however the resource that the response cites was not helpful (there is one line of code that is a 1-1 relationship, but no mention of how to define it).

1
12
5/23/2017 10:31:35 AM

Accepted Answer

Do you just want something like this?

public class User
{
    public int Id { get; set; }
    public string Username { get; set; }
    public Profile Profile { get; set; }
    public int ProfileId { get; set; }
}

public class Profile
{
    public int Id { get; set; }
    public string FirstName { get; set; }
    public string LastName { get; set; }
    public string PostalCode { get; set; }
    // etc...
}

public class UserMapping : EntityConfiguration<User>
{
    public UserMapping()
    {
        this.HasKey(u => u.Id);
        this.Property(u => u.Username).HasMaxLength(32);

        // User has ONE profile.
        this.HasRequired(u => u.Profile);
    }
}

public class ProfileMapping : EntityConfiguration<Profile>
{
    public ProfileMapping()
    {
        this.HasKey(p => p.Id);
        this.Property(p => p.FirstName).HasMaxLength(32);
        this.Property(p => p.LastName).HasMaxLength(32);
        this.Property(p => p.PostalCode).HasMaxLength(6);
    }
}

Yes, I didn't have Visual Studio in front of me, but you need add the following line to theUserMapping as opposed to the existingHasRequired and include aProfileId property (as opposed toProfile_Id you inserted):

this.HasRequired(u => u.Profile).HasConstraint((u, p) => u.ProfileId == p.Id);

There doesn't seem to be a way around this right now, but given we're just in CTP4, I'm sure that will change. If I could say, I'd want to say:

this.HasRequired(u => u.Profile).WithSingle().Map(
    new StoreForeignKeyName("ProfileId"));

In this manner, I may omit aProfileId property. Perhaps there is a workaround for this right now, but it's too early in the morning for me to think about it.

Don't forget to call, too..Include("Profile") while adding a "navigational attribute".

11
10/1/2013 9:05:16 PM

Popular Answer

Three approaches:

A) Declare a relationship between the two classes with navigational attributes. Add the ForeignKey attribute to the Primary Key of the dependant table in one of the tables. EF deduces this to mean:

public class AppUser
{
    public int Id { get; set; }

    public string Username { get; set; }

    public OpenIdInfo OpenIdInfo { get; set; }
}

​public class OpenIdInfo
{
    [ForeignKey("AppUser")]
    public int Id { get; set; }

    public string OpenId { get; set; }

    public AppUser AppUser { get; set; }
}

http://weblogs.asp.net/manavi/archive/2011/05/01/associations-in-ef-4-1-code-first-part-5-one-to-one-foreign-key-associations.aspx

My lack of usagevirtual and you ought not to either.

B) Declare an inheritance hierarchy that results in Table-Per-Type and a common Primary Key by explicitly stating the names of both tables.

using System.ComponentModel.DataAnnotations;

[Table("AppUser")]
public class AppUser
{
    public int Id { get; set; }

    public string Username { get; set; }

    public OpenIdInfo OpenIdInfo { get; set; }
}

[Table("AdminUser")]      
public class AdminUser : AppUser
{
    public bool SuperAdmin { get; set; }
}

You will get 2 tables: an AppUser table and an AdminUser table. AdminUser is 1:1 with AppUser and is Dependent, therefore you cannot remove an AdminUser while an AppUser is still pointed to by an AdminUser without receiving a Constraint Violation Error. ​

C) In EF, there are two halfway measures for one-to-one instruction:

Entity-Splitting, in which there are one or more one-to-one connected tables and only one Class, which is kept in a main table.

Where a tree of items flattens down into a single table is at Table-Splitting. For instance, columns for the Address object, such as Address City, would be flattened into a single table in a class having an Address field.

*Virtual may be added to any EF property or collection starting with You can lazy-load them if you want to.. If you provide an object with lazy-loaded attributes to, for instance, the MVC JSON converter or anything else that traverses the object hierarchy, this might lead to endless loops or loading the whole database. Always blocking the thread and in sync, lazy loading occurs without warning. In conclusion, there are several methods to use it to freeze your code, application, or server. On EF classes, stay away from using virtual. Yes, there are several code examples using it online. No, you shouldn't still use it.



Related Questions





Related

Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow
Licensed under: CC-BY-SA with attribution
Not affiliated with Stack Overflow