Next.jsでサクッとOGP設定やってみた!
ちょっと株式会社のKindBurgerです!
本記事ではNext.jsの機能を使って、お手軽にOGP設定する実装を紹介します!
やってみたこと🐧
架空のサイト「ペンギンブログ」にて、2つのOGP設定をやってみました!
◆ 汎用的なOGP
トップページやカテゴリページなど、どの画面でも共通して使用できるOGP画像を設定
◆ 記事詳細で使える動的なOGP
記事ごとの画像やタイトルを組み込んだOGP画像を生成
技術的なはなし
◆ 静的画像を用いたOGP
汎用的なOGPでは静的な画像を用意し、各ページに対して共通のOGP情報を設定しました。
Rootのpage.tsx
にてStatic Metadataを記述することで、簡単にOGPタグを設定できます。
project-root/
├── public/
│ └── ogp/
│ └── thumbnail.png // 🌟 静的画像
└── src/
└── app/
└── page.tsx // 🌟 Static Metadataの設定
✏️ コード例
import ArticleList from "./_components/ArticleList";
import styles from "./page.module.css";
// 🌟 Static Metadata
export const metadata = {
openGraph: {
title: "ペンギンブログ",
description:
"ペンギンブログは、世界中のペンギンの生態、特徴、驚くべき行動を紹介するブログです。ペンギン好きにはたまらない情報が満載!",
images: [{
url: "/ogp/thumbnail.png", // 🌟 静的画像の指定
width: 1200,
height: 630
}],
},
};
export default function Home() {
return (
<div className={styles.container}>
<h1 className={styles.title}>ペンギンブログ</h1>
<ArticleList />
</div>
);
}
ローカルでの確認
ローカルでは開発者ツールを用いて<head>
タグにOGP情報が出力されていることを確認できます。
<meta property="og:title" content="ペンギンブログ">
<meta property="og:description" content="ペンギンブログは、世界中のペンギンの生態、特徴、驚くべき行動を紹介するブログです。ペンギン好きにはたまらない情報が満載!">
<meta property="og:image" content="http://localhost:3000/ogp/thumbnail.png">
<meta property="og:image:width" content="1200">
<meta property="og:image:height" content="630">
デプロイ後の確認
本記事ではVercelにデプロイしたのち、OGPデバッガーを使って各SNSでどのように表示されるか確認しています。
◆ 動的データを用いたOGP
記事ごとのOGPはリモートコンテンツからデータ取得し動的に生成しています。
本記事ではopengraph-image.tsx
とgenerateMetadata
の組み合わせで動的にOGP設定してみます。
project-root/
└── src/
└── app/
└── articles/
└── [id]/
├── opengraph-image.tsx // 🌟 コードから画像生成
└── page.tsx // 🌟 generateMetadataの設定
opengraph-image.tsx
によるOGP画像生成
Next.jsではopengraph-image.tsx
を使用してコードからOGP画像を生成できます。
本記事では記事タイトルとサムネ画像を取得し、ImageResponseを返却することでOGP画像を生成しました。
✏️ コード例
import { ImageResponse } from "next/og";
import { getArticleDetail } from "@/app/_libs/microcms/services";
export const runtime = "edge";
export const size = {
width: 1200,
height: 630,
};
export const contentType = "image/png";
export default async function Image({ params }: { params: { id: string } }) {
// 🌟 リモートコンテンツを取得
const article = await getArticleDetail(params.id);
// 🌟 ImageResponseを返却
return new ImageResponse(
(
<div
style={{
background: "#8bd0dd",
width: "100%",
height: "100%",
display: "flex",
flexDirection: "column",
alignItems: "center",
justifyContent: "center",
}}
>
<div
style={{
display: "flex",
width: 200,
height: 200,
}}
>
<img
// 🌟 リモートコンテンツのサムネイル画像を埋め込み
src={article.thumbnail.url}
alt=""
style={{
width: "100%",
height: "100%",
objectFit: "contain",
}}
/>
</div>
<p
style={{
fontSize: 32,
marginTop: 24,
}}
>
{/* 🌟 リモートコンテンツのタイトルを埋め込み */}
{article.title}
</p>
</div>
),
{
...size,
},
);
}
generateMetadata
によるOGP設定
generateMetadata
を用いて、動的に記事ごとのOGP情報を設定します。
本記事では記事タイトルと概要を取得し、generateMetadata
にてog:title
og:description
を設定しています。
✏️ コード例
import { Metadata } from "next";
import ArticleDetail from "@/app/_components/ArticleDetail";
import { getArticleDetail } from "@/app/_libs/microcms/services";
import styles from "./page.module.css";
export async function generateMetadata({ params }: Props): Promise<Metadata> {
// 🌟 リモートコンテンツを取得
const article = await getArticleDetail(params.id);
return {
// 🌟 リモートコンテンツのタイトルとディスクリプションを設定
openGraph: {
title: article.title,
description: article.description,
},
};
}
interface Props {
params: {
id: string;
};
}
export default async function ArticleDetailPage({ params }: Props) {
const article = await getArticleDetail(params.id);
return (
<div className={styles.container}>
<ArticleDetail article={article} />
</div>
);
}
確認方法
動的データを用いたOGPであっても開発者ツールによるローカル確認とOGPデバッガーによる確認が可能です。
ふりかえり
Next.jsのStatic Metadata
やgenerateMetadata
を使って、汎用的なOGPと動的なOGPの両方をお手軽に実装してみました。
特にリモートコンテンツのデータを用いた動的な生成は、記事ごとに最適なOGPを提供できるので、SNSでのシェア時に視覚的な魅力が高まります!
ぜひ、みなさんもNext.jsでOGP設定を試してみてください🐧✨
ちょっと株式会社(chot-inc.com)のエンジニアブログです。 フロントエンドエンジニア募集中! カジュアル面接申し込みはこちらから chot-inc.com/recruit/iuj62owig
Discussion