はじめに
LLM(Large Language Model)を使ったアプリケーション開発で、こんな悩みを抱えていませんか?
- OpenAIのAPIを使っているが、障害時の代替手段がない
- Anthropic Claudeも試したいが、コード全体を書き換えるのが面倒
- 複数のLLMプロバイダーのコスト管理が煩雑
- チーム開発でAPIキーの管理が難しい
any-llmは、これらの課題を一気に解決するMozilla.aiが開発したPythonライブラリです。プロバイダーを切り替える際もモデル名の文字列を変更するだけで対応できる、シンプルで強力なツールです。
LLMプロバイダーのロックイン問題を解決するany-llmの基礎から実践的な活用法までまとめました。
この記事は、2025年11月にリリースされたany-llm v1.0の情報に基づいています。
any-llmとは?
any-llmは、単一のインターフェースでOpenAI、Anthropic、Google、Mistral、Ollamaなど、複数のLLMプロバイダーと通信できるPythonライブラリです。
主な特徴
- 統一されたAPI: プロバイダーが変わってもコードはほぼそのまま
- 公式SDK活用: 各プロバイダーの公式SDKを内部で使用し、最大限の互換性を確保
- プロキシ不要: 直接接続でシンプルな構成
- 開発者フレンドリー: 型ヒント完備、明確なエラーメッセージ
LangChainとの違い
| 項目 | any-llm | LangChain |
|---|---|---|
| 目的 | プロバイダー抽象化に特化 | LLMアプリケーション全般のフレームワーク |
| 学習コスト | 低い(既存コードをほぼ変更不要) | 高い(独自の概念が多い) |
| 依存関係 | 軽量 | 多数のパッケージが必要 |
| 適用場面 | プロバイダー切り替え、コスト最適化 | 複雑なRAG、エージェント構築 |
any-llmは**「シンプルに複数のLLMを使いたい」**というニーズに最適化されています。
インストールと基本的な使い方
インストール
# 特定のプロバイダーのみ
pip install any-llm-sdk[anthropic]
# 複数のプロバイダー
pip install any-llm-sdk[anthropic,openai,mistral]
# すべてのプロバイダー
pip install any-llm-sdk[all]
必要なプロバイダーのみインストールすることで、依存関係を最小限に抑えられます。
最初のコード
プロバイダーを切り替える様子を見てみましょう。
from any_llm import completion
# OpenAI GPT-4o-miniを使用
response = completion(
model="openai:gpt-4o-mini",
messages=[{"role": "user", "content": "Pythonの特徴を3つ教えて"}]
)
print(response.choices[0].message.content)
# Anthropic Claude Haiku 4.5に切り替え(モデル名を変えるだけ!)
response = completion(
model="anthropic:claude-haiku-4-5-20251001",
messages=[{"role": "user", "content": "Pythonの特徴を3つ教えて"}]
)
print(response.choices[0].message.content)
たったこれだけで異なるLLMプロバイダーを使い分けられます!
環境変数の設定
APIキーは環境変数で管理します。
# OpenAI
export OPENAI_API_KEY="sk-..."
# Anthropic
export ANTHROPIC_API_KEY="sk-ant-..."
# Google
export GOOGLE_API_KEY="..."
または.envファイルで管理:
from dotenv import load_dotenv
load_dotenv()
実践: プロバイダー切り替えとフォールバック
実際のアプリケーションでは、メインプロバイダーが使えない時の代替手段が必要です。
フォールバック実装
from any_llm import completion
import os
def smart_completion(user_message: str, use_fallback: bool = True):
"""
プライマリプロバイダー失敗時に自動的にフォールバック
"""
# プライマリ: Anthropic Claude
primary_model = "anthropic:claude-sonnet-4-5-20250929"
# フォールバック: OpenAI GPT-4o-mini
fallback_model = "openai:gpt-4o-mini"
messages = [{"role": "user", "content": user_message}]
try:
response = completion(model=primary_model, messages=messages)
print(f"✓ 使用モデル: {primary_model}")
return response.choices[0].message.content
except Exception as e:
if not use_fallback:
raise
print(f"⚠ プライマリ失敗: {e}")
print(f"→ フォールバックへ切り替え: {fallback_model}")
response = completion(model=fallback_model, messages=messages)
return response.choices[0].message.content
# 使用例
result = smart_completion("機械学習とディープラーニングの違いは?")
print(result)
コスト最適化: タスク別モデル選択
def cost_optimized_completion(user_message: str, task_complexity: str = "simple"):
"""
タスクの複雑さに応じて最適なモデルを選択
"""
# タスク複雑度別のモデルマッピング
model_mapping = {
"simple": "openai:gpt-4o-mini", # 低コスト・高速
"medium": "anthropic:claude-haiku-4-5-20251001", # バランス
"complex": "anthropic:claude-sonnet-4-5-20250929" # 高性能
}
model = model_mapping.get(task_complexity, "openai:gpt-4o-mini")
response = completion(
model=model,
messages=[{"role": "user", "content": user_message}]
)
print(f"選択モデル: {model} (複雑度: {task_complexity})")
return response.choices[0].message.content
# シンプルなタスク → 低コストモデル
simple_result = cost_optimized_completion(
"こんにちは、元気ですか?",
task_complexity="simple"
)
# 複雑なタスク → 高性能モデル
complex_result = cost_optimized_completion(
"量子コンピューティングがブロックチェーンのセキュリティに与える影響について、技術的な観点から詳しく説明してください。",
task_complexity="complex"
)
FastAPIとの統合例
実際のWebアプリケーションでの使用例を見てみましょう。
from fastapi import FastAPI, HTTPException
from pydantic import BaseModel
from any_llm import completion
import logging
app = FastAPI()
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)
class ChatRequest(BaseModel):
message: str
model: str = "openai:gpt-4o-mini"
max_tokens: int = 500
class ChatResponse(BaseModel):
response: str
model_used: str
fallback_used: bool = False
@app.post("/chat", response_model=ChatResponse)
async def chat_endpoint(request: ChatRequest):
"""
LLMチャットエンドポイント
プライマリモデル失敗時は自動的にフォールバック
"""
fallback_model = "anthropic:claude-haiku-4-5-20251001"
fallback_used = False
try:
response = completion(
model=request.model,
messages=[{"role": "user", "content": request.message}],
max_tokens=request.max_tokens
)
model_used = request.model
except Exception as e:
logger.warning(f"Primary model failed: {e}")
logger.info(f"Falling back to: {fallback_model}")
try:
response = completion(
model=fallback_model,
messages=[{"role": "user", "content": request.message}],
max_tokens=request.max_tokens
)
model_used = fallback_model
fallback_used = True
except Exception as fallback_error:
logger.error(f"Fallback also failed: {fallback_error}")
raise HTTPException(
status_code=503,
detail="All LLM providers are currently unavailable"
)
return ChatResponse(
response=response.choices[0].message.content,
model_used=model_used,
fallback_used=fallback_used
)
# 使用例
# curl -X POST "http://localhost:8000/chat" \
# -H "Content-Type: application/json" \
# -d '{"message": "Hello, world!"}'
ストリーミングレスポンス
リアルタイムでLLMの応答を受け取る方法です。
from any_llm import completion
def stream_chat(user_message: str):
"""
ストリーミングでLLMの応答を逐次表示
"""
response = completion(
model="openai:gpt-4o-mini",
messages=[{"role": "user", "content": user_message}],
stream=True
)
print("AI: ", end="", flush=True)
for chunk in response:
if chunk.choices[0].delta.content:
print(chunk.choices[0].delta.content, end="", flush=True)
print() # 改行
# 使用例
stream_chat("Pythonの非同期処理について簡潔に説明してください")
any-llm Gateway: チーム開発を加速する
v1.2.0で追加されたGateway機能は、組織でのLLM利用を一元管理できる強力な機能です。
Gatewayが解決する課題
従来の問題:
- 各開発者が個別にAPIキーを管理 → セキュリティリスク
- 誰がいくら使ったか不明 → コスト超過
- プロバイダーごとにバラバラの管理 → 運用負担
Gatewayによる解決:
- ✅ APIキーを一元管理(暗号化保存)
- ✅ ユーザー/チーム別の予算設定
- ✅ 使用状況のリアルタイム追跡
- ✅ 仮想APIキーでアクセス制御
Gateway基本セットアップ
# Dockerで起動
docker run -p 8080:8080 \
-e OPENAI_API_KEY=sk-... \
-e ANTHROPIC_API_KEY=sk-ant-... \
mozilla/any-llm-gateway
Gateway経由でのLLM呼び出し
from any_llm import completion
# Gateway URLを指定
response = completion(
model="openai:gpt-4o-mini",
messages=[{"role": "user", "content": "Hello!"}],
api_base="http://localhost:8080", # Gateway URL
api_key="your-virtual-key" # 仮想APIキー
)
チーム別予算管理の例
# gateway-config.yaml
users:
- id: "team-frontend"
virtual_key: "vk-frontend-xxx"
budget:
monthly_limit: 50.00 # 月額50ドルまで
alert_threshold: 40.00 # 40ドルで警告
allowed_models:
- "openai:gpt-4o-mini"
- "anthropic:claude-haiku-4-5-20251001"
- id: "team-backend"
virtual_key: "vk-backend-yyy"
budget:
monthly_limit: 200.00
alert_threshold: 160.00
allowed_models:
- "openai:gpt-4o"
- "anthropic:claude-sonnet-4-5-20250929"
プロバイダー比較: どのモデルを選ぶべきか
実際のプロジェクトでは、タスク特性に応じた適切なモデル選択が重要です。
タスク別推奨モデル
| タスク種別 | 推奨モデル | 理由 |
|---|---|---|
| 簡単な会話・要約 | OpenAI: gpt-4o-mini | 低コスト・高速 |
| コード生成・レビュー | Anthropic: Claude Sonnet | コード理解に優れる |
| 複雑な推論タスク | Anthropic: Claude Opus | 最高品質の出力 |
| 大量の軽量処理 | OpenAI: gpt-4o-mini | コスパ最高 |
| ローカル実行 | Ollama: llama3.2 | プライバシー重視 |
コスト比較(例)
# 各モデルの概算コスト(1M tokens)
cost_comparison = {
"openai:gpt-4o-mini": {
"input": 0.15, # USD per 1M tokens
"output": 0.60
},
"anthropic:claude-haiku-4-5-20251001": {
"input": 0.25,
"output": 1.25
},
"anthropic:claude-sonnet-4-5-20250929": {
"input": 3.00,
"output": 15.00
}
}
def estimate_cost(input_tokens: int, output_tokens: int, model: str):
"""
概算コストを計算
"""
costs = cost_comparison.get(model)
if not costs:
return "Unknown model"
input_cost = (input_tokens / 1_000_000) * costs["input"]
output_cost = (output_tokens / 1_000_000) * costs["output"]
total = input_cost + output_cost
return f"${total:.4f}"
# 使用例
print(estimate_cost(1000, 500, "openai:gpt-4o-mini"))
# 出力: $0.0004
v1.0の新機能
2025年11月リリースのv1.0では、以下の機能が追加されました:
1. 標準化された推論出力
from any_llm import completion
# どのプロバイダーでも同じ形式で推論過程を取得
response = completion(
model="anthropic:claude-sonnet-4-5-20250929",
messages=[{"role": "user", "content": "2+2は?"}],
reasoning=True # 推論過程を含める
)
# 推論過程へのアクセス(プロバイダーに依らず統一)
if response.reasoning:
print("推論:", response.reasoning)
print("回答:", response.choices[0].message.content)
2. List Models API
from any_llm import list_models
# プロバイダーがサポートするモデル一覧を取得
models = list_models(provider="openai")
for model in models:
print(f"- {model.id}: {model.description}")
3. 再利用可能なクライアント接続
from any_llm import CompletionClient
# クライアントを再利用してパフォーマンス向上
client = CompletionClient(model="openai:gpt-4o-mini")
for i in range(10):
response = client.complete(
messages=[{"role": "user", "content": f"質問{i}"}]
)
print(response.choices[0].message.content)
client.close()
まとめ
any-llmを使うことで
✅ プロバイダーロックインから解放される
✅ 1行の変更でLLMを切り替えできる
✅ コスト最適化が簡単に実現
✅ チーム開発でのAPI管理が一元化
LLM活用の柔軟性を手に入れるために、ぜひany-llmを試してみてください!