denodrivers / mongo

🍃 MongoDB driver for Deno 🦕
https://deno.land/x/mongo
MIT License
514 stars 95 forks source link

Uncaught (in promise) TimedOut: timed out at async WireProtocol.receive #419

Open masx200 opened 1 month ago

masx200 commented 1 month ago

Deno 2.0.2

Linux msx-PC 6.9.6-amd64-desktop-rolling #23.01.01.02 SMP PREEMPT_DYNAMIC Tue Jul 23 12:20:02 CST 2024 x86_64 GNU/Linux

error: Uncaught (in promise) TimedOut: timed out
      rr = await this.#rd.read(this.#buf);
           ^
    at async TlsConn.read (ext:deno_net/01_net.js:135:15)
    at async BufReader.read (https://deno.land/std@0.154.0/io/buffer.ts:383:12)
    at async BufReader.readFull (https://deno.land/std@0.154.0/io/buffer.ts:415:20)
    at async WireProtocol.receive (https://deno.land/x/mongo@v0.32.0/src/protocol/protocol.ts:110:28)
  private async receive() {
    if (this.#isPendingResponse) return;
    this.#isPendingResponse = true;
    while (this.#pendingResponses.size > 0) {
      const headerBuffer = await this.read_socket(16);
      if (!headerBuffer) {
        throw new MongoDriverError("Invalid response header");
      }
      const header = parseHeader(headerBuffer);
      let bodyBytes = header.messageLength - 16;
      if (bodyBytes < 0) bodyBytes = 0;
      const bodyBuffer = await this.read_socket(header.messageLength - 16);
      if (!bodyBuffer) {
        throw new MongoDriverError("Invalid response body");
      }
      const reply = deserializeMessage(header, bodyBuffer);
      const pendingMessage = this.#pendingResponses.get(header.responseTo);
      this.#pendingResponses.delete(header.responseTo);
      pendingMessage?.resolve(reply);
    }
    this.#isPendingResponse = false;
  }

  async command<T = Document>(db: string, body: Document): Promise<T[]> {
    const requestId = nextRequestId++;
    const commandTask = {
      requestId,
      db,
      body,
    };

    this.#commandQueue.push(commandTask);
    this.send();

    const pendingMessage = Promise.withResolvers<Message>();
    this.#pendingResponses.set(requestId, pendingMessage);
    this.receive();
    const message = await pendingMessage.promise;

    let documents: T[] = [];

    for (const section of message?.sections!) {
      if ("document" in section) {
        documents.push(section.document as T);
      } else {
        documents = documents.concat(section.documents as T[]);
      }
    }

    return documents;
  }
masx200 commented 1 month ago

Uncaught (in promise) cause process exit?

lucsoft commented 1 month ago

We do not handle reconnects currently.

masx200 commented 1 month ago

We do not handle reconnects currently.

It is not a matter of connection timeouts, but rather an error that does not catch and causes the program to exit.

lucsoft commented 1 month ago

well there is a darft PR about your issue atleast https://github.com/denodrivers/mongo/pull/401

For a workaround i would recommend using docker or systemd with auto restarts/health checks so if your connection drops out your service is not down