【问题标题】:Consolidating changes when syncing with a server from offline localStorage从离线 localStorage 与服务器同步时合并更改
【发布时间】:2012-09-02 15:13:51
【问题描述】:

我计划为backbone.us 使用localStorage 适配器,以允许它同步/获取到本地存储,而不是通过jqXHR。这是为了让我的应用可以离线工作。

但是,一旦我的应用重新上线,我会进行 ajax 调用以将本地数据集与服务器同步,或者构建某种“重放”系统以仅发送更改。

但是,当数据集发生分歧(服务器和客户端都发生变化)时,我将如何处理?哪个来源的数据集正确?

【问题讨论】:

    标签: backbone.js local-storage jqxhr


    【解决方案1】:

    您应该能够通过执行以下操作来创建简单的双向同步协议:

    1. 在所有应同步的表上,有一个“上次更新”时间戳字段,每当您修改行时都会更新该字段(包括插入和删除,请参阅下文)。

    2. 对于“id”,避免使用自动递增的整数(这需要与服务器对话才能确定下一个值),而是使用 GUID。 localStorage 适配器默认执行此操作。使用 GUID,服务器和客户端都可以生成新行,而无需相互交谈。

    3. 您需要使用“软删除”。与其实际删除一行,不如使用一个标记为已删除的标志,并在需要列出对象集合时过滤此标志。这样,即使删除也能正确传播。您可以对在一定时间内仍被删除的所有行进行“整理”(实际上是删除行),该时间需要大于最大可能的“离线”时间,以确保删除已经传播。

    4. 在客户端上存储您上次与服务器同步的本地时间戳。确保使用正确的时区在服务器和客户端上存储时间戳非常重要。

    5. 当您从客户端与服务器同步时,将您的“上次同步”时间戳发送给它,服务器应该向您发送自那时以来发生的所有更改。使用服务器提供的新时间戳,将其作为新的“上次同步时间”存储在客户端本地。根据 GUID 更新/插入接收到的任何行(如果本地有则更新,如果没有则插入)。

    6. 如果您有本地存储的更改,请将自原始时间戳以来的所有本地修改的行从您的客户端发送到服务器,最好在从服务器读取更新之前(您也可以在之后执行此操作,但无论如何,您可能应该检查更新的时间戳以确定哪个更新是最近的,并根据您选择的任何冲突解决策略进行处理,如果不重要则不处理)。

    7. 当您意识到对于实际的跨平台本地存储使用而言,您目前被限制为大约 2.5 兆字节的数据时会感到痛苦。这有望很快改变。在您决定改用 IndexedDB 来解决这些限制之前,API 尚未稳定下来,而且大多数实现都是半途而废且不兼容的。

    【讨论】:

    • 感谢 Marius 提供的 cmets -- 在这里可以学到很多与传统的 web-to-RDBMS 模型不同的东西!
    • 还需要注意的是,客户端的时钟可能与服务器完全不同步,从而导致数据同步问题,例如知道哪些更改实际上是最新的。一个好主意是在每个请求上发送客户端的时间,让服务器计算差异并使用正确的日期。
    • 是的,可以猜测延迟(往返时间)和时钟差异。但是,如果这对您的地区/产品来说是一个主要问题,那么另一种选择可能是使用“生成密钥”(一个递增的整数)而不是时间,服务器会在每次更新时增加它并找出要发送回的更改客户端基于从客户端传递的最后一代密钥(连同任何更新)。
    【解决方案2】:

    如何简单地确保您的数据在上次编辑时有一些标记?然后就可以比较了,如果服务器较新,就覆盖客户端,反之亦然。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-02-28
      • 1970-01-01
      • 1970-01-01
      • 2023-04-10
      • 2013-01-24
      • 1970-01-01
      相关资源
      最近更新 更多