ネットワークデプロイメント
ZeroClaw をデプロイして外部からの接続を受け入れるための設定:ゲートウェイの公開、Webhook チャネル、トンネル、LAN 内限定と公開向けの構成。Raspberry Pi やその他の家庭用ネットワークホストは、ここで主要な対象となります。
インバウンドポートが重要な場合
| モード | インバウンドポート? | 注釈 |
|---|---|---|
| Telegram(ロングポーリング) | いいえ | ZeroClaw は api.telegram.org をポーリングし、NAT 環境下でも動作します |
| Matrix / Mattermost / Nextcloud Talk | いいえ | 同期/WebSocket、送信のみ |
| Discord / Slack(Socket Mode) | いいえ | アウトバウンド WebSocket |
Signal (signal-cli-rest-api) | いいえ | ローカルホストのコンテナ |
| Nostr / IMAP / MQTT | いいえ | すべてのアウトバウンド |
| Webhooks(GitHub、Slack Events API、WhatsApp、Nextcloud Talk ボット、カスタム) | はい | 公開のPOSTエンドポイントが必要です |
| LANからのゲートウェイペアリング | はい(LANスコープ) | 0.0.0.0 にバインドするか、トンネルを使用してください。 |
| Discord / Slack (HTTP イベント) | はい | Socket Mode を使用しない場合 |
結論: Telegram専用のbotは、ポートフォワーディングなしで、家庭用ルーター背後のPi上で動作します。webhookベースのものはすべて到達可能なURLが必要であり、そこでトンネルの出番となります。
ゲートウェイのバインド
デフォルトでは、ゲートウェイは 127.0.0.1 にバインドされ、他のデバイスからはアクセスできません。これを公開する方法は3つあります。
オプション1: パブリックバインド (LAN)
LAN 上の任意のデバイスから http://<pi-ip>:42617 にアクセスできるようになります。インターネットから到達可能な webhook には役立ちません。ルーターのパブリック IP は Pi に転送されないためです。
安全性: 0.0.0.0 へのバインドは重大な設定変更となるため、allow_public_bind = true の設定が必要です。この設定がない場合、デーモンはバインドを拒否します。これは意図的な動作です。
オプション2: トンネル(インターネット経由でアクセス可能)
その後、デーモンを再起動すると、トンネルは設定から宣言的に管理され、ゲートウェイと一緒に起動します。
トンネルはパブリックURLからゲートウェイ(127.0.0.1)へ転送します。ルーター設定もポート開放も不要です。tunnel.tunnel_provider をサポートされている値のいずれかに設定してください。いずれも同様に動作します。
| プロバイダー | セットアップの摩擦 | コスト | 良い |
|---|---|---|---|
tailscale | アカウント + クライアント | 無料ティア | 長期にわたる安定したURL |
cloudflare | アカウント + cloudflared + トークン | 無料 | カスタムドメイン |
ngrok | アカウント + エージェント + トークン | 制限付きで無料 | テスト、短命 |
pinggy | SSH、アカウントなし | 無料ティア | 短時間のワンショットURL |
openvpn | 自分の OpenVPN 出口 | セルフホスト | 既存のVPNインフラ |
custom | [tunnel.custom] 配下のコマンド | 依存関係 | その他 |
tunnel_provider = "none"(デフォルト)の場合、ゲートウェイはローカルのままでトンネルを使用しません。各プロバイダーの [tunnel.<provider>] フィールドについては、設定リファレンスを参照してください。
オプション3: リバースプロキシ
nginx / Caddy / Traefik をゲートウェイの前に配置し、そこで TLS を終了し、localhost:42617 にプロキシします。以下に適しています:
- 実在するパブリックIPアドレスを持つサーバー
- Let’s Encrypt を使用した既存のリバースプロキシ設定
- 同じホストで複数のサービスを提供する
最小限のCaddy設定:
agent.example.com {
reverse_proxy localhost:42617
}
ゲートウェイは 127.0.0.1 にバインドされたままで、リッスンはプロキシが行います。
汎用ゲートウェイの Webhook 認証
ゲートウェイの POST /webhook と SOP 専用の POST /sop/* ルートでは、ペアリングとは独立して、共有シークレットヘッダーの完全一致を要求できます:
[gateway]
webhook_secret = "replace-with-a-random-secret"
値を X-Webhook-Secret として送信します。require_pairing = true で webhook_secret が設定されている場合、呼び出し元はペアリング済みの Bearer トークンと webhook シークレットの両方を送信する必要があります。汎用ゲートウェイシークレットは [channels.webhook.<alias>].secret とは意図的に分離されています。チャネルエイリアスは独自のリスナーを実行し、代わりに本文の HMAC 検証を使用します。
ゲートウェイ設定の書き込みは、稼働中のゲートウェイ設定ビューを通じて反映されます。ファイルを直接編集した場合は、通常のデーモンの再読み込み(またはゲートウェイ単体の再起動)が必要です。
リモートデーモンの再読み込み
POST /admin/reload は config.toml を再読み込みし、すべてのサブシステムをその場で再構築します(PID は同一、ダウンタイムは 1 秒未満)。これは、完全な再起動を行わずに設定変更を適用するためにサポートされている方法です。デフォルトではループバックからの呼び出しのみを受け付けるため、リモートのダッシュボードや別マシンからの curl は 403 Forbidden を受け取ります。
認証されたリモートからのリロードを許可するには:
[gateway]
allow_remote_admin = true # off by default
require_pairing = true # required for remote reload (also the default)
これを有効にすると、ループバック以外の呼び出し元が /admin/reload にアクセスできるのは、ペアリング認証も通過した場合のみ です(Authorization: Bearer <token>)。ループバックの呼び出し元(ローカルのCLI)は常に許可され、トークンは不要です。/admin/shutdown とペアリングコードのエンドポイントは、このフラグに関係なくlocalhostからのみアクセス可能です。
リモートアクセスはペアリングを通じて強制されるため、require_pairing も有効になっていない限り allow_remote_admin は効果を持ちません。ペアリングが無効の場合、リモートの呼び出し元は認証できないため、リクエストは匿名で許可されるのではなく 403 Forbidden で拒否されます。これにより、単一のフラグを切り替えるだけで未認証のリモートリロードを公開してしまうことが不可能になります。
安全性: 別のホストからリロードする必要が特にない限り、allow_remote_admin はオフのままにしてください。リロードが匿名でトリガーされないように、require_pairing = true(デフォルト)を維持してください。
Raspberry Pi のデプロイメント
前提条件
- Raspberry Pi 3/4/5(または同様のSBC)とRaspberry Pi OSまたはAlpine
- ネットワーク接続(WiFi またはイーサネット)
- オプション: ハードウェア統合用のUSB周辺機器
インストール
クローンしてインストーラーを実行します。フラグを指定しない場合、対話形式の選択画面が表示され、ビルドタイプとコンパイルに含める機能(GPIO/I2C/SPI のハードウェア機能を含む)を選択できます。Pi では Pi 向けに調整された cargo プロファイルも使用します。スワップの設定とモデルごとのビルドマトリックスについては、Raspberry Pi のセットアップ を参照してください。
Raspberry Pi OS
git clone https://github.com/zeroclaw-labs/zeroclaw.git
cd zeroclaw
./install.sh
Alpine
apk add curl rust cargo openssl-dev pkgconf git
git clone https://github.com/zeroclaw-labs/zeroclaw.git
cd zeroclaw
./install.sh
ハードウェア機能を選択すると、rppal を介して GPIO、I2C、SPI へのアクセスを許可します。標準のサービスユニットでは、ユーザーがすでに gpio、spi、i2c グループに追加されています。
チェックリスト
- バイナリをインストールします(
./install.sh、ピッカーで機能を選択してください) -
zeroclaw quickstartを実行します - チャンネルを設定します。Telegramにはポートが不要ですが、Webhookにはトンネルが必要です
- サービスをインストールします:
zeroclaw service install && zeroclaw service start - LAN アクセスの場合:
[gateway] host = "0.0.0.0"およびallow_public_bind = trueを設定 - Webhookの場合、
[tunnel]をプロバイダーで設定してください。
Alpine Linux (OpenRC)
OpenRC サービスはシステム全体で実行されます。root としてインストールしてください:
sh
sudo zeroclaw service install
作成します:
/etc/init.d/zeroclaw: init スクリプト/etc/zeroclaw/: 設定ディレクトリ/var/log/zeroclaw/: ログファイル
有効化して開始:
sh
sudo rc-update add zeroclaw default
sudo rc-service zeroclaw start
sudo rc-service zeroclaw status
ログ:
sh
sudo tail -f /var/log/zeroclaw/error.log
OpenRCのノート
- サービスは
zeroclaw:zeroclawとして実行されます(最小権限)。 - システム全体のみ:ユーザーレベルの OpenRC サービスはありません
- すべてのサービス操作には
sudoが必要です。
Telegramのポーリングに関する注意点
Telegram Bot API の getUpdates は、ボットトークンごとに単一のポーラーのみ対応しています。同じトークンで2つのインスタンスを実行することはできず、2つ目は Conflict: terminated by other getUpdates request を受け取ります。
これが見える場合:
-
ps aux | grep zeroclawを実行し、デーモンが1つだけ実行されていることを確認してください。 -
開発セッションから
cargo run --bin zeroclaw -- channel start telegramが残っていないか確認してください。 -
期限切れの場合、Telegramの投票セッションをリセットします:
sh
curl -X POST "https://api.telegram.org/bot$TOKEN/close"
Webhookを安全に公開する
公開可能なWebhookURLは攻撃対象となります。少なくとも:
- HMAC署名検証: 各Webhookチャネルに設定された
secret - ソースIPのホワイトリスト:サービスが固定の送信元IPを使用している場合(GitHub、AWS SNSなど)
- レート制限: webhook チャネル設定の
rate_limit_per_sec
詳細な設定については、チャンネル → ウェブフック を参照してください。
関連項目も参照してください
- Setup → Container: Docker固有のネットワーク設定
- セットアップ → サービス管理: プラットフォームサービスの統合
- 操作 → 概要
- セキュリティ → 概要