VBAで複数のファイルをバックアップとしてZIP形式に圧縮・保存したい場合、まずその入れ物となる「空のZIPファイル」を作成する必要があります。
VBAには「ZIPファイルを作成する」という直接的な命令はありませんが、ZIPファイルの構造を利用した少し特殊な方法で、中身が何もない、有効なZIPファイルを新規作成することが可能です。
この記事では、そのテクニックと、作成したZIPファイルに実際にファイルを追加する方法までを解説します。
完成したVBAコード
以下が、指定した場所に「Backup.zip」という名前の空のZIPファイルを作成するVBAコードです。
Sub CreateEmptyZipFile()
' 変数を宣言します
Dim zipFilePath As String
Dim fileNumber As Integer
Dim zipHeader() As Byte ' ZIPファイルのヘッダー情報
' 作成するZIPファイルのパスを指定
zipFilePath = ThisWorkbook.Path & "\Backup.zip"
' --- 1. 空のZIPファイルとして成立するための最小限のバイナリデータを作成 ---
' ZIPファイルの仕様である「End of Central Directory record」の22バイト
zipHeader = StrConv("PK" & Chr(5) & Chr(6) & String(18, 0), vbFromUnicode)
' --- 2. バイナリモードでファイルを開き、ヘッダーを書き込む ---
fileNumber = FreeFile ' 空いているファイル番号を取得
Open zipFilePath For Binary As #fileNumber
Put #fileNumber, , zipHeader
Close #fileNumber
MsgBox "空のZIPファイルを作成しました。" & vbCrLf & zipFilePath
End Sub
コードのポイント解説
① ZIPファイルの「ヘッダー情報」
zipHeader = StrConv("PK" & Chr(5) & Chr(6) & String(18, 0), vbFromUnicode)
このコードの核心部分であり、少し不思議に見えるかもしれません。これは、ZIPファイルの末尾に必ず記録される**「End of Central Directory record (EOCD)」**という22バイトの識別情報を作成しています。
"PK" & Chr(5) & Chr(6)
: ZIPファイルが持つ固有の署名(シグネチャ)の一部です。P
(80)K
(75) と 5, 6 というバイト列が「これはEOCDですよ」という目印になります。String(18, 0)
: EOCDレコードの残りの18バイト部分です。ここにはファイル数などの情報が入りますが、空のZIPファイルなので、すべてゼロ(Chr(0)
)で埋めます。StrConv(..., vbFromUnicode)
: VBAの文字列を、ファイルに書き込むための純粋なバイト配列に変換しています。
この22バイトのデータを書き込むだけで、Windowsはそれを「中身が0個の、有効なZIPファイル」として認識してくれます。
② バイナリモードでの書き込み
Open zipFilePath For Binary As #fileNumber
Put #fileNumber, , zipHeader
Close #fileNumber
Open ... For Binary
は、テキストではなく、バイトデータを直接読み書きするためのファイルオープンモードです。Put
ステートメントを使って、作成したヘッダー情報(バイト配列)をファイルに直接書き込んでいます。
【応用】作成したZIPファイルにファイルを追加する方法
空のZIPファイルを作成しただけでは意味がありません。実際にファイルを追加するには、Shell.Application
オブジェクトを使うのが一般的です。
'参照設定: Microsoft Shell Controls And Automation
Sub AddFilesToZip()
Dim shellApp As Object
Dim zipFilePath As String
Dim folderToZipPath As String
' 事前に空のZIPファイルを作成しておく
CreateEmptyZipFile
zipFilePath = ThisWorkbook.Path & "\Backup.zip"
folderToZipPath = ThisWorkbook.Path & "\SourceFolder" ' ZIPに追加したいファイルが入っているフォルダ
Set shellApp = CreateObject("Shell.Application")
' ZIPファイルの中身(名前空間)に、指定したフォルダの中身をコピーする
shellApp.Namespace(zipFilePath).CopyHere shellApp.Namespace(folderToZipPath).Items
MsgBox "ZIPファイルにファイルを追加しました。"
End Sub
このコードは、SourceFolder
というフォルダの中にあるすべてのファイルを、先ほど作成したBackup.zip
の中に圧縮して追加します。
まとめ
VBAでZIPファイルを作成・操作する手順は、以下の2段階で行うのが一般的です。
- この記事で紹介したバイナリ書き込みのテクニックを使い、まず空のZIPファイルを器として作成する。
Shell.Application
オブジェクトを使い、作成したZIPファイルに目的のファイルやフォルダをコピーしていく。
この2つのテクニックを組み合わせることで、バックアップの作成や、複数のレポートファイルを一つにまとめて圧縮するといった、ファイル操作の自動化が実現できます。