tk3.biz
ブログ一覧に戻る Back to Blog

機密コードをクラウドに出さずにAIでレビューする(ローカルLLM × dev-orchestra) 機密コードをクラウドに出さずにAIでレビューする(ローカルLLM × dev-orchestra)

AIローカルLLMコードレビューdev-orchestraセキュリティ

はじめに

AI にコードレビューをさせると、自分では気づけないバグが見つかります。 3 つの AI にレビューさせた回では、自分で書いた 1,418 行から実バグが 11 件出ました。

ただ、クラウドの AI にコードを送れない場面があります。

  • 業務のコードで、社外のサービスに送ることが契約や規程で禁じられている
  • 個人情報や認証情報に近い処理が含まれている
  • まだ公開していない製品のコード

そういうコードでも、手元の PC の中だけでAI にレビューさせる方法をまとめます。 使うのは、ミニPCで動かしているローカル LLM(Qwen3.6-35B-A3B)と、 複数の AI にレビューを分担させるツール dev-orchestra です。

コードがどこまで出ていくかの2パターン。A. ローカルで完結する場合は、ターミナルからdev-orchestraを直接実行し、--onlyでローカルLLMだけに絞るので、差分はPCの中から出ない。B. クラウドと併用する場合は、dev-orchestraが全レビュアーに差分を渡し、クラウドのAI(Claude・Codex)に差分が出る。ローカルLLMは3つ目の意見になる。注意として、dev-orchestraをAIのエージェントから呼ぶと、そのAIがコードを読む

方針: 2 つの使い方を分ける

A. ローカルで完結B. クラウドと併用
向いているコード社外に出せないもの公開してよいもの
レビュアーローカル LLM だけクラウドの AI + ローカル LLM
コードの行き先PC の中だけクラウドにも送られる
見つかる量少なめ多い

機密のものは A、それ以外は B。 1 つの仕組みで、この 2 つを切り替えられるようにします。

構成

dev-orchestra の「プロバイダ」は、CLI をラップする設計です。API を直接叩く口がありません。 そこで、プロンプトを標準入力で受けて答えを標準出力に返すだけの薄い CLI を挟みます。

dev-orchestra
  └─ プロバイダ localllm(ユーザープロバイダとして登録)
       └─ local-llm.cmd → local-llm.py(stdin → API → stdout)
            └─ llama-server(127.0.0.1:8080、この PC の中)

dev-orchestra 0.9.0 から、プラグイン本体に手を入れずに独自のプロバイダを足せる仕組み(ユーザープロバイダ)が入りました。 アダプタは dev-orchestra の設定フォルダに置くので、プラグインを更新しても消えません。 作り方の詳細はレビュアーに追加した回に書いています。

手順

1. アダプタを入れて、レビュアーとして登録する

アダプタ(localllm.py)と、プロンプトを中継する薄い CLI の中身は、 レビュアーに追加した回で説明しています。 ここでは、それを dev-orchestra の設定フォルダ(providers)に置いた前提で進めます。

# アダプタを dev-orchestra の設定フォルダに入れる(私の環境ではインストーラを Python で書いた)
python integrations\dev-orchestra\install.py

# プラグインの場所(バージョン番号として比べて、いちばん新しいもの)
$P = (Get-ChildItem "$env:USERPROFILE\.claude\plugins\cache\dev-orchestra\dev-orchestra" -Directory |
      Sort-Object { [version]$_.Name } -Descending | Select-Object -First 1).FullName

# レビュアーとして追加し、名前とモデルを付ける
python "$P\scripts\dev_orchestra.py" reviewer add --provider localllm --role general
python "$P\scripts\dev_orchestra.py" reviewer list          # 追加された番号を確かめる
python "$P\scripts\dev_orchestra.py" reviewer set 3 --model qwen3.6-35b-a3b --id localllm-qwen

reviewer set の番号は、reviewer list で確かめたものに置き換えてください。

インストーラは Python で書いてあります。 dev-orchestra が Microsoft Store 版の Python で動いている場合、 Store 版は %APPDATA% を別の場所に振り替えるので、PowerShell でコピーしたファイルは dev-orchestra から見えません。 読む側と同じ Python で書き込めば、振り替えの有無に関係なく一致します。

2. 機密のコードは、ターミナルから直接、ローカルだけでレビューする

python "$P\scripts\dev_orchestra.py" review snapshot
python "$P\scripts\dev_orchestra.py" state record test ok
python "$P\scripts\dev_orchestra.py" review run --only localllm-qwen

--only でレビュアーを絞るのが肝です。付け忘れると、登録してある全レビュアー(クラウドの AI を含む)に差分が送られます。

結果は dev-orchestra の統合ファイルに書き出されるので、それを自分で読んで採否を決めます。

3. 公開してよいコードは、全員でレビューする

python "$P\scripts\dev_orchestra.py" review run

クラウドの AI 2 つとローカル LLM の、3 つの意見が揃います。

最大の落とし穴: 呼び出し元の AI がコードを読む

dev-orchestra は、Claude Code などの AI のエージェントから呼び出して使うこともできます。 その場合、呼び出した AI 自身が、レビューの対象のコードを読みます。

レビュアーをローカル LLM だけに絞っても、呼び出し元がクラウドの AI なら、コードはクラウドに出ていきます。

