はじめに
docker composeを使って、ollama + open-webui + mcpo によるローカルLLMでMCPサーバーの使用を体験してみようと思います。初心者向け解説は他記事に任せます。自分がやったことを雑多にまとめます。
Open WebUIとMCPOでローカルLLMにMCPツールを使ってもらう この記事とほぼ内容かぶります。
異なるのはMCPOもdockerコンテナで建てたことです。
同記事ではdaemon化していて、より難しそう?全部dockerで統一したらいいのにな、と思いました。記事が4月だからまだmcpoコンテナが出ていなかったのか?
Open-webuiではMCPではなく、MCPOを使う理由
your cloud instance can’t speak directly to an MCP server running locally on your machine via stdio.
インスタンスは、stdio 経由でローカル マシン上で実行されている MCP サーバーに直接通信できません。
出典: MCP Support
使用するコンテナ
使うコンテナは以下のリポジトリ
記事作成時点ではmcpoのリポジトリがPublic archiveとなってから3ヶ月過ぎているが、大丈夫だろうか。他に移転してしまったのだろうか。知っている人いたら教えてください。軽くググった感じ出てきませんでした。
コンテナの設定
まずはコンテナ構成をyamlに書きます。
# docker の場合
# docker run -t --gpus=all -v ollama:/root/.ollama -p 11434:11434 --name ollama ollama/ollama
# docker run -t -p 13000:8080 --gpus all --add-host=host.docker.internal:host-gateway -v open-webui:/app/backend/data --name open-webui ghcr.io/open-webui/open-webui:cuda
services:
ollama:
image: ollama/ollama:0.9.6
volumes:
- ollama:/root/.ollama
ports:
- "11434:11434"
# 以下はGPUを使う人のみ
deploy:
resources:
reservations:
devices:
- capabilities: [gpu]
open-webui:
image: ghcr.io/open-webui/open-webui:cuda
hostname: open-webui
ports:
- "13000:8080"
volumes:
- open-webui:/app/backend/data
extra_hosts:
- "host.docker.internal:host-gateway"
# 以下はGPUを使う人のみ
deploy:
resources:
reservations:
devices:
# - driver: nvidia # お手本に書いてあったが、書くと動作しなかったのでコメントアウト
# - count: all # お手本に書いてあったが、書くと動作しなかったのでコメントアウト
- capabilities: [gpu]
mcpo:
image: ghcr.io/alephpiece/mcpo:0.1.1
ports:
- "18000:8000"
volumes:
- ./config.json:/app/config.json
volumes:
ollama:
external: true # 既存volume使い回しのため
open-webui:
external: true # 既存volume使い回しのため
GPUを使うので、deployの部分に書き足しています。open-webuiはmainではなく、cudaタグを使用します。GPUを使用しないと低速なのでおすすめしませんが、どうしてもGPUが使えないけど試したい方は、open-webuiのタグをmainにしてdeploy以下をコメントアウトしましょう。
external: true
は事前にdocker単体でvolumeを作っていたのでそれを使いまわすためにつけた。初めてdocker-compose.ymlでボリューム作る人には不要です。
MCPの設定
そしてMCPの設定をconfig.jsonに書きます。
{
"mcpServers": {
"sequential-thinking": {
"command": "npx",
"args": [
"-y",
"@modelcontextprotocol/server-sequential-thinking"
]
},
"memory": {
"command": "npx",
"args": [
"-y",
"@modelcontextprotocol/server-memory"
]
},
"time": {
"command": "uvx",
"args": [
"mcp-server-time",
"--local-timezone=Asia/Tokyo"
]
},
"fetch": {
"command": "uvx",
"args": ["mcp-server-fetch"]
}
}
}
立ち上げるには、docker-compose.yml
とconfig.json
を同じディレクトリに入れて、docker compose up
です。構成簡単ですね。そしてブラウザにlocalhost:13000
を打ち込んで接続してください。open-webuiのログイン画面が表示されますので、メールアドレス(仮でOK)とパスワードを設定してログインしましょう。
次にユーザーセッティングからToolsを選択し、config.jsonに記載したツールとそのエンドポイントを入力しましょう。最後にSaveボタンを押してください。
時刻を聞いてみた
LLMには難しい、時刻を聞く問題。情報を与えられない限りLLMは適当な数値を言うはずです。
1つ目の回答はMCPサーバー使っていないながらもやや惜しい、AM3:40をPM3:17と間違えています。ツールを使っていなければ当然です。
2つ目の回答はAM3:42を午後3時43分と答えています。AMとPMを間違えていますが、TOOL:tool_get_current_time_post と表示されているので、ツールは使えたようです。
TOOL:... の部分をクリックすると、設定したタイムゾーンや取得した日時、確かに03:43と書かれていますが、AMかPMか、12時間表記か24時間表記か明記されていないので、前の会話の「午後3時...」に引っ張られてしまったのでしょう。つまりツールを使えたが、前の会話のせいで凡ミスした、と。
様々なMCPコンテナ
コンテナとしてポータブルに使えるMCPサーバーがdockerhub/mcpこんなにも出ていることに驚きました。日々のニュース記事で見る感じ続々と出ているとは聞いていたけど、記事を書いた時点で142リポジトリ!alephpiece/mcpo
ではdocker
コマンドは使えず、npx
またはuvx
を使って公開されているコードを取得してくるようです。uvxならPyPI, npxならnpmから。
まとめ
open-webuiとollamaは以前から使用しており、セキュリティ面が気になる局面で使用できるかと準備だけしておりましたが、個人が用意するPCでは速度や規模の面でクラウドLLMに叶うはずもなく、この構成が活きることはありませんでした。
しかしながら、今になって到来しているMCPサーバーブーム!この技術はユーザーのニッチな要求に厳格に答えつつ、LLMと統合することでより柔軟性を取り入れたツール製作に役立つ技術です。LLMサーバーはユーザーのローカルなデータやAPIへアクセスできるので、クラウドLLMを使うよりローカルLLMを使うことで完全にセキュリティを保った構成でLLMツールを作成できるので、今後の伸びに非常に注目です。