Gatsby-Starter-Lumenはmatejlatin/Gutenbergにインスパイアされているということで、シンプルでテキストそのものが読みやすいようなデザインになっている。
シンプルを突き詰めているため、一般的なブログサービスにデフォルトで装備されている機能がないケースがある。 例えば、サイドバーのカテゴリーリストとか月別アーカイブなどである。
シンプルを目指しているものに何やかんや色々付け足すのはどうかとも思うが、最低限必要な機能だけは追加しておきたい。 そこで、今回はサイドバーにカテゴリーリストを追加していく。
まず、最初にgastby-starter-lumenのディレクトリ構成を確認しておく。
└── src
├── assets
│ ├── fonts
│ │ └── fontello-771c82e0
│ │ ├── css
│ │ └── font
│ └── scss
│ ├── base
│ ├── mixins
│ └── pages
├── components
│ ├── CategoryTemplateDetails
│ ├── Disqus
│ ├── Links
│ ├── Menu
│ ├── PageTemplateDetails
│ ├── Post
│ ├── PostTemplateDetails
│ ├── Sidebar
│ └── TagTemplateDetails
├── layouts
├── pages
│ ├── articles
│ │ ├── 2016-01-09---Perfecting-the-Art-of-Perfection
│ │ ├── 2016-01-12---The-Origins-of-Social-Stationery-Lettering
│ │ ├── 2016-02-02---A-Brief-History-of-Typography
│ │ ├── 2017-18-08---The-Birth-of-Movable-Type
│ │ └── 2017-19-08---Humane-Typography-in-the-Digital-Age
│ └── pages
│ ├── 2015-05-01---about
│ └── 2015-05-01---contact
└── templates
コンポーネントはcomponents
ディレクトリ配下に置かれているので、これから作るカテゴリーリストのコンポーネントもそちらに追加する。
mkdir src/components/CategoriesInSidebar/
cd src/components/CategoriesInSidebar/
emacs -nw index.jsx style.scss
次にCategoriesInSidebar/index.jsx
を書いていく。このようなコンポーネントになった。
import React from 'react';
import { navigateTo } from 'gatsby-link';
import kebabCase from 'lodash/kebabCase'
import './style.scss';
class CategoriesInSidebar extends React.Component {
render() {
const categories = this.props.data;
return (
<div className="categories-in-sidebar">
<p className="categories-in-sidebar__title">
カテゴリー
</p>
<ul className="categories-in-sidebar__list">
{Object.keys(categories).map(category => (
<li className="categories-in-sidebar__list-item">
<a
onClick={ () => navigateTo(`/categories/${kebabCase(category)}/`)}
className="categories-in-sidebar__list-item-link"
>
{`${category} (${categories[category]})`}
</a>
</li>
))
}
</ul>
</div>
);
}
}
export default CategoriesInSidebar;
カテゴリ名がkeyで記事数がvalueである連想配列であるcategories
は、あらかじめ親コンポーネントであるSidebar
の処理の中で作っておき、それを子のCategoriesInSidebar
にpropsとして受け渡している。
Sidebar
内では次のようにしてcategories
を作成する。
// lodash使う
import uniq from 'lodash/uniq'
// もっと良いやり方あるか
let categories = {};
const categories_list = this.props.data.allCategoryNames.edges.map((edge) => {
return (edge.node.frontmatter.category)
})
uniq(categories_list).forEach(category => {
categories[category] = categories_list.filter(item => item === category).length;
});
// categories ==> {Javascript: 2, Docker: 1, Python: 1}
// 以下のように受け渡す
<CategoriesInSidebar data={categories}/>
こんな感じでカテゴリーリストを追加することができた。
次は月別アーカイブを実装したい。