note-leva

ホームラボと計測のノート

NVMe を「キャッシュ」にするか「置き場」にするか

記録日
2026-08-11
対象
x86 NAS / M.2 NVMe × 2 / HDD アレイ
前提
Docker コンテナと PostgreSQL を同居させる構成

NAS に M.2 スロットが 2 つある。ここに SSD を挿すとき、多くの NAS OS は「リードキャッシュ」「リード/ライトキャッシュ」として使う設定を用意してくれる。ボタン一つで速くなりそうに見えるが、用途によってはキャッシュにしないほうが速い。整理しておく。

キャッシュが効く条件

ブロックキャッシュは、アクセスが局所的であるほど効く。同じデータに繰り返し触るワークロードなら、ヒット率が上がって体感が変わる。逆に、アクセスが広く薄く散る、あるいは毎回違うデータを触る用途では、キャッシュは温まらないまま終わる。

自宅 NAS で実際に多いのは後者に近い。写真ライブラリを一度ずつスキャンする、大きな動画を一度だけ読む、といった使い方はキャッシュの得意分野ではない。

ライトキャッシュを避ける理由

書き込みキャッシュを有効にすると、電源断や SSD の故障がアレイ全体の整合性に波及する。安全に使うには SSD をミラーにする必要があり、結局 2 本を消費する。個人環境で、この冗長性コストと障害リスクを引き受けて得られるものは、思っているより少ない。

速くしたいデータが特定できているなら、キャッシュに「当たることを期待する」より、そこに直接置いたほうが速く、かつ挙動が読める。

コンテナと DB を載せる場合

Docker のイメージレイヤ、node_modules、ビルド中間物、PostgreSQL のデータディレクトリ。これらに共通するのは、小さいファイルへのランダム書き込みが大量に発生することだ。HDD アレイに置くと、シーケンシャル性能がいくら出ていても体感は重い。

この場合の答えははっきりしていて、キャッシュではなく独立ボリュームにする。

M.2 #1 + #2  ---  RAID1  ---  高速ボリューム
                              |- Docker data-root
                              |- コンテナのボリューム
                              |- PostgreSQL データディレクトリ
                              '- サムネイル / 生成物キャッシュ

HDD  x N     ---  RAID5/6 ---  大容量ボリューム
                              |- 写真・動画の原本
                              '- SSD 側のバックアップ先

リードキャッシュは設定しない。大容量のシーケンシャル読み出しは HDD アレイで十分に速く、ランダム読みが効くデータはすべて SSD 側に載っているからだ。

容量と製品選び

500GB × 2 のミラーだと実効 500GB。Docker イメージ、依存パッケージ群、DB、サムネイルを全部載せると意外と早く埋まる。1TB × 2 にしておくと後悔が少ない。差額は小さいが、後から入れ替えるとデータ移行が発生する。

製品は、ランダム書き込みが多い前提で TBW の高い DRAM 搭載 TLC を選ぶ。安価な DRAM レス QLC は、この用途で寿命と持続書き込み性能の両方を落とす。

まとめ

  • キャッシュは「何が速くなるか分からないが、たぶん速くなる」機能。用途が特定できているなら使わない
  • ライトキャッシュは冗長性コストと障害リスクに見合わないことが多い
  • 速くしたいものが分かっているなら、明示的にそこへ置く。予測可能性は速度と同じくらい価値がある