PowerShellで空きディスク容量が少ない場所を特定して警告を出す方法

Windows ServerやWindows PCの空き容量をPowerShellで調べるなら、Get-VolumeのSizeとSizeRemainingから空き率を計算し、割合と絶対容量の両方で判定します。たとえば「空き15%未満、または20GB未満」を警告条件にすると、大容量・小容量ボリュームの偏りを減らせます。本記事のサンプルは読み取り専用で、容量を削除・圧縮しません。警告を見て即座にファイルを消すのではなく、増加元、所有者、保持規則、バックアップ、復旧手順を確認してから対処します。

目次

まずGet-Volumeで現在値を確認する

WindowsのStorageモジュールにあるGet-Volumeは、ボリュームのドライブ文字、ラベル、ファイルシステム、HealthStatus、SizeRemaining、Sizeなどを返します。最初はGet-Volumeだけを実行し、対象サーバーに存在するボリュームと値を確認します。ドライブ文字を限定するならGet-Volume -DriveLetter Cです。結果はオブジェクトなので、文字列を切り取るより数値プロパティをそのまま計算へ使えます。

PowerShellを管理者として開く必要があるかは環境とリモート管理方式で異なります。容量の読み取りだけに過剰なDomain Admins権限を与えず、監視用アカウントには対象ホストで必要な最小権限だけを付与します。Storageモジュールがない古い環境や別OSからの管理では、Get-CimInstanceとWin32_LogicalDiskなどを代替にできます。旧Get-WmiObjectはPowerShell 3.0以降Get-CimInstanceに置き換えられているため、新規スクリプトではCIMを優先します。

空き率と空きGBを別々に計算する

空き率はSizeRemaining / Size * 100、空きGBはSizeRemaining / 1GBで求めます。Sizeが0または取得できないオブジェクトで除算しないよう、Size -gt 0を先に確認します。小数は[math]::Round()で表示用に丸めますが、判定精度を保つため、可能なら丸める前の値で比較します。PowerShellの1GBは2進単位に基づくため、ストレージ製品の10進GB表示と数字が少し異なることも記録します。

割合だけでは、10TBの15%が1.5TBとなり早すぎる警告になる一方、40GBの5%は2GBで遅すぎる場合があります。絶対容量だけでも、ボリューム規模が違えば余裕時間を比較できません。まず「空き率がしきい値未満、または空きGBが最低値未満」という安全側の条件を使い、サービスごとの日次増加量と必要な復旧時間から調整します。SQLログ、WSUS、バックアップ、仮想ディスクなど用途ごとに同じ値を強制しません。

読み取り専用の警告スクリプト

次の例は、ドライブ文字がありSizeが0より大きいボリュームを取得し、空き率と空きGBを一覧化します。サンプル値の15%・20GBは例であり、本番基準ではありません。IsLowがTrueの行へWrite-Warningを出し、一件でも該当すれば終了コード2、なければ0で終了します。ファイルの削除、圧縮、サービス停止、設定変更は行いません。

コンソールのWarningは担当者へ自動通知する機能ではありません。監視製品やタスクスケジューラから実行する場合、標準出力、Warningストリーム、終了コードをどのように収集するかを先に決めます。既存監視があるなら、スクリプト内で独自メール送信を増やすより、監視エージェントが終了コード2を検知して重複抑制・エスカレーションする構成が管理しやすくなります。

$PercentThreshold = 15
$MinimumFreeGB = 20

$volumes = Get-Volume | Where-Object { $_.DriveLetter -and $_.Size -gt 0 }
$results = foreach ($volume in $volumes) {
    $freePercentRaw = ($volume.SizeRemaining / $volume.Size) * 100
    $freeGBRaw = $volume.SizeRemaining / 1GB
    [pscustomobject]@{
        Drive = "$($volume.DriveLetter):"
        Label = $volume.FileSystemLabel
        Health = $volume.HealthStatus
        FreeGB = [math]::Round($freeGBRaw, 2)
        FreePercent = [math]::Round($freePercentRaw, 2)
        IsLow = ($freePercentRaw -lt $PercentThreshold) -or ($freeGBRaw -lt $MinimumFreeGB)
    }
}

