İlişkiler
Gezinti özelliklerini yapılandırma
Not
Bu özellik EF Core 5,0 ' de tanıtılmıştı.
Gezinti özelliği oluşturulduktan sonra, daha fazla yapılandırmanız gerekebilir.
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Blog>()
.HasMany(b => b.Posts)
.WithOne();
modelBuilder.Entity<Blog>()
.Navigation(b => b.Posts)
.UsePropertyAccessMode(PropertyAccessMode.Property);
}
Not
Bu çağrı bir gezinti özelliği oluşturmak için kullanılamaz. Yalnızca daha önce bir ilişki tanımlayarak veya bir kurala göre oluşturulmuş olan bir gezinti özelliğini yapılandırmak için kullanılır.
Yabancı anahtar
belirli bir ilişki için yabancı anahtar özelliği olarak kullanılması gereken özelliği yapılandırmak için Fluent apı 'sini kullanabilirsiniz:
internal class MyContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<Post> Posts { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Post>()
.HasOne(p => p.Blog)
.WithMany(b => b.Posts)
.HasForeignKey(p => p.BlogForeignKey);
}
}
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public int BlogForeignKey { get; set; }
public Blog Blog { get; set; }
}
Gölge yabancı anahtar
HasForeignKey(...)Bir gölge özelliği yabancı anahtar olarak yapılandırmak için ' nin dize aşırı yüklemesini kullanabilirsiniz (daha fazla bilgi için bkz. HasForeignKey(...) ). Gölge özelliğini, yabancı anahtar olarak kullanmadan önce modele açıkça eklememiz önerilir (aşağıda gösterildiği gibi).
internal class MyContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<Post> Posts { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
// Add the shadow property to the model
modelBuilder.Entity<Post>()
.Property<int>("BlogForeignKey");
// Use the shadow property as a foreign key
modelBuilder.Entity<Post>()
.HasOne(p => p.Blog)
.WithMany(b => b.Posts)
.HasForeignKey("BlogForeignKey");
}
}
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public Blog Blog { get; set; }
}
Yabancı anahtar kısıtlama adı
Kural gereği, bir ilişkisel veritabanını hedeflerken, yabancı anahtar kısıtlamaları FK_ < bağımlı tür adı > _ < asıl tür adı > _ < yabancı anahtar özellik adı > olarak adlandırılır. Bileşik yabancı anahtarlar için < yabancı anahtar özellik adı, > yabancı anahtar özellik adlarının alt çizgiyle ayrılmış bir listesi haline gelir.
Kısıtlama adını aşağıdaki şekilde de yapılandırabilirsiniz:
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Post>()
.HasOne(p => p.Blog)
.WithMany(b => b.Posts)
.HasForeignKey(p => p.BlogId)
.HasConstraintName("ForeignKey_Post_Blog");
}
Gezinti özelliği olmadan
Bir gezinti özelliği sağlamanız gerekmez. İlişkinin yalnızca bir tarafında yabancı anahtar sağlayabilirsiniz.
internal class MyContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<Post> Posts { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Post>()
.HasOne<Blog>()
.WithMany()
.HasForeignKey(p => p.BlogId);
}
}
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public int BlogId { get; set; }
}
Asıl anahtar
yabancı anahtarın birincil anahtar dışında bir özelliğe başvurmasına isterseniz, ilişkinin asıl anahtar özelliğini yapılandırmak için Fluent apı 'sini kullanabilirsiniz. Asıl anahtar olarak yapılandırdığınız özellik otomatik olarak alternatif bir anahtarolarak ayarlanır.
internal class MyContext : DbContext
{
public DbSet<Car> Cars { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<RecordOfSale>()
.HasOne(s => s.Car)
.WithMany(c => c.SaleHistory)
.HasForeignKey(s => s.CarLicensePlate)
.HasPrincipalKey(c => c.LicensePlate);
}
}
public class Car
{
public int CarId { get; set; }
public string LicensePlate { get; set; }
public string Make { get; set; }
public string Model { get; set; }
public List<RecordOfSale> SaleHistory { get; set; }
}
public class RecordOfSale
{
public int RecordOfSaleId { get; set; }
public DateTime DateSold { get; set; }
public decimal Price { get; set; }
public string CarLicensePlate { get; set; }
public Car Car { get; set; }
}
Gerekli ve isteğe bağlı ilişkiler
ilişkinin gerekli veya isteğe bağlı olup olmadığını yapılandırmak için Fluent apı 'sini kullanabilirsiniz. Sonuç olarak bu, yabancı anahtar özelliğinin gerekli veya isteğe bağlı olup olmadığını denetler. Bu, büyük bir gölge durumu yabancı anahtar kullanırken faydalıdır. Varlık sınıfınızda yabancı anahtar özelliği varsa, ilişkinin gereklik durumu yabancı anahtar özelliğinin gerekli veya isteğe bağlı olup olmadığına göre belirlenir (daha fazla bilgi için bkz. gerekli ve Isteğe bağlı özellikler ).
Yabancı anahtar özellikleri bağımlı varlık türünde bulunur, bu nedenle gerekli olarak yapılandırılırsa, her bağımlı varlığın ilgili bir sorumlu varlığına sahip olması gerektiği anlamına gelir.
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Post>()
.HasOne(p => p.Blog)
.WithMany(b => b.Posts)
.IsRequired();
}
Not
Çağırma IsRequired(false) , aksi belirtilmedikçe yabancı anahtar özelliğini de isteğe bağlı hale getirir.
Basamaklı silme
belirli bir ilişki için basamaklı silme davranışını açıkça yapılandırmak için Fluent apı 'sini kullanabilirsiniz.
Her seçeneğe ilişkin ayrıntılı bir tartışma için bkz. Cascade Delete .
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Post>()
.HasOne(p => p.Blog)
.WithMany(b => b.Posts)
.OnDelete(DeleteBehavior.Cascade);
}
Diğer ilişki desenleri
Bir-bir
Bir ilişkinin her iki tarafında da başvuru gezintisi özelliği vardır. Tek-çok ilişkilerle aynı kurallara uyar, ancak her sorumluyla yalnızca bir bağımlı ilişki olduğundan emin olmak için yabancı anahtar özelliğinde benzersiz bir dizin sunulmuştur.
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public BlogImage BlogImage { get; set; }
}
public class BlogImage
{
public int BlogImageId { get; set; }
public byte[] Image { get; set; }
public string Caption { get; set; }
public int BlogId { get; set; }
public Blog Blog { get; set; }
}
Not
EF, bir yabancı anahtar özelliği algılama özelliğine göre bağımlı olacak varlıklardan birini seçer. bağımlı olarak yanlış varlık seçilirse, bunu düzeltmek için Fluent apı 'sini kullanabilirsiniz.
Fluent apı 'siyle ilişki yapılandırılırken, HasOne ve WithOne yöntemlerini kullanırsınız.
Yabancı anahtarı yapılandırırken, bağımlı varlık türünü belirtmeniz gerekir HasForeignKey . aşağıdaki listede, için belirtilen genel parametreyi görürsünüz. Bire çok ilişkisinde, başvuru gezinmesi olan varlığın bağımlı olduğunu ve koleksiyonun asıl öğe olduğunu unutmayın. Ancak bu, bire bir ilişkide değildir, bu nedenle açıkça tanımlanması gerekir.
internal class MyContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<BlogImage> BlogImages { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Blog>()
.HasOne(b => b.BlogImage)
.WithOne(i => i.Blog)
.HasForeignKey<BlogImage>(b => b.BlogForeignKey);
}
}
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public BlogImage BlogImage { get; set; }
}
public class BlogImage
{
public int BlogImageId { get; set; }
public byte[] Image { get; set; }
public string Caption { get; set; }
public int BlogForeignKey { get; set; }
public Blog Blog { get; set; }
}
Bağımlı taraf varsayılan olarak isteğe bağlıdır, ancak gerektiği şekilde yapılandırılabilir. Ancak EF, bağımlı bir varlığın sağlandığını doğrulamaz, bu nedenle bu yapılandırma yalnızca veritabanı eşlemesi zorunlu kılınmaya izin veriyorsa bir fark yapar. Bunun için yaygın bir senaryo, varsayılan olarak tablo bölme kullanan başvuruya ait türlerdir.
modelBuilder.Entity<Order>(
ob =>
{
ob.OwnsOne(
o => o.ShippingAddress,
sa =>
{
sa.Property(p => p.Street).IsRequired();
sa.Property(p => p.City).IsRequired();
});
ob.Navigation(o => o.ShippingAddress)
.IsRequired();
});
Bu yapılandırmayla, öğesine karşılık gelen sütunlar ShippingAddress veritabanında null yapılamayan olarak işaretlenir.
Not
Null atanabilir olmayan başvuru türleri kullanıyorsanız , bu gerekli değildir.
Not
EF Core 5,0 ' de bağımlı 'nin gerekli olup olmadığını yapılandırma özelliği.
Çok-çok
Birçok çoğa ilişki her iki tarafta bir koleksiyon gezintisi özelliği gerektirir. Bunlar diğer ilişki türleri gibi kurala göre keşfedilir.
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public ICollection<Tag> Tags { get; set; }
}
public class Tag
{
public string TagId { get; set; }
public ICollection<Post> Posts { get; set; }
}
Bu ilişkinin veritabanına uygulanma şekli, hem hem de için yabancı anahtarlar içeren bir JOIN tablosudur PostTag . Örneğin, bu, yukarıdaki model için bir ilişkisel veritabanında EF 'in oluşturulacağı şeydir.
CREATE TABLE [Posts] (
[PostId] int NOT NULL IDENTITY,
[Title] nvarchar(max) NULL,
[Content] nvarchar(max) NULL,
CONSTRAINT [PK_Posts] PRIMARY KEY ([PostId])
);
CREATE TABLE [Tags] (
[TagId] nvarchar(450) NOT NULL,
CONSTRAINT [PK_Tags] PRIMARY KEY ([TagId])
);
CREATE TABLE [PostTag] (
[PostsId] int NOT NULL,
[TagsId] nvarchar(450) NOT NULL,
CONSTRAINT [PK_PostTag] PRIMARY KEY ([PostsId], [TagsId]),
CONSTRAINT [FK_PostTag_Posts_PostsId] FOREIGN KEY ([PostsId]) REFERENCES [Posts] ([PostId]) ON DELETE CASCADE,
CONSTRAINT [FK_PostTag_Tags_TagsId] FOREIGN KEY ([TagsId]) REFERENCES [Tags] ([TagId]) ON DELETE CASCADE
);
İçten, EF, JOIN varlık türü olarak ifade edilecek JOIN tablosunu temsil eden bir varlık türü oluşturur. Dictionary<string, object> , yabancı anahtar özelliklerinin herhangi bir birleşimini işlemek için şu anda kullanılıyor, daha fazla bilgi için bkz. Dictionary<string, object> . Modelde birden çok çoktan çoğa ilişki bulunabilir, bu nedenle bu durumda JOIN varlık türüne benzersiz bir ad verilmelidir PostTag . Buna izin veren özelliği, paylaşılan türdeki varlık türü olarak adlandırılır.
Önemli
Kurala göre varlık türlerini Birleştir için kullanılan CLR türü, performansı artırmak için gelecek sürümlerde değişebilir. Dictionary<string, object>Bu, sonraki bölümde açıklandığı gibi açık bir şekilde yapılandırılmadığı sürece, JOIN türüne bağlı değildir.
Birçok-çok gezginler, JOIN varlık türü üzerinde etkin bir şekilde atlama yaparken, gezinmeleri atlama olarak adlandırılır. Toplu yapılandırma kullanıyorsanız, tüm atlama gezginlerini Getskipgezintilerdenelde edilebilir.
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
foreach (var skipNavigation in entityType.GetSkipNavigations())
{
Console.WriteLine(entityType.DisplayName() + "." + skipNavigation.Name);
}
}
Varlık türü yapılandırmasına Birleştir
Yapılandırma, JOIN varlık türüne uygulamak yaygındır. Bu eylem aracılığıyla gerçekleştirilebilir UsingEntity .
modelBuilder
.Entity<Post>()
.HasMany(p => p.Tags)
.WithMany(p => p.Posts)
.UsingEntity(j => j.ToTable("PostTags"));
Anonim türler kullanılarak, JOIN varlık türü için model tohum verileri sağlayabilirsiniz. Kural tarafından oluşturulan özellik adlarını belirleyebilmeniz için model hata ayıklama görünümünü inceleyebilirsiniz.
modelBuilder
.Entity<Post>()
.HasData(new Post { PostId = 1, Title = "First" });
modelBuilder
.Entity<Tag>()
.HasData(new Tag { TagId = "ef" });
modelBuilder
.Entity<Post>()
.HasMany(p => p.Tags)
.WithMany(p => p.Posts)
.UsingEntity(j => j.HasData(new { PostsPostId = 1, TagsTagId = "ef" }));
Ek veriler, JOIN varlık türünde depolanabilir, ancak bunun en iyisi, bir Bespoke CLR türü oluşturmaktır. İlişkiyi özel bir JOIN varlık türü ile yapılandırırken, hem yabancı anahtarların hem de açıkça belirtilmesi gerekir.
internal class MyContext : DbContext
{
public MyContext(DbContextOptions<MyContext> options)
: base(options)
{
}
public DbSet<Post> Posts { get; set; }
public DbSet<Tag> Tags { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Post>()
.HasMany(p => p.Tags)
.WithMany(p => p.Posts)
.UsingEntity<PostTag>(
j => j
.HasOne(pt => pt.Tag)
.WithMany(t => t.PostTags)
.HasForeignKey(pt => pt.TagId),
j => j
.HasOne(pt => pt.Post)
.WithMany(p => p.PostTags)
.HasForeignKey(pt => pt.PostId),
j =>
{
j.Property(pt => pt.PublicationDate).HasDefaultValueSql("CURRENT_TIMESTAMP");
j.HasKey(t => new { t.PostId, t.TagId });
});
}
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public ICollection<Tag> Tags { get; set; }
public List<PostTag> PostTags { get; set; }
}
public class Tag
{
public string TagId { get; set; }
public ICollection<Post> Posts { get; set; }
public List<PostTag> PostTags { get; set; }
}
public class PostTag
{
public DateTime PublicationDate { get; set; }
public int PostId { get; set; }
public Post Post { get; set; }
public string TagId { get; set; }
public Tag Tag { get; set; }
}
İlişki yapılandırmasını birleştirme
EF, çoka çok ilişkiyi temsil etmek için JOIN varlık türü üzerinde 2 1-çok ilişkisi kullanır. Bu ilişkileri UsingEntity bağımsız değişkenlerde yapılandırabilirsiniz.
modelBuilder.Entity<Post>()
.HasMany(p => p.Tags)
.WithMany(p => p.Posts)
.UsingEntity<Dictionary<string, object>>(
"PostTag",
j => j
.HasOne<Tag>()
.WithMany()
.HasForeignKey("TagId")
.HasConstraintName("FK_PostTag_Tags_TagId")
.OnDelete(DeleteBehavior.Cascade),
j => j
.HasOne<Post>()
.WithMany()
.HasForeignKey("PostId")
.HasConstraintName("FK_PostTag_Posts_PostId")
.OnDelete(DeleteBehavior.ClientCascade));
Not
Çok-çok ilişkilerini yapılandırma özelliği EF Core 5,0 ' de kullanıma sunulmuştur, önceki sürüm için aşağıdaki yaklaşımı kullanın.
Dolaylı çoktan çoğa ilişkiler
Ayrıca, yalnızca JOIN varlık türünü ekleyerek ve iki ayrı bire çok ilişkiyi eşleyerek çoktan çoğa ilişkiyi temsil edebilirsiniz.
public class MyContext : DbContext
{
public MyContext(DbContextOptions<MyContext> options)
: base(options)
{
}
public DbSet<Post> Posts { get; set; }
public DbSet<Tag> Tags { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<PostTag>()
.HasKey(t => new { t.PostId, t.TagId });
modelBuilder.Entity<PostTag>()
.HasOne(pt => pt.Post)
.WithMany(p => p.PostTags)
.HasForeignKey(pt => pt.PostId);
modelBuilder.Entity<PostTag>()
.HasOne(pt => pt.Tag)
.WithMany(t => t.PostTags)
.HasForeignKey(pt => pt.TagId);
}
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public List<PostTag> PostTags { get; set; }
}
public class Tag
{
public string TagId { get; set; }
public List<PostTag> PostTags { get; set; }
}
public class PostTag
{
public DateTime PublicationDate { get; set; }
public int PostId { get; set; }
public Post Post { get; set; }
public string TagId { get; set; }
public Tag Tag { get; set; }
}
Not
Veritabanından çoka çok ilişkilerinin iskelesi oluşturma desteği henüz eklenmedi. İzleme sorununa bakın.
Ek kaynaklar
- EF Core Community oturumundaÇoka çok'a ve altyapının bunu derinlemesine incelemesini sağlar.
İlişki, iki varlığın arasındaki ilişkiyi tanımlar. İlişkisel veritabanında bu, yabancı anahtar kısıtlaması ile temsil edildi.
Not
Bu makaledeki örneklerin çoğu kavramları göstermek için bire çok ilişkisi kullanır. Bire bir ve çoka çok ilişkilerine örnekler için makalenin sonundaki Diğer İlişki Desenleri bölümüne bakın.
Terimlerin tanımı
İlişkileri açıklamak için kullanılan bir dizi terim vardır
Bağımlı varlık: Bu, yabancı anahtar özelliklerini içeren varlıktır. Bazen ilişkinin 'alt' olarak da adlandırılır.
Asıl varlık: Bu, birincil/alternatif anahtar özelliklerini içeren varlıktır. Bazen ilişkinin 'üst' öğesi olarak da adlandırılır.
Asıl anahtar: Asıl varlığı benzersiz olarak tanımlamak için özellikler. Bu, birincil anahtar veya alternatif bir anahtar olabilir.
Yabancı anahtar: Bağımlı varlıkta ilgili varlığın asıl anahtar değerlerini depolamak için kullanılan özellikler.
Gezinti özelliği: İlgili varlığa başvurulan sorumlu ve/veya bağımlı varlık üzerinde tanımlanan bir özellik.
Koleksiyon gezinti özelliği: Birçok ilgili varlık için başvurular içeren bir gezinti özelliği.
Başvuru gezinti özelliği: Tek bir ilgili varlığa başvuru tutan gezinti özelliği.
Ters gezinti özelliği: Belirli bir gezinti özelliği tartışırken, bu terim ilişkinin diğer ucundaki gezinti özelliğini ifade eder.
Kendine başvuran ilişki: Bağımlı ve asıl varlık türlerinin aynı olduğu bir ilişki.
Aşağıdaki kod, ile arasındaki bire çok ilişkisini Blog gösterir Post
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public int BlogId { get; set; }
public Blog Blog { get; set; }
}
Postbağımlı varlıktırBlogasıl varlıktırBlog.BlogIdasıl anahtardır (bu durumda alternatif anahtar yerine birincil anahtardır)Post.BlogIdyabancı anahtardırPost.Blogbir başvuru gezinti özelliğidirBlog.Postsbir koleksiyon gezinti özelliğidirPost.Blog, 'nin ters gezintiBlog.Postsözelliğidir (veya tam tersi)
Kurallar
Varsayılan olarak, bir tür üzerinde bulunan bir gezinti özelliği olduğunda bir ilişki oluşturulur. Bir özellik, geçerli veritabanı sağlayıcısı tarafından skaler tür olarak eşlenmemişse, bir gezinti özelliği olarak kabul edilir.
Not
Kural tarafından bulunan ilişkiler her zaman asıl varlığın birincil anahtarını hedefler. Alternatif bir anahtarı hedeflemek için api'sini kullanarak ek Fluent gerekir.
Tam tanımlı ilişkiler
İlişkiler için en yaygın desen, ilişkinin her iki ucunda da tanımlanan gezinti özelliklerine ve bağımlı varlık sınıfında tanımlanan yabancı anahtar özelliğine sahip olmaktır.
İki tür arasında bir çift gezinti özelliği bulunursa, bunlar aynı ilişkinin ters gezinti özellikleri olarak yapılandırılır.
Bağımlı varlık, bu desenlerden biri ile eşleşen bir ad içeren bir özellik içeriyorsa, yabancı anahtar olarak yapılandırılır:
<navigation property name><principal key property name><navigation property name>Id<principal entity name><principal key property name><principal entity name>Id
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public int BlogId { get; set; }
public Blog Blog { get; set; }
}
Bu örnekte, ilişkiyi yapılandırmak için vurgulanan özellikler kullanılacaktır.
Not
Özelliğin birincil anahtar olması veya asıl anahtarla uyumlu bir tür olması, yabancı anahtar olarak yapılandırılmaz.
Yabancı anahtar özelliği yok
Bağımlı varlık sınıfında tanımlanmış bir yabancı anahtar özelliği olması önerilmez, ancak gerekli değildir. Yabancı anahtar özelliği bulunamasa, adla bir gölge yabancı anahtar özelliği tanıtılacak veya bağımlı türde bir gezinti <principal entity name><principal key property name> yoksa.
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public Blog Blog { get; set; }
}
Bu örnekte, gölge yabancı BlogId anahtar, gezinti adının hazırlanmasının gereksiz olmasıdır.
Not
Aynı adla bir özellik zaten varsa, gölge özellik adı bir sayı ile son eke sahip olur.
Tek gezinti özelliği
Yalnızca bir gezinti özelliğinin (ters gezinti ve yabancı anahtar özelliği yok) dahil etmek, kurala göre tanımlanan bir ilişkiye sahip olmak için yeterlidir. Ayrıca tek bir gezinti özelliğine ve yabancı anahtar özelliğine de sahip olabilirsiniz.
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
}
Sınırlamalar
İki tür arasında tanımlanan birden çok gezinti özelliği olduğunda (yani, birbirine işaret eden birden fazla gezinti çifti) gezinti özellikleriyle temsil edilen ilişkiler belirsizdir. Belirsizlik sorununu çözmek için bunları el ile yapılandırmanız gerekir.
Basamaklı silme
Kural gereği, gerekli ilişkiler için basamaklı silme, isteğe bağlı ilişkiler için ClientSetNull olarak ayarlanır. Basamak, bağımlı varlıkların da silinecek olduğu anlamına gelir. ClientSetNull, belleğe yüklenmeyen bağımlı varlıkların değişmeden kalarak el ile silinmesi veya geçerli bir asıl varlığa işaret etmek için güncelleştirildiği anlamına gelir. Belleğe yüklenen varlıklar için, EF Core yabancı anahtar özelliklerini null olarak ayarlamayı denemez.
Gerekli ve isteğe bağlı ilişkiler arasındaki fark için Gerekli ve İsteğe Bağlı İlişkiler bölümüne bakın.
Farklı silme davranışları ve kural tarafından kullanılan varsayılanlar hakkında daha fazla bilgi için bkz. Basamaklı Silme.
El ile yapılandırma
api'sinde bir Fluent yapılandırmak için, ilişkiyi tanımlayan gezinti özelliklerini belirleyerek başlarsınız. HasOne veya HasMany yapılandırmaya başlarken varlık türü üzerinde gezinti özelliğini tanımlar. Ardından ters gezintiyi tanımlamak WithOne için veya WithMany çağrısı zincirleme. HasOne/WithOne, başvuru gezintisi özellikleri için ve HasMany/WithMany koleksiyon gezinti özellikleri için kullanılır.
internal class MyContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<Post> Posts { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Post>()
.HasOne(p => p.Blog)
.WithMany(b => b.Posts);
}
}
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
public Blog Blog { get; set; }
}
Tek gezinti özelliği
Yalnızca bir gezinti özelliğiniz varsa ve 'nin parametresiz aşırı yüklemeleri WithOneWithMany vardır. Bu, kavramsal olarak ilişkinin diğer ucunda bir başvuru veya koleksiyon olduğunu gösterir, ancak varlık sınıfına dahil edilen bir gezinti özelliği yoktur.
internal class MyContext : DbContext
{
public DbSet<Blog> Blogs { get; set; }
public DbSet<Post> Posts { get; set; }
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Blog>()
.HasMany(b => b.Posts)
.WithOne();
}
}
public class Blog
{
public int BlogId { get; set; }
public string Url { get; set; }
public List<Post> Posts { get; set; }
}
public class Post
{
public int PostId { get; set; }
public string Title { get; set; }
public string Content { get; set; }
}