今回は、各記事間のページネーションを実装したいと思います.
gatsby-node.js
はこんな感じになっていると思います.
const path = require('path')
module.exports.onCreateNode = ({ node , actions }) => {
const { createNodeField } = actions
if (node.internal.type === 'MarkdownRemark') {
const slug = path.basename(node.fileAbsolutePath , '.md' )
createNodeField({
node,
name: 'slug',
value: slug
})
}
}
module.exports.createPages = async ({ graphql , actions }) => {
const { createPage } = actions
const blogTemplate = path.resolve('./src/templates/blog-template.js')
const res = await graphql(`
query {
allMarkdownRemark {
edges {
node {
fields {
slug
}
}
}
}
}
`)
res.data.allMarkdownRemark.edges.forEach( ({ node }) => {
createPage({
component: blogTemplate ,
path: `/bloglist/${node.fields.slug}` ,
context: {
slug: node.fields.slug
}
})
})
const { paginate }= require('gatsby-awesome-pagination')
const bloglistTemplate = path.resolve('./src/templates/blog-list-template.js')
paginate({
createPage,
items: res.data.allMarkdownRemark.edges,
itemsPerPage: 3,
pathPrefix: '/bloglist',
component: bloglistTemplate,
})
}
ここでページや、スラグなどの情報を作るのでした.
注目してほしいのは以下の部分.
query {
allMarkdownRemark {
edges {
node {
fields {
slug
}
}
}
}
}
これはすべての記事情報を表すクエリです. 記事間を移動するページネーションを実装するには、前後の記事リンクが分からないと移動できませんよね. allMarkdownRemark
内にて前後の記事リンク (パス) を取得できるクエリがあります. それが next
previous
です. 以下のように書き直します.
query {
allMarkdownRemark {
edges {
previous{
frontmatter {
title
}
fields {
slug
}
}
next {
frontmatter {
title
}
fields {
slug
}
}
node {
fields {
slug
}
frontmatter {
title
}
}
}
}
}
node
が今の記事、next
previous
がそれぞれ次の、前の記事情報で、今回はパスにした slug
を取得しています. これを各記事へ context
として渡すため以下のように書き換えます.
res.data.allMarkdownRemark.edges.forEach( ({node , previous , next}) => {
createPage({
component: blogTemplate ,
path: `/bloglist/${node.fields.slug}` ,
context: {
slug: node.fields.slug ,
previous ,
next
}
})
})
ここで、なぜ
edges.next.fields.slug
のようにしないかというと、記事の一番端に行ってしまうと、>next
またはprevious
がそのままnull
になってしまうため、fields
にたどり着けず、エラーにな>るからです.
blog-template.js
にて context
を渡してあげましょう.
import React from 'react'
+import { graphql , Link} from 'gatsby'
import Layout from '../Layouts/common'
export const query = graphql`
query ( $slug: String! ) {
markdownRemark (fields: { slug: { eq: $slug } }) {
frontmatter {
title
date(formatString: "MMMM DD, YYYY")
}
html
}
}
`
const Blog = (props) => {
+ const { previous, next } = props.pageContext
return (
<Layout>
<h1>{props.data.markdownRemark.frontmatter.title}</h1>
<p>{props.data.markdownRemark.frontmatter.date}</p>
<div dangerouslySetInnerHTML={{ __html: props.data.markdownRemark.html}}></div>
//追加ここから
<ul>
<li>
{previous && (
<Link to={`/blog/${previous.fields.slug}`} className="arrow-link">
<strong className="ring">Previous</strong> <br/>
<h4>{previous.frontmatter.title}</h4>
</Link>
)}
</li>
<li>
{next && (
<Link to={`/blog/${next.fields.slug}`} className="arrow-link">
<strong className="ring">Next</strong> <br/>
<h4>{next.frontmatter.title}</h4>
</Link>
)}
</li>
</ul>
//追加ここまで
</Layout>
)
}
export default Blog
これで記事間のページネーションできるようになりました !
ここまで読んでくださってありがとうございました.