gpt4 book ai didi

c# - DDD - 实体状态转换

转载 作者:塔克拉玛干 更新时间:2023-11-03 03:52:26 25 4
gpt4 key购买 nike

考虑以下简化示例:

public class Ticket
{
public int Id;
public TicketState State;

public Ticket()
{
// from where do I get the "New" state entity here? with its id and name
State = State.New;
}

public void Finished()
{
// from where do I get the "Finished" state entity here? with its id and name
State = State.Finished;
}
}

public class TicketState
{
public int Id;
public string Name;
}

类状态直接在域对象票证中使用。在票证生命周期的后期,可能会设置其他状态。

票据和 TicketState 都保存在 Ticket 表中。因此在数据库中,票证将具有票证状态表的外键。

在我的实体中设置适当的状态时,如何从数据库加载状态实例?我是否必须将存储库注入(inject)实体?对于这种情况,我是否需要使用像城堡这样的框架?或者是否有更好的解决方案,也许是从外部传递状态?

public class Ticket
{
//...
public ITicketStateRepository stateRep; //<-- inject

public Ticket()
{
State = stateRep.GetById(NEW_STATE_ID);
}
//...
}

有什么最佳实践吗?到目前为止,我没有使用任何依赖注入(inject)框架或任何东西,并且将任何持久性的东西都放在我的领域之外..

另一种方法:

public class Ticket
{
//...

public Ticket(NewTicketState newTicketState)
{
State = newTicketState;
}
public void Finished(FinishedTicketState finishedTicketState)
{
State = finishedTicketState;
}
//...
}

最佳答案

票证不会引用存储库。它与 TicketState 具有一对一的关系,而 TicketRepository 将简单地执行 JOIN 并将值映射到 Ticket。

当我创建模型对象时,我通常不会让它们知道它们是否持久,因此它们不会注入(inject)存储库。存储库处理所有 CRUD 操作。

有些人对此表示反对,说这会导致 anemic domain model ;也许你就是其中之一。如果是这种情况,请将存储库注入(inject)您的 Ticket 对象,但简单地要求它执行 JOIN 并返回填充其状态的 Ticket。当您插入或更新时,您必须将两个表作为一个工作单元进行修改,因此请务必打开事务。

我喜欢在域模型对象之外进行 CRUD 操作的原因是它通常不是参与用例或事务的唯一域对象。例如,您的简单“买票”用例可能会有一个 Ticket 对象,但可能还必须有一些其他对象来处理预订、座位、总帐和行李 list 以及各种其他事情。您确实希望将多个模型对象作为一个单一的工作单元进行持久化。只有服务层才能知道模型对象何时单独行动,何时是更大、更宏伟计划的一部分。

更新:

我不喜欢用 DAO 注入(inject)模型对象以使其能够处理持久性任务的想法的另一个原因是层的破坏和它引入的循环依赖性。如果您保持模型不受任何对持久性类的引用,则可以使用它们而无需调用其他层。这是一种单向依赖;持久性知道模型,但模型不知道持久性。

将持久性注入(inject)到模型中,它们循环地相互依赖。您永远不能在没有另一个的情况下使用或测试任何一个。没有分层,没有关注点分离。

关于c# - DDD - 实体状态转换,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2241133/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com