【问题标题】:Is adding ETag to strongly typed model really a bad idea?将 ETag 添加到强类型模型真的是个坏主意吗?
【发布时间】:2022-05-23 20:34:53
【问题描述】:

我正在使用 .NET SDK 通过 DocumentDb API 实现乐观并发。

在几个地方我发现提到在强类型模型上使用ETag 是一个坏主意。 在这里明确: https://www.google.hr/amp/s/peter.intheazuresky.com/2016/04/28/documentdb-revisited-part-3-concurrency-in-documentdb/amp/

即使是 github 上的官方示例也显示它使用 dynamic/Document 类而不是强类型类。

现在,我不明白为什么不在模型上存储ETag? 根据文档,ETag,就像其他资源属性(例外是id)只是get,并且总是由服务器专门更改。 参考: https://docs.microsoft.com/en-us/azure/cosmos-db/documentdb-resources#system-vs-user-defined-resources

所以,如果我们将ETag 放在我们的模型上并且:

  1. 从数据库读取文档到具有etag属性的强类型模型

  2. 将其发送给客户端(为简单起见,我们忽略表示层dtos)

  3. 客户端更新并发回

  4. 我们将更新/替换发送到 cosmosdb(将 AccessCondition 设置为 etag 从客户端获取并仍在模型属性之一中)

我很难找到那里的问题? 为什么要打扰dynamics/Document

还是我遗漏了一些明显的东西?

【问题讨论】:

    标签: azure azure-cosmosdb optimistic-concurrency


    【解决方案1】:

    Etag 是服务器构造,最初您的文档是在没有它的情况下诞生的。恕我直言,这取决于您对文档的追求程度。

    正如示例所说,您可以拥有 ETag,也可以拥有纯对象 (theOrder)

    var theOrder = (Order)(动态)orderDoc;

    Debug.WriteLine(theOrder.Customer.FirstName + “.Etag” + orderDoc.ETag);

    根据上面的示例,您必须保留返回的文档对象以获取 ETag,或者您是否应该有一个 theOrder 对象与 Etag 属性一起使用,直到您来并发。

    【讨论】:

    • 嗯,示例有点简单,因为它不包括往返客户端然后返回更新。当您将客户端包含在混合中时,我认为除了将其打包在某种强类型对象中之外别无他法。我们现在可以讨论它是商业模式还是dto,但那是另一个讨论。关键是,归根结底,它是在强类型对象中。
    【解决方案2】:

    我的理解是在模型本身上包含 ETag 是不好的,因为 strong ETag 应该是从文档字节生成的。

    如果 ETag 是文档的一部分,那就不可能了:

    您从文档字节生成 ETag(例如哈希函数)。这会给你一个 ETag 字符串。 在文档的 ETag 属性上设置该字符串的那一刻,哈希不再匹配,因此 ETag 值是错误的。

    您可以实现一些忽略散列函数中的 ETag 值的东西,但这将被视为“弱”ETag。

    【讨论】:

      【解决方案3】:

      如果 Entity Framework for SQL 可以添加 Timestamp 属性,为什么不能为 cosmos 添加 etag

      微软示例:

      https://docs.microsoft.com/en-us/ef/core/modeling/concurrency?tabs=data-annotations#timestamprowversion

      【讨论】:

        猜你喜欢
        • 2022-01-20
        • 1970-01-01
        • 1970-01-01
        • 2017-07-09
        • 1970-01-01
        • 1970-01-01
        • 2010-11-01
        • 1970-01-01
        • 2012-05-02
        相关资源
        最近更新 更多