本文へスキップ

ローカルLLM(Ollama、LM Studio)

AI生成エンドポイントは特別な provider: "local" に対応しており、自分でホストしているOpenAI互換のchat-completionsサーバーにエンジンを向けられます。重い処理(QRのレンダリング、ISO 18004の検証、スキャン保証)は引き続きサーバーが行い、デザインを提案する言語モデルだけがあなたのマシン上で動きます。

使いどころ

  • プライバシー重視の構成。 プロンプトはLLMに届くまでの間、あなたのネットワークの外に出ません。Signet APIが目にするのは結果のJSON設定だけで、入力した自然言語の説明は見えません。
  • コストの管理。 すでにほかの用途でOllama / LM Studioを動かしていて、費用を払った、またはダウンロード済みのモデルを再利用したい場合。
  • 独自にチューニングしたモデル。 QRデザイン用のプロンプトで小さなオープンモデルをファインチューニングしていて、Signetをそのモデルに向けたい場合。

次の用途には向いていません。

  • APIサーバー上の localhost に到達しようとするSaaSの呼び出し元 — Signet APIはAzure Functions上で動いており、あなたのノートPCに直接到達できません。公開トンネルが必要です(下記参照)。
  • 自分で管理していないホスト型のOllamaクラウド — その場合は、該当するネイティブのプロバイダー(openai、groq など)を使ってください。

セットアップ

1. ローカルサーバーを起動する

Ollama:

ollama serve
# in another shell, pull a model
ollama pull llama3.3

Ollamaは、OpenAI互換のAPIを最初から http://localhost:11434/v1/chat/completions で公開しています。

LM Studio:

GUIでモデルを読み込み、「Local Server」タブを開いて「Start Server」をクリックします。デフォルトのエンドポイントは http://localhost:1234/v1 です。

vLLM / llama.cppサーバー: どちらも /v1/chat/completions をネイティブに公開しています。起動時に指定したホスト / ポートを使ってください。

2. サーバーを外部から到達可能にする

Azure Functionsはあなたのマシンの localhost に到達できないため、トンネルが必要です。設定不要の選択肢が2つあります。

# ngrok
ngrok http 11434
# → https://your-tunnel.ngrok.io

# Cloudflare Tunnel
cloudflared tunnel --url http://localhost:11434
# → https://random-words.trycloudflare.com

得られた公開HTTPSのURLを localEndpoint として使います。SSRFを防ぐため、APIはRFC1918 / リンクローカルのIP(10.x、172.16-31.x、192.168.x、169.254.x)を拒否します。受け付けるのは公開アドレスか localhost(API自体のローカル開発用)だけです。

3. APIを呼び出す

curl -X POST https://signetqr-core.azurewebsites.net/api/qr/ai/generate \
  -H "Content-Type: application/json" \
  -H "X-RapidAPI-Proxy-Secret: $RAPIDAPI_PROXY_SECRET" \
  -d '{
    "provider": "local",
    "localEndpoint": "https://your-tunnel.ngrok.io/v1",
    "model": "llama3.3",
    "apiKey": "ollama",
    "prompt": "Tech startup QR, neon cyan and magenta on near-black, hexagonal modules with subtle glow",
    "content": "https://example.com"
  }'

注意点:

  • apiKey はフィールドの検証で必須ですが、ほとんどのローカルサーバーでは値に意味はありません。Ollamaは空でない任意の文字列を受け付けます。慣例として "ollama" を渡してください。LM Studioも、明示的にAPIキーを設定していない限りこの値を無視します。
  • ローカルでは model が必須です。サーバー側のデフォルトはありません。サーバーが公開しているモデル名(llama3.3、qwen2.5:14b、mistral など)を正確に渡してください。
  • localEndpoint には、ベースURL(https://host/v1)とフルパス(https://host/v1/chat/completions)のどちらも指定できます。APIが両方を正規化します。
  • JSONモード(response_format: { type: "json_object" })はローカルサーバーには転送されません。対応していないランタイムがあり、エラーになるためです。システムプロンプトは十分に厳密なので、指示に従うモデルならきれいなJSONを返します。モデルがJSONを文章で囲んでしまう場合は、creativity を 0.0 に近づけるか、より指示追従性の高いモデルを選んでください。

失敗のパターン

症状原因対処法
400 localEndpoint must be a publicly reachable address公開インターネットから 10.x / 192.168.x / 127.0.0.1 のIPを渡したトンネル(ngrok、Cloudflare Tunnel)を使い、公開URLを渡す
400 For provider='local' the 'llmModel' field is requiredmodel を指定し忘れたローカルサーバーが公開しているモデル名を model に設定する
500 AI generated an invalid configurationローカルモデルが不正な形式のJSONを返したより強力なモデル(7Bパラメータ以上)を試すか、creativity を下げる
AIサービスからの 502 / connection refusedトンネルが落ちている / サーバーが起動していないollama serve を再起動し、cloudflared tunnel を再実行する

セキュリティに関する注意

  • Signet APIは localEndpoint と apiKey の内容をログに記録しません。課金用のテレメトリーとして、プロバイダー名(local)とモデル識別子は記録します。
  • トンネルのURLはAPIキーと同等の機密情報として扱ってください。URLを知っている人は誰でも、あなたのハードウェア上のローカルモデルを呼び出せます。
  • プライバシーの保証が重要な本番環境では、ngrokよりCloudflare Tunnelをおすすめします。ngrokのURLは推測可能で、無料枠には認証がありません。