Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/little-badgers-sparkle.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"@opennextjs/aws": patch
---

Fix external rewrites for binary data
4 changes: 4 additions & 0 deletions examples/pages-router/next.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,10 @@ const nextConfig: NextConfig = {
},
],
},
{
source: "/external-on-image",
destination: "https://opennext.js.org/share.png",
},
],
redirects: async () => [
{
Expand Down
12 changes: 6 additions & 6 deletions packages/open-next/src/overrides/proxyExternalRequest/node.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,19 +47,19 @@ const nodeProxy: ProxyExternalRequest = {
rejectUnauthorized: false,
},
(_res) => {
const resHeaders = _res.headers;
const nodeReadableStream =
_res.headers["content-encoding"] === "br"
resHeaders["content-encoding"] === "br"
? _res.pipe(require("node:zlib").createBrotliDecompress())
: _res.headers["content-encoding"] === "gzip"
: resHeaders["content-encoding"] === "gzip"
? _res.pipe(require("node:zlib").createGunzip())
: _res;

const isBase64Encoded =
isBinaryContentType(headers["content-type"]) ||
!!headers["content-encoding"];
isBinaryContentType(resHeaders["content-type"]) ||
!!resHeaders["content-encoding"];
const result: InternalResult = {
type: "core",
headers: filterHeadersForProxy(_res.headers),
headers: filterHeadersForProxy(resHeaders),
statusCode: _res.statusCode ?? 200,
// TODO: check base64 encoding
isBase64Encoded,
Expand Down
6 changes: 1 addition & 5 deletions packages/tests-e2e/tests/appRouter/og.test.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,10 @@
import { createHash } from "node:crypto";
import { expect, test } from "@playwright/test";
import { validateMd5 } from "../utils";

// This is the md5sums of the expected PNGs generated with `md5sum <file>`
const OG_MD5 = "6e5e794ac0c27598a331690f96f05d00";
const API_OG_MD5 = "cac95fc3e2d4d52870c0536bb18ba85b";

function validateMd5(data: Buffer, expectedHash: string) {
return createHash("md5").update(data).digest("hex") === expectedHash;
}

test("Open-graph image to be in metatags and present", async ({
page,
request,
Expand Down
10 changes: 10 additions & 0 deletions packages/tests-e2e/tests/pagesRouter/rewrite.test.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,7 @@
import { expect, test } from "@playwright/test";
import { validateMd5 } from "../utils";

const EXT_PNG_MD5 = "405f45cc3397b09717a13ebd6f1e027b";

test("Single Rewrite", async ({ page }) => {
await page.goto("/rewrite");
Expand All @@ -13,3 +16,10 @@ test("Rewrite with query", async ({ page }) => {
const el = page.getByText("SSR");
await expect(el).toBeVisible();
});

test("Rewrite to external image", async ({ request }) => {
const response = await request.get("/external-on-image");
expect(response.status()).toBe(200);
expect(response.headers()["content-type"]).toBe("image/png");
expect(validateMd5(await response.body(), EXT_PNG_MD5)).toBe(true);
});
5 changes: 5 additions & 0 deletions packages/tests-e2e/tests/utils.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
import { createHash } from "node:crypto";

export function validateMd5(data: Buffer, expectedHash: string) {
return createHash("md5").update(data).digest("hex") === expectedHash;
}
Loading