Using the new ASP.NET Core and Entity Framework 7.0 RC1 Final. I have two fields with a one-to-many relationship between Standards and Students. If I just have the one FK and Navigation Key the code works just fine, but when I add in the second FK (Standard2) and Nav field (Students2) I get the following error message:
InvalidOperationException: The navigation 'Students' on entity type 'TestProject.Models.Standard' has not been added to the model, or ignored, or target entityType ignored.
public class Standard
{
public Standard()
{
}
public int StandardId { get; set; }
public string StandardName { get; set; }
public IList<Student> Students { get; set; }
public IList<Student> Students2 { get; set; }
}
public Student()
{
}
public int StudentID { get; set; }
public string StudentName { get; set; }
public DateTime DateOfBirth { get; set; }
public byte[] Photo { get; set; }
public decimal Height { get; set; }
public float Weight { get; set; }
//Foreign key for Standard
public int StandardId { get; set; }
public int StandardId2 { get; set; }
[ForeignKey("StandardId")]
public Standard Standard { get; set; }
[ForeignKey("StandardId2")]
public Standard Standard2 { get; set; }
}
How do I have two FK's to the same table in EF 7?
The problem is that you need to specify the other end of your relationships by using InverseProperty attribute, something that EF cannot infer on its own and hence throws an exception:
public class Standard
{
public int StandardId { get; set; }
public string StandardName { get; set; }
[InverseProperty("Standard")]
public IList<Student> Students { get; set; }
[InverseProperty("Standard2")]
public IList<Student> Students2 { get; set; }
}
Or you can achieve the same results by using fluent API:
modelBuilder.Entity<Standard>()
.HasMany(s => s.Students)
.WithOne(s => s.Standard)
.HasForeignKey(s => s.StandardId);
modelBuilder.Entity<Standard>()
.HasMany(s => s.Students2)
.WithOne(s => s.Standard2)
.HasForeignKey(s => s.StandardId2);
Related
I have table Categories With Id column when insert occur is shows it shows errorSqlException: Invalid column name 'CategoriesId'.
public partial class Categories
{
public Categories()
{
CategoryTabs = new HashSet<CategoryTabs>();
}
public int Id { get; set; }
public string Title { get; set; }
public int? ParentId { get; set; }
public int? SeasonId { get; set; }
public int? Levels { get; set; }
public string Image { get; set; }
public string Description { get; set; }
public virtual Seasons Season { get; set; }
public List<Categories> children { get; set; }
public virtual ICollection<CategoryTabs> CategoryTabs { get; set; }
}
public partial class CategoryTabs
{
public int Id { get; set; }
public int? CategoryId { get; set; }
public int? TabId { get; set; }
public virtual Categories Category { get; set; }
public virtual Tabs Tab { get; set; }
}
CategoriesId is the conventional name for the Foreign Key property/column associated with the one-to-many self relationship introduced by
public List<Categories> children { get; set; }
collection navigation property inside Categories entity.
Looking at the entity model, most likely the idea was to use the ParentId for that purpose. Since it doesn't match EF Core naming conventions, it has to be mapped explicitly by using either ForeignKey data annotation:
[ForeignKey(nameof(ParentId))]
public List<Categories> children { get; set; }
or fluent API inside OnModelCreating override:
modelBuilder.Entity<Categories>()
.HasMany(e => e.children)
.WithOne()
.HasForeignKey(e => e.ParentId);
I'm using Entity Framework 6.0 and have defined 2 POCO's to map to my database:
[Table("PortfolioGroups")]
public class PortfolioGroup : AuditableEntity<int>
{
[Column("Company_Id")]
public int CompanyId { get; set; }
[ForeignKey("CompanyId")]
public Company Company { get; set; }
public string Name { get; set; }
public string Description { get; set; }
public ICollection<PortfolioGroupItem> PortfolioGroupItems { get; set; }
public PortfolioGroup()
{
PortfolioGroupItems = new Collection<PortfolioGroupItem>();
}
}
And the PortfolioGroupItem:
[Table("PortfolioGroupItems")]
public class PortfolioGroupItem : AuditableEntity<int>
{
[Column("PortfolioGroup_Id")]
public int PortfolioGroupId { get; set; }
[ForeignKey("PortfolioGroupId")]
public PortfolioGroup PortfolioGroup { get; set; }
[Column("Trademark_Id")]
public int? TrademarkId { get; set; }
[ForeignKey("TrademarkId")]
public Trademark.Trademark Trademark { get; set; }
[Column("TrademarkRegistration_Id")]
public int? TrademarkRegistrationId { get; set; }
[ForeignKey("TrademarkRegistrationId")]
public TrademarkRegistration TrademarkRegistration { get; set; }
[Column("Domain_Id")]
public int? DomainId { get; set; }
[ForeignKey("DomainId")]
public Domains.Domain Domain { get; set; }
}
However - when I attempt to query the PortfolioGroups, Entity Framework for some reason attempts to query a field named "Trademark_Id" - which doesn't exist on the PortfolioGroup entity:
Context.PortfolioGroups.SingleOrDefault(i => i.Id == id && i.CompanyId == companyId);
Throws:
Invalid column name 'Trademark_Id'.
I've used this kind of setup other places in my application without any problems. I simply cannot find out why EF is trying to query a column that's not in my entity!
Any suggestions would be greatly appreciated. I'm at the end of my rope here.
Thanks guys! :)
The problem is that you've added a Navigation Property on Trademark that requires a Foreign Key on Portfolio Group:
public class Trademark
{
[Key]
public int Id { get; set; }
[MaxLength(250)]
[Required]
public string Name { get; set; }
[MaxLength(150)]
public string Filename { get; set; }
public ICollection<PortfolioGroup> PortfolioGroups { get; set; }
public Trademark()
{
PortfolioGroups = new Collection<PortfolioGroup>();
}
}
EF expects PortfolioGorup to have a Trademark_ID column to store which PortfolioGroups are associated with a Trademark.
I am trying to create navigation properties for two table.
Here is the code.
public class CourseMaster
{
public int Id { get; set; }
public string Name { get; set; }
public int? TeamLeaderId { get; set; }
[ForeignKey("TeamLeaderId")]
public StudentMaster TeamLeader { get; set; }
public int? GroupLeaderId { get; set; }
[ForeignKey("GroupLeaderId")]
public StudentMaster GroupLeader { get; set; }
public virtual ICollection<StudentMaster> Students { get; set; }
}
public class StudentMaster
{
public int id { get; set; }
public string Name { get; set; }
public int FirstSemCourseId { get; set; }
[ForeignKey("FirstSemCourseId")]
public CourseMaster FirstSemCourse { get; set; }
public int SecondSemCourseId { get; set; }
[ForeignKey("SecondSemCourseId")]
public CourseMaster SecondSemCourse { get; set; }
public int ThirdSemCourseId { get; set; }
[ForeignKey("ThirdSemCourseId")]
public CourseMaster ThirdSemCourse { get; set; }
public int CourseMasterId { get; set; }
public CourseMaster Course { get; set; }
}
// Fluent API
modelBuilder.Entity<StudentMaster>()
.HasOne(p => p.Course)
.WithMany(b => b.Students)
.HasForeignKey(p => p.CourseMasterId);
But when i am creating migrations i am getting following error.
Unable to determine the relationship represented by navigation property 'CourseMaster.TeamLeader' of the type 'StudentMaster'. Either manually configure the relationship, or ignore this property from model.
Whether the procedure i am following is right or should i create intermediate class.
or how should i create class.
Any help are appreciated.
Thanks
Using EntityFramework 6.1.3, I've got the following
public class RacesContext:DbContext
{
public DbSet<Race> Races { get; set; }
public DbSet<Sailboat> Sailboats { get; set; }
public DbSet<VenueParticipation> VenueParticipations { get; set; }
}
public class Crew
{
public int CrewId { get; set; }
public string Name { get; set; }
}
public class Sailboat
{
[Key]
public int SailboatId { get; set; }
public string Name { get; set; }
public string Skipper { get; set; }
public virtual ICollection<Crew> BoatCrew { get; set; }
}
public class VenueParticipation
{
[Key]
public int Id { get; set; }
public virtual ICollection<Sailboat> Boats { get; set; }
public virtual ICollection<Race> Races { get; set; }
}
public class Race
{
[Key]
public int RaceId { get; set; }
public string Venue { get; set; }
public DateTime Occurs { get; set; }
}
EF creates the Creates the Crews table with the proper PK and FK as I would expect. But creates the Races Sailboats, VenueParticipations tables in an unexpected way. Sailboats get's the expected PK but the unexpected FK VenueParticipation_Id as does Races. I was expecting the VenueParticipations table to get FKs to the others allowing a many to many relationship.. I'm sure I'm missing something here. Any advice would be great.
You can either configure the joining tables VenueParticipationSailboat, VenueParticipationRace with the proper FKs or you can use the fluent API:
modelBuilder.Entity<VenueParticipation>()
.HasMany(t => t.Sailboats)
.WithMany(t => t.VenueParticipations)
.Map(m =>
{
m.ToTable("VenueParticipationSailboat");
m.MapLeftKey("VenueParticipationID");
m.MapRightKey("SailboatID");
});
https://msdn.microsoft.com/en-us/data/jj591620.aspx#ManyToMany
I have the following classes:
public class Bicycle
{
public int BicycleId { get; set; }
public DateTime YearOfManufacture { get; set; }
public int BicycleManufactuerId { get; set; }
public BicycleManufacturer BicycleManufacturer { get; set; }
}
public class BicycleManufacturer
{
public int BicycleManufacturerId { get; set; }
public string Description { get; set; }
}
Each Bicycle must have a BicycleManufacturer (1:1). There could be some BicycleManufacturer that isn't associate with any Bicycle. Most will be associated with multiple Bicycle entities.
I have the following fluent API code to set up the FK relationship:
modelBuilder.Entity<Bicycle>()
.HasRequired(a => a.BicycleManufacturer)
.WithMany()
.HasForeignKey(u => u.BicycleManufactuerId);
This all seems to work fine. However, I would really like to remove the BicycleManufacturerId property from the Bicycle entity. It's only there to establish the FK relationship. Is there a way I can create the proper FK relationship if I remove this property?
You can remove the property and use the mapping:
modelBuilder.Entity<Bicycle>()
.HasRequired(a => a.BicycleManufacturer)
.WithMany()
.Map(m => m.MapKey("BicycleManufactuerId"));
You can also do it by convention by adding the relationship on the other side as a collection.
public class Bicycle
{
public int BicycleId { get; set; }
public DateTime YearOfManufacture { get; set; }
public int BicycleManufactuerId { get; set; }
public BicycleManufacturer BicycleManufacturer { get; set; }
}
public class BicycleManufacturer
{
public int BicycleManufacturerId { get; set; }
public ICollection<Bicycle> Bicycles { get; set; }
public string Description { get; set; }
}