首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >建模内容管理域

建模内容管理域
EN

Software Engineering用户
提问于 2017-05-10 19:48:29
回答 3查看 255关注 0票数 3

域比较简单--我有一篇文章(或者更确切地说是几种类型的文章),我想编辑和发布这些文章。发布的文章通过API向公众公开。我有一个问题,就是进一步编辑一篇已发表的文章。目前版本控制、修订等都是无关紧要的。我只需要模拟这个过程:

  • 作者/编辑创建一篇文章(我们有一篇新文章)
  • 作者编辑并保存它(文章的数据被更新)
  • 作者发表文章(该文章可供公众查阅)
  • 作者再次编辑文章并保存(发布的版本没有改变,文章发生了什么?)

在我的描述中,我并不是说它是一个“状态变化”,因为它可能会比需要的更快地提出状态模式。我试着用以下方法来处理这个问题:

  1. 项目作为可以访问当前版本和已发布版本的聚合。但这似乎很奇怪,因为它基本上引用了它自己的版本
  2. 将问题分成两个上下文(编辑和发布),并在文章发表时创建一个新的PublishedArticle实体,但它并不真正模拟实际情况。没有一个领域专家会说“我们从这篇文章中创建了一篇已发表的文章”
  3. 我研究了状态模式,但试图理解如何在我的具体示例中实际使用它,却迷失了方向。

DBs/语言与此无关。我很乐意看到任何有用的东西,无论是进一步研究的链接,还是任何语言中的代码。谢谢

EN

回答 3

Software Engineering用户

发布于 2017-05-10 20:33:10

因此,域驱动设计的答案是“去倾听你的领域专家的意见”,当他们似乎用同一个词表达两个不同生命周期的不同想法时,他们会非常小心地进行探索。

没有一个领域专家会说“我们从这篇文章中创建了一篇已发表的文章”

没错,但你可能会听到他们说我们发表了这份草案;或者我们发表了这份意见书(不是一回事)。或者一个修订版已经出版(也不是一回事)。

项目作为可以访问当前版本和已发布版本的聚合。但这似乎很奇怪,因为它基本上引用了它自己的版本

没有那么奇怪--想想源代码管理;我们有一个文档历史记录和标签,可以告诉我们该历史记录中的哪个项目是当前的开发快照,哪个用于夜间构建,哪个用于最新版本.

将问题分成两个上下文(编辑和发布)

也许-两个上下文(从蓝皮书中有界上下文的意义上来说)通常意味着不同的受众使用相同的语言和不同的语义。如果“编辑”在说“文章”时意味着一件事,而出版商则意味着不同的东西,那么两种不同的上下文可以帮助实现这一点。

但是,如果编辑器和发布者共享相同的词汇表,那么您可能需要两个不同的聚合。

我研究了状态模式,但试图理解如何在我的具体示例中实际使用它,却迷失了方向。

状态模式对于流程非常有效;诀窍是流程实例和贯穿流程的文档是不同的。一个跟踪完成的工作(状态机),另一个跟踪工作(文档)。

仍然对国家的模式感到好奇。你能详细说明一下在我的场景中可能会是什么样子吗?

进程倾向于使用“事件源”--流程的当前状态只是到目前为止发生的事件的一倍。

代码语言:javascript
复制
DraftCreated
DraftModified
DraftSubmitted
SubmissionRejected
DraftModified
DraftSubmitted
SubmissionApproved
ArticlePublished
ArticleRetracted
...

因此,假设有一个状态机;您从Begin状态开始,每次看到发生了什么事情,就会将事件和它计算下一个状态。通知您的机器实例。

比喻说,我们在信封(过程)里有一张纸(文章)。每当有人对文件做了些什么,他们就会在信封上写下他们所做的事情。你可以想象这个信封从一个收件箱移动到另一个收件箱。

从根本上说,当前的状态是回答问题的关键;考虑到目前为止发生了什么,接下来会发生什么?我们在等谁?花了多长时间?给作者多少钱?诸若此类

一组与你问的问题完全不同的问题:你的标题是什么?你多久了?你的阅读水平是多少?诸若此类。

票数 3
EN

Software Engineering用户

发布于 2017-05-10 20:49:28

我是这样做的:

  • Article.Save -创建具有新版本号和指定内容的新文章。
  • Publication?.Publish(文章)-使用指定的版本号添加/更新PublishedArticleVersionNumber
  • Article.Load(versionId)-返回文章的选定/最新版本以进行编辑。

这是非常灵活的,因为您从不删除一篇文章并将发布与创建和编辑分开。

但是,它确实占用了大量的磁盘空间,除非您在存储所有这些修订版方面做了一些聪明的事情。您可以保存delta、使用事件源或只删除旧版本。最简单的选择,买更大的硬盘

票数 0
EN

Software Engineering用户

发布于 2017-05-11 17:08:27

为了在这里添加其他好的答案,并且更多的元,我们应该(能够)直接以客户所熟悉的域术语进行域设计,而不引用任何实现模式,比如状态模式。

状态模式确实可以在编码过程中应用,但此时考虑还为时过早。

域设计需要捕获实体及其关系,这将由用户需要谈论的内容以及随着时间推移而完成的内容驱动。

在DDD中,首先要做的事情之一是在域中的用户之间建立通用词汇表。这个常见的词汇是内置在实体和关系中的。最终,该词汇表通过代码构建到功能和行为中。当我们开始编写代码时,就会应用行为软件模式(例如状态模式)。

我喜欢@VoiceOfUn故的取笑条款草案和出版超过超载的术语文章。

我认为,您可能也会担心有一个稳定的文章标识,或者草案之间有明确的关系,这样一系列草案将支持除了其他内容之外更改标题。问你的领域专家一些事情。

票数 0
EN
页面原文内容由Software Engineering提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://softwareengineering.stackexchange.com/questions/348719

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档