$results | Sort-Object FreePercent | Format-Table -AutoSize
$results | Where-Object IsLow | ForEach-Object {
    Write-Warning ("{0} free space is {1} GB ({2}%)" -f $_.Drive, $_.FreeGB, $_.FreePercent)
}

if ($results.IsLow -contains $true) { exit 2 }
exit 0

結果をオブジェクトのまま保存する

画面確認ではFormat-Tableが便利ですが、CSVやJSONへ保存する前にFormat-Tableを通すと表示用オブジェクトへ変換され、再利用しにくくなります。保存するなら$results | Export-Csv -NoTypeInformationのように元のオブジェクトを出力します。ファイル名にはサーバー名とUTCまたは明示したタイムゾーンの時刻を含め、実行アカウントだけが書き込めるログフォルダーを使います。

履歴を毎回別ファイルへ無制限に残すと、監視スクリプト自身がディスクを圧迫します。中央ログ、監視製品、イベント収集へ送るか、保持日数と最大容量を設定します。値が取得できなかったホストを「空き容量正常」と扱わず、取得失敗として別アラートにします。結果件数が0、対象ドライブが欠落、CIM接続に失敗、SizeRemainingがnullの場合は、監視対象外と区別できる終了コードとログを設計します。

ドライブ文字のないマウントポイントを見落とさない

サンプルの$_.DriveLetterフィルターは、C:やD:のような通常ドライブだけを見やすくする反面、フォルダーへマウントしたボリューム、回復パーティション、Cluster Shared Volumeなどを除外します。対象サーバーのストレージ台帳とGet-Volume全件を比較し、業務データがマウントポイントにある場合はPath、UniqueId、FileSystemLabelなどで識別する別ルールを作ります。

ドライブ文字がない全ボリュームを一律に警告対象へ入れると、通常は監視不要なシステム予約領域まで混ざります。対象は「存在するものを全部」ではなく、「容量枯渇が業務へ影響する管理対象一覧」と照合します。フェールオーバークラスター、Storage Spaces Direct、共有ストレージ、仮想ディスクはノードから見える値の意味が異なることがあるため、その製品の対応する監視方法を使います。

HealthStatusと容量を分けて評価する

Get-VolumeにはHealthStatusもありますが、Healthyだから空き容量が十分という意味ではなく、空きが多いからストレージ障害がないという意味でもありません。容量アラートとストレージヘルスアラートを別条件にし、どちらか一方を満たしたときにもう一方を抑制しません。ファイルシステムエラー、ディスク障害、Storage SpacesのOperationalStatus、イベントログ、バックアップ失敗は容量とは別に監視します。

容量警告を受けたら、最初に増加速度と残り時間を確認します。前回値との差分を実行間隔で割れば概算の増加率が得られますが、ログローテーションやバックアップ削除で増減するため、一点の予測を確定値にしません。通常時、月末、更新日、バックアップ実行中の傾向を比較し、Warning、Critical、予測枯渇の段階を分けます。急増はしきい値到達前でも異常として検知します。

複数サーバーはCIMセッションで読み取る

Get-Volumeは-CimSessionを受け取れるため、承認済みの管理端末から複数サーバーを読み取れます。対象名をコードへ直書きし続けるのではなく、CMDBや管理対象CSVなど信頼できる一覧から読み込み、重複、廃止、環境区分を検証します。接続先ごとにサーバー名を結果へ付与し、あるホストのD:を別ホストのD:と混同しない形式にします。

リモートCIMには名前解決、認証、ファイアウォール、WinRMまたはCIMセッションの構成が関係します。資格情報をスクリプトへ平文保存せず、管理されたサービスアカウント、gMSA、タスク実行資格情報、シークレット管理など環境に適した方法を使います。全サーバーへDomain Adminsで接続する構成を避け、読み取りに必要な権限だけを委任します。タイムアウトとThrottleLimitを設定し、接続失敗で全体の結果が失われないようホスト単位で記録します。

定期実行は署名・権限・重複抑制を設計する

