将不太友好的实体遗留架构映射到实体

本文关键字:实体 映射 | 更新日期: 2023-09-27 17:59:07

好吧,我真的被这个卡住了。基本上,我们在数据库中有一个遗留表(+规范化表),应该在不更改表模式的情况下从中创建真正的域实体。表格如下:

# identity table
| Domain (CK) | Group (CK) | Name (CK) | Password |
|-------------|------------|-----------|----------|
| root        |            |           |          |
| root        | group1     |           |          |
|             | group1     | someuser  | XXXXXX   |
|             | group2     |           |          |
|             |            | otheruser | XXXXXX   |
(CK = composite key)

旧应用程序强制执行以下规则:

  • 如果只设置了Domain,则实体是一个,它可以包含用户和组
  • 如果只设置了Group,则实体是可以包含用户的
  • 如果设置了GroupDomain,则实体是域内的
  • 如果设置了Name,则实体是相应中的用户(取决于设置了哪些)
  • 等等。(我希望你能看到照片)

我们最终想要的是这样的实体(伪):

class Domain {
    string Name;
    addUser(user);
    addGroup(group);
}
class Group {
    string Name;
    addUser(user);
}
class User {
    string Name;
    string Password;
}

我能想到的解决这一问题的唯一两种方法是:

  • 创建所有三个标识类的基类,并创建包含鉴别器的第二个映射表。但是:我怎么能告诉EF鉴别器在另一个表中?我如何执行业务规则,例如,表中同时具有GroupName的实体是User

  • 创建存储库来完成映射等全部工作,并将每个业务规则表示为纯粹的应用程序逻辑,但这样就没有办法结合EF的酷东西,如延迟加载、自动映射、LINQ等,我们基本上可以继续使用我们的遗留代码。)

具体问题:

  • 是否可以将鉴别器映射到EF中的另一个表
  • 有没有可能使鉴别器不是一个值,而是有条件的?(例如组的鉴别器=>hasValue(Group) && !hasValue(Name)

将不太友好的实体遗留架构映射到实体

可以欺骗一点,而不将这些视为完整的域实体。相反,您可以将用户管理视为一个单独的子域,它有自己的有界上下文。通过一个反腐败层将不列颠哥伦比亚省与你的其他领域隔离开来,该层可以将该不列颠哥伦比亚省的语言翻译为一般领域的语言。通常,AC层将涉及从旧的、设计糟糕的类到新的DomainGroupUser类的映射器。

我认为这是最明智的方式,可以立即从主域中干净的用户管理实体中受益,同时保留对身份模块和数据库进行彻底改造的选项(我想这应该是最终目标)。