6 分で読了 #devops
このページの目次

ストレージ操作マニュアル

LVM、ファイルシステム、マウント、swap などのストレージ層の操作。ディスクの表示/SMART については disk-ops.md を参照してください。

LVM (論理ボリューム管理)

LVM の3層: PV (物理ボリューム、ディスク/パーティション) → VG (ボリュームグループ、PV のプール) → LV (論理ボリューム、フォーマット可能なブロックデバイス)。

# === PV レベル ===
pvdisplay                                 # すべての PV の詳細
pvs                                       # 簡潔な表示
pvcreate /dev/sdb1                        # PV の作成
pvremove /dev/sdb1                        # 削除 (VG から削除済みであることを確認)
pvresize /dev/sdb1                        # パーティション拡張後に PV サイズを更新

# === VG レベル ===
vgdisplay                                 # すべての VG の詳細
vgs                                       # 簡潔な表示
vgcreate vg0 /dev/sdb1                    # VG の作成、PV を追加
vgextend vg0 /dev/sdc1                    # VG に新しい PV を追加 (プールの拡張)
vgreduce vg0 /dev/sdc1                    # VG から PV を削除 (事前に pvmove でデータを移動)
vgremove vg0                              # VG の削除 (! 危険)

# === LV レベル ===
lvdisplay                                 # すべての LV の詳細
lvs                                       # 簡潔な表示
lvcreate -L 50G -n data vg0               # 50G の LV を作成
lvcreate -l 100%FREE -n data vg0          # 残りの全領域を使用
lvcreate -L 50G -n data vg0 --type raid1  # ミラーリング LV (PV が2つ必要)
lvremove vg0/data                         # LV の削除 (! 危険)
lvextend -L +10G vg0/data                 # 10G 拡張
lvextend -l +100%FREE vg0/data            # 空き容量のすべてまで拡張
lvreduce -L -10G vg0/data                 # 10G 縮小 (! 注意、XFS は縮小非対応)

# 拡張後はファイルシステムも拡張する必要があります:
resize2fs /dev/vg0/data                   # ext4 の場合
xfs_growfs /mnt/data                      # XFS の場合 (マウント済みである必要あり)

# リネーム
lvrename vg0 oldname newname

# スナップショット (LVM thin 推奨)
lvcreate -L 5G -s -n snap_data vg0/data   # 従来のスナップショット
lvcreate -L 5G -s -n snap_data vg0/data --permission r  # 読み取り専用スナップショット
lvconvert --merge vg0/snap_data           # スナップショットの復元 (復元後、スナップショットは自動削除)
lvs -a                                    # スナップショットの表示 (隠し LV を含む)

# スキャン/アクティベーション
vgscan --mknodes                          # VG を再スキャンし、デバイスノードを作成
vgchange -ay vg0                          # VG 内のすべての LV をアクティベート
vgchange -an vg0                          # VG をデアクティベート

ファイルシステム

# 作成
mkfs.ext4 -L mylabel /dev/sdb1            # ラベル付き ext4
mkfs.ext4 -L mylabel -m 0 /dev/sdb1       # -m 0 = ルート用予約領域なし
mkfs.xfs -L mylabel /dev/vg0/data         # XFS
mkfs.btrfs -L mylabel /dev/sdb1           # btrfs
mkfs.vfat -F32 /dev/sdb1                  # FAT32 (EFI/USBメモリ用)
mkfs.exfat /dev/sdb1                      # exFAT (大容量ファイル用USBメモリ)
mkswap -L swap /dev/vg0/swap              # swap 領域

# ラベル
e2label /dev/sdb1 mylabel                 # ext ファイルシステムのラベル変更
xfs_admin -L mylabel /dev/vg0/data        # XFS のラベル変更
btrfs filesystem label /dev/sdb1 mylabel  # btrfs のラベル変更

# 表示
blkid                                      # UUID とファイルシステムタイプ
findfs UUID=abc123                         # UUID → デバイスパス
dumpe2fs /dev/sdb1 | head -40             # ext ファイルシステムのスーパーブロック情報
xfs_info /mnt/data                         # XFS の情報
btrfs filesystem show                      # btrfs の概要
btrfs filesystem df /mnt                   # btrfs の空き容量使用状況

# 修復 (必ず umount してから実行)
fsck /dev/sdb1                             # ext (重大でない問題は自動修復)
fsck -y /dev/sdb1                          # すべて自動 yes
fsck -n /dev/sdb1                          # チェックのみ、修復しない
xfs_repair /dev/vg0/data                   # XFS の修復 (fsck より高速)
xfs_repair -n /dev/vg0/data                # XFS のチェックのみ
btrfs check /dev/sdb1                      # btrfs のチェック (読み取り専用)
btrfs check --repair /dev/sdb1             # btrfs の修復 (! 注意して使用)

# 強制チェック (次回再起動時)
tune2fs -c 1 /dev/sdb1                     # 次回マウント時に fsck を実行
touch /forcefsck                           # ルートパーティションの強制チェック (systemd)

