Почему PostTag содержит PostId и TagId?Эта информация содержится в Post и Tag (также два поля в PostTag).Похоже, что эти поля дублируются.
Как вы знаете, PostTag.PostId
является внешним ключом, который ссылается на Post.Id
, а PostTag.TagId
является внешним ключом, который ссылается на Tag.Id
.PostTag.PostId
называется Foreign Key Property
, а PostTag.Post
- это Navigation Property
.
На самом деле, если у вас нет свойства внешнего ключа для свойства навигации в явном виде, EF Core
также будет работать должным образом.В этом случае два свойства теневого внешнего ключа PostId
и TagId
будут введены для вас автоматически.Он называется Shadow Properties
.
Свойства теней могут быть созданы по соглашению, когда обнаружена связь, но в классе зависимого объекта не найдено свойство внешнего ключа.В этом случае будет введено свойство внешнего ключа.Свойство теневого внешнего ключа будет иметь имя <navigation property name><principal key property name>
(для именования используется навигация по зависимому объекту, которая указывает на главный объект).Если имя свойства основного ключа включает в себя имя свойства навигации, тогда оно будет просто <principal key property name>
.Если у зависимого объекта нет свойства навигации, то вместо него используется имя основного типа.
Хотя этот внешний ключ может быть выведен с помощью PostTag.Post.Id
и PostTag.Tag.Id
соответственно, они не дублируются .
Допустим, у нас есть существующая база данных, в которой внешние ключи названы fk_post_id
и fk_tag_id
, и вы хотите переименовать свойство внешнего ключа PostId
в MyPostId
, мы не можем опустить *Свойства 1045 * и TagId
:
public class PostTag
{
[Column("fk_post_id")]
public Guid MyPostId { get; set; }
[ForeignKey("MyPostId")]
public Post Post { get; set; }
[Column("fk_tag_id")]
public Guid TagId { get; set; }
public Tag Tag { get; set; }
}
Рекомендуется иметь свойство внешнего ключа, определенное в классе зависимого объекта для свойства навигации
Добавляет ли PostTag также сообщение и тег?
Ваш код автоматически добавляет сообщение и тег для вас, поскольку он знает, что вам нужносоздать новый пост и новый тег.Но это не всегда так.Это зависит от состояния отслеживания и самого объекта.
Если вы выполните следующий код:
var tagTracked = this._dbContext.Tag.FirstOrDefault();
var post = new Post { Id=Guid.NewGuid(), Description="Test Post3" };
var PostTag = new PostTag {
Post=post,
Tag=tagTracked,
MyPostId= post.Id,
TagId= tagTracked.Id,
};
this._dbContext.Add(PostTag);
this._dbContext.SaveChanges();
tagTracked
вставляться не будет.Если вы хотите вставить новую запись тега, вам нужно сделать tag
неотслеживаемым:
var tagTracked = this._dbContext.Tag.AsNoTracking().FirstOrDefault();
tagTracked.Id = Guid.NewGuid();
var post = new Post { Id=Guid.NewGuid(), Description="Test Post3" };
var PostTag = new PostTag {
Post=post,
Tag=tagTracked,
MyPostId= post.Id,
TagId= tagTracked.Id,
};
this._dbContext.Add(PostTag);
this._dbContext.SaveChanges();
Опять же, он вставит новую запись тега в базу данных.Для получения дополнительной информации см. документы здесь