Skip to content

Commit dd4cadc

Browse files
Open graph dynamic image generation (#6357)
Co-authored-by: Claudio Wunder <[email protected]>
1 parent fe93dd6 commit dd4cadc

File tree

7 files changed

+1519
-3
lines changed

7 files changed

+1519
-3
lines changed
Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,67 @@
1+
import { ImageResponse } from 'next/og';
2+
3+
import HexagonGrid from '@/components/Icons/HexagonGrid';
4+
import JsIconWhite from '@/components/Icons/Logos/JsIconWhite';
5+
import { ENABLE_STATIC_EXPORT, VERCEL_REVALIDATE } from '@/next.constants.mjs';
6+
import { defaultLocale } from '@/next.locales.mjs';
7+
import tailwindConfig from '@/tailwind.config';
8+
import { hexToRGBA } from '@/util/hexToRGBA';
9+
10+
// This is the Route Handler for the `GET` method which handles the request
11+
// for generating OpenGrapgh images for Blog Posts and Pages
12+
// @see https://nextjs.org/docs/app/building-your-application/routing/router-handlers
13+
export const GET = async (request: Request) => {
14+
const { searchParams } = new URL(request.url);
15+
16+
// ?title=<title>
17+
const hasTitle = searchParams.has('title');
18+
const title = hasTitle ? searchParams.get('title')?.slice(0, 100) : undefined;
19+
20+
//?type=<type>
21+
const type = searchParams.get('type') ?? 'announcement';
22+
23+
const typeAttributes: { [key: string]: string } = {
24+
announcement: tailwindConfig.theme.colors.green['700'],
25+
release: tailwindConfig.theme.colors.info['600'],
26+
vulnerability: tailwindConfig.theme.colors.warning['600'],
27+
};
28+
29+
const gridBackground = `radial-gradient(circle, ${hexToRGBA(typeAttributes[type])}, transparent)`;
30+
31+
return new ImageResponse(
32+
(
33+
<div tw="relative flex items-center justify-center bg-black w-[1200px] h-[600px]">
34+
<HexagonGrid style={{ background: gridBackground }} />
35+
36+
<div tw="absolute mx-auto flex max-w-xl flex-col text-center text-3xl font-semibold text-white">
37+
<JsIconWhite width={71} height={80} tw="mx-auto" />
38+
39+
<h2>{title}</h2>
40+
</div>
41+
</div>
42+
),
43+
{ width: 1200, height: 600 }
44+
);
45+
};
46+
47+
// This route is fully dynamic hence there shouldn't be any static param
48+
// available to ensure that the route is not statically generated
49+
export const generateStaticParams = async () => [
50+
{ locale: defaultLocale.code },
51+
];
52+
53+
// We want to use `edge` runtime when using Vercel
54+
export const runtime = process.env.NEXT_PUBLIC_VERCEL_URL ? 'edge' : false;
55+
56+
// Enforces that only the paths from `generateStaticParams` are allowed, giving 404 on the contrary
57+
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#dynamicparams
58+
export const dynamicParams = true;
59+
60+
// Enforces that this route is used as static rendering
61+
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#dynamic
62+
export const dynamic = ENABLE_STATIC_EXPORT ? 'force-static' : 'auto';
63+
64+
// Ensures that this endpoint is invalidated and re-executed every X minutes
65+
// so that when new deployments happen, the data is refreshed
66+
// @see https://nextjs.org/docs/app/api-reference/file-conventions/route-segment-config#revalidate
67+
export const revalidate = VERCEL_REVALIDATE;

0 commit comments

Comments
 (0)