【问题标题】:Custom ASPNET Identity one to many relationship using multiple context application使用多上下文应用程序自定义 ASPNET Identity 一对多关系
【发布时间】:2016-03-15 17:28:21
【问题描述】:

基本上,我希望有一个用户可以创建自己的故事。

我有这些课程:

public class ApplicationUser : IdentityUser
{
  public string DisplayedName { get; set; }
}

public class Story
{
  public int Id { get; set; }
  public string Content { get; set; }
}

它们在不同的上下文中进行管理,它们的迁移也是如此。像这样。

public class MyDbContext : DbContext
{
  public DbSet<Story> Stories { get; set; }
}

public class IdentityContext : IdentityDbContext<ApplicationUser>
{
}

当我尝试添加迁移然后单独更新它们时,它可以正常工作,但是当我尝试在我的应用程序用户中添加故事集合时。

public class ApplicationUser : IdentityUser
{
  public string DisplayedName { get; set; }
  public virtual ICollection<Story> Stories { get; set; }
}

public class Story
{
  public int Id { get; set; }
  public string Content { get; set; }
  public string WrittenById { get; set; }
  public virtual ApplicationUser WrittenBy { get; set; }
}

public class StoryMap : EntityTypeConfiguration<Story>
{
  public StoryMap()
  {
    HasOptional(s => s.WrittenBy)
      .WithMany(s => s.Stories)
      .HasForeignKey(s => s.WrittenById)
      .WillCascadeOnDelete(false);
  }
}

然后使用 MyDbContext 的内容在我的 Story 实体上进行迁移,它失败了。

Data.IdentityUserLogin: : EntityType 'IdentityUserLogin' has no key defined. Define the key for this EntityType.
Data.IdentityUserRole: : EntityType 'IdentityUserRole' has no key defined. Define the key for this EntityType.
IdentityUserLogins: EntityType: EntitySet 'IdentityUserLogins' is based on type 'IdentityUserLogin' that has no keys defined.
IdentityUserRoles: EntityType: EntitySet 'IdentityUserRoles' is based on type 'IdentityUserRole' that has no keys defined.

但是当我尝试使用 IdentityContext 进行迁移的其他方式时,它会创建一个 Story 的新表

目前,有效的方法是合并我的上下文。类似的东西。

public class MyDbContext : IdentityDbContext<ApplicationUser>
{
  public DbSet<Story> Stories { get; set; }
}

但是必须有一种单独管理它们的方法,对吧?还是我做错了?

【问题讨论】:

  • 继承上下文是要走的路,除非你准备好解耦身份的苦差事。另一种解决方法是创建一个 User 类的副本,该副本映射到您用于设置关系的应用上下文中的 AspNetUser 表。
  • @SteveGreene 继承上下文是什么意思?至于解决方法,由于我从视觉示例中学习,您能否展示一些示例以供参考。
  • @BoyPasmo: "inherited context" 仅表示您在问题底部所做的事情:您从 IdentityDbContext 继承您的应用程序上下文,以便一切都在一个上下文中。
  • @SteveGreene:你的“解决方法”行不通。如果正在使用迁移(意味着 EF 控制数据库),那么如果添加映射到 AspNetUsers 表的 User 类,Entity Framework 将尝试再次创建该表。要么一切都必须走现有的数据库路线(意味着 OP 将负责管理数据库模式),要么没有办法实现它。
  • 是的,我丢失了我的参考链接,但我确实有一个概念证明工作,充其量是不稳定的 - 我相信注释掉一些 Up() 代码来欺骗 EF 忽略影子表。我最终只使用了一个已经运行了几年的单一上下文。

标签: asp.net-mvc entity-framework asp.net-identity


【解决方案1】:

您不能在另一个上下文中引用实体,否则该上下文也会尝试管理这些实体,从而导致有关已存在表的错误。你有两个选择:

  1. 如果您实际上需要两个单独的上下文(即,它们都是 Code First,并且您可以将所有内容都放在一个数据库中),那么最好和最简单解决方案是像你所做的那样合并它们。拥有多个上下文没有任何好处,而且正如您所见,有很多不利之处。使用多个上下文的唯一充分理由是,如果您正在处理其他现有数据库。

  2. 创建一个简单的列来存储相关的 id(不是外键)。你失去了拥有真正外键的优化和延迟加载的能力,但你至少仍然可以通过这种方式将事物联系起来。本质上,您只需使用其他上下文中相关对象的 id 设置此属性。然后,当您需要检索该对象时,您只需使用该 id 使用该其他上下文发出查询。换句话说,您只需手动获取对象。

很遗憾,这是您唯一的选择。

【讨论】:

    猜你喜欢
    • 2016-08-09
    • 2015-06-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-09-15
    • 2014-02-13
    • 1970-01-01
    相关资源
    最近更新 更多