08/Documentation
音声入力とWeb Push
コンポーザー内のマイクと、エージェントがユーザーの入力を待機しているときの通知
両機能ともデフォルトでは無効です。コンポーザー内のマイクボタンや、エージェントが入力を待っているときに発火するブラウザ通知を有効にできます。
音声入力(任意)
入力欄の入力欄のマイクボタンと、設定のハンズフリースイッチ。ボタンをタップして話すと、文字起こしが入力欄に配置され、内容を確認して送信できます。ハンズフリーを有効にすると自動で送信されます。この送信は、手動入力したメッセージと同じ保護された返信経路を通り、それを迂回することはありません。
入力欄が空の間、マイクは行末の丸いボタンとなります。1文字でも入力すると「送信」ボタンに戻ります。メッセージは音声入力するかタイピングするかのどちらかであるため、入力欄の幅を競合させることなく、主操作を1つにまとめています。
collie stt setupを実行するまで存在しません。 ボタンは描画されず、音声がスマートフォンから送信されることもなく、認証情報は保持されず、子プロセスも実行されません。「無効化」ではなく「存在しない」状態です。利用可能なプロバイダは2種類あります:
| プロバイダ | 概要 |
|---|---|
openai-compatible | POST /audio/transcriptionsに対応する任意のエンドポイント。パブリックなOpenAI API、クラウド上のWhisperクローン、または外部送信を完全に遮断できる、同一マシン上のローカルエンジン(以下)です。 |
codex | すでに信頼済みのcodexバイナリを利用して短期間有効なトークンを取得します。新しいアカウントやキーは不要です。非公開・サポート外エンドポイントを使用し、yesの入力による同意手順を挟みます(以下)。 |
設定をCLIで行うのは、ペアリングと同様の理由です。認証情報を扱う操作であるため、ホスト側のキーボードで行う必要があります。Web上の設定フォームはありません。
$ bin/collie stt setup
Which speech-to-text provider?
openai-compatible any endpoint that speaks POST /audio/transcriptions —
the public OpenAI API, or a local whisper.cpp / parakeet.cpp
server, which is the zero-egress choice and the one to prefer.
codex borrow your own `codex` sign-in. No new key, no new account —
and a private endpoint that may break without notice.
provider [openai-compatible]:
The API base, INCLUDING its version prefix — the provider appends /audio/transcriptions.
local http://127.0.0.1:8080/v1 (whisper.cpp / parakeet.cpp — nothing leaves the host)
cloud https://api.openai.com/v1 (room audio leaves this machine)
base URL: http://127.0.0.1:8080/v1
The model the endpoint understands. Empty takes Collie's default, gpt-transcribe.
model [gpt-transcribe]: whisper-1
API key [none]:
The language you speak, as a two-letter ISO-639-1 code — en, de, tr, ja.
LEAVE IT EMPTY to let the model detect it, which is what you want if you mix languages in one
sentence. Name one only if short clips keep coming back in a language you did not speak: a few
seconds of accented audio is too little for the model to detect from, and it guesses.
spoken language [auto-detect]: en
✓ speech-to-text configured — /home/you/.local/state/collie/stt.json (owner-only)
Live immediately — no restart needed. The bridge re-reads this file per request.
Check it end to end with `collie stt test`.上記の各項目にはフラグが用意されているため(--provider · --url · --model · --key · --lang)、プロビジョニング実行時にターミナル操作は不要です。キーを空にしておく設定もサポートされています。キーのないエンドポイントに対しては、空のAuthorizationヘッダーではなく、ヘッダー自体を送信せずに接続します。
音声言語の設定が必要になるのは、特定の認識失敗が起きる場合のみです。 空欄(デフォルト)の場合、モデルが言語を自動検出します。これは1文の中で2言語を混ぜて話す場合に必要な挙動です。短いクリップで話していない言語が頻繁に返ってくる場合にのみ設定してください。アクセントのある数秒の音声では検出材料が不足し、モデルが誤認することがあります。2文字の言語コード、またはCollieが簡略化する地域タグ(en-GB → en)を指定します。これはopenai-compatibleプロバイダでのみ有効です。codexエンドポイントは言語設定を受け付けず、collie stt statusでもその旨が表示されます。
長い録音には長い制限時間を割り当てます。 1つのクリップに対するブラウザの処理制限時間は固定値ではなく、クリップのサイズに応じて決まります。上り速度を256 kb/sと想定し、ブリッジ自体のプロバイダ制限時間を加算するため、上限の8 MiBの場合は約6分弱が割り当てられます。Collieが録音を受け付けたクリップであれば、その完了まで待機します。アップロード中はポーリングを停止し、接続バナーの警告レベルも引き上げません。音声データによる上り帯域の逼迫は障害ではないため、障害として報告すべきではありません。
動作確認 stt test は、スマートフォンが録音可能なコンテナごとに、生成した0.2秒間の無音データを実際のプロバイダーに1回ずつ送信します。
$ bin/collie stt test
provider: openai-compatible (http://127.0.0.1:8080/v1, model whisper-1, language en)
sending: 0.2 s of generated silence as audio/wav (the setup probe) … ✓ 214 ms
transcript: (empty) — expected from silence, and the empty answer still proves the pipeline.
sending: 0.2 s of generated silence as audio/webm;codecs=opus (Chrome, Android, Firefox) … ✓ 198 ms
sending: 0.2 s of generated silence as audio/mp4 (Safari, iOS) … ✓ 190 ms文字起こし結果が空であれば成功。無音は空のテキストに変換されるため、通信の往復が確認できれば成功です。失敗した場合は、エラーの種類(認証、エンドポイント、レスポンス形式)が表示されます。その後、スマートフォンでCollieを再読み込みすると、入力欄の横にマイクが表示されます。collie stt statusで設定内容と各設定の適用元(設定ファイルか、それを上書きする環境変数か)を確認できます。collie stt offを実行するとstt.jsonが削除され、ボタンは再び非表示になります。どちらの操作も再起動は不要です。
コンテナの対応状況はプロバイダーによって異なります
スマートフォンはWAV形式で録音しません。Chrome、Android、FirefoxではWebMコンテナのOpus、SafariやiOSではMP4コンテナのAACで録音し、そのバイトデータをそのまま送信します。WAVを文字起こしできるプロバイダーであっても、これら両方に400エラーを返す場合があり、その際stt testが正常に見えてもディクテーションはすべて「refused」で失敗します。stt testが3種類すべてのクリップを送信するのはそのためです。拒否される問題をスマートフォン上ではなくセットアップ時に検出します。
2026-09-01にOpenRouterのPOST /v1/audio/transcriptionsで確認した例:
| フォーマット | mistralai/voxtral-small-24b-2507-stt | openai/whisper-large-v3-turbo |
|---|---|---|
| wav | 可 | 可 |
| ogg/opus | 可 | 可 |
| webm/opus | 不可、400 | 可 |
| mp4/m4a AAC | 不可、400 | 可 |
回避策はキーではなくモデルの変更です。同じOpenRouterキーの接続先を、4種類すべてを受け付けるopenai/whisper-large-v3-turboに設定してください。
bin/collie stt setup --provider openai-compatible \
--url https://openrouter.ai/api/v1 --model openai/whisper-large-v3-turbo --key <key>文字起こしが拒否された場合、アップストリームのステータスと送信時のコンテナ名が表示されるようになり、プロバイダーがどのフォーマットを拒否したかがスマートフォンのエラーに表示されます。( #148、@drewbitt に感謝します)
外部送信ゼロ: 自前のエンジンを指定する
openai-compatibleを選択すべき理由: ローカルのベースURLと周囲の音声がホスト外へ送信されることはありませんを指定します。OpenAI互換の文字起こしエンドポイントを提供するエンジンは2つあります。whisper.cppに同梱されるserver、およびmudler/parakeet.cpp(MIT)です。それぞれの説明書に従ってビルドまたはインストールし、ループバックで実行して、--urlをそのアドレスに設定してください:
bin/collie stt setup --provider openai-compatible --url http://127.0.0.1:8080/v1連携に必要なのはこれだけです。Collieはどのエンジンが応答するかを関知しません。
MistralのVoxtralに専用のサポートは不要。この規約に準拠する他のコンポーネントも同様です。この境界設計の利点はそこにあります。vLLMはオープンウェイトのVoxtralモデルを/v1/audio/transcriptionsで配信するため、ローカルモデルも他のエンジンと同じ--urlで扱えます。ホスト型モデルも、Mistral独自のエンドポイントに対して同じリクエストを送るだけです。
bin/collie stt setup --provider openai-compatible \
--url https://api.mistral.ai/v1 --model voxtral-mini-latest --key <key> --lang enVoxtral Mini Transcribeは13言語に対応し、Collieがすでに送信しているものと同じISO-639-1のlanguageフィールドを受け取ります。信頼する前にcollie stt testで動作を確認してください。「OpenAI互換」は各エンドポイントが独自に主張しているに過ぎず、このコマンドはその検証のために用意されています。
Codexプロバイダ: 同意事項
collie stt setup --provider codexは同意確認ブロックを表示し、yesと入力するまで処理を停止します。正確に言えば、録音データは現在のサインインで認証された文書化されていない非サポートのChatGPTエンドポイントに送信されるため、ChatGPTアカウントがレート制限や利用停止のリスクを負うことになり、予告なしに動作しなくなる可能性があります。
Collieはまずまず独自の名前で問い合わせるそのエンドポイントに問い合わせます。自身のアイデンティティが拒否された場合にのみCodex CLIのヘッダーへフォールバックします。そのフォールバックは設定に明記され、collie stt statusによって表示されます。Collieが~/.codex/auth.jsonを読み取ったり保存したりすることはありません。すでに信頼しているバイナリのみがそれにアクセスします。
上記すべての理由(2回却下された背景、変更点、境界がこのように設計された理由)は、ADR 0029に記載されています。
Web Push(任意)
デフォルトでは無効です。セットアップには3つのステップが必要です。送信ライブラリ(web-push)はビルド時にオプショナルな依存関係として含まれます。
collie push-keys # 1. generate + write the VAPID keys
collie restart # 2. Collie reads them at start
# 3. on your phone: Settings → notificationspush-keys コマンドはキーペアを生成し、パーミッション 600 で COLLIE_VAPID_PUBLIC と COLLIE_VAPID_PRIVATE をアクティブな .env に書き込みます。これはバイナリインストールの場合は ~/.config/collie/.env、Herdr インストールの場合は Herdr のプラグイン設定ディレクトリ内のものです。
RFC 8292のsubjectクレームを設定するには、連絡先URIを引数として渡します。
collie push-keys mailto:you@example.comHerdrで管理された環境では、両方のステップをアクション(herdr plugin action invoke push-keys --plugin herdr.collieおよびrestart)として利用できます。Herdrのアクションは位置引数を受け取らないため、subjectを設定するにはシェルでコマンドを直接実行する必要があります。
鍵の取り扱いに関する詳細:
このコマンドは、--forceを渡さない限り既存の鍵を上書きしません。鍵を更新すると既存のすべての購読が無効になり、通知を再度受信するには各デバイスで再購読が必要になります。既存の設定に対してsubject引数を指定した場合は、連絡先アドレスのみが更新され、現在の鍵は維持されます。
注。 0.8.0より前のHerdrバージョンでは、アクションはプラグインの初期インストール時にキャッシュされたセットに固定されたままになります(ADR 0006)。push-keysおよびpush-testアクションは、herdr plugin installを実行するまで表示されません。代わりにbash scripts/collie-ctl.sh push-keysを直接実行してください。ラッパースクリプトがコマンドをバイナリへ直接渡します。
購読しているすべてのデバイスへの配信パスをテストします。
collie push-test # or: push-test "Title" "Body"配信には1〜2秒かかります。プッシュが無効であると報告された場合は、サービスを再起動して生成された鍵を読み込ませてください。購読デバイスがないと報告された場合は、スマートフォンのブラウザでステップ3を完了してください。
Web Pushにはセキュアコンテキスト(HTTPS)が必要です。これはtailscale serve(MagicDNS証明書)またはTLSを終端する外部リバースプロキシ(バリアント C)によって提供されます。プレーンHTTP環境(COLLIE_SERVE_MODE=http)にはセキュアコンテキストがないため、ブラウザは「Settings」内の購読コントロールを無効化します。
Collieは、エージェントがblockedまたはdone状態になると通知を送信し、エージェントのメッセージを本文に含めます。通知を選択すると、Web UI上の該当エージェントへ直接移動します。
ホーム画面からの再インストールやService Workerのリセットによって、HTTP 410を返さずに新しいエンドポイントが作成されることがあるため、古い購読情報が蓄積する可能性があります。デバイスが再登録されると、Collieはレコードを更新します。保存されているエンドポイントは直接確認および削除できます。
# one line per device: service, since, user agent, endpoint tail
bin/collie push list
bin/collie push forget <substring> # or: push forget --all