Entity framework 4 – Code-only, How-to map a combined PK

I got a question today of how to map an entity with a primarykey that is built up using two fields. The answer: using an anonymous type.

The entity

[Serializable]
public class Car
{
    public string LicencePlate { get; set; }
    public int CountryCode { get; set; }
}

The mapping

[Serializable]
public class CarMapping : EntityConfiguration<Car>
{
    public CarMapping()
    {
        HasKey(c => new {c.CountryCode, c.LicencePlate});
    }
}

//Daniel

3 thoughts on “Entity framework 4 – Code-only, How-to map a combined PK

  1. Hi,

    OK this helps :).
    But what if, to build on your example:

    public class LicensePlate{
    public int ID {get;set;}
    public string Plate{get;set;}
    }

    public class Country{
    public int ID{get;set;}
    public string Name{get;set;}
    }

    public class Car{
    public LicensePlate LicensePlate{get;set;}
    public Country Country{get;set;}
    public int SomeProperty{get;set;}
    }
    So you’ll have a join table with extra fields.

    To map the Car I would expect: HasKey(c => new { LicensePlate_ID = c.LicensePlate.ID, Country_ID = c.Country.ID });

    However, the key expression is not valid.

    Greets,
    Arne

    • I sent you an email. I hope it will solve the issue.

      For others. You have to include properties in car that holds the value of the Id in Country and LicensePlate.

          [Serializable]
          public class Car
          {
              private LicencePlate _licencePlate;
              private Country _country;
      
              public LicencePlate LicencePlate
              {
                  get { return _licencePlate; }
                  set
                  {
                      _licencePlate = value;
                      LicencePlateId = value != null ? value.Id : 0;
                  }
              }
      
      
              public Country Country
              {
                  get { return _country; }
                  set
                  {
                      _country = value;
                      CountryId = value != null ? value.Id : 0;
                  }
              }
      
              public int LicencePlateId { get; private set; }
      
              public int CountryId { get; private set; }
      
              public string Color { get; set; }
      
              public Car()
              {
              }
          }
      
          [Serializable]
          public class LicencePlate
          {
              public int Id { get; set; }
              public string Plate { get; set; }
          }
      
          [Serializable]
          public class Country
          {
              public int Id { get; set; }
              public string Name { get; set; }
          }
      
          [Serializable]
          public class LicencePlateMapping : EntityConfiguration<LicencePlate>
          {
              public LicencePlateMapping()
              {
                  HasKey(l => l.Id);
                  Property(l => l.Id).IsIdentity();
                  Property(l => l.Plate).IsRequired();
              }
          }
      
          [Serializable]
          public class CountryMapping : EntityConfiguration<Country>
          {
              public CountryMapping()
              {
                  HasKey(c => c.Id);
                  Property(c => c.Id).IsIdentity();
                  Property(c => c.Name).IsRequired();
              }
          }
      
          [Serializable]
          public class CarMapping : EntityConfiguration<Car>
          {
              public CarMapping()
              {
                  HasKey(c => new { c.CountryId, c.LicencePlateId });
      
                  Property(c => c.Color);
      
                  Relationship<LicencePlate>(c => c.LicencePlate).IsRequired().HasConstraint((c, l) => c.LicencePlateId == l.Id);
                  Relationship<Country>(c => c.Country).IsRequired().HasConstraint((car, country) => car.CountryId == country.Id);
              }
          }
      
  2. Pingback: Entity framework 4 – CTP3 – Code first vs Linq to Sql « Daniel Wertheim

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s