Gatsbyで下書き・予約投稿をする
-
いつの日かのあなたへ
この記事を読んでいるということは、私は Gatsby の下書き・予約投稿に成功したということだろう。
この機会にそれらの方法をまとめておこうと思う。
といった感じで Gatsby で個人的に納得のできる下書き・予約投稿ができるようになったので、今回はその備忘録です。
Gatsbyとは
モダンで高速でセキュアで美しい静的サイトジェネレーター。
下書き・予約投稿する
このブログの記事は、以下のようなフォーマットで書かれた Markdown で管理しています。
---
title: first post
date: 2019-01-17
---
This Blog is Built with Gatsby!!!
自分が欲しかった機能は:
- frontmatter 内の
date
で日時が指定されている date
の日時がgatsby build
で実行日時より前であれば記事はビルドされて公開されるdate
の日時がgatsby build
の実行日時より後であればビルドされずに公開もされない
というものです。
下書き機能は、記事の日付から公開するどうかを判別できることが最終目的です。この下書き機能が実装できれば、あとは CI で定期的にビルドすることで予約投稿も実現します。
試したこと
GraphQLで日付を比較する
gatsby-node.js
の createPages
で実行される GraphQL 内でフィルターを使って、日付の比較を試すも失敗。
文字列ではなく、date: 20190117
のような数値で比較することはできるのですが、あまり得策ではないのでこの手法は却下しました。
nodeのfieldに下書きフラグを追加する
Gatsby の API には createNodeField
があり、データ管理をする node にメタデータを追加することができます。これを利用して、公開するかどうか判断するための下書き field を node に追加します。今回はこの方法で下書き機能を実装しました。
exports.onCreateNode = ({ node, actions }) => {
const { createNodeField } = actions;
if (node.internal.type !== 'MarkdownRemark') {
return;
}
const nodeDate = new Date(node.frontmatter.date);
const nowDate = new Date();
const isDraft = nowDate.getTime() <= nodeDate.getTime();
createNodeField({
node,
name: 'draft',
value: isDraft,
});
};
最後に GraphQL のクエリに filter
を追加することで、ビルド日時より前の記事だけを公開することができるようになりました。
{
site {
siteMetadata {
title
}
}
allMarkdownRemark(
filter: { fields: { draft: { eq: false } } } # これを追加する
) {
edges {
node {
excerpt
frontmatter {
date
title
}
}
}
}
}
余談
Gatsby で下書き機能・予約投稿を実装することができました。今回まとめた方法で node の field に下書きフラグを追加するプラグイン gatsby-plugin-draft も公開しました。気になったら使ってみてください。