WordPress GraphQL API に接続する
WordPress から、Next.js に乗り換えたいけど、WordPress の記事数が多すぎて、データを移行するのが大変という場合は、WordPress の GraphQL API を使って、データを取得することができます。GraphQL は、WordPress のプラグインをインストールすることで、WordPress からデータを取得することができるようになります。
Next.js と TypeScript を使って、WordPress の GraphQL API に接続してデータを取得してみましょう。まずは、WordPress に GraphQL プラグインをインストールして有効化し、API エンドポイントが利用可能になることを確認してください。続いて、apollo-client
および関連パッケージをプロジェクトにインストールします。
npm install @apollo/client graphql
次に、Apollo Client のインスタンスを作成し、WordPress の GraphQL API エンドポイントを指定します。
// lib/apolloClient.ts
import { ApolloClient, InMemoryCache } from '@apollo/client'
const apolloClient = new ApolloClient({
uri: 'https://your-wordpress-url/graphql',
cache: new InMemoryCache(),
})
export default apolloClient
クエリを作成してデータを取得する
次に、GraphQL クエリを作成し、WordPress からデータを取得します。ここでは、投稿データを取得するクエリを定義してみます。
// graphql/queries.ts
import { gql } from '@apollo/client'
export const GET_POSTS = gql`
query GetPosts {
posts {
edges {
node {
id
title
content
}
}
}
}
`
データを Next.js のページで表示する
次に、getStaticProps
関数を使って Next.js のページでクエリを実行し、取得したデータを表示します。
// pages/index.tsx
import { GetStaticProps } from 'next'
import { useQuery } from '@apollo/client'
import apolloClient from '../lib/apolloClient'
import { GET_POSTS } from '../graphql/queries'
type Post = {
id: string
title: string
content: string
}
type Props = {
initialPosts: Post[]
}
const Home = ({ initialPosts }: Props) => {
const { data } = useQuery(GET_POSTS, {
ssr: false,
})
const posts = data?.posts.edges.map(({ node }: any) => node) || initialPosts
return (
<div>
{posts.map((post: Post) => (
<div key={post.id}>
<h2>{post.title}</h2>
<div dangerouslySetInnerHTML={{ __html: post.content }} />
</div>
))}
</div>
)
}
export const getStaticProps: GetStaticProps = async () => {
const { data } = await apolloClient.query({
query: GET_POSTS,
})
const initialPosts = data.posts.edges.map(({ node }: any) => node)
return {
props: {
initialPosts,
},
revalidate: 60, // 60 seconds
}
}
export default Home
ここでは、getStaticProps
関数を使用して、ビルド時にデータを取得し、静的ページを生成しています。revalidate
オプションにより、60 秒ごとにページを再生成することでデータが更新されるようになります。また、useQuery
を使ってクライアントサイドでデータを取得し、既存のデータがあればそれを表示します。
カスタムフックを作成してデータ取得を簡潔にする
データ取得のロジックをカスタムフックにまとめることで、コンポーネントがすっきりとして可読性が向上します。
まず、カスタムフックを定義しましょう。
// hooks/usePosts.ts
import { useQuery } from '@apollo/client'
import { GET_POSTS } from '../graphql/queries'
type Post = {
id: string
title: string
content: string
}
export const usePosts = (initialPosts: Post[]) => {
const { data } = useQuery(GET_POSTS, {
ssr: false,
})
const posts = data?.posts.edges.map(({ node }: any) => node) || initialPosts
return posts
}
次に、pages/index.tsx
でカスタムフックを使用します。
// pages/index.tsx
import { GetStaticProps } from 'next'
import apolloClient from '../lib/apolloClient'
import { GET_POSTS } from '../graphql/queries'
import { usePosts } from '../hooks/usePosts'
type Post = {
id: string
title: string
content: string
}
type Props = {
initialPosts: Post[]
}
const Home = ({ initialPosts }: Props) => {
const posts = usePosts(initialPosts)
return (
<div>
{posts.map((post: Post) => (
<div key={post.id}>
<h2>{post.title}</h2>
<div dangerouslySetInnerHTML={{ __html: post.content }} />
</div>
))}
</div>
)
}
export const getStaticProps: GetStaticProps = async () => {
const { data } = await apolloClient.query({
query: GET_POSTS,
})
const initialPosts = data.posts.edges.map(({ node }: any) => node)
return {
props: {
initialPosts,
},
revalidate: 60,
}
}
export default Home
これで、Next.js と TypeScript を使って WordPress の GraphQL API を使ってデータを取得し、表示する方法が完成しました。カスタムフックを利用することで、コンポーネント内でのデータ取得のロジックが簡潔になり、再利用性が向上します。