Node EventEmitter event.on() 在仅发出一次发射后触发两次

问题描述 投票:0回答:1

我有一个 VSCode 扩展(不涉及浏览器),我需要在其中管理会话分配。 我的 SessionManager 类中有以下代码片段:

private event = new EventEmitter();
private sessionArray = [];
public async getSession(sessionName: string) {
    let index: number;
    index = this.sessionArray.findIndex((a) => a.sessionName === sessionName && a.inUse === false);
    if (index === -1) {
      // no session available
      await new Promise((resolve) => this.event.on("available", resolve));
      index = this.sessionArray.findIndex((a) => a.sessionName === sessionName && a.inUse === false);
    }
    this.sessionArray[index].inUse = true;
    return { session: this.sessionArray[index], id: index };
  }
  /**
   * set the session status back to available and emit the event
   */
  public async freeSession(id: number) {
    this.sessionArray[id].inUse = false;
    this.event.emit("available");
    return;
  }

我的会话数组只有一个条目 当我第一次使用调试器单步调试代码时,我在 sessionArray 中找到了空槽,我使用该槽并将其设置为 inUse。 第二个请求进入会话,找不到可用的会话,因此触发了 Promise 上的等待,等待发出事件触发。 第三个请求进来并执行相同的操作,并在发出事件时对 Promise 进行排队 最后,第一个请求完成并发出 freeSession,它将插槽设置为可用并发出事件。事件立即触发并解决承诺并触发寻找现在可用的插槽 - 到目前为止一切都很好。

但是...立即,event.on 再次触发并导致错误,因为没有可用的插槽,因此索引返回 -1

我遗漏了一些明显的东西,但我不明白为什么在仅发出一次发射后事件会快速连续触发两次。

如有任何帮助,我们将不胜感激。

javascript node.js vscode-extensions eventemitter
1个回答
0
投票

可能

this.event
始终是同一事件。因此,触发此事件将触发当时等待该事件的所有侦听器。

顺便说一下,你永远不会删除旧的侦听器(或将其设置为

once
),因此你会出现内存泄漏,并且也会无用地对已经解决的承诺调用
resolve

© www.soinside.com 2019 - 2024. All rights reserved.