From 17120cefdc1cd2cee6dd717cab0a96f26fc2d394 Mon Sep 17 00:00:00 2001 From: Ciro Spaciari Date: Tue, 24 Jun 2025 17:31:19 -0700 Subject: [PATCH] fix(http2) fix remoteSettings not emitting on default settings (#20622) --- src/bun.js/api/bun/h2_frame_parser.zig | 6 ++++-- test/js/node/http2/node-http2.test.js | 25 +++++++++++++++++++++++++ 2 files changed, 29 insertions(+), 2 deletions(-) diff --git a/src/bun.js/api/bun/h2_frame_parser.zig b/src/bun.js/api/bun/h2_frame_parser.zig index 9009855bae..14352b7246 100644 --- a/src/bun.js/api/bun/h2_frame_parser.zig +++ b/src/bun.js/api/bun/h2_frame_parser.zig @@ -1461,7 +1461,7 @@ pub const H2FrameParser = struct { } pub fn sendSettingsACK(this: *H2FrameParser) void { - log("HTTP_FRAME_SETTINGS ack true", .{}); + log("send HTTP_FRAME_SETTINGS ack true", .{}); var buffer: [FrameHeader.byteSize]u8 = undefined; @memset(&buffer, 0); var stream = std.io.fixedBufferStream(&buffer); @@ -2386,7 +2386,7 @@ pub const H2FrameParser = struct { if (this.remoteSettings == null) { // ok empty settings so default settings - const remoteSettings: FullSettingsPayload = .{}; + var remoteSettings: FullSettingsPayload = .{}; this.remoteSettings = remoteSettings; log("remoteSettings.initialWindowSize: {} {} {}", .{ remoteSettings.initialWindowSize, this.remoteUsedWindowSize, this.remoteWindowSize }); @@ -2399,6 +2399,7 @@ pub const H2FrameParser = struct { } } } + this.dispatch(.onRemoteSettings, remoteSettings.toJS(this.handlers.globalObject)); } } @@ -3785,6 +3786,7 @@ pub const H2FrameParser = struct { pub fn request(this: *H2FrameParser, globalObject: *JSC.JSGlobalObject, callframe: *JSC.CallFrame) bun.JSError!JSValue { JSC.markBinding(@src()); + log("request", .{}); const args_list = callframe.arguments_old(5); if (args_list.len < 4) { diff --git a/test/js/node/http2/node-http2.test.js b/test/js/node/http2/node-http2.test.js index b218cb22ac..4b01bc1177 100644 --- a/test/js/node/http2/node-http2.test.js +++ b/test/js/node/http2/node-http2.test.js @@ -214,6 +214,31 @@ for (const nodeExecutable of [nodeExe(), bunExe()]) { expect(parsed.url).toBe(`${HTTPS_SERVER}/get`); } }); + it("http2 should receive remoteSettings when receiving default settings frame", async () => { + const { promise, resolve, reject } = Promise.withResolvers(); + const session = http2.connect(HTTPS_SERVER, TLS_OPTIONS); + + session.once("remoteSettings", resolve); + session.once("close", () => { + reject(new Error("Failed to receive remoteSettings")); + }); + try { + const settings = await promise; + expect(settings).toBeDefined(); + expect(settings).toEqual({ + headerTableSize: 4096, + enablePush: false, + maxConcurrentStreams: 4294967295, + initialWindowSize: 65535, + maxFrameSize: 16384, + maxHeaderListSize: 65535, + maxHeaderSize: 65535, + enableConnectProtocol: false, + }); + } finally { + session.close(); + } + }); it("should be able to mutiplex POST requests", async () => { const results = await doMultiplexHttp2Request(HTTPS_SERVER, [ { headers: { ":path": "/post", ":method": "POST" }, payload: JSON.stringify({ "request": 1 }) },