🚀

プログラマ向けに最高にクールなポートフォリオサイトを作った!!

2024/06/13に公開


自分のポートフォリオサイトを初めて制作しました。
https://terminal.yuuki008.dev

これまでも自分のポートフォリオサイトが欲しいと思っていましたが、デザインや構成を考えるのが面倒で制作していませんでした。先月、大塚製薬さんのプログラマーに向けた特設サイトを拝見し、CUI で操作するポートフォリオサイトを作りたいと思い、制作しました。
https://www.otsuka.co.jp/cmt/to_programmer/cui/

非エンジニアの方には少し使いづらいかもしれませんが、UNIXコマンドに慣れ親しんだプログラマにとっては最高にクールなウェブサイトになったと思っています。

サイトの概要

このサイトは macOS のターミナルアプリのデザインを模倣しており、基本的なUNIXコマンド(ls, cd, catなど)で操作可能です。オリジナルのコマンドも用意しているので、サイトでhelpと入力してもらえると使用できるコマンドの一覧を見ることができます。

隠しコマンドもあるかもしれないので、思いつくコマンドを入力してみてください!

技術構成

できるだけに早く作りたかったこともあり、普段から慣れ親しんでいる以下の技術を使って制作しました。

こだわった & 苦労したところ

ファーストビュー

黒い画面にぽちぽち入力するサイトなので、ハッカーっぽいファーストビューにしたいと考えました。映画などでよく見る、コードが上から降ってくるようなアニメーションを作りたいと思い、以下の動画を参考に実装しました。
https://youtu.be/f5ZswIE_SgY?si=NCbU3RUqal_r6n2F

実行済みコマンドのメモ化

コマンドの履歴をステートで管理し、各コマンドの出力結果をコンポーネントで表示していました。開発当初は出力結果のメモ化を行っておらず、コマンドを入力するたびに過去のコマンドのコンポーネントが再レンダリングされていました。それだとカレントディレクトリが変わると過去のコマンドの出力結果が変わってしまうので、コマンドのコンポーネントをメモ化し、過去のコマンドの表示が変わらないようにしました。

ファイルシステム

このサイトのルートディレクトリは、 Next.js の public ディレクトリと同期しています。

動的なファイルシステム

開発初期は、ファイルシステムをハードコーディングしていました。しかしこれだと public ディレクトリ内のファイル名を変更したり、作成したりするたびにファイルシステムのオブジェクトを変更しなければなりませんでした。

例: publicにREADME.mdファイルを作成 -> ファイルシステムにも追加

export const FileSystem = {
  name: "public",
  type: 'directory',
  children: [
    { name: "about", type: 'directory', children: [...] },
    { name: "README.md", type: 'file' }
  ]
}

これを改善するために、サイトのマウント時に public ディレクトリ構造をクライアントに渡し、クライアントでファイルシステムを構築するように変更しました。これにより public ディレクトリを変更すれば、シームレスにサイトからもアクセスできるようになっています。

カレントディレクトリの移動

開発当初は、子から親への参照ができないデータ構造でファイルシステムを構築していたため、cd ../ の挙動を実現できませんでした。親ディレクトリへの移動を実現するために、子から親へたどることのできるデータ構造にファイルシステムを実装し直し、ディレクトリ移動の挙動を実現しました。

まとめ

サイトの実装は完了しましたが、載せている情報が少ないので、これからどんどん充実させていきます。ご興味ある方は、アクセスしてお好きなコマンドを入力してみてくたさい!!
https://terminal.yuuki008.dev

ソースコードはこちらになります。
https://github.com/yuuki008/portfolio

バグがありましたら、優しく教えていただけると幸いです 🙏

参考・関連

CalorieMate to Programmer CUIモード | 大塚製薬
Matrix Rain Experiments in JavaScript (tutorial)

Discussion