0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

(告知編)自作の VBA 管理ツールを更新 ── Excel MCP を参考に、開いたままのブックを触れるようにした話

0
Last updated at Posted at 2026-06-13

はじめに

この連載で何度か紹介してきた自作ツール vba_manager.py(GitHub で公開中)を大きく更新したので、その告知です。あわせて、使ってみて分かった「これで何が変わったのか」の話をします。

もともとこのツールは、Excel の VBA コードを管理するためのものでした。マクロの一覧を出す、コードを取り出す、直して戻す。コマンドにして 9 個、それだけの道具でした。

今回の更新で、シートそのものを操作する機能を足して、約 50 コマンドになりました。

きっかけは Excel MCP

きっかけは、ステファンさん(Stefan Broenner さん)が公開している Excel MCP(sbroenne/mcp-server-excel)を触ったことです。COM 経由で Excel を操作する MCP サーバーで、範囲編集・書式・グラフ・ピボット・PowerQuery まで一通りそろっています。よくできています。

ただ、Excel MCP は「対象ファイルは Excel で閉じておく」前提の設計になっています。COM の排他制御を考えれば確実で正しい判断だと思います。一方、私は秀.xlsm をアドインとして常時開いていますし、作業ファイルも開きっぱなしで触る流儀です。

そこで、Excel MCP の機能を参考にしながら、「開いたままのブック」を対象に同じようなことができる機能を、Claude Code との会話で vba_manager.py に足していきました。vba_manager.py はもともと GetActiveObject で起動中の Excel に横から接続する作りなので、土台はそのまま使えました。

何を足したか

大きく三段階あります。

読む系(AIの目) ── シートの状態をテキストや画像で確認する

py vba_manager.py read-range A1:D10      # セル値をテキスト格子で
py vba_manager.py sheet-info             # シート構成・使用範囲
py vba_manager.py screenshot A1:H30     # 範囲をPNGに

書く系(AIの手) ── 値・書式・行列・検索置換・印刷設定など

py vba_manager.py write-range C1 "=SUM(A1:A10)"
py vba_manager.py format-range A1:D1 --bold --bg "#FFFF00"
py vba_manager.py find-replace   A1:Z99

重量級 ── グラフ・ピボット・スライサー・PowerQuery・データモデル

py vba_manager.py chart create A1:B5 --type column --title "月別売上"
py vba_manager.py pivot create 元データ!A1:C100 --rows 部門 --values 売上
py vba_manager.py powerquery load 商品マスタ --to sheet

ファイルパスを省略すると、いま Excel で開いているアクティブなブックが自動的に対象になります。

一番変わったのは「会話の中身」

機能一覧より、こちらが本題かもしれません。

この連載の第1回は「会話するだけでマクロが直る」という話でした。あれは今でも本当です。ただ、あの頃の AI が見ていたのはコードだけでした。コードを読み、コードの理屈で直す。マクロが実際に操作するシートがどうなっているかは、私が言葉で説明するしかありませんでした。

目と手が付くと、ここが変わります。実際にあった例を一つ。

先日、公開している「ファイル一覧」(フォルダ配下のファイルを Excel に一覧化する自作ツール)のマクロを AI にレビューさせました。検索マクロの中に、こういう行があります。

wsTarget.Range("A1").AutoFilter Field:=1, Criteria1:="*" & CTV & "*"

コードだけ読めば、これは A 列を検索しているように見えます。ところがこのシートの A 列は連番で、ファイル名は B 列です。つまり「検索ワードを番号列に当てている=このマクロは壊れている」という指摘になるはずでした。

AI は指摘する前に、シートを見ました。sheet-info でシート構成を確認し、ヘッダー行を読み、さらに実際にフィルタをかけて挙動を測りました。すると、シートには既にオートフィルタが B 列起点(B1:F)で張られていて、Field:=1 は B 列=ファイル名に効いていることが分かりました。7.8 万行の実データに "md" でフィルタすると 1,773 件。マクロは正しく動いていました。

補足:Field:=1 がなぜ B 列に効くのか

AutoFilter の Field は、シートの列番号ではなくフィルタ範囲の左端から数えた相対番号です。

シートの列 A(番号) B(ファイル名) C(フォルダ) D(更新日時)
フィルタ範囲 B1:F の中では ―(範囲外) Field 1 Field 2 Field 3

このシートには既にフィルタが B 列起点(B1:F) で張られていたため、Field:=1
A 列ではなく B 列=ファイル名に効いていました。つまりこのコードが正しいかどうかは、
コードだけでは決まらず、いまシートにどんな範囲でフィルタが張られているかで決まります。
だから「実物を見てから物を言う」が効いた、という話です。

結果、指摘はこうなりました ──「バグではない。ただし既存フィルタへの暗黙の依存なので、誰かがフィルタを解除すると検索が静かに 0 件になる。範囲を明示した方がいい」。修正後は、AI が自分でその検索マクロを実行して、同じ 1,773 件が出ることまで確認してから「直りました」と言ってきました。

コードしか見えない AI なら、正常なコードを「バグ」と直して本当のバグを作ったか、何も気づかず素通りしたか、どちらかだったと思います。「コードとして正しいか」ではなく「実物と整合しているか」を確かめてから物を言うようになった、ということです。コードの中の Offset(0, 4) が何を指すかも、シートを見れば一目で分かります(B列のファイル名から4つ右=F列のパス)。会話するだけでマクロが直る、の「会話」の中身が、別物に濃くなりました。

Excel MCP との棲み分け

競合ではなく使い分けの話です。

  • 閉じたファイルを確実に一括処理する → Excel MCP
  • 開いたままのブックをその場で見て・触って・確かめる → vba_manager.py

開いたままを触る方式には引き換えもあります。プログラム経由の変更は Excel の Undo 履歴を消します。なので vba_manager の編集系コマンドは既定では保存しません。Excel の画面で確認して、良ければ保存、ダメなら保存せずに閉じれば変更を破棄できます。Undo の代わりはそうやって確保しています。

安全まわり

地味な部分ですが、今回の更新で一緒に入れたものです。

  • 置換系コマンドは実行前に自動バックアップを取ります(ブック全体+モジュール単位の二段)
  • .bas ファイルの文字コード事故(CP932 を UTF-8 で上書きして日本語が壊れるやつ)を、インポート前に機械的に検知して止めます
  • Excel が未起動の状態でパス指定すると自動化用の Excel が新しく立ち上がりますが、これにはアドインや PERSONAL.XLSB が読み込まれません。普段使いには手動起動した Excel を使ってください(ツールが警告を出します)

おわりに

使い方の詳細は README にまとめてあります。VBA のコード管理だけが目的なら今までどおり 9 個のコマンドで足りますし、そこから先はぶら下がっているだけなので、邪魔にはならないはずです。

ユーチューブ
https://www.youtube.com/watch?v=fjtYmq7UV9M

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?