fix: harden OpenResponses URL input fetching

This commit is contained in:
Peter Steinberger
2026-02-13 01:38:15 +01:00
parent 4199f9889f
commit 99f28031e5
13 changed files with 431 additions and 11 deletions

View File

@@ -1,5 +1,9 @@
import { describe, expect, it, vi } from "vitest";
import { createPinnedLookup, resolvePinnedHostname } from "./ssrf.js";
import {
createPinnedLookup,
resolvePinnedHostname,
resolvePinnedHostnameWithPolicy,
} from "./ssrf.js";
describe("ssrf pinning", () => {
it("pins resolved addresses for the target hostname", async () => {
@@ -68,4 +72,34 @@ describe("ssrf pinning", () => {
expect(fallback).toHaveBeenCalledTimes(1);
expect(result.address).toBe("1.2.3.4");
});
it("enforces hostname allowlist when configured", async () => {
const lookup = vi.fn(async () => [{ address: "93.184.216.34", family: 4 }]);
await expect(
resolvePinnedHostnameWithPolicy("api.example.com", {
lookupFn: lookup,
policy: { hostnameAllowlist: ["cdn.example.com", "*.trusted.example"] },
}),
).rejects.toThrow(/allowlist/i);
expect(lookup).not.toHaveBeenCalled();
});
it("supports wildcard hostname allowlist patterns", async () => {
const lookup = vi.fn(async () => [{ address: "93.184.216.34", family: 4 }]);
await expect(
resolvePinnedHostnameWithPolicy("assets.example.com", {
lookupFn: lookup,
policy: { hostnameAllowlist: ["*.example.com"] },
}),
).resolves.toMatchObject({ hostname: "assets.example.com" });
await expect(
resolvePinnedHostnameWithPolicy("example.com", {
lookupFn: lookup,
policy: { hostnameAllowlist: ["*.example.com"] },
}),
).rejects.toThrow(/allowlist/i);
});
});