gpt4 book ai didi

asynchronous - 在回流中排队异步操作

转载 作者:行者123 更新时间:2023-12-01 06:07:22 26 4
gpt4 key购买 nike

在异步操作中使用 RefluxJS 存储时,您很容易在操作之间出现竞争条件。

问题的摘要描述

例如,我们的 store 处于状态 X。从 X 调用了一个异步操作 A,在它完成之前,另一个异步操作 B 被调用,也是从 X 调用的。从这里开始,无论哪个操作先完成,都会出错。

  • B首先完成状态Y1,A最后完成并用Y2覆盖状态Y1。
  • A 首先以状态 Y2 结束,B 用 Y1 覆盖 Y2。

  • 所需的行为是:
      A    B
    X -> Y -> Z

    其中 B 不是基于 X,而是基于 Y,并导致一致的 Z 状态,而不是基于相同状态的两个 Action ,导致不一致的状态:
      A   
    X -> Y1 .--> Y2
    \ /
    '----'
    B

    问题的实现示例

    我写了一个最小的工作示例,用 Node 运行,关于我正在谈论的问题。

    var Q = require('q');
    var Reflux = require('reflux');
    var RefluxPromise = require('reflux-promise');
    Reflux.use(RefluxPromise(Q.Promise));

    var AsyncActions = Reflux.createActions({
    'add': { asyncResult: true }
    });

    var AsyncStore = Reflux.createStore({
    init: function () {
    // The state
    this.counter = 0;

    AsyncActions.add.listenAndPromise(this.onAdd, this);
    },

    // Increment counter after a delay
    onAdd: function(n, delay) {
    var that = this;
    return apiAdd(this.counter, n, delay)
    .then(function (newCounter) {
    that.counter = newCounter;
    that.trigger(that.counter);
    });
    }
    });

    // Simulate an API call, that makes the add computation. The delay
    // parameter is used for testing.
    // @return {Promise<Number>}
    function apiAdd(counter, n, delay) {
    var result = Q.defer();

    setTimeout(function () {
    result.resolve(counter + n);
    }, delay);

    return result.promise;
    }

    // Log the store triggers
    AsyncStore.listen(console.log.bind(undefined, 'Triggered'));

    // Add 3 after 1 seconds.
    AsyncActions.add(3, 1000);
    // Add 100 almost immediately
    AsyncActions.add(100, 1);

    // Console output:
    // > Triggered 100
    // > Triggered 3

    // Desired output (queued actions):
    // > Triggered 3
    // > Triggered 103

    使用 package.json 中的这些依赖项

    {
    "dependencies": {
    "q": "^1.3.0",
    "reflux": "^0.3",
    "reflux-promise": "^1"
    }
    }

    问题的性质

    我希望 RefluxJS 将操作排队,但事实并非如此。所以我正在寻找一种方法来正确排序这些操作。但是,即使我设法以某种方式将这些操作排队(因此 B 在 A 之后发出)我怎么能确定,当 A 完成时,发出 B 仍然是一个有效的操作?
    也许我一开始就以错误的方式使用了 RefluxJS,而这种情况不会发生在结构正确的应用程序中。

    异步操作的排队(假设这在 Reflux 应用程序中是可能的)是解决方案吗?或者我们应该首先以某种方式避免这些情况?

    最佳答案

    您的示例似乎更像是“事实来源”概念的问题,而不是其他任何问题。您仅存储号码客户端的当前状态,但仅在收到服务器端对正在执行的操作的确认后才更新它。

    当然会出问题。您正在以一种奇怪的方式混合对数字的操作和数字的存储,其中在任何给定时刻都没有单一的真实来源。在 Action 被称为完成的时间之间处于不确定状态……这不好。

    要么在客户端存储号码,每次添加时,直接添加到该号码,然后告诉服务器端新号码是什么......(即客户端负责作为号码的真实来源当客户端运行时)

    或者存储服务器端的号码,每次从客户端启动它时,服务器都会返回新的更新号码。 (即数字的真实来源完全是服务器端)。

    然后,即使发生种族问题,您仍然有数字的真实来源,并且可以检查和确认该来源。例如,如果服务器端持有数字的真实来源,那么 API 还可以在每次返回该值时返回该值状态的时间戳,您可以根据从 API 获得的最后一个值来检查它确保您实际上使用的是最新值。

    关于asynchronous - 在回流中排队异步操作,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36940449/

    26 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com