Skip to content
This repository was archived by the owner on Feb 1, 2025. It is now read-only.

Commit 7d8ffea

Browse files
authored
Fix sub-inheritance mapping attributes generation (#347)
* 1. Fix sub-inheritance mapping attributes generation * 1. Simplification
1 parent acca69a commit 7d8ffea

File tree

8 files changed

+91
-9
lines changed

8 files changed

+91
-9
lines changed

Source/LinqToDB.EntityFrameworkCore/EFCoreMetadataReader.cs

Lines changed: 27 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -112,16 +112,9 @@ public MappingAttribute[] GetAttributes(Type type)
112112
{
113113
foreach (var e in _model.GetEntityTypes())
114114
{
115-
if (e.BaseType == et && e.GetDiscriminatorValue() != null)
115+
if (GetBaseTypeRecursive(e) == et && e.GetDiscriminatorValue() != null)
116116
{
117-
118-
result.Add(
119-
new InheritanceMappingAttribute()
120-
{
121-
Type = e.ClrType,
122-
Code = e.GetDiscriminatorValue()
123-
}
124-
);
117+
result.AddRange(GetMappingAttributesRecursive(e));
125118
}
126119
}
127120
}
@@ -137,6 +130,31 @@ public MappingAttribute[] GetAttributes(Type type)
137130
return result == null ? Array.Empty<MappingAttribute>() : result.ToArray();
138131
}
139132

133+
static IEntityType GetBaseTypeRecursive(IEntityType entityType)
134+
{
135+
if (entityType.BaseType == null)
136+
return entityType;
137+
return GetBaseTypeRecursive(entityType.BaseType);
138+
}
139+
140+
static IEnumerable<InheritanceMappingAttribute> GetMappingAttributesRecursive(IEntityType entityType)
141+
{
142+
var mappings = new List<InheritanceMappingAttribute>();
143+
return ProcessEntityType(entityType);
144+
145+
List<InheritanceMappingAttribute> ProcessEntityType(IEntityType et)
146+
{
147+
mappings.Add(new()
148+
{
149+
Type = et.ClrType, Code = entityType.GetDiscriminatorValue()
150+
});
151+
152+
if (et.BaseType == null)
153+
return mappings;
154+
return ProcessEntityType(et.BaseType);
155+
}
156+
}
157+
140158
static bool CompareProperty(MemberInfo? property, MemberInfo memberInfo)
141159
{
142160
if (property == memberInfo)

Tests/LinqToDB.EntityFrameworkCore.BaseTests/ForMappingTestsBase.cs

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -161,5 +161,22 @@ public virtual void TestMappingSchemaCachedWithCustomSchema()
161161
pk.IsIdentity.Should().BeFalse();
162162
Assert.AreEqual("Field", pk.ColumnName);
163163
}
164+
165+
[Test]
166+
public virtual async Task TestInheritance()
167+
{
168+
using var context = CreateContext();
169+
using var connection = context.CreateLinqToDBConnection();
170+
171+
context.WithInheritance.AddRange(new List<WithInheritanceA1>() { new() { }, new() { } });
172+
context.WithInheritance.AddRange(new List<WithInheritanceA2>() { new() { }, new() { } });
173+
await context.SaveChangesAsync();
174+
175+
var result = context.GetTable<WithInheritanceA>().ToList();
176+
177+
result.OfType<WithInheritance>().Should().HaveCount(4);
178+
result.OfType<WithInheritanceA1>().Should().HaveCount(2);
179+
result.OfType<WithInheritanceA2>().Should().HaveCount(2);
180+
}
164181
}
165182
}

Tests/LinqToDB.EntityFrameworkCore.BaseTests/Models/ForMapping/ForMappingContextBase.cs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,5 +14,10 @@ protected ForMappingContextBase(DbContextOptions options) : base(options)
1414
public DbSet<StringTypes> StringTypes { get; set; } = null!;
1515

1616
public DbSet<WithDuplicateProperties> WithDuplicateProperties { get; set; } = null!;
17+
18+
public DbSet<WithInheritance> WithInheritance { get; set; } = null!;
19+
public DbSet<WithInheritanceA> WithInheritanceA { get; set; } = null!;
20+
public DbSet<WithInheritanceA1> WithInheritanceA1 { get; set; } = null!;
21+
public DbSet<WithInheritanceA2> WithInheritanceA2 { get; set; } = null!;
1722
}
1823
}
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
namespace LinqToDB.EntityFrameworkCore.BaseTests.Models.ForMapping;
2+
3+
public class WithInheritance
4+
{
5+
public int Id { get; set; }
6+
public string Discriminator { get; set; } = null!;
7+
}
8+
9+
public class WithInheritanceA : WithInheritance
10+
{
11+
12+
}
13+
14+
public class WithInheritanceA1 : WithInheritanceA
15+
{
16+
17+
}
18+
19+
public class WithInheritanceA2 : WithInheritanceA
20+
{
21+
22+
}

Tests/LinqToDB.EntityFrameworkCore.PomeloMySql.Tests/Models/ForMapping/ForMappingContext.cs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,11 @@ protected override void OnModelCreating(ModelBuilder modelBuilder)
2525
{
2626
b.HasKey(e => e.Id);
2727
});
28+
29+
modelBuilder.Entity<WithInheritance>(b =>
30+
{
31+
b.HasDiscriminator(x => x.Discriminator);
32+
});
2833
}
2934
}
3035
}

Tests/LinqToDB.EntityFrameworkCore.PostgreSQL.Tests/Models/ForMapping/ForMappingContext.cs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,11 @@ protected override void OnModelCreating(ModelBuilder modelBuilder)
2323
{
2424
b.HasKey(e => e.Id);
2525
});
26+
27+
modelBuilder.Entity<WithInheritance>(b =>
28+
{
29+
b.HasDiscriminator(x => x.Discriminator);
30+
});
2631
}
2732
}
2833
}

Tests/LinqToDB.EntityFrameworkCore.SQLite.Tests/Models/ForMapping/ForMappingContext.cs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,11 @@ protected override void OnModelCreating(ModelBuilder modelBuilder)
2020
{
2121
b.HasKey(e => e.Id);
2222
});
23+
24+
modelBuilder.Entity<WithInheritance>(b =>
25+
{
26+
b.HasDiscriminator(x => x.Discriminator);
27+
});
2328
}
2429
}
2530
}

Tests/LinqToDB.EntityFrameworkCore.SqlServer.Tests/Models/ForMapping/ForMappingContext.cs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,11 @@ protected override void OnModelCreating(ModelBuilder modelBuilder)
3030
b.Property(e => e.UnicodeString).HasMaxLength(50).IsUnicode();
3131
}
3232
);
33+
34+
modelBuilder.Entity<WithInheritance>(b =>
35+
{
36+
b.HasDiscriminator(x => x.Discriminator);
37+
});
3338
}
3439
}
3540
}

0 commit comments

Comments
 (0)