模型上的操作在应用程序设计模式中属于哪里?
Posted
技术标签:
【中文标题】模型上的操作在应用程序设计模式中属于哪里?【英文标题】:Where do operations on models belong in Application Design Patterns? 【发布时间】:2017-01-24 02:49:14 【问题描述】:假设我们要创建一个包含以下内容的application
:
operations
on selected objects
对于某个object
,我们希望访问关联operation
的status
。
show
、cancel
和pause
这些操作来自multiple views
。
那么我的问题如下:
这些operations
和它们的progress/status
属于应用程序设计模式的什么位置?
这里是一个虚拟应用程序:
示例应用:
我们有一个应用程序,您可以在其中将不同的Filters
应用到Images
。应用程序由Directory View
和Detail View
组成。
filter
可以应用asynchronously
到来自每个view
的任何image
。
filter
操作可以是来自views
的observed
和canceled
。
如果已经为filter-type
和image
启动了过滤操作,或者如果这样的filter
已经产生了result
,则无法启动过滤操作。
在这个虚拟应用程序中,视图是后续的,但在一般情况下,您不能直接在视图之间传递信息。
进展
在 MVC
或 MVVM
这样的设计模式中将 Service Layer
或 Network Controller
与 View
和 Model
分离是非常简单的,只要您不提供更多 UX feedback
当有一个活动的network request
时,而不是spinner
。
但是,当我正在处理一个确认符合上述标准的应用程序时,我总是要么
不允许user
在operation
期间更改view
Tagging
对当前处理的对象的id
进行操作并将其传递给views
,或者直接从views/view controllers
中查看Network Controller
为operations
创建一个单独的entities
,突然我的model
中有一个request operation
显然有(非常臭)方法可以解决这个问题,但他们都觉得很脏,不符合模式的预期。
那么纯粹从软件架构和设计模式的角度来看,您会如何处理这个问题?
【问题讨论】:
【参考方案1】:对于这个设计问题,我通常更喜欢 promise 对象。 Promise 对象可以包含取消操作、检查操作状态的方法,甚至包含要根据操作发生的情况(成功、失败、取消等)执行的闭包。
promise 对象可以从一个视图传递到另一个视图,也可以在多个请求时从网络层提供服务(视图 A 启动操作,视图 B 稍后尝试启动它,但它已经在运行,因此获得相同的 promise对象)。
这意味着在这种情况下,服务层或网络层需要呈现针对哪个对象正在进行的哪些操作、请求,对吗?因为您不想仅仅为了获取 promise 对象而发起请求,以防在操作已经开始时应该隐藏按钮。我想您会将这些承诺对象保留在您的应用程序模型之外,因为它们不在会话之间存在,并且网络层将通过 url 存储它们,但是您通常如何从网络层返回这些对象而不暴露于太多网络层到用户界面?
网络层有方便的方法供 UI 用来启动用户发起的请求。网络层确定请求是否已经开始并返回相同的承诺。即使网络层在内部启动了进程(自动刷新等),如果 UI 尝试启动相同的进程,它仍然可以将 Promise 传递回 UI。
promise 对象仅在操作进行时才存在。实际上,我让操作成为 promise 对象的真正持有者,并且网络控制器持有操作队列。然后,当一个请求进来时,我会在队列中搜索该操作是否存在,如果存在,则从该操作中返回 Promise。如果它不存在,我创建一个新操作,将它放入队列并返回它的 promise 对象。
UI 和后端之间的接口是网络控制器上暴露的方法。 UI 没有操作知识,它只是有一个功能说“去刷新这个或去拿那个”并得到一个承诺。它不需要知道或关心作业是如何执行的,它只知道 promise 是它检查该操作状态的方式。
现在,如果是数据刷新,那么数据更新不需要承诺,NSFetchedResultsController
将处理它。这种情况下的承诺只处理“我是否活跃”和“取消我”类型的请求。
【讨论】:
【参考方案2】:有很多方法可以做到这一点。但这里有一个想法......也许你可以使用messaging 作为样式:定义一个“状态”频道,可能使用发布-订阅模型来获取正在进行的操作的状态/进度。这样,执行操作的流程会在频道上发布状态,并且您的多个视图订阅该频道并显示状态。现在,如果您必须取消/暂停操作,您可能需要另一个控制通道。你必须管理并发、订单等。
【讨论】:
消息传递确实是一种方法。现在在您回答之后再次查看我的问题,我意识到我需要重新调整自己。但真正的问题归结为如何在呈现新视图时检查某个进程是否对某个对象处于活动状态。明天我将重新提出我的问题并添加一个示例。感谢您的推动! 是的,现在你让我开始思考了。因此,每次进程激活时,它都需要存储/发布一些状态 - 进度/状态您需要的任何信息。更新它的状态可能是过程的责任,这是一个设计问题。但是,一旦您的流程状态发布,在多个视图中显示它应该不是问题。现在,管理控制通道更加复杂,因为您正在更改活动进程的状态。再次管理并发、排序等,你必须设计得很好。我认为这是一个好的开始。你会到达那里!祝你好运! 你当然需要一些好的设计,这就是为什么它是一个设计问题! =) 感谢您的意见,如果您还有其他想法,请告诉我!以上是关于模型上的操作在应用程序设计模式中属于哪里?的主要内容,如果未能解决你的问题,请参考以下文章