マウント (mount / fstab)

# 一時的なマウント
mount /dev/sdb1 /mnt/data
mount -t ext4 /dev/sdb1 /mnt/data          # タイプを指定
mount -o ro,noexec /dev/sdb1 /mnt/data     # 読み取り専用+実行禁止
mount -o remount,rw /                      # 読み書き可能で再マウント
mount -o remount,ro /                      # 読み取り専用で再マウント
umount /mnt/data                           # アンマウント
umount -l /mnt/data                        # ラジアンアンマウント (誰も使わなくなったらアンマウント)
umount -f /mnt/data                        # 強制アンマウント (NFS などが応答しない場合)
fuser -mv /mnt/data                        # このマウントポイントを使用しているプロセス

# 永続化: /etc/fstab
# UUID=abc123    /mnt/data    ext4    defaults,noatime    0 2
# /dev/vg0/swap  none         swap    sw                  0 0
# //server/share /mnt/smb    cifs    credentials=/etc/smb.cred,uid=1000  0 0

# 列の意味: device  mountpoint  type  options  dump  fsck_order
# dump: 0=バックアップしない, 1=バックアップする
# fsck_order: 0=チェックしない, 1=ルート(最初), 2=その他

# fstab でよく使うオプション:
# defaults = rw,suid,dev,exec,auto,nouser,async
# noatime     アクセス時刻を更新しない (SSD 推奨、書き込みを削減)
# relatime    atime < mtime の場合のみ更新 (バランス型)
# nodiratime  ディレクトリのアクセス時刻を更新しない
# discard     TRIM (NVMe はカーネル組み込みの discard を使用するのがより良い)
# x-systemd.automount  アクセス時にマウント (遅延マウント)
# x-systemd.device-timeout=10  デバイスの出現を最大10秒待機

# fstab のテスト
mount -a                                   # fstab にある未マウント項目をすべてマウント
findmnt --verify                           # fstab の構文チェック

# マウントの表示
findmnt                                    # マウントツリー
findmnt -t ext4,xfs                        # タイプでフィルタ
findmnt /home                              # /home のマウント元とオプションを表示

swap

# 表示
swapon --show                              # 現在の swap 状態 (デバイス/サイズ/使用量)
free -h                                    # swap 使用量を含む
cat /proc/swaps                            # カーネルの視点

# 管理
swapon /dev/vg0/swap                       # 有効化
swapoff /dev/vg0/swap                      # 無効化
mkswap -L swap /dev/vg0/swap               # swap シグネチャの作成
swapon -a                                  # fstab にあるすべての swap を有効化

# swap ファイル (代替案)
dd if=/dev/zero of=/swapfile bs=1M count=4096  # 4G の作成
chmod 600 /swapfile
mkswap /swapfile
swapon /swapfile
# fstab: /swapfile none swap sw 0 0

# swap の優先順位 (複数の swap がある場合)
# swapon -p 10 /dev/sda1       # 0-32767, 高いほど優先
# fstab: ... sw pri=10 0 0

# 最適化
sysctl vm.swappiness                        # 現在の swappiness (0-100, 低い値=swap をあまり使用しない)
# デスクトップ向けは 1-10、サーバーは状況による

btrfs 常用

# サブボリューム
btrfs subvolume list /                      # サブボリュームのリスト
btrfs subvolume create /mnt/@data           # サブボリュームの作成
btrfs subvolume delete /mnt/@data           # サブボリュームの削除
btrfs subvolume snapshot /mnt/@data /mnt/@data-snap  # スナップショット

# 圧縮 (マウントオプション)
# mount -o compress=zstd /dev/sdb1 /mnt
# fstab: UUID=... /mnt btrfs compress=zstd,noatime 0 0

# scrub (データ整合性チェック)
btrfs scrub start /mnt
btrfs scrub status /mnt
btrfs scrub cancel /mnt

# デバイス管理
btrfs device add /dev/sdc1 /mnt             # デバイスの追加 (拡張)
btrfs device delete /dev/sdc1 /mnt          # デバイスの削除
btrfs balance start /mnt                    # データ分布の再バランス

# RAID (btrfs 原生、mdadm と重ねて使用しないこと)
# mkfs.btrfs -m raid1 -d raid1 /dev/sdb1 /dev/sdc1

パーティション操作

# 表示
fdisk -l                                    # MBR
gdisk -l                                    # GPT (推奨)
parted -l                                   # 両方対応

# インタラクティブなパーティション作成
gdisk /dev/sdb                              # GPT
# n → 新規作成, d → 削除, w → 書き込み, q → 保存せずに退出

# 非インタラクティブ
parted /dev/sdb mklabel gpt                 # GPT パーティションテーブルの作成
parted /dev/sdb mkpart primary ext4 0% 100% # 1つのパーティションで全領域を使用
parted /dev/sdb mkpart primary ext4 1MiB 51201MiB  # 正確なサイズ

