こんにちは!開発現場で日夜、自動化の仕組みを追い求めている先輩エンジニアです。
マクロの記録や単純なバッチ処理から一歩抜け出して、「本格的なシステム自動化をしたい!」と思ったとき、真っ先に壁として立ちふさがるのがVBScript(Visual Basic Scripting Edition)ですよね。
今回は、VBScriptの真骨頂であるFSO(FileSystemObject)を駆使し、巨大なファイル本体は一切コピーせずに、フォルダの階層構造(ディレクトリツリー)だけを完璧にミラーリング(複製)する「スケルトン構造複製ツール」の作り方を解説します。
「テラバイト級のファイルサーバーの整理をしたいけれど、フォルダ構造だけ先に新サーバーへ再現してアクセス権のテストをしたい…」そんな現場のリアルな課題を1発で解決できる実践的な内容です。ここをクリアすれば、あなたもFSOの扱いにおいて中級者以上の実力が身につきますよ。それでは、一緒に紐解いていきましょう!
—
なぜ「スケルトン構造複製」が必要なのか?
ファイルサーバーの移行や、定期的なバックアップ先の事前準備を行う際、すべてのファイルをそのままコピーすると、膨大な時間とストレージ容量を消費してしまいます。
ここで私たちがやりたいのは、「ガワ(骨組み=スケルトン)」だけを瞬時に作ることです。
[コピー元 (Source)] [コピー先 (Destination)]
📁 2023年度 📁 2023年度
┣ 📄 巨大データ.zip ➔ ┣ (フォルダのみ)
┗ 📁 4月 ┗ 📁 4月
┣ 📄 決算書.xlsx ┣ (フォルダのみ)
┗ 📁 詳細 ┗ 📁 詳細
VBScriptのFSOを使えば、この複雑なツリー構造の再現を、わずか数十行のコードで実現できます。しかも、特別な開発環境は不要。Windowsのメモ帳さえあれば、今すぐ動かせます。
—
VBScript × FSO の基本戦略
今回のスクリプトの心臓部は、「再帰呼び出し(Recursive Call)」というプログラミングのテクニックです。
フォルダの中にフォルダがあり、さらにその中に……という階層構造に対し、同じ処理(フォルダの作成)を自分自身を呼び出しながら潜っていくことで、無限の深さを持つツリーにも完全に対応できます。
覚えておくべきFSOの主要パーツ
1. `Scripting.FileSystemObject`: すべての操作の起点となる司令塔オブジェクト。
2. `GetFolder(path)`: 指定したパスのフォルダオブジェクトを取得する。
3. `SubFolders` コレクション: あるフォルダの中にある「直下のフォルダたち」のリスト。
—
実装コード:スケルトン構造複製ツール
以下のコードをメモ帳に貼り付け、拡張子を `.vbs` (例: `SkeletonMirror.vbs`)として保存してください。
‘ ==============================================================================
‘ スケルトン構造複製ツール (SkeletonMirror.vbs)
‘ 概要: 指定したフォルダのディレクトリツリーのみを、実ファイルなしで複製します。
‘ 著者: 先輩エンジニア
‘ ==============================================================================
Option Explicit
Dim fso, sourcePath, destPath
‘ 1. FileSystemObjectの生成(ここがすべてのスタート地点です)
Set fso = CreateObject(“Scripting.FileSystemObject”)
‘ ==============================================================================
‘ 【設定エリア】ここを用途に合わせて書き換えてください
‘ ==============================================================================
sourcePath = “C:\Work\SourceFolder” ‘ コピー元のパス
destPath = “C:\Work\DestFolder” ‘ コピー先のパス
‘ ==============================================================================
‘ 実行前の存在確認
If Not fso.FolderExists(sourcePath) Then
MsgBox “コピー元のフォルダが存在しません:” & vbCrLf & sourcePath, vbCritical, “エラー”
WScript.Quit
End If
‘ 処理開始の時刻を記録
Dim startTime: startTime = Now
‘ 複製処理のメイン関数を呼び出し
On Error Resume Next
Call CopyFolderStructure(sourcePath, destPath, fso)
If Err.Number <> 0 Then
MsgBox “エラーが発生しました: ” & Err.Description, vbCritical, “予期せぬエラー”
Else
MsgBox “スケルトンの作成が完了しました!” & vbCrLf & _
“所要時間: ” & DateDiff(“s”, startTime, Now) & ” 秒”, vbInformation, “完了”
End If
Set fso = Nothing
WScript.Quit
‘ ==============================================================================
‘ 再帰的にフォルダ構造をコピーする核心的プロシージャ
‘ ==============================================================================
Sub CopyFolderStructure(srcPath, dstPath, fsoObj)
Dim srcFolder, subFolder, targetSubPath
‘ 1. コピー元フォルダオブジェクトを取得
Set srcFolder = fsoObj.GetFolder(srcPath)
‘ 2. コピー先のフォルダがなければ作成する(これがスケルトン作りのキモ)
If Not fsoObj.FolderExists(dstPath) Then
fsoObj.CreateFolder(dstPath)
WScript.Echo “作成: ” & dstPath ‘ 進行状況をコンソールに表示
End If
‘ 3. 現在のフォルダ内にあるサブフォルダをすべてループ処理(再帰の起点)
For Each subFolder In srcFolder.SubFolders
‘ コピー先での対応するサブフォルダのパスを組み立てる
targetSubPath = dstPath & “\” & subFolder.Name
‘ 自分自身を再度呼び出す(再帰呼び出し)
‘ これにより、何階層下であっても自動的に潜っていきます
Call CopyFolderStructure(subFolder.Path, targetSubPath, fsoObj)
Next
Set srcFolder = Nothing
End Sub
—
コードの読み解きポイント(ここが分かれば怖くない!)
1. `Option Explicit` のお約束
冒頭にあるこの宣言は、「変数の宣言を強制する」というプロフェッショナル必須の作法です。スペルミスによる意図しないバグを防ぐため、VBScriptを書くときは必ず記述しましょう。
2. 再帰呼び出しの魔法
`CopyFolderStructure` プロシージャの中で、自分自身を呼び出している部分に注目してください。
Call CopyFolderStructure(subFolder.Path, targetSubPath, fsoObj)
「フォルダを見つけたら、まず自分と同じ仕事をするプログラムにその中身を渡す」という発想です。これにより、人間が何階層あるか数える必要もなく、システムが勝手に一番深いところまで自動で掘り進んでくれます。
3. ファイルを一切触らないという選択
通常のファイルコピー(`CopyFile` や `CopyFolder` メソッド)は使いません。あえて `fsoObj.CreateFolder(dstPath)` で「フォルダを作る」動作だけに絞っているからこそ、重たいファイルコピー処理が完全にバイパスされ、爆速で動作するのです。
—
陥りやすい罠とエラー回避の知見
実務でVBScriptを扱う際、初心者が必ずと言っていいほどハマるポイントがあります。
トラップ 1: パスの末尾の「バックスラッシュ(¥マーク)」問題
フォルダパスを結合するとき、`C:\Folder` と `SubFolder` の間に `\` が抜けてしまう、あるいは `\` が二重になってしまう(`C:\Folder\\Sub`)エラーが頻発します。
今回のコードでは、`dstPath & “\” & subFolder.Name` と明示的に結合し、さらにFSOがパスの正規化をよしなに補正してくれる特性を利用しているため、このトラブルを回避しています。
トラップ 2: アクセス権限(パーミッション)エラー
社内サーバーなどを巡回させると、アクセス権がないフォルダ(System Volume Informationなど)にぶつかり、スクリプトが赤文字エラーで強制終了することがあります。
これを防ぐため、コード内には `On Error Resume Next` を仕込んでいます。これにより、万が一アクセス拒否されたフォルダに遭遇しても、エラーを無視して次のフォルダの処理へスマートに移行できます。
—
まとめ:VBScriptの基礎はこれでバッチリ!
今回は、FSOを使った高度なフォルダ構造のミラーリング手法を通じて、オブジェクトの操作、条件分岐、そして「再帰処理」の概念を解説しました。
一見古めかしく見えるVBScriptですが、Windows環境さえあれば追加のインストールなしで今すぐ動き、ちょっとした自動化ツールをサッと作るには世界一フットワークの軽い言語です。
「ここをクリアすれば、VBScriptの基本はバッチリですよ!」
ぜひ今回のコードをベースに、不要な古いログフォルダだけを自動削除する仕組みや、ファイル数・フォルダ数を集計する機能などにカスタマイズして、あなたの現場の業務効率化に役立ててください。
それでは、次の自動化の旅でお会いしましょう!
