diff --git a/mdx-components.tsx b/mdx-components.tsx index 492ecd6..0307310 100644 --- a/mdx-components.tsx +++ b/mdx-components.tsx @@ -168,4 +168,4 @@ export function useMDXComponents( ...components, wrapper: BlogWrapper, } -} +} \ No newline at end of file diff --git a/package-lock.json b/package-lock.json index 27f1789..bec39f7 100644 --- a/package-lock.json +++ b/package-lock.json @@ -7,6 +7,7 @@ "": { "name": "dev-tools-compare", "version": "1.0.0", + "hasInstallScript": true, "dependencies": { "@clerk/nextjs": "^6.12.0", "@mdx-js/loader": "^3.1.0", @@ -33,6 +34,7 @@ "nanoid": "^5.1.2", "next": "^15.1.7", "next-view-transitions": "^0.3.4", + "prisma": "^6.3.1", "react": "^19.0.0", "react-dom": "^19.0.0", "react-icons": "^5.5.0", @@ -1397,6 +1399,51 @@ } } }, + "node_modules/@prisma/debug": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/@prisma/debug/-/debug-6.3.1.tgz", + "integrity": "sha512-RrEBkd+HLZx+ydfmYT0jUj7wjLiS95wfTOSQ+8FQbvb6vHh5AeKfEPt/XUQ5+Buljj8hltEfOslEW57/wQIVeA==", + "license": "Apache-2.0" + }, + "node_modules/@prisma/engines": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/@prisma/engines/-/engines-6.3.1.tgz", + "integrity": "sha512-sXdqEVLyGAJ5/iUoG/Ea5AdHMN71m6PzMBWRQnLmhhOejzqAaEr8rUd623ql6OJpED4s/U4vIn4dg1qkF7vGag==", + "hasInstallScript": true, + "license": "Apache-2.0", + "dependencies": { + "@prisma/debug": "6.3.1", + "@prisma/engines-version": "6.3.0-17.acc0b9dd43eb689cbd20c9470515d719db10d0b0", + "@prisma/fetch-engine": "6.3.1", + "@prisma/get-platform": "6.3.1" + } + }, + "node_modules/@prisma/engines-version": { + "version": "6.3.0-17.acc0b9dd43eb689cbd20c9470515d719db10d0b0", + "resolved": "https://registry.npmjs.org/@prisma/engines-version/-/engines-version-6.3.0-17.acc0b9dd43eb689cbd20c9470515d719db10d0b0.tgz", + "integrity": "sha512-R/ZcMuaWZT2UBmgX3Ko6PAV3f8//ZzsjRIG1eKqp3f2rqEqVtCv+mtzuH2rBPUC9ujJ5kCb9wwpxeyCkLcHVyA==", + "license": "Apache-2.0" + }, + "node_modules/@prisma/fetch-engine": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/@prisma/fetch-engine/-/fetch-engine-6.3.1.tgz", + "integrity": "sha512-HOf/0umOgt+/S2xtZze+FHKoxpVg4YpVxROr6g2YG09VsI3Ipyb+rGvD6QGbCqkq5NTWAAZoOGNL+oy7t+IhaQ==", + "license": "Apache-2.0", + "dependencies": { + "@prisma/debug": "6.3.1", + "@prisma/engines-version": "6.3.0-17.acc0b9dd43eb689cbd20c9470515d719db10d0b0", + "@prisma/get-platform": "6.3.1" + } + }, + "node_modules/@prisma/get-platform": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/@prisma/get-platform/-/get-platform-6.3.1.tgz", + "integrity": "sha512-AYLq6Hk9xG73JdLWJ3Ip9Wg/vlP7xPvftGBalsPzKDOHr/ImhwJ09eS8xC2vNT12DlzGxhfk8BkL0ve2OriNhQ==", + "license": "Apache-2.0", + "dependencies": { + "@prisma/debug": "6.3.1" + } + }, "node_modules/@radix-ui/primitive": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/@radix-ui/primitive/-/primitive-1.1.1.tgz", @@ -5528,7 +5575,6 @@ "version": "2.3.3", "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", - "dev": true, "hasInstallScript": true, "optional": true, "os": [ @@ -8950,6 +8996,33 @@ } } }, + "node_modules/prisma": { + "version": "6.3.1", + "resolved": "https://registry.npmjs.org/prisma/-/prisma-6.3.1.tgz", + "integrity": "sha512-JKCZWvBC3enxk51tY4TWzS4b5iRt4sSU1uHn2I183giZTvonXaQonzVtjLzpOHE7qu9MxY510kAtFGJwryKe3Q==", + "hasInstallScript": true, + "license": "Apache-2.0", + "dependencies": { + "@prisma/engines": "6.3.1" + }, + "bin": { + "prisma": "build/index.js" + }, + "engines": { + "node": ">=18.18" + }, + "optionalDependencies": { + "fsevents": "2.3.3" + }, + "peerDependencies": { + "typescript": ">=5.1.0" + }, + "peerDependenciesMeta": { + "typescript": { + "optional": true + } + } + }, "node_modules/prop-types": { "version": "15.8.1", "resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz", diff --git a/package.json b/package.json index 7f65fab..6efefb6 100644 --- a/package.json +++ b/package.json @@ -37,6 +37,7 @@ "nanoid": "^5.1.2", "next": "^15.1.7", "next-view-transitions": "^0.3.4", + "prisma": "^6.3.1", "react": "^19.0.0", "react-dom": "^19.0.0", "react-icons": "^5.5.0", diff --git a/public/og-bg.png b/public/og-bg.png new file mode 100644 index 0000000..16b3982 Binary files /dev/null and b/public/og-bg.png differ diff --git a/public/og-image.png b/public/og-image.png new file mode 100644 index 0000000..22f1e26 Binary files /dev/null and b/public/og-image.png differ diff --git a/src/app/api/og/route.tsx b/src/app/api/og/route.tsx new file mode 100644 index 0000000..2add219 --- /dev/null +++ b/src/app/api/og/route.tsx @@ -0,0 +1,96 @@ +import { baseUrl } from "@/lib/metadata" +import { ImageResponse } from "next/og" +import { NextRequest } from "next/server" +export async function GET(req: NextRequest) { + const { searchParams } = req.nextUrl + const postTitle = searchParams.get("title") + return new (ImageResponse as any)( + ( +
+