# パーティションの拡張 (パーティション後に未割り当て領域がある場合)
growpart /dev/sdb 1                         # パーティション1を最大まで拡張 (cloud-init でよく使用)
# その後: resize2fs /dev/sdb1 または xfs_growfs /mnt

# パーティションテーブルのバックアップ/復元
sgdisk --backup=table.bak /dev/sdb          # GPT のバックアップ
sgdisk --load-backup=table.bak /dev/sdb     # 復元

ZFS (Zettabyte File System)

Pool: tank

属性
タイプMirror (2-way)
ディスクWDC WD40EFZZ 4TB ×2 (D4-320 USB3)
ashift12 (4K)
ARC 上限32GB (/etc/modprobe.d/zfs.conf)
マウントポイント/tank
作成日2026-07-02
# デバイス識別子 (by-id, 安定)
/dev/disk/by-id/ata-WDC_WD40EFZZ-68CPAN0_WD-WX12DA5H2PCN  → sda
/dev/disk/by-id/ata-WDC_WD40EFZZ-68CPAN0_WD-WX12DA5H234S  → sdb

Dataset 構成

Datasetrecordsizecompression用途共有
tank128Klz4ルート-
tank/media1Mlz4家庭用映画ライブラリSMB + NFS
tank/photos128Klz4家庭用アルバムSMB + NFS
tank/data128Klz4追加ストレージSMB + NFS
tank/backup128Klz4バックアップコンテナ非共有
tank/backup/system1Mlz4システムディスクバックアップ (restic)非共有

常用操作

# 状態と健全性
zpool status tank                         # プール + VDEV の状態
zpool list -v tank                        # プールのサイズ/使用量
zfs list -r tank                          # dataset のツリー
zpool events tank -v                      # イベント履歴

# Scrub (データ整合性チェック、毎月自動実行)
zpool scrub tank                          # 手動トリガー
zpool scrub -s tank                       # 停止
zpool status tank | grep scan             # 進行状況の確認

# スナップショット
zfs snapshot tank/documents@before-reorg  # 作成
zfs list -t snapshot                      # すべてのスナップショットをリスト
zfs rollback tank/documents@before-reorg  # ロールバック (以降の変更は破棄される!)
zfs destroy tank/documents@old-snap       # スナップショットの削除

# ディスク交換 (mirror がデグラード時)
zpool offline tank <故障ディスクID>
# 物理的にディスク交換後:
zpool replace tank <旧ディスクID> <新ディスクID>
zpool status -v tank                      # resilver の監視

# インポート/エクスポート
zpool export tank                         # 安全なアンマウント (移行前)
zpool import -d /dev/disk/by-id/ tank     # インポート

# パフォーマンス監視
arc_summary                               # ARC キャッシュの詳細統計
zpool iostat -v 1                         # リアルタイム IO (1秒ごと)

サービス一覧

サービスsystemd unit説明
Sambasmb.serviceguest 共有 /tank/{media,photos,data}
NFSnfs-server.service192.168.31.0/24 へエクスポート
ZFS マウントzfs-mount.service起動時に dataset を自動マウント
ZFS イベントzfs-zed.serviceディスク故障時のメール通知 (root)
ZFS メトリクスzfs-prometheus.timer5分ごと収集 → Prometheus
月次 scrubzfs-scrub-monthly@tank.timerデータ整合性の月次チェック

Grafana 監視

  • ダッシュボード: ホストステータス / li-home-0 · ZFS Pool (uid: host-li-home-0-zfs)
  • アラートルール: /etc/grafana/provisioning/alerting/zfs-storage.yaml
    • pool DEGRADED/FAULTED → critical
    • 容量 >80% → warning, >90% → critical
    • 単一 VDEV の故障 → critical
    • ARC ヒットレート <50% → warning

復旧手順

単一ディスク故障 (mirror 存続)

  1. zpool status tank で故障ディスク ID を確認
  2. 故障ディスクを物理的に交換
  3. zpool replace tank <旧> <新>
  4. zpool status -v tank で resilver の完了を監視

プールをインポートできない場合

  1. ls /dev/disk/by-id/ata-* でディスクが見えるか確認
  2. zpool import -f -d /dev/disk/by-id/ tank で強制インポート
  3. すでにエクスポート済みの場合: zpool import -d /dev/disk/by-id/ -a

Samba が利用できない場合

  1. systemctl status smb
  2. zfs mount で /tank がマウントされているか確認
  3. testparm && systemctl restart smb

NFS が利用できない場合

  1. systemctl status nfs-server
  2. showmount -e localhost
  3. exportfs -ra

USB ディスクの接続断 (D4-320)

  1. USB ケーブルが緩んでいないか確認
  2. dmesg | tail -30 で USB disconnect のログを確認
  3. echo "0224" | sudo -S modprobe -r usb-storage uas && echo "0224" | sudo -S modprobe uas usb-storage
  4. zpool online tank <ディスク> (自動で offline になっていた場合)