ef代码优先-实体框架创建外键对象,而不是使用那些已经可用的对象



我当前的项目首先基于实体框架代码。我有三种类型:任务、任务类型和模块。

    public class Task
    {
        public int ID { get; set; }
        public Module Module { get; set; }
        public TaskType Type { get; set; }
    }
    public class TaskType
    {
        public int ID { get; set; }
        public string Name { get; set; }
    }
    public class Module
    {
        public int ID { get; set; }
        public string Name { get; set; }
    }

表中为Task类型定义了外键关系。

我的问题是,当我尝试创建一个链接到已可用的TaskType和Module对象(ID=1)的新Task对象时,这些对象会在其相应的表中创建为新行。

        TaskRepository repo = new TaskRepository();
        Task task = new Task();
        task.Module = Modules.SingleOrDefault(m => m.ID == 1);
        task.Type = TaskTypes.SingleOrDefault(t => t.ID == 1);
        Tasks.Add(task);

这将在我的TaskType表和Modules表中创建一个新行,而不仅仅是使用已经可用的TaskType ID和Module-ID。

我希望我能弄清楚我的问题是什么;-)

提前感谢您的帮助。我很感激。

谨致问候,Kevin

如果不使用同一上下文实例加载相关实体,则不能简单地将它们添加到新实体中,并期望使用数据库中的现有记录。新的上下文不知道这些实例存在于数据库中——你必须对上下文说出来。

解决方案:

  1. 在加载相关实体和保存新实体时使用相同的上下文
  2. 不加载相关实体并使用虚拟对象
  3. 从第一个上下文加载实体并拆离它们,将实体附着到新上下文,然后将它们指定给新实体
  4. 添加具有关系的新实体后,手动将关系状态从Added更改为Unchanged

示例1:

var module = context.Modules.SingleOrDefault(m => m.ID == 1);
var taskType = context.TaskTypes.SingleOrDefault(t => t.ID == 1);
Task task = new Task();
task.Module = module;
task.Type = taskType;
context.Tasks.Add(task);

示例2:

var module = new Module { Id = 1 };
var taskType = new TaskType { Id = 1 };
context.Modules.Attach(module);
context.TaskTypes.Attach(taskType);
Task task = new Task();
task.Module = module;
task.Type = taskType;
context.Tasks.Add(task);

示例3:

var module = otherContext.Modules.SingleOrDefault(m => m.ID == 1);
otherContext.Entry(module).State = EntityState.Detached;
var taskType = otherContext.TaskTypes.SingleOrDefault(t => t.ID == 1);
otherContext.Entry(taskType).State = EntityState.Detached;
context.Modules.Attach(module);
context.TaskTypes.Attach(taskType);
Task task = new Task();
task.Module = module;
task.Type = taskType;
context.Tasks.Add(task);

示例4:

var module = otherContext.Modules.SingleOrDefault(m => m.ID == 1);
otherContext.Entry(module).State = EntityState.Detached;
var taskType = otherContext.TaskTypes.SingleOrDefault(t => t.ID == 1);
otherContext.Entry(taskType).State = EntityState.Detached;
Task task = new Task();
task.Module = module;
task.Type = taskType;
context.Tasks.Add(task);
context.Entry(module).State = EntityState.Unchanged;
context.Entry(taskType).State = EntityState.Unchanged;

我是实体框架的新手,但我刚刚遇到了同样的问题,我的外键属性被填充,但导航对象为空,代码如下:

public class EntryRecord
{        
    [Key]
    public int Id { get; set; }
}
public class QueueItem 
{       
    [Key]
    public int Id { get; set; }

    public int EntryRecordId { get; set; }
    [ForeignKey("EntryRecordId")]
    public EntryRecord EntryRecord { get; set;}

}

将导航属性设置为虚拟可以修复问题并启用延迟加载:

    [ForeignKey("EntryRecordId")]
    public virtual EntryRecord EntryRecord { get; set;}

相关内容

  • 没有找到相关文章

最新更新