【実務・中級編】【大容量ファイル安全ダウンロード】MSXML2.XMLHTTP による進捗考慮型取得とデータ破損チェック – VBScript (Visual Basic Scripting Edition)解析バイブル

スポンサーリンク

VBScriptを極める:大容量ファイルを「壊さず」ダウンロードする技術的処方箋

現場でよくある悲劇。`ADODB.Stream`と`MSXML2.XMLHTTP`を適当に組み合わせたスクリプトで、数百MBのファイルを落とそうとして「メモリ不足」で落ちる、あるいは「ファイルサイズが足りないのに完了判定される」。

VBScriptはレガシーと言われるが、Windows環境下で外部依存なしに自動化を完遂できる強力な武器だ。ただし、「メモリ管理」と「非同期的なデータの揺らぎ」を制御できなければ、それはただの時限爆弾である。

本稿では、プロフェッショナルが実務で採用する、堅牢かつ安全なダウンロード・アーキテクチャを伝授する。

1. なぜ「一括読み込み」は失敗するのか

初心者が書くコードの典型はこれだ。

‘ 絶対にやってはいけないアンチパターン
Set objHTTP = CreateObject(“MSXML2.XMLHTTP”)
objHTTP.Open “GET”, url, False
objHTTP.Send
‘ 応答をそのままファイルに書き込む
objStream.Write objHTTP.ResponseBody

`objHTTP.ResponseBody`は、データをメモリ上に一気に展開する。ファイルサイズが100MBを超えれば、VBScriptの実行環境(WScript.exe)のメモリ空間を圧迫し、不安定になるのは必然だ。「ストリームを意識しないコード」は、業務自動化の敵である。

2. 堅牢なダウンロードを支える3つの鉄則

1. ストリームのバイナリモード固定: `Type = 1 (adTypeBinary)` を徹底すること。これ以外は文字化けとデータ破損の温床となる。
2. Content-Lengthの検証: ダウンロード後に `FileSize` と `Content-Length` を比較せよ。これを行わない限り、ネットワーク遮断による「不完全なファイル」を正常とみなしてしまう。
3. オブジェクトの解放順序: 実行順序ではなく、メモリ開放順序を意識せよ。`Nothing`代入は単なる儀式ではなく、COM参照カウンタへの明示的な意思表示だ。

3. 実装:プロダクション・レベルのダウンロード・スクリプト

以下は、業務でそのまま利用可能な、堅牢性を重視したテンプレートである。

Option Explicit

‘ 実行用サブルーチン
Call DownloadFile(“http://example.com/largefile.zip”, “C:\Temp\downloaded.zip”)

Sub DownloadFile(strUrl, strSavePath)
Dim objHTTP, objStream, objFSO

‘ 1. HTTPリクエストの初期化
Set objHTTP = CreateObject(“MSXML2.XMLHTTP”)
objHTTP.Open “GET”, strUrl, False
objHTTP.Send

‘ ステータスコードの検証 (200以外は即時終了)
If objHTTP.Status <> 200 Then
WScript.Echo “Error: HTTP ” & objHTTP.Status
Exit Sub
End If

‘ 2. ADODB.Streamによるバイナリ書き込み
Set objStream = CreateObject(“ADODB.Stream”)
objStream.Type = 1 ‘ adTypeBinary
objStream.Open
objStream.Write objHTTP.ResponseBody
objStream.SaveToFile strSavePath, 2 ‘ adSaveCreateOverWrite
objStream.Close

‘ 3. ダウンロード妥当性チェック
Set objFSO = CreateObject(“Scripting.FileSystemObject”)
Dim expectedSize, actualSize
expectedSize = CLng(objHTTP.getResponseHeader(“Content-Length”))
actualSize = objFSO.GetFile(strSavePath).Size

If expectedSize = actualSize Then
WScript.Echo “Success: ファイルの整合性を確認しました。”
Else
WScript.Echo “Warning: サイズ不一致。破損の可能性があります。”
End If

‘ メモリ解放の儀式
Set objStream = Nothing
Set objHTTP = Nothing
Set objFSO = Nothing
End Sub

4. プロの視点:さらなる高みを目指すために

このコードは、一般的な業務利用では十分な堅牢性を持つ。しかし、さらに大規模なファイル(GB単位)を扱う場合、`MSXML2.XMLHTTP`の限界に直面する。その場合は、`WinHttp.WinHttpRequest.5.1`への切り替えを検討せよ。

  • WinHttpの利点: より厳格なHTTPヘッダー制御が可能であり、タイムアウト設定も柔軟だ。ネットワーク接続が不安定な環境下では、`XMLHTTP`よりも遥かに高い生存能力を示す。
  • データベース連携の注意: ダウンロードしたファイルをDBのBLOB列に格納する場合、VBScriptで読み込む際にファイルサイズがメモリ制限(2GBの壁)を超えないか常に監視せよ。巨大なバイナリはDBに置かず、パスのみを記録し、ファイルシステムで管理するのが「正解」である。

最後に:コードは「保守」されて初めて価値が出る

VBScriptは「動けばいい」という考え方で書かれがちだが、それはプロの仕事ではない。なぜその定数を使ったのか、なぜその順番で解放するのか。その理由を言語化できる人間だけが、システムを止めずに業務を自動化できる。

このスクリプトを、あなたの自動化ツールボックスの「核」として活用してほしい。現場の課題を解決するのは、派手なライブラリではなく、こうした堅牢な基礎の積み重ねだ。

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