この記事で分かること
- 前回の試み(ローカルLLMでClaudeCodeフレームワーク代替)がなぜ壁にぶつかったか
- 「代替」から「役割分担」への発想の転換とその根拠
- Claude Code(フロンティアLLM)をオーケストレーター、Gemma4:26(ローカルLLM)をワーカーとする構成の具体的な実装手順
- どのタスクをClaudeに任せ、どのタスクをGemmaに流すかの判断基準
- よくある落とし穴と対策
はじめに——前回の結末から
前回の記事で私は、Claude Code Maxの月額コストに疑問を感じ、「ローカルLLMでClaudeCodeフレームワーク全体を代替できないか」という実験を試みた。
結論は限定的な成功と決定的な壁だった。
Ollamaのチューニング(OLLAMA_NUM_GPU=999、OLLAMA_FLASH_ATTENTION=1などの環境変数)で推論速度の問題は解決できた。Qwen 3.6-35B MoEモデルが83 tok/sで動作し、Claude Codeのフレームワーク機能(CLAUDE.md・agents/・skills/・hooks/)もローカルLLMで一部機能することを確認できた。
しかし、どうしても越えられない壁があった——MCPが動かない。
MCPは Claude Code CLI の機能であり、
ローカルLLMを CLAUDE_API_KEY の代わりに使うだけでは現状では利用できない。
私がClaude Codeで構築しているRAGシステムはMCPを通じてRAGデータベースに接続している。MCPなしではRAGの根幹が失われる。現状の環境ではローカルLLMのみでの完全移行は諦めるしかなかった。
しかしすべてを諦める必要はないと考えた
ローカルLLMで全部出来ないなら簡単な処理だけでも手伝わせればいい
前提知識
本記事を読む前に以下の概念を確認しておいてください。
| 用語 | 意味 |
|---|---|
| Claude Code | Anthropicが提供するエージェント型コーディングツール。CLAUDE.mdでAIの行動を制御し、agents/・skills/・hooks/・memory/でワークフローを自動化できる |
| MCP(Model Context Protocol) | ClaudeがRAGや外部ツールを呼び出すための標準プロトコル。Claude Code CLIが接続を管理する。RAGデータベース・ブラウザ・ファイルシステムなどをClaudeに接続する仕組み |
| Ollama | ローカルLLMをAPIサーバーとして動かすためのツール。OpenAI互換のエンドポイントを提供し、様々なオープンソースモデルをローカルで実行できる |
| Gemma4:26 | GoogleのGemma 4シリーズのOllama向けモデル。マルチモーダル対応(テキスト・画像)でツールコールも利用可能。量子化版は約18GB、動作に約24GB VRAMが必要 |
| フロンティアLLM | OpenAI GPT-4oやAnthropic Claudeのような最先端モデル。高い推論・判断能力を持つが、API利用にはコストが発生する |
| オーケストレーター | 複数のエージェントやツールを指揮・調整する司令塔的なLLM。タスクの分解・割り当て・結果統合を担う |
なぜ「ローカルLLMで全部やる」は難しかったのか
Claude Codeフレームワークの機能は「誰が実行するか」で2つに分かれる
前回の実験で判明した最重要な事実。Claude Codeのフレームワーク機能は「CLIが実行する機能」と「LLMが実行する機能」に明確に分かれている。
実験から得た結論:
-
hooks/はローカルLLMでも動く(CLIが実行するため) - MCPはClaude Code CLIなしでは絶対に動かない
-
CLAUDE.md・agents/・skills/はローカルLLMの能力次第で品質が変わる
RAG接続が必要なシステムにとって「MCPが使えない」は致命傷だ。この制約は技術的チューニングでは解決できない。
ローカルLLMの能力的な限界
加えて、能力面での壁もある。前回の実験でQwen 3.6-35B MoEが速度的に実用的(83 tok/s)だったとはいえ、高次の判断は難しかった。
- 得意: 明確な指示に応答する、フォーマットに従って出力する
- 苦手: 複数ステップにまたがる自律的な推論、ツールの組み合わせ判断、曖昧な状況での意思決定
「指示通りに動く」のは得意でも「自律的に考えて判断する」のはフロンティアLLMに劣る。
今回はスペック的に余裕があり論理思考的なレスポンスが悪くない Gemma4:26B をローカルLLMに採用することにした。
本質的な問い: ローカルLLMに「全部やらせよう」とするから無理が出る。最初から「決まった作業をこなす」役割に特化させればいいのではないか?
アーキテクチャの転換——「代替」から「分業」へ
発想を180度変えた。
Before(前回の試み): ローカルLLMがClaudeを完全に代替する
ユーザー → ローカルLLM(全部やる)
↑ MCPが動かない / 複雑な推論が苦手
After(今回のアプローチ): Claudeが指揮を取り、ローカルLLMが特定タスクをこなす
ユーザー → Claude(判断・制御・MCP管理) → ローカルLLM(定型作業を実行)
↑ MCPもRAGも使える ↑ コストゼロで高速処理
この転換の核心は「それぞれのLLMが得意なことをやる」という当たり前の原則だ。
| 役割 | モデル | 担当領域 |
|---|---|---|
| オーケストレーター | Claude(フロンティアLLM) | 複雑な推論・計画立案・MCP連携・最終品質保証 |
| ワーカー | Gemma4:26(ローカルLLM) | テキスト整形・キーワード抽出・要約・分類など定型作業 |
全体アーキテクチャ
新しい構成を図で示す。MCPはClaudeの管轄に残したまま、Gemmaを「MCPを通じて呼ばれる側」に置くのがポイントだ。
設計の核心:
- MCPはClaudeの管轄のまま: ローカルLLMはMCPを「使う側」ではなく「MCPを通じて呼ばれる側」になる。これにより前回の壁(MCPが使えない)を完全に回避する
- Claudeが品質を保証する: ローカルLLMの出力はClaudeがレビュー・統合するため、精度の低い出力もClaudeが修正できる
- コスト最適化: 定型作業をGemmaに流すことで、Claudeのトークン消費を抑えられる
実装手順
ステップ1: Ollamaのセットアップと最適化
まずGemma4:26をOllamaで動かす。
# モデルの取得
ollama pull gemma4:26
# パフォーマンスチューニング(前回記事の知見)
export OLLAMA_NUM_GPU=999 # すべてのGPUを使用
export OLLAMA_FLASH_ATTENTION=1 # Flash Attentionを有効化
# 確認
ollama run gemma4:26 "こんにちは"
前回の実験で判明したGPU活用率の原則:VRAMの90%以下に収めること。この境界を超えるとCPUスピルオーバーが発生し、推論速度が実用域から5.8 tok/sまで急落する。
Gemma4:26(量子化版約18GB)は24GB VRAM環境で安全に動作する。2026年6月5日にQAT(Quantization-Aware Training)版の重みが追加されており、通常量子化と比べて精度と速度のバランスが改善されている。
ワーカー用途向けのModelfile設定:
# Modelfile.gemma4-worker
FROM gemma4:26
PARAMETER num_ctx 8192
PARAMETER num_predict 2048
PARAMETER temperature 0.3
ollama create gemma4-worker -f Modelfile.gemma4-worker
定型タスクに使うため、temperature 0.3で創造性より一貫性を優先している。コンテキスト長も8192に絞り、VRAMを節約した。
ステップ2: mcp-local-llm の導入
Claude CodeがローカルLLMを呼び出すためのブリッジとなるMCPサーバーを導入する。
mcp-local-llm は「Claudeが考え、ローカルモデルが雑用をこなす(Claude does the thinking, your local model does the grunt work)」というコンセプトで作られたMCPサーバーだ。
# GitHubから取得・セットアップ
git clone https://github.com/aplaceforallmystuff/mcp-local-llm
cd mcp-local-llm
npm install && npm run build
.claude/settings.jsonにMCPの設定を追加する:
{
"mcpServers": {
"local-llm": {
"command": "node",
"args": ["/path/to/mcp-local-llm/dist/index.js"],
"env": {
"OLLAMA_BASE_URL": "http://localhost:11434",
"DEFAULT_MODEL": "gemma4-worker"
}
}
}
}
動作確認は簡単だ:
# Claude Code 内で
/mcp
→ local-llm が一覧に表示されていれば接続成功
ステップ3: CLAUDE.md でタスク割り当てルールを明文化する
どのタスクをGemmaに委ねるかをCLAUDE.mdに書く。ここが今回の構成の肝だ。曖昧にしておくとClaudeが全部自分でやって節約効果がゼロになる。
## ローカルLLM(Gemma)への委譲ルール
以下のタスクは `mcp__local-llm__query` ツールを使って Gemma(gemma4-worker)に委譲すること。
自分(Claude)で処理してはならない。
### Gemmaに委譲するタスク(定型作業)
1. **テキスト整形・フォーマット変換**: Markdownへの変換、箇条書き整理、表形式への変換
2. **軽量な情報抽出**: テキストからのキーワード・日時・エンティティの抽出
3. **短いテキストの要約(入力1000文字以内)**: 単一ドキュメントの要約
4. **分類・タグ付け**: あらかじめ定義されたカテゴリへの分類
5. **重複チェック**: 複数テキストが同じ内容か否かの二値判定
### 自分(Claude)が担当するタスク
- 複数ステップにまたがる推論と意思決定
- MCPツールの組み合わせが必要な処理
- ユーザーへの最終回答生成
- Gemmaの出力の品質検証・修正
- 不明確な状況での判断
## Gemma出力の検証ルール
Gemmaの出力を使用する前に必ず確認すること:
1. 元テキストに存在しない事実・数値が混入していないか
2. 求めたフォーマットに合致しているか
不合格の場合はClaudeが自分で処理し直す。
タスク振り分けの判断フロー
どのタスクをどちらに流すか、実運用で使えるフローチャートを示す。
実際に試した結果、以下のタスク分類で安定して機能した。
| タスク種別 | Claude処理 | Gemma処理 | 判断理由 |
|---|---|---|---|
| 記事の章構成立案 | ✅ | 創造的判断・マルチステップ推論が必要 | |
| 執筆済み文章の箇条書き整形 | ✅ | フォーマット変換は定型作業 | |
| RAG検索結果の統合・分析 | ✅ | 複数ツール・複雑な推論が必要 | |
| 検索結果からのキーワード抽出 | ✅ | 単純な抽出タスク | |
| ユーザーへの最終回答生成 | ✅ | 品質担保にClaudeが必要 | |
| 中間データのJSON整形 | ✅ | フォーマット変換は定型作業 | |
| 複数文書の矛盾・重複検出 | ✅ | 高度な推論が必要 | |
| 単一ドキュメントの要約(短文) | ✅ | 短いテキストの要約は十分な精度 | |
| 意思決定・計画立案 | ✅ | オーケストレーター固有の役割 | |
| 重複の二値判定 | ✅ | 明確な定型タスク |
Gemma4:26の特性——何が得意で何が苦手か
Gemma 4はGoogleが開発したマルチモーダルモデルで、テキスト・画像の両入力に対応している。量子化版で約18GB、24GB VRAMのGPUで動作する。ツールコールも利用可能だ。
実際に使ってわかった特性を正直に書く:
得意なこと:
- 明確で短い指示への素直な応答
- フォーマット変換(JSON化・Markdown化・表形式化)
- 2000文字程度までのテキスト要約・抽出
- シンプルなツールコール(1〜2ツール程度)
苦手なこと:
- 長いコンテキストにわたる一貫した推論
- 複数のツールを自律的に判断して組み合わせること
- 曖昧な指示の解釈と補完
- 「何をすべきか」の計画立案
これはGemmaに限らずローカルLLM全般の傾向だ。この特性を踏まえると「ワーカーとしての役割」に特化させる設計が正解になる。
速度の参考値(前回実験の知見を転用、チューニング済みの環境):
| VRAM使用率 | 状態 | 推論速度 |
|---|---|---|
| ~90% | 安全圏 | 50〜80 tok/s程度 |
| 90〜100% | 注意 | 急激に低下 |
| 100%超 | CPU スピルオーバー | 5.8 tok/s前後(実用不可) |
Gemma4:26(量子化版18GB)を24GB VRAM環境で動かすと、VRAMの75%程度の使用率に収まり、安全圏で動作する。
よくある落とし穴と対策
落とし穴1: Gemmaへの委譲が多すぎる
コスト削減の動機から、Claudeが担うべきタスクまでGemmaに流してしまうと、出力品質が著しく落ちる。特に「最終回答の生成」をGemmaに任せると、事実確認の甘い回答がユーザーに届く。
対策: CLAUDE.mdの「委譲禁止リスト」に「ユーザーへの最終回答」「MCPツールの組み合わせが必要な処理」を必ず入れる。
落とし穴2: Ollamaサーバーが落ちているときのハンドリング
Claudeがmcp-local-llmを呼び出したときにOllamaサーバーが起動していないと、エラーで処理が止まる。
対策: hooks/を使ってClaude Codeセッション開始時にOllamaの起動を確認するスクリプトを仕込む。
#!/bin/bash
# .claude/hooks/pre-session.sh
if ! curl -s http://localhost:11434/api/tags > /dev/null 2>&1; then
echo "Ollamaサーバーを起動します..."
ollama serve &
sleep 3
echo "起動完了"
fi
落とし穴3: Gemmaの要約出力を無検証で使う
Gemma4:26は要約・抽出タスクで元文書にない内容を混入させることがある(いわゆるハルシネーション)。特に固有名詞・数値・日付の扱いが不安定だ。
対策: CLAUDE.mdに検証ルールを書くだけでなく、高リスクなデータ(数値・日付・固有名詞)が含まれる場合はGemmaに委譲しないようルールを追記する。
## 委譲禁止の条件(Gemmaに流してはならないケース)
- 出力に数値・日付・固有名詞が含まれる可能性があるタスク
- ユーザーに直接見せる成果物の最終生成
- 判断が曖昧でフォールバックロジックが必要なケース
落とし穴4: モデルのロード時間を考慮しない
Ollamaはモデルが起動してから一定時間使われないとメモリから降ろす。次の呼び出し時に再ロードが発生し、初回だけ数秒〜十数秒の待ちが生まれる。
対策: OllamaのOLLAMA_KEEP_ALIVE環境変数を設定してモデルをメモリに保持する。
export OLLAMA_KEEP_ALIVE=30m # 30分間はメモリに保持
コスト感——「下請け」構成で何が変わるか
フロンティアLLMの出力トークンは高コストだ。Claudeのモデル料金は出力側が特に高く、テキスト生成量が多い作業では一日の費用が大きくなりやすい。
ハイブリッド構成で節約効果が大きいのは「大量の短いテキスト処理」だ。例えば:
- 100件の記事からそれぞれキーワードを抽出する処理
- ログファイルをMarkdown形式に変換する処理
- 複数のドキュメントを同じフォーマットに揃える処理
これらはClaudeに任せると出力トークンを多く消費するが、Gemmaに委ねることで電力コストのみに抑えられる。
一方で注意点がある。Claudeが最終的にGemmaの出力をレビューしている以上、「重い推論タスク」をGemmaに任せるとGemmaの精度不足を補うためにClaudeの作業量が増え、逆にコストが増加することがある。
原則: タスクをGemmaに委譲するのは「定型処理」「テキスト整形」「単純な抽出・分類」に限定する。高度な推論タスクをGemmaに流すと品質とコストの両方を失う。
まとめ——失敗から得た「役割分担」という答え
前回の実験で「ローカルLLMでフロンティアLLMを完全代替しようとしたが、MCPの壁に阻まれた」という結論を得た。
今回の試みは、その失敗から導いた逆転の発想だ。
ローカルLLMはClaudeの「代替」ではなく「下請け」として使う。
フロンティアLLM(Claude)がオーケストレーターとして指揮を取り続けることで、MCPも使えるし判断品質も維持できる。ローカルLLM(Gemma4:26)はテキスト整形・キーワード抽出・軽量な分類など「決まった作業をこなす」役割に特化させる。
この構成のポイントを最後にまとめる:
| 観点 | ポイント |
|---|---|
| 役割設計 | Claudeがオーケストレーター、Gemmaがワーカー。逆にしない |
| MCPの扱い | MCPはClaudeの管轄に残す。ローカルLLMはMCPを使う側ではなく使われる側 |
| 委譲ルール | CLAUDE.mdで委譲先・委譲禁止を明文化。曖昧にするとClaudeが全部やる |
| 品質ゲート | Gemmaの出力はClaudeが必ず検証する。特に数値・固有名詞は要注意 |
| チューニング | VRAMの90%以下を守る(前回実験の知見)。OLLAMA_KEEP_ALIVEでロード待ちを防ぐ |
今日できる一歩は mcp-local-llm をインストールし、Claude Code内からGemmaに「Hello」とだけ送ってみることだ。MCPリストにlocal-llmが出て返答が返ってきたら接続成功だ。動いたら、CLAUDE.mdにテキスト整形タスクの委譲ルールを1行追加してみてほしい。