如何区分应用程序状态和资源状态

Posted

技术标签:

【中文标题】如何区分应用程序状态和资源状态【英文标题】:How to distinguish application state and resource state 【发布时间】:2015-01-19 04:20:21 【问题描述】:

我知道要制作一个无状态的应用程序,我们需要来回传输用户状态,而不是服务器保存用户状态。

但是,服务器中肯定存储了一些状态,我看了article 说存储在服务器中的状态称为资源状态。所以如果我是对的,我们通常所说的客户端状态应该与应用程序相同状态。

那么,我如何区分这两者,因为它将决定它们是应该存储在服务器中还是传输。

以购物车为例。

    如果用户在完成购买之前有 5 个步骤,那么用户所处的阶段(#3,#4)似乎是应用程序状态,但这是否意味着如果他们关闭浏览器并再次点击支付,他将不得不从step1开始?

    他图表中的项目呢?如果我们将其视为应用程序状态,我们需要将所有项目放入请求中。但是如果我们这样做,当用户关闭浏览器并再次登录时,他将无法再次找到他的项目,因为浏览器无法记住所有项目。所以看来我们应该把它当作资源状态。但如果是这样,当用户点击支付时,他们将有一个不同的页面:去支付或根据他的购物车是否为空说“你的购物车是空的”。那么,同样的请求输入完全相同的参数,得出的结果不同,我们还能说它是无状态的吗?

也许我理解错了,任何人都可以回答如何区分不同类型的状态以及如何区别对待它们吗?

【问题讨论】:

【参考方案1】:

资源状态 是一种状态,即使在客户端断开/重新启动/会话结束/无论如何之后也需要持久和可生存。 应用程序状态应该存在于客户端,并且应该随每个客户端请求提供(如果我们正在讨论 REST 架构并计划很好地扩展我们的应用程序)。

如何区分应用状态和资源状态?

这取决于您正在处理的任务。例如。如果您想弄清楚当前在您的画廊中查看的图片的索引保存在哪里,您可能可以在您的应用程序状态中执行此操作,因为您可能不需要此状态来为下一个会话生存这个客户的。当然,您可以将其保存在您的资源状态(数据库)中,但这会产生开销(付出很大的努力才能获得很小的收益)。

但是,如果您正在处理多步采购流程,可能最好将此流程的状态保存在您的资源状态(数据库)中,因为您希望永久保存此状态。否则,您的客户需要在断开连接/重新启动/无论如何之后重新填写大量信息。 当然,例如,您可以在 cookie 中执行此操作(它将是应用程序状态),并且此状态可以在浏览器重新启动后存在。但它有两个缺点:1)这种状态在其他用户的设备上不可用,2)如果您正在创建真正的 REST 服务,cookie 会使客户端的生活变得复杂,因为并非所有客户端都能很好地操作 cookie(浏览器除外)。

【讨论】:

【参考方案2】:

我只引用书中的一段RESTful Web Services:

Flickr 网络服务允许您将图片上传到您的帐户,这些图片存储在 服务器。让客户把它的每一张照片连同 对 flickr.com 的每个请求,只是为了让服务器不必存储任何状态

应用程序状态与客户端可以遵循的路径相关以进行某些操作。 例如,在查阅文章时,会出现“加入购物车”的链接。在查看他的购物车时,如果您的购物车中有一篇文章,则会提供“支付您的订单”链接,否则不会出现此链接。用户可以根据他所关注的链接随意创建自己的应用程序状态。基本上,应用程序状态是一个上下文的问题。

在我回到你之前提到的同一本书中的另一个引用示例:

资源状态停留在服务器上并且是 仅以陈述的形式发送给客户。应用程序状态保持在 客户端,直到它可以用于创建、修改或删除资源。然后发送到 服务器作为 POST、PUT 或 DELETE 请求的一部分,并变为资源状态。

假设您有一些身份验证机制(基于令牌)。一个用户帐户与一个购物车相关联。 当您在购物车中添加商品时,您正在修改您的购物车资源。由于资源状态是服务器端的,它在服务器上。 假设您断开连接,然后按照第一点所述重新连接。购物车还在这里。 只要客户端在每次请求时发送不同的身份验证凭证,您的应用程序就会保持无状态。

关于如何管理它的一个很好的讨论:Do sessions really violate RESTfulness?

现在,事实如何:根据购物车是否有商品,咨询您的购物车会导致您采取 2 种不同的操作。 很简单。服务器向客户端提供的服务取决于服务器维护的资源状态。this good website 上的一个非常简单的例子。您可以看到,根据帐户上的金额,服务器会提供一个链接到客户端以进行提款或不提款。 客户可以随意(再次)制作自己的应用程序并点击链接。

我建议您查看 HATEOAS 和解释它的 Richardson Maturity Model。 顺便说一句,这两段的引文与该模型出自同一作者。

【讨论】:

以上是关于如何区分应用程序状态和资源状态的主要内容,如果未能解决你的问题,请参考以下文章

Prometheus:区分应用程序指标

用户态/内核态用户栈/内核栈

如何在 iOS 7 上更改状态栏背景颜色和文本颜色?

再战设计模式之享元模式

如何在应用程序中使用多个 openGL 状态?

如何在iOS 7上更改状态栏背景颜色和文本颜色? Warif Akhand Rishi