こちらはNotion Advent Calendar 2022の17日目です。
こんにちはhoromi(@mineral_30)です。
私はNotion APIが大好きです。
でもNotionも好きです。
なぜNotion APIが好きになったかというと
easy-notion-blogがキッカケでした。
https://github.com/otoyo/easy-notion-blog
今ではeasy-notion-blogのコミュニティ運営をしたり
ちょっとしたPRを本家に送ってニヤニヤしたり
ドハマリ中なhoromiではありますが
はじめから
こんな改造オタクではありませんでした。
この記事では
それまでに至ったNotion遍歴を紹介させていただこうと思います。
私のNotionはまず交換日記から始まりました。
気の合う仲間と交換日記
本当に気の合う仲間のみで始めたteamプラン(現 プラスプラン)。
コメント機能をとことん使い続ける...
といった運用の仕方でしたが
招待制SNSのような感覚で楽しめました。
プログラミングを趣味で始めたメンバーで
構成されていて
いつも
「今何の勉強してるの?」というコメントから
話題が発展していきます。
全員が全く同じ課題に取り組むことは稀で
大抵がバラバラ。
でも興味はある。
だから気になる。
そんな感じで
Twitterやネットなどで見つけた話題や
オススメの本なども紹介し合ったりと
交流を続けてかれこれ1年10ヶ月。
特にルールもなく
気になった人がDBに収納したり
ブロック制限に近づいてきたら
専用アカウントに移動させたり
なんとなくゆるく運用しています。
勉強したことをNotionに書き溜める習慣がついてきた時期に
「ブログにして公開したい」
という欲が出てきました。
ヘッドレスCMS_easy-notion-blog
Notionに書き溜めたのに
わざわざ編集画面を開いて作業をするのは面倒です。
ブログを続けられたためしがなかったので
極力手間の少ないやり方でできるやり方は無いかと探しました。
そんな時
発見したのがeasy-notion-blogでした。
NotionDBに収納して
それを記事として公開できる!!
デザインも
自由に改造できて
無料\(^o^)/
改造したくなるデザインというのがまた憎いッwww
「これ作りたい!!」
という欲求のままに
コードを解読して
分からない部分は勉強して
作ってみて
失敗して
エラーに泣かされ
気づけばあっという間の1年でした。
Notionのデータを使って
ブログに表示させているので
改造していく中で
Notion APIについても分かるようになってきたので
代表的なNotion APIメソッドをいくつか紹介します。
NotionDB内Pageを取得する_Query a database
https://github.com/otoyo/easy-notion-blog/blob/main/lib/notion/client.ts#L69
これは
NotionDBに入れられたPageを全て取得するための関数です。
公式リファレンスでは以下のように明記されています。
https://developers.notion.com/reference/post-database-query
const { Client } = require('@notionhq/client');
const notion = new Client({ auth: process.env.NOTION_API_KEY });
(async () => {
const databaseId = 'd9824bdc-8445-4327-be8b-5b47500af6ce';
const response = await notion.databases.query({
database_id: databaseId,
filter: {
or: [
{
property: 'In stock',
checkbox: {
equals: true,
},
},
{
property: 'Cost of next trip',
number: {
greater_than_or_equal_to: 2,
},
},
],
},
sorts: [
{
property: 'Last ordered',
direction: 'ascending',
},
],
});
console.log(response);
})();
このコードを使って実装するには
キャッシュの知識が必要だということに気づくことができました。
また
変数で整理していく様子も見て学ぶことができるので
自分で改造する時に
「分かりやすく書いていこう!」という意識で取り組めました。
queryメソッドはlib/notion/client.tsx
で沢山使われているので
ブログには無くてはならない存在なんだなということも知れました。
Page内のBlockを1つ取得する_Retrieve a block
https://github.com/otoyo/easy-notion-blog/blob/main/lib/notion/client.ts#L416
NotionのPageが記事の内容になるんですが、
その中には様々なBlockが含まれています。
それをswitchで条件反射させて取得していく様子を見ることができます。
公式リファレンスでは以下のように明記されています。
https://developers.notion.com/reference/retrieve-a-block
const { Client } = require('@notionhq/client');
const notion = new Client({ auth: process.env.NOTION_API_KEY });
(async () => {
const blockId = 'c02fc1d3-db8b-45c5-a222-27595b15aea7';
const response = await notion.blocks.retrieve({
block_id: blockId,
});
console.log(response);
})();
Block内で入れ子にする場合にはもっと複雑になります。
Block内の入れ子も含めて取得する_Retrieve block children
https://github.com/otoyo/easy-notion-blog/blob/main/lib/notion/client.ts#L372
Notionを使っていると
当たり前のようにこんなことしませんか?
Blockの中にまたblockをいれちゃうあれです。
これをブログで実装すると
びっくりするほど
大変なんだなということが分かります。
https://github.com/otoyo/easy-notion-blog/blob/main/lib/notion/client.ts#L372
Childrenっていうのがキーワードっぽいです。
公式リファレンスではこう明記されています。
https://developers.notion.com/reference/get-block-children
const { Client } = require('@notionhq/client');
const notion = new Client({ auth: process.env.NOTION_API_KEY });
(async () => {
const blockId = '59833787-2cf9-4fdf-8782-e53db20768a5';
const response = await notion.blocks.children.list({
block_id: blockId,
page_size: 50,
});
console.log(response);
})();
NotionDBのPropertyにデータを追加する _Update page
easy-notion-blogは開発者(otoyoさん)のブログのコードも公開されています。
ここからたくさんのヒントを得ることができます。
特に印象的だったのが【いいねボタン】のコードです。
https://github.com/otoyo/notion-blog/blob/main/src/lib/notion/client.ts#L687
これは
記事末尾に設置されたいいねボタンをトリガーとして
NotionDBのPropertyに+1増やすという機能です。
日常的によく使っているいいねボタンですが
実装には頭を抱えるほど難しいということを知りました。
いいねボタンを押したときに直接呼び出せば良いような気がしますが、これはできません。
JavaScript がアクセスできるのは、その JavaScript が生成されたドメインと同じドメインだけという決まりがあります。
ブログの画面上でボタンが押されたら
それをトリガーに
apiでPUT通信をし
Notionサーバーに送る。
送れた合図で+1をNotionDBのPropertyに入れる。
といった流れです。
この改造で
「ブログはNotionにある内容を公開するだけではなく、
ブログからアクションしてもらってNotionにためることもできるんだな」
ということを知りました。
解説記事を読みながら
習得できたことを
まとめたのが以下の記事です。
公式リファレンスでは以下のように明記されています。
https://developers.notion.com/reference/patch-page
const { Client } = require('@notionhq/client');
const notion = new Client({ auth: process.env.NOTION_API_KEY });
(async () => {
const pageId = '59833787-2cf9-4fdf-8782-e53db20768a5';
const response = await notion.pages.update({
page_id: pageId,
properties: {
'In stock': {
checkbox: true,
},
},
});
console.log(response);
})();
NotionDB内にPageを新規作成する_Create a page
https://github.com/herohoro/data-world-blog/blob/main/lib/submit_form/client.ts
これはいいねボタンからヒントを得て
自分で実装したコードです。
ブログの画面上で入力フォームを用意し
https://data.herohoro.com/world/submit
そこに入力されたデータを
apiでPOST通信し
Notionサーバーへ送る。
そのデータをNotionDB内の1つのPageとして作成する...
といった機能です。
特にapiの部分に苦戦しましたがなんとか完走しました。
ここまで来ると
公式リフェレンスでは結構簡単に書かれてることでも
実際にやろうとすると苦戦するなといったことを経験できました。
https://developers.notion.com/reference/post-page
const { Client } = require('@notionhq/client');
const notion = new Client({ auth: process.env.NOTION_API_KEY });
(async () => {
const response = await notion.pages.create({
"cover": {
"type": "external",
"external": {
"url": "https://upload.wikimedia.org/wikipedia/commons/6/62/Tuscankale.jpg"
}
},
"icon": {
"type": "emoji",
"emoji": "🥬"
},
"parent": {
"type": "database_id",
"database_id": "d9824bdc-8445-4327-be8b-5b47500af6ce"
},
"properties": {
"Name": {
"title": [
{
"text": {
"content": "Tuscan kale"
}
}
]
},
"Description": {
"rich_text": [
{
"text": {
"content": "A dark green leafy vegetable"
}
}
]
},
"Food group": {
"select": {
"name": "🥬 Vegetable"
}
}
},
"children": [
{
"object": "block",
"heading_2": {
"rich_text": [
{
"text": {
"content": "Lacinato kale"
}
}
]
}
},
{
"object": "block",
"paragraph": {
"rich_text": [
{
"text": {
"content": "Lacinato kale is a variety of kale with a long tradition in Italian cuisine, especially that of Tuscany. It is also known as Tuscan kale, Italian kale, dinosaur kale, kale, flat back kale, palm tree kale, or black Tuscan palm.",
"link": {
"url": "https://en.wikipedia.org/wiki/Lacinato_kale"
}
},
"href": "https://en.wikipedia.org/wiki/Lacinato_kale"
}
],
"color": "default"
}
}
]
});
console.log(response);
})();
Twitterで広がったeasy-notion-blogの輪
easy-notion-blogにはコミュニティも用意されています。
easy-notion-blog/README/community
ツイートに#easy_notion_blog
をつけると
比較的関連した方々からイイネがあります。
私が開発者のotoyoさん(@otoyo0122)とつながれたのもTwitterのおかげでした。
導入で詰まってる方を見かけると
私はすかさず飛んでいくようにしています。
なぜなら
ほぼ初心者状態でGitHubも分からなかった時期に
easy-notion-blogを使い始めてしまい
かなり苦労した経験があるからです。
pushとかaddとか全然分かりませんでした。
このコミュニティを通じて
お互いのブログの情報交換をしています。
「どんな改造したの?」
「それ記事に出す予定ある?」
など平和なやりとりもあれば
「今回のアップデート大変〜〜〜」
「ここで詰まってる」
といった嘆きツイートもあり楽しいです。
でもみんなNotionが好きで
好きだからずっと使いたくって
ブログにして記事を出しているのかなと
思ったりしています。
おわりに
Notionを使い始めてから
使えば使うほど欲が出てきて
ブログを始め、
easy-notion-blogがキッカケで
Notion API に触れるようになり
ワクワクが止まらない1年でした。
そんなeasy-notion-blogも
Starがそろそろ3ケタになろうとしていて
一緒にブログの改造をしながら
Notion APIやNext.jsなどを
習得できたらいいなと思っています\(^o^)/
長くなりましたが
最後まで読んでくださり
ありがとうございました★