定期監視する場合は、スクリプトを改ざんされにくい管理フォルダーへ置き、コードレビュー、署名、バージョン管理を行います。タスクスケジューラでは専用アカウント、必要最小限の「バッチジョブとしてログオン」、実行ディレクトリ、タイムアウト、失敗時の再試行、同時実行禁止を設定します。ExecutionPolicyをBypassへ広く変更する方法は採用せず、組織のPowerShell実行基準に合わせます。

同じ容量不足を5分ごとに通知すると担当者が重要アラートを見落とします。最初のWarning、一定時間継続したCritical、容量がさらに減ったときの再通知、回復通知を区別します。保守中や計画的な大容量処理には期限付き抑制を使い、無期限の除外を残しません。監視自体が停止したことを検知するため、最後の正常実行時刻と対象ホスト数も別メトリックとして監視します。

警告後に安全に原因を絞り込む

容量不足を検知した直後に、Temp、ログ、バックアップ、ユーザープロファイルを一括削除してはいけません。まず対象ドライブ、増加開始時刻、所有サービス、直近の更新・障害・バックアップ、最大ディレクトリ、開いているファイル、保持規則を確認します。ログには監査や障害解析に必要な情報、バックアップには唯一の復旧点が含まれる可能性があります。削除権限と業務承認を分けます。

対処は、アプリケーション公式のクリーンアップ、ログローテーション、保持期間の見直し、別ボリュームへの安全な移行、容量拡張などから選びます。変更前にバックアップ、停止要否、サービス依存、復旧、監視しきい値を確認します。Windowsコンポーネントストア、WSUS、SQL、Exchange、バックアップ製品などは、それぞれのサポート手順を使います。エクスプローラーで大きく見えるフォルダーを推測で消すことは避けます。

しきい値は残り時間と業務要件で見直す

最適なしきい値は、ボリューム容量ではなく「枯渇するまでに対処できる時間」と「サービスが安全に動作する最低余裕」によって決まります。日次増加量が50GBで休日対応がないサーバーなら、20GB警告は遅すぎます。逆に固定された読み取り中心ボリュームでは、割合だけで早期警告が続くことがあります。最低空き、変化率、予測日数を組み合わせ、所有部門と合意します。

本番導入後は、誤検知、見逃し、対処所要時間、休日発報、実際の最小空き、拡張リードタイムを定期レビューします。新しいドライブやマウントポイントが追加されたときに監視へ自動または承認付きで登録される仕組みを用意します。スクリプトの成功は容量管理の成功ではありません。対象網羅性、取得鮮度、通知到達、担当者の応答、問題解消、再発防止までを一連の運用として測定します。

確認チェックリスト

  • Get-Volume全件とストレージ台帳を比較し監視対象を決める
  • Sizeが0より大きいことを確認して空き率と空きGBを計算する
  • 割合・絶対容量・増加速度・対処時間からしきい値を決める
  • 取得失敗と容量正常を別の終了コード・ログで表す
  • Warningストリームと終了コードを監視製品で重複抑制して通知する
  • 削除前に増加元、所有者、保持、バックアップ、公式手順を確認する

PowerShellで空き容量を監視する基本は、Get-VolumeのSizeRemainingとSizeを数値のまま使い、空き率と空きGBを二重判定することです。サンプルは読み取り専用で、Write-Warningと終了コードを返します。ドライブ文字のないマウントポイント、取得失敗、HealthStatus、複数サーバーの識別、ログ保持を見落とさず、監視製品へ接続してください。容量不足は削除命令ではありません。増加速度と残り時間を確認し、アプリケーション所有者、保持規則、バックアップ、復旧をそろえてから、安全なクリーンアップや拡張を実施します。

公式情報・参考資料

この記事を書いた人

実務の現場で詰まりがちなポイントを地図にするITブログ「IT trip」を運営。Windows/Office(Teams・Excel)からSQL、サーバ運用、ガジェットまで、再現性のある手順と“なぜそうなるか”を丁寧に解説します。読んだらすぐ試せること、そして迷った人の次の一歩が見えることを大切にしています。

コメント

コメントする

目次