diff --git a/src/h2tunnel.test.ts b/src/h2tunnel.test.ts index 9b2a386..400ef89 100644 --- a/src/h2tunnel.test.ts +++ b/src/h2tunnel.test.ts @@ -6,6 +6,7 @@ import { TunnelServer, } from "./h2tunnel.js"; import net from "node:net"; +import * as http2 from "node:http2"; // localhost HTTP1 server "python3 -m http.server" const LOCAL_PORT = 14000; @@ -372,7 +373,7 @@ class EchoServer { } } -await test( +await test.only( "basic connection and termination", { timeout: 10000 }, async (t) => { @@ -391,9 +392,10 @@ await test( | "localhost" )[]) { for (const proxyPort of [LOCAL_PORT, PROXY_TEST_PORT, PROXY_PORT]) { - // if (term !== "FIN" || by !== "client") { + // if (term !== "RST" || by !== "browser" || proxyPort !== PROXY_PORT) { // continue; // } + // clean termination by browser RST on 14004 console.log(`clean termination by ${by} ${term} on ${proxyPort}`); const echoServer = new EchoServer(LOCAL_PORT, proxyPort); await echoServer.startAndWaitUntilReady(); @@ -422,7 +424,7 @@ await test( }, ); -await test.only("happy-path", { timeout: 5000 }, async (t) => { +await test("happy-path", { timeout: 5000 }, async (t) => { const echo = new EchoServer(LOCAL_PORT, PROXY_PORT); await echo.startAndWaitUntilReady(); diff --git a/src/h2tunnel.ts b/src/h2tunnel.ts index 3d9c2bd..feb35c4 100644 --- a/src/h2tunnel.ts +++ b/src/h2tunnel.ts @@ -162,28 +162,25 @@ export abstract class AbstractTunnel< }); let endTimeout: NodeJS.Timeout | null = null; duplex1.on("end", () => { - log({ [tag]: "end" }); - // 'end' comes before 'error', so we need to wait make sure 'error' doesn't come it before processing 'end' - // https://github.com/nodejs/node/issues/39400 - endTimeout = setTimeout(() => { - if (!duplex2.writableEnded) { - log({ [tag]: "closing opposite" }); - duplex2.end(); - } - }, 50); + log({ [tag]: "end", ts: new Date().getTime() }); + if (!duplex2.writableEnded) { + log({ [tag]: "closing opposite" }); + duplex2.end(); + } }); duplex1.on("close", () => { - log({ [tag]: "close" }); - if (duplex1.errored && !duplex2.destroyed) { + log({ [tag]: "close", ts: new Date().getTime() }); + if (duplex1.errored && !duplex2.closed) { if (endTimeout) { clearTimeout(endTimeout); } - log({ [tag]: "destroying opposite" }); if (isStream) { + log({ [tag]: "destroying socket" }); socket.resetAndDestroy(); } else { - stream.close(http2.constants.NGHTTP2_INTERNAL_ERROR); + log({ [tag]: "destroying stream" }); + stream.destroy(new Error()); } } });