機密のコードを扱うときは、AI のエージェントを通さず、ターミナルから dev-orchestra のコマンドを直接実行してください。 上の図の A が成り立つのは、この条件のときだけです。

ローカル LLM のレビューの実力

では、ローカル LLM だけでどこまで見つけられるのか。2 つの計測があります。

わざと入れたバグは見つけた

関数に 2 つの欠陥を仕込んで、レビューさせました。

仕込んだ欠陥結果
ガードを消して ZeroDivisionError が起きる検出(critical)
[:n+1] のオフバイワン検出(high)

所要時間は 29 秒。要求した出力の形式も守れていました。

実際のコードでは、6 件中 1 件だった

自分で書いた 1,418 行を、クラウドの AI 2 つとローカル LLM にレビューさせたときの結果です。

レビュアー指摘採用却下重複
Claude6600
Codex6402
ローカル LLM6150

ローカル LLM の却下 5 件は、「〜の可能性がある」で終わる推測の指摘が多く、 中には自分の指摘と矛盾しているものもありました。 採用した 1 件(エラー応答の本文を握り潰している件)は、まっとうな指摘です。

見つかる量と正確さは、クラウドの AI に及びません。 これは正直に書いておきます。

なぜ差が出るのか

いちばん大きいのは、見えている範囲の違いです。

クラウドの AI(エージェント型)ローカル LLM
見えるもの差分に加えて、関連ファイルを自分で読みに行ける渡された差分だけ
できる指摘「この関数の呼び出し元で壊れる」差分の中で閉じた指摘

ローカル LLM の役割は、あくまでレビュアーです。 ファイルを読み書きできないので、設計や実装を任せる用途には向きません(アダプタでも実装の役割は断るようにしています)。

それでもローカルで回す価値

観点ローカル LLM だけのレビュー
コードの行き先PC の外に出ない
費用電気代だけ。何回回しても課金されない
見つかる量クラウドより少ない
手間推測の指摘を読んで却下する手間が増える

「クラウドに出せないから、AI のレビューを諦める」よりは、ずっと良いと考えています。 わざと入れた典型的なバグは見つけられたので、見落としやすい単純なミスの網としては働きます。

長い差分を扱うときの注意

  • コンテキスト長: 1,400 行・62 KB の差分で 19,303 トークンになり、16K の設定では断られた。-c 65536 にしてある
  • 読み込み時間: 3 万トークンの差分なら 2〜3 分。レビューを回すたびにかかる
  • 2 回目は速いとは限らない: 同じ文書への質問なら読み直しは末尾だけで済むが、差分が変われば読み直しになる

まとめ

  • 機密のコードはローカル LLM だけ、公開してよいものはクラウドと併用、と使い分ける
  • dev-orchestra のユーザープロバイダでローカル LLM を登録し、--only でレビュアーを絞る
  • AI のエージェントから呼ぶと、その AI がコードを読む。 機密のものはターミナルから直接実行する
  • ローカル LLM は、仕込んだバグ 2 件は見つけたが、実コードでは 6 件中 1 件。網としては働くが、クラウドの代わりにはならない
  • それでも、コードを外に出さずに AI の目を通せるのは大きい

関連記事 Related Posts

自分が書いた1418行を3つのAIにレビューさせたら、実バグが11件出た 自分が書いた1418行を3つのAIにレビューさせたら、実バグが11件出た

Claude・Codex・ローカルQwenの3枚に、自分で書いて自分で動かしていたスクリプトをレビューさせました。3件は自力では気づけないもので、1件は「レビュー結果を集計するスクリプト自体」のバグでした。一方で、3枚とも見逃した欠陥もあります。 Claude・Codex・ローカルQwenの3枚に、自分で書いて自分で動かしていたスクリプトをレビューさせました。3件は自力では気づけないもので、1件は「レビュー結果を集計するスクリプト自体」のバグでした。一方で、3枚とも見逃した欠陥もあります。

ローカルLLMをdev-orchestraのコードレビュアーに追加してみた ローカルLLMをdev-orchestraのコードレビュアーに追加してみた

自宅PCで動かしているQwenを、複数モデルで独立レビューするdev-orchestraの3枚目のレビュアーとして組み込みました。プロバイダがAPIではなくCLIをラップする設計だったので、薄いCLIを1枚挟んで繋いだ話です。翌日の公式対応と、Store版Pythonのパス罠についても追記しました。 自宅PCで動かしているQwenを、複数モデルで独立レビューするdev-orchestraの3枚目のレビュアーとして組み込みました。プロバイダがAPIではなくCLIをラップする設計だったので、薄いCLIを1枚挟んで繋いだ話です。翌日の公式対応と、Store版Pythonのパス罠についても追記しました。

WSLからホストのローカルLLMを使う方法を調べて、やめた WSLからホストのローカルLLMを使う方法を調べて、やめた

WSL上の開発でWindowsホストのローカルLLMをレビュアーとして使いたい。経路は2つあり、どちらも実現はできます。ただし片方は安全性を、もう片方は信頼性を差し出す必要があったので見送りました。その判断の記録です。 WSL上の開発でWindowsホストのローカルLLMをレビュアーとして使いたい。経路は2つあり、どちらも実現はできます。ただし片方は安全性を、もう片方は信頼性を差し出す必要があったので見送りました。その判断の記録です。