问题
Hi I'm planning to test EF Code First in one of my project. This is what I want actually. I have three tables and the structure is as follows
public partial class App_user
{
public int id { get; set; }
public string name { get; set; }
public string email_address { get; set; }
public string password { get; set; }
public int user_type { get; set; }
public List<Role> Roles { get; set; }
}
public partial class Role
{
public int id { get; set; }
public string name { get; set; }
}
public partial class User_role
{
public int user_id { get; set; }
public int role_id { get; set; }
public virtual Role Role { get; set; }
public virtual App_user App_user { get; set; }
}
In the third table there is no primary key. So it gives an error while running. Here is the error message -
System.Data.Edm.EdmEntityType: : EntityType 'User_role' has no key defined. Define the key for this EntityType. System.Data.Edm.EdmEntitySet: EntityType: The EntitySet User_roles is based on type User_role that has no keys defined.
Why its is happening? Is there a solution for this?
回答1:
If think you are trying to model many-to-many relation between user and role. In such case your model is completely wrong.
Use this instead:
public partial class App_user
{
public int id { get; set; }
public string name { get; set; }
public string email_address { get; set; }
public string password { get; set; }
public int user_type { get; set; }
public virtual ICollection<Role> Roles { get; set; }
}
public partial class Role
{
public int id { get; set; }
public string name { get; set; }
public virtual ICollection<User> Users { get; set; }
}
This will create many-to-many automatically and you will not need to bother with junction table. If you need to expose junction table you must use this:
public partial class App_user
{
public int id { get; set; }
public string name { get; set; }
public string email_address { get; set; }
public string password { get; set; }
public int user_type { get; set; }
public virtual ICollection<User_Role> UserRoles { get; set; }
}
public partial class Role
{
public int id { get; set; }
public string name { get; set; }
public virtual ICollection<User_Role> UserRoles { get; set; }
}
public partial class User_role
{
[Key, ForeignKey("App_user"), Column(Order = 0)]
public int user_id { get; set; }
[Key, ForeignKey("Role"), Column(Order = 1)]
public int role_id { get; set; }
public virtual Role Role { get; set; }
public virtual App_user App_user { get; set; }
}
Exposing junction table is meaningless if you don't need additional properties in it.
To your error - each entity in Entity framework must have primary key defined.
回答2:
You can simply do like this:
public partial class User_role
{
[Key]
public int user_id { get; set; }
[Key]
public int role_id { get; set; }
public virtual Role Role { get; set; }
public virtual App_user App_user { get; set; }
}
回答3:
Because I used an ADO.net Entiry Data Model with automated generated code I didn't want to change the Model classes so I changed the WebApiConfig.cs to define the keys of the underlying models:
ODataConventionModelBuilder builder = new ODataConventionModelBuilder();
EntitySetConfiguration<Registration> EntitySetConfiguration_Registration = builder.EntitySet<Registration>("Registration");
EntitySetConfiguration<Lead> EntitySetConfiguration_Lead = builder.EntitySet<Lead>("Lead");
EntitySetConfiguration<Session> EntitySetConfiguration_Session = builder.EntitySet<Session>("Session");
EntitySetConfiguration_Registration.EntityType.HasKey(p => p.Registration_Id);
EntitySetConfiguration_Lead.EntityType.HasKey(p => p.Lead_Id);
EntitySetConfiguration_Session.EntityType.HasKey(p => p.Session_Id);
config.Routes.MapODataRoute("odata", "odata", builder.GetEdmModel());
回答4:
make sure you are using (using System.ComponentModel.DataAnnotations;)
just add the keyword [Key] at the top of the data field in the Model
来源:https://stackoverflow.com/questions/5482670/entity-framework-code-first-define-the-key-for-this-entitytype