I migrated our solution from .NET Core 3.1 to .NET 5. Now I am facing this issue : I have a Link model which has discriminator column with two types of values, now the LINQ to this table is not working and when I convert it to sql query and compare with previous version , these are two different queries and the .NET 5 one gave me error when I run it in PostgreSQL.
var test = _identityContext.Links.AsQueryable();
These are two different queries I get in two different versions :
In .Net Core 3.1 :
SELECT l."Id", l."Discriminator", l."Inserted", l."UserId", l.xmin
FROM "Links" AS l
WHERE l."Discriminator" IN ('GamecenterLinkModel', 'GooglePlayLinkModel')
In .Net 5:
SELECT l."Id", l."Inserted", l."UserId", l.xmin, CASE
WHEN (g0."Id" IS NOT NULL) THEN 'GooglePlayLinkModel'
WHEN (g."Id" IS NOT NULL) THEN 'GamecenterLinkModel'
END AS "Discriminator"
FROM "Links" AS l
LEFT JOIN "GamecenterLinks" AS g ON l."Id" = g."Id"
LEFT JOIN "GooglePlayLinks" AS g0 ON l."Id" = g0."Id"
Is something has changed in defining the discriminator in .NET 5 ?
This is My Link Model :
[Table("Links")]
public abstract class LinkModel : ILinkModel, ITimeStampInserted
{
public string Id { get; set; }
public UserModel User { get; set; }
public DateTime Inserted { get; set; }
public abstract ILink ToLink();
}
[Table("GamecenterLinks")]
public class GamecenterLinkModel : LinkModel
{
public override ILink ToLink()
{
return new GameCenterLink(Id);
}
}
[Table("GooglePlayLinks")]
public class GooglePlayLinkModel : LinkModel
{
public override ILink ToLink()
{
return new GooglePlayLink(Id);
}
}
My IdentityContext class :
public class IdentityContext : DbContextBase
{
public DbSet<UserModel> Users { get; set; }
public DbSet<RefreshTokenModel> RefreshTokenLinks { get; set; }
public DbSet<GamecenterLinkModel> GamecenterLinks { get; set; }
public DbSet<GooglePlayLinkModel> GooglePlayLinks { get; set; }
public DbSet<LinkConflictModel> LinkConflicts { get; set; }
public DbSet<LinkModel> Links { get; set; }
public IdentityContext(DbContextOptions<IdentityContext> options) : base(options)
{
}
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<UserModel>().UseXminAsConcurrencyToken();
modelBuilder.Entity<RefreshTokenModel>().UseXminAsConcurrencyToken();
modelBuilder.Entity<GamecenterLinkModel>().UseXminAsConcurrencyToken();
modelBuilder.Entity<LinkModel>().UseXminAsConcurrencyToken();
}
}
UPDATE : I downgraded the EF version,Npgsql and Npgsql.EntityFrameworkCore.PostgreSQL to 3.1.3 and things work fine now, so guess it is EF upgrade issue.
UPDATE 2: I removed the [Table("GamecenterLinks")] and [Table("GooglePlayLinks")] annotation from top of the two derived classes and it solved the issue, think when I updated EF Core, it confused it with Table-Per-type and assumed they are two different table for each derived class.