Мое простое тестовое приложение, которое я настроил для диагностики другой возникшей у меня проблемы, похоже, извлекает связанные данные из таблицы, которую я не ожидал, и когда я включаю ведение журнала, я не вижу ссылки на эту таблицу в сгенерированном SQL.
Мое тестовое приложение имеет две простые сущности — Band, каждая из которых может иметь множество альбомов. После настройки некоторых тестовых данных я запускаю запрос, чтобы вернуть одну из групп, и, похоже, она возвращается вместе со связанными с ней альбомами, хотя я их не запрашивал и не вижу никакой ссылки на Таблица альбома в сгенерированном SQL, зарегистрированном Entity Framework.
Субъекты выглядят следующим образом.
public class Band
{
public Guid Id { get; set; }
public string BandName { get; set; }
public List Albums { get; set; } = [];
}
public class Album
{
public Guid Id { get; set; }
public string AlbumName { get; set; }
public Guid BandId { get; set; }
public Band Band { get; set; }
}
Я настраиваю ведение журнала следующим образом, в методе OnConfiguring: -
optionsBuilder.LogTo(Console.WriteLine);
optionsBuilder.EnableSensitiveDataLogging();
После настройки набора тестовых данных (которые я не буду вставлять сюда для краткости) я запускаю следующий простой тестовый код: -
Band band = context.Bands.Where(b => b.BandName == "The Cure").Single();
List albums = band.Albums;
Console.WriteLine($"{band.BandName} has released {albums.Count} albums: -");
foreach (Album album in band.Albums)
{
Console.WriteLine(album.AlbumName);
}
На самом деле я ожидал, что моя коллекция альбомов будет пустой, поскольку я не добавил Include в свой первоначальный оператор LINQ. Но коллекция альбомов полностью заполнена, поэтому в коде перечислены альбомы этой группы. Это справедливо, но, глядя на сгенерированный оператор SQL из журнала, я не вижу ничего, что каким-либо образом ссылается на таблицу «Альбомы». Вот общая сумма SQL, которая отображается в журнале: -
SELECT "b"."Id", "b"."BandName"
FROM "Bands" AS "b"
WHERE "b"."BandName" = 'The Cure'
LIMIT 2
Кстати, если я добавлю оператор включения, то сгенерированный SQL ссылается на таблицу «Альбомы», как я и ожидал, а остальная часть кода выполняется точно таким же образом, создавая тот же результат.
Может ли кто-нибудь предложить какую-либо помощь в разгадке этой загадки?
Изменить: добавление полного кода моего примера приложения ниже по запросу комментатор.
Это код класса контекста БД: -
public class MusicContext : DbContext
{
private readonly SqliteConnection DbConnection;
public MusicContext(SqliteConnection dbConnection)
{
DbConnection = dbConnection;
}
public DbSet Bands { get; set; }
public DbSet Albums { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
AddRelationships(modelBuilder);
base.OnModelCreating(modelBuilder);
}
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
optionsBuilder.UseSqlite(DbConnection);
optionsBuilder.LogTo(Console.WriteLine);
optionsBuilder.EnableSensitiveDataLogging();
}
private void AddRelationships(ModelBuilder modelBuilder)
{
modelBuilder.Entity()
.HasOne(a => a.Band)
.WithMany(b => b.Albums)
.HasForeignKey(a => a.BandId)
.OnDelete(DeleteBehavior.NoAction);
}
}
А вот полный код Program.cs, который настраивает тестовые данные, затем извлекает одну из полос, а затем выводит детали в виде теста: -SqliteConnection connection;
connection = new SqliteConnection("Filename=:memory:");
connection.Open();
MusicContext context = SetupDbWithEntities(connection);
OutputTestData(context);
void OutputTestData(MusicContext context)
{
Band band = context.Bands.Where(b => b.BandName == "The Cure").Single();
List albums = band.Albums;
Console.WriteLine($"{band.BandName} has released {albums.Count} albums: -");
foreach (Album album in band.Albums)
{
Console.WriteLine(album.AlbumName);
}
}
MusicContext SetupDbWithEntities(SqliteConnection connection)
{
MusicContext context = new MusicContext(connection);
if (context.Database.EnsureCreated())
{
Band band1 = new()
{
BandName = "The Cure"
};
context.Bands.Add(band1);
Band band2 = new()
{
BandName = "Pink Floyd"
};
context.Bands.Add(band2);
Album album1 = new()
{
AlbumName = "Seventeen Seconds"
};
band1.Albums.Add(album1);
Album album2 = new()
{
AlbumName = "Disintegration"
};
band1.Albums.Add(album2);
Album album3 = new()
{
AlbumName = "Wish"
};
band1.Albums.Add(album3);
Album album4 = new()
{
AlbumName = "The Dark Side of the Moon"
};
band2.Albums.Add(album4);
Album album5 = new()
{
AlbumName = "Wish You Were Here"
};
band2.Albums.Add(album5);
}
context.SaveChanges();
return context;
}
Подробнее здесь: https://stackoverflow.com/questions/790 ... ringing-ba