こんにちは!VBScriptの世界へようこそ。
マクロの記録ボタンを押すだけの世界から一歩抜け出し、「本物のスクリプト制御」を手にしたいあなたへ。今回は、プロの現場でもうならせる「プロセス間の高速データ共有」という少しディープで最高にクールなテクニックをお伝えします。
「複数のVBScript同士で、ファイルを一切作らずにデータをやり取りしたい」
そんな無茶ぶりをスマートに解決するのが、Windowsが持つ「Volatile(揮発性)環境変数」です。
ここをクリアすれば、あなたのVBScriptのスキルは間違いなく一段上のステージに到達します。さあ、一緒に扉を開けましょう!
—
1. なぜ「ファイルを使わない」必要があるのか?
VBScriptで複数のプログラム(プロセス)が連携するとき、よくあるアプローチは「テキストファイルに書き込んで、別のスクリプトがそれを読み取る」という方法です。
しかし、現場のシステムではこんな問題が起きます。
- I/Oのボトルネック: ハードディスクやSSDへの書き込み・読み込みは、メモリ上の処理に比べて圧倒的に遅い。
- 排他制御の地獄: 「書き込み中」のファイルを別のスクリプトが読みに行き、`エラー 70: 書き込みできません` が発生してスクリプトがクラッシュする。
- ゴミの山: 処理が終わった後、一時ファイルの消し忘れでストレージが汚染される。
ここで登場するのが、Windowsのメモリ上にデータを保持する「Volatile(揮発性)環境変数」です。OSが再起動すれば綺麗に消える、まさに一時的なデータ共有の特等席。これを`WScript.Shell`経由で極限までスマートに操ります。
—
2. Volatile環境変数の仕組みとWScript.Shellの魔法
Windowsの環境変数には、通常のものとは別に、レジストリの特殊な領域(`HKCU\Volatile Environment`など)に展開される「プロセス(セッション)スコープの揮発性変数」が存在します。
WScript.Shellオブジェクトを使うと、この領域に超高速でアクセスできます。
基本的なアプローチ
1. 書き込み側: 環境変数に一時的なステータス(例:`”STATUS=RUNNING”`)を書き込む。
2. 読み取り側: その環境変数を瞬時に読み取り、現在の状態を把握する。
ファイルアクセスが一切発生しないため、爆速かつ安全(排他エラー知らず)です。
—
3. 実践!プロセス間データ共有スクリプト
百聞は一見に如かず。実際に2つのスクリプトを動かしてみましょう。
今回は、「親スクリプトが処理の進捗(ステータス)をVolatile環境変数に書き込み、子(または別タスク)スクリプトがそれをリアルタイムに監視する」というシナリオです。
スクリプト①:データを書き込む側(`producer.vbs`)
まずは、データを送信(生産)するメインのスクリプトです。
‘ ==============================================================================
‘ スクリプト名: producer.vbs
‘ 概要: Volatile環境変数にステータスを書き込み続ける親プロセス
‘ ==============================================================================
Option Explicit
Dim wshShell, i
Set wshShell = CreateObject(“WScript.Shell”)
WScript.Echo “— データ送信(生産)プロセスを開始します —”
‘ ダミーの処理ループ(全5ステップ)
For i = 1 To 5
‘ 1. Volatile環境変数に現在の進捗を書き込む
‘ ※ 通常の環境変数と違い、Volatile領域を意識したキー操作を行います
wshShell.Environment(“User”)(“MY_APP_STATUS”) = “STEP_” & i & “_PROCESSING”
WScript.Echo “[親] ステータスを更新しました: STEP_” & i
‘ 処理のシミュレーション(2秒待機)
WScript.Sleep 2000
Next
‘ 2. 処理完了の合図を書き込む
wshShell.Environment(“User”)(“MY_APP_STATUS”) = “COMPLETED”
WScript.Echo “[親] 全ての処理が完了しました。”
Set wshShell = Nothing
スクリプト②:データを監視・読み取る側(`consumer.vbs`)
次に、別の独立したプロセスとして動き、親の状況をリアルタイムで覗き見るスクリプトです。
‘ ==============================================================================
‘ スクリプト名: consumer.vbs
‘ 概要: Volatile環境変数からステータスを高速に読み取る子プロセス
‘ ==============================================================================
Option Explicit
Dim wshShell, currentStatus, isRunning
Set wshShell = CreateObject(“WScript.Shell”)
WScript.Echo “— ステータス監視プロセスを開始します —”
isRunning = True
Do While isRunning
‘ Volatile環境変数から値を取得
currentStatus = wshShell.Environment(“User”)(“MY_APP_STATUS”)
‘ 値が空(まだ設定されていない)場合のハンドリング
If currentStatus = “” Then
currentStatus = “WAITING…”
End If
WScript.Echo “[子] 現在のステータス検知: ” & currentStatus
‘ 完了ステータスを検知したらループを抜ける
If currentStatus = “COMPLETED” Then
WScript.Echo “[子] 親プロセスの完了を確認しました。監視を終了します。”
isRunning = False
Else
‘ 1秒間隔でポーリング(監視)
WScript.Sleep 1000
End If
Loop
‘ 後始末(必要に応じて環境変数をクリア)
wshShell.Environment(“User”)(“MY_APP_STATUS”) = “IDLE”
Set wshShell = Nothing
💡 実行のコツ
1. コマンドプロンプトを2つ立ち上げます。
2. 片方で `cscript consumer.vbs` を実行して待機状態にします。
3. もう片方で `cscript producer.vbs` を実行します。
4. ファイルを一切使わず、コンソール上でリアルタイムにステータスが同期されていく感動を味わってください!
—
4. 陥りやすい罠とエンジニアの知見(注意点)
この手法は非常に強力ですが、VBScriptのライフサイクルやWindowsの仕様を知らないと、思わぬハマりポイントに遭遇します。
⚠️ 罠1: スコープの選択ミス
`wshShell.Environment(“Process”)` は、そのプロセス内だけで有効なため、別のプロセスとは共有できません。
必ず `”User”` または `”System”` スコープを指定してください(※通常は権限の都合上 `”User”` が安全です)。
⚠️ 罠2: ゴミデータの残留
スクリプトが異常終了(エラー落ち)した場合、環境変数に古いステータス(例:`COMPLETED` にならず `RUNNING` のまま)が残り続けます。
実務で使う場合は、プロセスの最初で必ず環境変数を初期化(リセット)する、または処理の最後に確実にクリーンアップする防衛的プログラミングを心がけましょう。
—
まとめ:ここをクリアすれば、あなたはもう初心者じゃない!
今回は、`WScript.Shell` と環境変数を組み合わせた、ファイルレスなプロセス間データ共有の極意をお伝えしました。
- ファイルI/Oの排除による圧倒的なパフォーマンスと安定性
- 独立したVBScript同士がメモリを介して会話する仕組み
ここをマスターしたあなたは、単なる「VBScriptの自動化スクリプトを書く人」から、「Windows環境をロジカルに制御するシステムエンジニア」へとステップアップしています。
日々の業務自動化を、もっとエレガントに、もっとスピーディに。
VBScriptの奥深い世界を、これからも一緒に楽しんでいきましょう!
