【実務・中級編】【実務中級者向け】FSO操作中のCtrl+Cや異常終了に備えるテンポラリファイル・ロック自動クリーンアップ – VBScript (Visual Basic Scripting Edition)解析バイブル

スポンサーリンク

VBScriptを掌握せよ:FSOにおける「死なない」ファイル操作と生存戦略

VBScriptはレガシーと言われる。だが、Windows環境でこれほど軽量かつ強力にシステムを叩ける言語は他にない。多くのエンジニアが「動けばいい」という甘えで書いたスクリプトは、Ctrl+Cや予期せぬエラーで停止した瞬間、ゴミファイルを撒き散らし、ロックを放置する。

本物のエンジニアなら、スクリプトが異常終了しても、システムは常にクリーンな状態を保つ「不可逆的な堅牢性」を実装すべきだ。今日は、FSO(FileSystemObject)を扱う上で避けて通れない「一時ファイル管理とクリーンアップ」の極意を伝授する。

—

1. なぜ「その場凌ぎ」のコードは地雷なのか

初心者が書くコードの典型はこうだ。
1. ファイルを作成する
2. 処理を行う
3. 最後に `DeleteFile` する

ここには致命的な欠陥がある。 処理の途中でエラーが発生したり、ユーザーがタスクを強制終了させれば、ステップ3には絶対に到達しない。結果、残骸ファイルがサーバーを圧迫し、次回の実行で「ファイルが既に存在します」という権限エラーを引き起こす。

我々が目指すべきは、「生存している限り常に消去可能な準備を整えておく」という設計思想だ。

—

2. 堅牢なファイル操作の設計パターン

異常終了に備えるための原則は以下の3点だ。

1. 命名規則の強制: テンポラリファイルにはユニークなGUIDやプロセスIDを付与し、既存ファイルと競合させない。
2. On Error Resume Next の限定使用: 全体を囲むのではなく、I/O操作の直前のみを捕捉する。
3. 終了ハンドラの概念: 終了処理を専用のサブルーチン(Cleanup)に切り出し、正常終了時も異常終了時も必ずそこを通るように制御フローを組む。

—

3. 実践:プロダクションコード例

以下は、ファイル処理の途中で何が起きても、生成したテンポラリファイルを確実に削除するクラス構造に近い設計だ。

‘ — メインロジック —
Option Explicit

Dim fso, tmpFilePath
Set fso = CreateObject(“Scripting.FileSystemObject”)

‘ 1. テンポラリパスの生成
tmpFilePath = fso.GetSpecialFolder(2) & “\tmp_” & fso.GetTempName()

‘ 処理開始
On Error Resume Next ‘ エラーを捕捉可能な状態にする

‘ 2. ファイル作成
Dim ts
Set ts = fso.CreateTextFile(tmpFilePath, True)
ts.WriteLine “作業中のデータ”
ts.Close

‘ 3. ここで重い処理やメインロジックを行う
‘ もしここで強制終了されても、Cleanupが呼ばれる構造にする
Call PerformHeavyTask(tmpFilePath)

‘ 4. 正常終了時のクリーンアップ
Call Cleanup(fso, tmpFilePath)

If Err.Number <> 0 Then
WScript.Echo “致命的なエラーが発生しました: ” & Err.Description
Call Cleanup(fso, tmpFilePath) ‘ 異常終了時も必ずクリーンアップ
WScript.Quit 1
End If

‘ — 安全なクリーンアップ用サブルーチン —
Sub Cleanup(fsoObj, path)
On Error Resume Next ‘ 削除失敗でスクリプト自体が止まるのを防ぐ
If fsoObj.FileExists(path) Then
fsoObj.DeleteFile path, True
End If
End Sub

Sub PerformHeavyTask(path)
‘ 何らかのロジック
‘ ここで意図的にエラーを起こすと、上のOn Errorで補足される
‘ Err.Raise 999
End Sub

—

4. プロフェッショナルへの道:さらに一歩先へ

上記のコードは基本だが、さらに高度な環境(多重起動が頻発する環境など)では以下の工夫が必要だ。

  • 排他ロックの考慮: `fso.OpenTextFile` 時に `ForAppending` や `ForWriting` を使う際、他プロセスが掴んでいるとエラーになる。これに対しては、`Sleep` を入れたリトライ処理をループ内に実装するのが定石だ。
  • 属性の復元: ファイルの属性(ReadOnlyなど)を一時的に変更した場合、`Cleanup` 内で必ず元の属性に戻すコードを記述すること。さもなくば、共有フォルダの管理者に怒られることになる。

まとめ:スクリプトに「人格」を持たせる

「動くコード」を書くのは簡単だ。だが、「壊れないコード」を書くには、システムが失敗する前提で設計する謙虚さが必要だ。

ファイル操作は、常に「作成」「利用」「削除」のライフサイクルを意識せよ。VBScriptという古き良き言語を操る我々だからこそ、こうした細部の丁寧さが、運用の安定性に直結する。

さあ、今すぐあなたの書いたスクリプトを見直し、終了ハンドラを組み込んでほしい。それが、プロのエンジニアの流儀だ。

タイトルとURLをコピーしました