+ {/* eslint-disable-next-line @next/next/no-img-element */} + Alt + + DevToolsAcademy + +

+ {postTitle && ( +
+

+ {postTitle} +

+
+ )} +

+ + A special blog made for Developers. + +

+
+ ), + { + width: 1920, + height: 1080, + } + ) +} diff --git a/src/app/blog/page.tsx b/src/app/blog/page.tsx index 95bb246..11bf28b 100644 --- a/src/app/blog/page.tsx +++ b/src/app/blog/page.tsx @@ -1,7 +1,7 @@ import { Link } from "next-view-transitions" import { cn, formatDate } from "@/lib/utils" -import { getMetadata } from "@/lib/metadata" +import { baseUrl, getMetadata } from "@/lib/metadata" import { allBlogs } from "./data" @@ -9,6 +9,7 @@ export const metadata = getMetadata({ path: "/blog", title: "Blog | DevTools Academy", description: "Learn about awesome developer tools with our blogs", + image: `${baseUrl}api/og?title=Blogs%20|%20DevToolsAcademy`, }) export default async function BlogPage() { diff --git a/src/app/contribute/page.tsx b/src/app/contribute/page.tsx index 9222a82..1a8d901 100644 --- a/src/app/contribute/page.tsx +++ b/src/app/contribute/page.tsx @@ -3,7 +3,7 @@ import { Link } from "next-view-transitions" import { GitBranch, GitCommit, GitPullRequest, HelpCircle } from "lucide-react" import { FaGithub } from "react-icons/fa6" -import { getMetadata } from "@/lib/metadata" +import { baseUrl, getMetadata } from "@/lib/metadata" import { Button } from "@/components/ui/button" export const metadata = getMetadata({ @@ -11,6 +11,7 @@ export const metadata = getMetadata({ title: "Contribute to Dev Tools Academy", description: "Learn how to contribute to Dev Tools Academy and help improve this open-source project", + image: `${baseUrl}api/og?title=Contribute%20|%20DevToolsAcademy`, }) export default function ContributeRoute() { diff --git a/src/app/sponsor/page.tsx b/src/app/sponsor/page.tsx index 8de8e2b..a23cc7b 100644 --- a/src/app/sponsor/page.tsx +++ b/src/app/sponsor/page.tsx @@ -1,12 +1,13 @@ import * as React from "react" -import { getMetadata } from "@/lib/metadata" +import { baseUrl, getMetadata } from "@/lib/metadata" import SponsorshipTiers from "@/components/SponsorshipTiers" export const metadata = getMetadata({ path: "/sponsor", title: "Sponsor | DevTools Academy", description: "Support the development of DevTools Academy", + image: `${baseUrl}api/og?title=Sponsor%20|%20DevToolsAcademy`, }) export default function SponsorPage() { diff --git a/src/app/tools/page.tsx b/src/app/tools/page.tsx index ba85439..ad5e9ca 100644 --- a/src/app/tools/page.tsx +++ b/src/app/tools/page.tsx @@ -1,6 +1,6 @@ import React, { Suspense } from "react" -import { getMetadata } from "@/lib/metadata" +import { baseUrl, getMetadata } from "@/lib/metadata" import ToolsPage from "@/components/tools/ToolsPage" import Categories from "@/components/tools/Categories" @@ -12,6 +12,7 @@ export const metadata = getMetadata({ path: "/tools", title: "Browse Tools | DevTools Academy", description: "Browser and compare tools, curated by DevTools Academy", + image: `${baseUrl}api/og?title=Tools%20|%20DevToolsAcademy`, }) interface SearchParams { diff --git a/src/lib/metadata.ts b/src/lib/metadata.ts index 7304c03..2e6992f 100644 --- a/src/lib/metadata.ts +++ b/src/lib/metadata.ts @@ -30,7 +30,7 @@ export const getMetadata = ({ }: MetadataArgs): Metadata => { const metaTitle = title const metaDescription = description - const metaImage = image ?? `${config.baseUrl}/cover.png` + const metaImage = image ?? `${baseUrl}api/og?title=DevTools Academy` const metadata: Metadata = { title: metaTitle,