microCMSのフィルタに存在するbegin_withを活用して実装する。
begins_withは指定した値から始まるコンテンツを取得するためのフィルタだが、公式ドキュメントにあるよう publishedAt[begins_with]2023-11
のようにすることで指定した年月に公開された記事の一覧を取得することができる。
["2024-01", "2024-02", ..., "2024-12"]
のような形で連続した年月の配列を生成する関数を実装
export const getMonthListFromStartToDate = (start: string): string[] => {
const result: string[] = [];
const [startYear, startMonth] = start.split("-").map(Number);
const startDate = new Date(startYear, startMonth - 1); // 開始年月
const currentDate = new Date(); // 現在年月
let currentYear = startDate.getFullYear();
let currentMonth = startDate.getMonth(); // 0から始まる月
while (
currentYear < currentDate.getFullYear() ||
(currentYear === currentDate.getFullYear() && currentMonth <= currentDate.getMonth())
) {
// YYYY-MM 形式で年月をリストに追加
const monthString = `${currentYear}-${String(currentMonth + 1).padStart(2, "0")}`;
result.push(monthString);
// 翌月に移行
currentMonth++;
if (currentMonth > 11) {
currentMonth = 0;
currentYear++;
}
}
return result;
};
以下のようにPromise.allを使用することで処理時間の短縮を図る
const getPosts = months.map(async (month) => {
const data = await client.getList<Post>({
endpoint: "blog",
queries: {
limit: 100,
filters: `publishedAt[begins_with]${month}`,
},
});
return {
totalCount: data.totalCount,
month: month,
};
});
const monthlyPosts = await Promise.all(getPosts);
月別の記事件数が取得できたので、あとは任意の形式で一覧表示する。
以下はremix + tailwindを活用した例。年月クリックで年月単位の記事一覧に遷移する想定。
export const MonthlyPosts: FC<Props> = ({ monthlyPosts }: Props) => {
return (
<>
<p className="mb-4">Monthly Archives</p>
{monthlyPosts
.filter((monthlyPost) => monthlyPost.totalCount >= 1)
.map((monthlyPost) => (
<Link key={monthlyPost.month} to={`monthly/${monthlyPost.month}`}>
<p className="text-gray-600 text-sm pl-2 pb-2">{`${monthlyPost.month.replace(/-/g, "/")} (${
monthlyPost.totalCount
})`}</p>
</Link>
))}
</>
);
};
以上。
富山在住のプログラマー。
フルリモートで働いています。
Categories
AWS
Cloudflare
Docker
Github
go
html
JavaScript
microCMS
MySQL
Monthly Archives
2024/12 (1)
2024/11 (3)
2024/10 (1)
2024/09 (3)
2024/08 (7)
2024/07 (7)
2024/06 (4)
2024/05 (5)
2024/04 (6)