C
C#9mo ago
daminko

Entity framework exception while creating a many to many relation

Hello everyone, I've been trying to make a many to many relation between two classes Voyage and Transporteur. these are the Three classes:
c#
public class Transporteur : IdentityUser
{
public string Nom { get; set; } = string.Empty;
public string Prenom { get; set; } = string.Empty;

public Vehicule? Vehicule { get; set; }
public string? VehiculeId { get; set; } = string.Empty;
public bool ExterneDuService { get; set; } = false;
public List<Voyage> Voyages { get; } = [];
public ICollection<TransporteurVoyage> TransporteurVoyages { get; } = [];
}
****************************************************
public class Voyage
{
[Key]
public string IdVoyage { get; set; } = string.Empty;
public DateTime DateSortieBon { get; set; }
public DateTime DateDepartVoyage { get; set; }

public string Etat { get; set; } = string.Empty;
//Demandeur
public Demandeur Demandeur { get; set; } = null!;
public string DemandeurId { get; set; } = string.Empty;
//public ICollection<Utilisateur> Utilisateurs { get; set; } = new List<Utilisateur>();
public Magasinier Magasinier { get; set; } = null!;
public string IdMagasinier { get; set; } = string.Empty;
public TypeVoyage TypeVoyage { get; set; } = null!;
public int TypeVoyageId { get; set; }
public List<Transporteur> Transporteurs { get; } = [];
public ICollection<TransporteurVoyage> TransporteurVoyages { get; } = [];


}
********************************************************************
public class TransporteurVoyage
{
public string TransporteurId { get; set; } = string.Empty;
public string VoyageId { get; set; } = string.Empty;
public bool Panne { get; set; } = false;
public Voyage Voyage { get; set; }
public Transporteur Transporteur { get; set; }

}
c#
public class Transporteur : IdentityUser
{
public string Nom { get; set; } = string.Empty;
public string Prenom { get; set; } = string.Empty;

public Vehicule? Vehicule { get; set; }
public string? VehiculeId { get; set; } = string.Empty;
public bool ExterneDuService { get; set; } = false;
public List<Voyage> Voyages { get; } = [];
public ICollection<TransporteurVoyage> TransporteurVoyages { get; } = [];
}
****************************************************
public class Voyage
{
[Key]
public string IdVoyage { get; set; } = string.Empty;
public DateTime DateSortieBon { get; set; }
public DateTime DateDepartVoyage { get; set; }

public string Etat { get; set; } = string.Empty;
//Demandeur
public Demandeur Demandeur { get; set; } = null!;
public string DemandeurId { get; set; } = string.Empty;
//public ICollection<Utilisateur> Utilisateurs { get; set; } = new List<Utilisateur>();
public Magasinier Magasinier { get; set; } = null!;
public string IdMagasinier { get; set; } = string.Empty;
public TypeVoyage TypeVoyage { get; set; } = null!;
public int TypeVoyageId { get; set; }
public List<Transporteur> Transporteurs { get; } = [];
public ICollection<TransporteurVoyage> TransporteurVoyages { get; } = [];


}
********************************************************************
public class TransporteurVoyage
{
public string TransporteurId { get; set; } = string.Empty;
public string VoyageId { get; set; } = string.Empty;
public bool Panne { get; set; } = false;
public Voyage Voyage { get; set; }
public Transporteur Transporteur { get; set; }

}
23 Replies
daminko
daminkoOP9mo ago
This is my dbContext:
c#
public class ApplicationDBContext : IdentityDbContext<IdentityUser>
{
public ApplicationDBContext(DbContextOptions dbContextOptions) : base(dbContextOptions)
{
}
public DbSet<Entrepot> Entrepot { get; set; }

public DbSet<Admin> Admin { get; set; }
public DbSet<Magasinier> Magasinier { get; set; }
public DbSet<Transporteur> Transporteur { get; set; }
public DbSet<TransporteurVoyage> TransporteurVoyage { get; set; }
public DbSet<Demandeur> Demandeur { get; set; }
public DbSet<Vehicule> Vehicule { get; set; }


protected override void OnModelCreating(ModelBuilder builder)
{
base.OnModelCreating(builder);
builder.Entity<TransporteurVoyage>().HasKey(t => new { t.TransporteurId, t.VoyageId });

builder.Entity<IdentityRole>().HasData(roles);
builder.Entity<TransporteurVoyage>()
.HasKey(pc => new { pc.TransporteurId, pc.VoyageId });
builder.Entity<TransporteurVoyage>()
.HasOne(p => p.Voyage)
.WithMany(pc => pc.TransporteurVoyages)
.HasForeignKey(p => p.VoyageId);
builder.Entity<TransporteurVoyage>()
.HasOne(p => p.Transporteur)
.WithMany(pc => pc.TransporteurVoyages)
.HasForeignKey(c => c.TransporteurId);
}
}
c#
public class ApplicationDBContext : IdentityDbContext<IdentityUser>
{
public ApplicationDBContext(DbContextOptions dbContextOptions) : base(dbContextOptions)
{
}
public DbSet<Entrepot> Entrepot { get; set; }

public DbSet<Admin> Admin { get; set; }
public DbSet<Magasinier> Magasinier { get; set; }
public DbSet<Transporteur> Transporteur { get; set; }
public DbSet<TransporteurVoyage> TransporteurVoyage { get; set; }
public DbSet<Demandeur> Demandeur { get; set; }
public DbSet<Vehicule> Vehicule { get; set; }


protected override void OnModelCreating(ModelBuilder builder)
{
base.OnModelCreating(builder);
builder.Entity<TransporteurVoyage>().HasKey(t => new { t.TransporteurId, t.VoyageId });

builder.Entity<IdentityRole>().HasData(roles);
builder.Entity<TransporteurVoyage>()
.HasKey(pc => new { pc.TransporteurId, pc.VoyageId });
builder.Entity<TransporteurVoyage>()
.HasOne(p => p.Voyage)
.WithMany(pc => pc.TransporteurVoyages)
.HasForeignKey(p => p.VoyageId);
builder.Entity<TransporteurVoyage>()
.HasOne(p => p.Transporteur)
.WithMany(pc => pc.TransporteurVoyages)
.HasForeignKey(c => c.TransporteurId);
}
}
This is the exception:
Unable to create a 'DbContext' of type ''. The exception 'Cannot use table 'TransporteurVoyage' for entity type 'TransporteurVoyage' since it is being used for entity type 'TransporteurVoyage (Dictionary<string, object>)' and potentially other entity types, but there is no linking relationship. Add a foreign key to 'TransporteurVoyage' on the primary key properties and pointing to the primary key on another entity type mapped to 'TransporteurVoyage'.' was thrown while attempting to create an instance. For the different patterns supported at design time, see https://go.microsoft.com/fwlink/?linkid=851728
Unable to create a 'DbContext' of type ''. The exception 'Cannot use table 'TransporteurVoyage' for entity type 'TransporteurVoyage' since it is being used for entity type 'TransporteurVoyage (Dictionary<string, object>)' and potentially other entity types, but there is no linking relationship. Add a foreign key to 'TransporteurVoyage' on the primary key properties and pointing to the primary key on another entity type mapped to 'TransporteurVoyage'.' was thrown while attempting to create an instance. For the different patterns supported at design time, see https://go.microsoft.com/fwlink/?linkid=851728
Angius
Angius9mo ago
I'd try configuring the join table with .UsingEntity()
daminko
daminkoOP9mo ago
how?
Angius
Angius9mo ago
https://learn.microsoft.com/en-us/ef/core/modeling/relationships/many-to-many#many-to-many-with-class-for-join-entity
builder.Entity<Transporteur>()
.HasMany(t => t.Voyages)
.WithMany(v => v.Transporteurs)
.UsingEntity<TransporteurVoyage>(/* other config */);
builder.Entity<Transporteur>()
.HasMany(t => t.Voyages)
.WithMany(v => v.Transporteurs)
.UsingEntity<TransporteurVoyage>(/* other config */);
daminko
daminkoOP9mo ago
I've tried this to be more precise
c#
builder.Entity<Transporteur>()
.HasMany(t => t.Voyages)
.WithMany(v => v.Transporteurs)
.UsingEntity<TransporteurVoyage>(
l => l.HasOne<Voyage>().WithMany().HasForeignKey(e => e.VoyageId),
r => r.HasOne<Transporteur>().WithMany().HasForeignKey(e => e.TransporteurId)
);
c#
builder.Entity<Transporteur>()
.HasMany(t => t.Voyages)
.WithMany(v => v.Transporteurs)
.UsingEntity<TransporteurVoyage>(
l => l.HasOne<Voyage>().WithMany().HasForeignKey(e => e.VoyageId),
r => r.HasOne<Transporteur>().WithMany().HasForeignKey(e => e.TransporteurId)
);
but got another exception
Error Number:1785,State:0,Class:16
Introducing FOREIGN KEY constraint 'FK_TransporteurVoyage_Voyage_VoyageId' on table 'TransporteurVoyage' may cause cycles or multiple cascade paths. Specify ON DELETE NO ACTION or ON UPDATE NO ACTION, or modify other FOREIGN KEY constraints.
Could not create constraint or index. See previous errors.
Warning! The maximum key length for a clustered index is 900 bytes. The index 'PK_TransporteurVoyage' has maximum length of 1800 bytes. For some combination of large values, the insert/update operation will fail.
Error Number:1785,State:0,Class:16
Introducing FOREIGN KEY constraint 'FK_TransporteurVoyage_Voyage_VoyageId' on table 'TransporteurVoyage' may cause cycles or multiple cascade paths. Specify ON DELETE NO ACTION or ON UPDATE NO ACTION, or modify other FOREIGN KEY constraints.
Could not create constraint or index. See previous errors.
Warning! The maximum key length for a clustered index is 900 bytes. The index 'PK_TransporteurVoyage' has maximum length of 1800 bytes. For some combination of large values, the insert/update operation will fail.
daminko
daminkoOP9mo ago
No description
Angius
Angius9mo ago
Why are the IDs 450-character long varchars
daminko
daminkoOP9mo ago
The Transporteur inherits from IdentityUser
Angius
Angius9mo ago
I'd change the type of the key it uses To a GUID or something
daminko
daminkoOP9mo ago
How can I change it?
Angius
Angius9mo ago
Because varchar IDs this long are a bad idea Transporteur : IdentityUser<TKey> TKey being the type of the key
daminko
daminkoOP9mo ago
ow
Angius
Angius9mo ago
You'll need to recreate the migrations, mind you Or, well, at least create a new one Actually... you will need to drop the database, delete migrations, and create them from zero
daminko
daminkoOP9mo ago
I'm still creating my database so np
Angius
Angius9mo ago
Since PK change is not backwards compatible
daminko
daminkoOP9mo ago
Just one more question
daminko
daminkoOP9mo ago
No description
daminko
daminkoOP9mo ago
I have these 4 classes that extends Utilisateur what I've done I created the Demandeur, Admin Magasinier and the transporteur classes all of them extends the IdentityUser is it a good approach? or there is a better one
Angius
Angius9mo ago
IMHO the best approach would be to use roles, not inheritance in this case But, sure, inheritance should work as well
daminko
daminkoOP9mo ago
my business logic imposes inheritance
Angius
Angius9mo ago
Then you do what you must
daminko
daminkoOP9mo ago
Tysm for your time
deem
deem9mo ago
no problem
Want results from more Discord servers?
Add your server