技術記事に戻る

Node.jsとExpressで構築するローカルメディアビューアー:プロジェクト構成と全体アーキテクチャ

Node.jsExpressJavaScript

Node.jsとExpressで構築するローカルメディアビューアー:プロジェクト構成と全体アーキテクチャ

ソースコード: https://github.com/hayate-hu6/local-media-viewer.git

はじめに

Windows11のアップデートに伴い、利用していない古いPCの画像データの整理に便利なツールを作成しました。その内容を本シリーズで解説していきます。 Local Media Viewerの利用画面

このアプリケーションは、ローカルネットワーク内で画像や動画ファイルを快適に閲覧するために開発された「Local Media Viewer」です。 第1回となる今回は、プロジェクトの全体的なアーキテクチャ、技術スタックの選定理由、そしてディレクトリ構成について詳細に見ていきます。

このアプリケーションは、自宅のNASやPC内にある大量のメディアファイルを、ブラウザを通じてスマホやタブレットから手軽に閲覧することを目的に作られています。複雑なデータベースを使わず、ファイルシステムを直接読み込むシンプルな設計が特徴です。

技術スタックと選定理由

このプロジェクトでは、以下の技術が採用されています。

  1. ランタイム: Node.js

    • 選定理由: ファイルシステムへのアクセス(fsモジュール)が容易であり、サーバーサイドJavaScriptとして軽量かつ高速に動作するためです。また、豊富なパッケージエコシステム(npm)を活用できる点も大きなメリットです。
  2. Webフレームワーク: Express

    • 選定理由: Node.jsにおけるデファクトスタンダードであり、ルーティング、ミドルウェア、静的ファイル配信の仕組みがシンプルかつ強力です。今回は特に、特定のIPアドレスからのアクセス制限や、クッキーを用いた簡易認証を実装するために、Expressのミドルウェア機能が重宝しています。
  3. フロントエンド: Vanilla JavaScript (No Framework)

    • 選定理由: ReactやVueなどのフレームワークを使用せず、標準のJavaScript(Vanilla JS)で構築されています。これは、ビルドステップ(WebpackやBabelなど)を不要にし、server.jsを起動するだけで即座に利用可能にするためです。コードベースが小さいため、学習コストも低く、メンテナンスも容易です。
  4. メディア変換: FFmpeg

    • 選定理由: Webブラウザがネイティブにサポートしていない形式(.avi, .mkvなど)を、汎用的な.mp4形式に変換するために使用します。Node.jsのchild_processからコマンドラインツールとして呼び出しています。

ディレクトリ構成の詳細解説

プロジェクトのルートディレクトリは以下のような構成になっています。非常にフラットで分かりやすい構造です。

local-media-viewer/
├── app.js             // フロントエンドロジック(ブラウザ側で実行)
├── server.js          // バックエンドロジック(Node.jsで実行)
├── convert_media.js   // メディア変換用スクリプト
├── config.json        // 設定ファイル(メディアパスなど)
├── package.json       // 依存関係の定義
├── public/            // 静的ファイル群
│   ├── index.html     // メインのHTML
│   └── styles.css     // (存在する場合) スタイルシート
└── m/                 // (例) デフォルトのメディア格納フォルダ

主要ファイルの役割

1. server.js (バックエンドの中核)

このファイルがアプリケーションのエントリーポイントです。expressサーバーを立ち上げ、以下の責務を担います。

  • HTML/JS/CSSの配信(express.static
  • メディアファイルの実体配信(認証付き)
  • ディレクトリ内のファイルスキャンAPI (/api/files)
  • ログイン認証とセッション管理(Cookie)
  • IPアドレスによるアクセス制限

2. app.js (フロントエンドの頭脳)

public/index.htmlから読み込まれ、ブラウザ上で動作します。

  • サーバーAPIからのデータ取得 (fetch)
  • DOM操作によるグリッド表示 (document.createElement)
  • ページネーションのロジック
  • 画像/動画閲覧用のモーダルウィンドウ制御
  • SPA(Single Page Application)的なタブ切り替え

3. convert_media.js (ユーティリティ)

独立したスクリプトとして動作し、指定されたディレクトリを再帰的に走査して、ブラウザ非対応の動画ファイルをMP4に一括変換します。これはサーバーとは別に、メンテナンス時に手動で実行することを想定しています。

データフローの仕組み

このアプリケーションのデータフローは「On-Demand Scan」方式を採用しています。

  1. 起動時: server.jsが起動し、設定ファイル(config.json)を読み込みます。
  2. アクセス時: ユーザーがブラウザでアクセスすると、まずパスワード入力画面が表示されます。
  3. 認証: 正しいパスワードが送信されると、サーバーはHttpOnlyなCookieを発行します。
  4. データ取得: フロントエンド(app.js)は認証成功後、/api/filesエンドポイントを叩きます。
  5. スキャン: サーバーはこのリクエストを受け取った瞬間に、指定されたメディアディレクトリを再帰的にスキャン(fs.readdirSync)します。データベースを持たないため、常にファイルシステムの最新状態が反映されます。
  6. レンダリング: 取得したファイルリスト(JSON)を元に、フロントエンドがDOMを生成して画面に描画します。

まとめ

Local Media Viewerは、複雑さを排除し「実用性」と「可搬性」を重視したアーキテクチャになっています。 DBレス構造にすることで、フォルダに画像を放り込むだけで即座にギャラリーに反映されるという手軽さを実現しています。

次回は、このアーキテクチャの中核である server.js の実装詳細、特にExpressを使った静的配信とAPI設計について深掘りしていきます。

次回: Node.js Expressによるセキュアなメディア配信サーバーの構築手法と実装の全貌


同シリーズ記事