Elixir言語を用いてブログ記事のマークダウンからfront matter(YAML形式のメタ情報ブロック)の部分だけ取り出します。
これからElixirを始める方にはこのサイトがおすすめです。
Elixirとコミュニティの雰囲気をゆるく味わいたい方は「先端ピアちゃん」さんの動画がオススメです。
front matterとは
Front matterはドキュメントにメタデータ(データについてのデータ)を埋め込むために利用されるYAMLの断片です。
Jekyllのドキュメントを見るとこう書かれています。
Middlemanのドキュメントではこう説明されています。
Frontmatter は YAML または JSON フォーマットでテンプレート上部に記述することが できるページ固有の変数です。--- Middleman
YAMLとは
ウィキります。
YAML(ヤメル、ヤムル)とは、構造化データやオブジェクトを文字列にシリアライズ(直列化)するためのデータ形式の一種。--- Wikipedia
YamlElixir.read_from_string!/1
ElixirでYAMLを解析するにはyaml_elixirパッケージが便利そうです。
YamlElixir.read_from_string!/1で簡単に読み込むことができます。
Mix.install([:yaml_elixir])
yaml = """
a: ""
b: 1
c: true
d: ~
e: nil
"""
YamlElixir.read_from_string!(yaml)
# %{"a" => "a", "b" => 1, "c" => true, "d" => nil, "e" => "nil"}
実験の準備
IExを開きます。
iex
IExの中でyaml_elixirパッケージをインストールします。
Mix.install([:yaml_elixir])
ブログ記事のマークダウンを用意します。
blog_post = """
---
title: Elixirでディレクトリ内のファイルを一覧を取得する。
tags:
- Elixir
- File
private: false
updated_at: '2023-08-15T05:58:24+09:00'
id: 968755b2ef712a42888d
organization_url_name: fukuokaex
slide: false
---
Elixirでディレクトリ内のファイルを列挙する方法について調べました。
これからElixirを始める方にはこのサイトがおすすめです。
https://elixir-lang.info/
"""
実験1
プログ記事を何も加工せずにそのまま渡してみます。
YamlElixir.read_from_string!(blog_post)
front matterの部分が無視されてそれ以外の本文だけ抽出されました。
"Elixirでディレクトリ内のファイルを列挙する方法について調べました。\nこれからElixirを始める方にはこのサイトがおすすめです。\nhttps://elixir-lang.info/"
実験2
String.split/3を使うと文字列を分割することができます。front matterの終端を示す"\n---\n"
で区切ってみます。そして、front matterの文字列だけをYamlElixir.read_from_string!/1に渡します。
[front_matter |_] = blog_post |> String.split("\n---\n", parts: 2)
front_matter |> YamlElixir.read_from_string!()
うまくMapに変換できました。
%{
"id" => "968755b2ef712a42888d",
"organization_url_name" => "fukuokaex",
"private" => false,
"slide" => false,
"tags" => ["Elixir", "File"],
"title" => "Elixirでディレクトリ内のファイルを一覧を取得する。",
"updated_at" => "2023-08-15T05:58:24+09:00"
}
実験3
これは実験2とほぼ同じですが、正規表現を用いて前処理を実施する試みです。Regex.named_captures/3が便利です。
front matterを抽出する正規表現については求められる仕様によりいろんなやり方が考えられると思います。Qiita記事をいくつか読んで参考にさせていただきました。
captures = Regex.named_captures(~r/^(?<yaml>---*[\r\n]*([\s\S]*?))---*[\r\n]/, blog_post)
captures["yaml"] |> YamlElixir.read_from_string!()
入力が同じなので、結果は実験2と同じです。
%{
"id" => "968755b2ef712a42888d",
"organization_url_name" => "fukuokaex",
"private" => false,
"slide" => false,
"tags" => ["Elixir", "File"],
"title" => "Elixirでディレクトリ内のファイルを一覧を取得する。",
"updated_at" => "2023-08-15T05:58:24+09:00"
}
実験4
実験3を終えてから、改めてhex.pmで検索していたら、yaml_elixirをベースにしてfront matter解析機能を実装したyaml_front_matterという別のパッケージが見つかりました。試してみます。
依存パッケージをインストールし直すため、まずIExを再起動する必要があります。
YamlFrontMatter.parse!/1を使ったら一発でfront matterと本文の両方を取り出せました。
Mix.install([:yaml_front_matter])
{front_matter, body} =
YamlFrontMatter.parse!("""
---
title: Elixirでディレクトリ内のファイルを一覧を取得する。
tags:
- Elixir
- File
private: false
updated_at: '2023-08-15T05:58:24+09:00'
id: 968755b2ef712a42888d
organization_url_name: fukuokaex
slide: false
---
Elixirでディレクトリ内のファイルを列挙する方法について調べました。
これからElixirを始める方にはこのサイトがおすすめです。
https://elixir-lang.info/
""")
{%{
"id" => "968755b2ef712a42888d",
"organization_url_name" => "fukuokaex",
"private" => false,
"slide" => false,
"tags" => ["Elixir", "File"],
"title" => "Elixirでディレクトリ内のファイルを一覧を取得する。",
"updated_at" => "2023-08-15T05:58:24+09:00"
},
"\nElixirでディレクトリ内のファイルを列挙する方法について調べました。\n\nこれからElixirを始める方にはこのサイトがおすすめです。\n\nhttps://elixir-lang.info/\n"}