Hosting
Fly.io
هدف: اجرای OpenClaw Gateway روی یک ماشین Fly.io با فضای ذخیرهسازی پایدار، HTTPS خودکار و دسترسی Discord/کانال.
پیشنیازها
- نصب بودن flyctl CLI
- حساب Fly.io (سطح رایگان نیز قابل استفاده است)
- احراز هویت مدل: کلید API برای ارائهدهنده مدل انتخابی شما
- اعتبارنامههای کانال: توکن ربات Discord، توکن Telegram و غیره
مسیر سریع برای مبتدیان
- مخزن را کلون و
fly.tomlرا سفارشی کنید - برنامه و جلد را ایجاد و رازها را تنظیم کنید
- با
fly deployاستقرار دهید - برای ایجاد پیکربندی از طریق SSH وارد شوید، یا از رابط کنترل استفاده کنید
ایجاد برنامه Fly
git clone https://github.com/openclaw/openclaw.gitcd openclaw # نام دلخواه خود را انتخاب کنیدfly apps create my-openclaw # معمولاً ۱ گیگابایت کافی استfly volumes create openclaw_data --size 1 --region iadمنطقهای نزدیک به خود انتخاب کنید. گزینههای رایج: lhr (لندن)، iad (ویرجینیا)، sjc (سنخوزه).
پیکربندی fly.toml
fly.toml را متناسب با نام برنامه و نیازهای خود ویرایش کنید. فایل fly.toml ردیابیشده در مخزن، الگوی عمومی نمایشدادهشده در زیر است؛ deploy/fly.private.toml گونه سختسازیشده بدون IP عمومی است (به استقرار خصوصی مراجعه کنید).
app = "my-openclaw" # نام برنامه شماprimary_region = "iad" [build] dockerfile = "Dockerfile" [env] NODE_ENV = "production" OPENCLAW_PREFER_PNPM = "1" OPENCLAW_STATE_DIR = "/data" NODE_OPTIONS = "--max-old-space-size=1536" [processes] app = "node dist/index.js gateway --allow-unconfigured --port 3000 --bind lan" [http_service] internal_port = 3000 force_https = true auto_stop_machines = false auto_start_machines = true min_machines_running = 1 processes = ["app"] [[vm]] size = "shared-cpu-2x" memory = "2048mb" [mounts] source = "openclaw_data" destination = "/data"نقطه ورود تصویر Docker مربوط به OpenClaw، tini است که بهطور پیشفرض node openclaw.mjs gateway را اجرا میکند. بخش [processes] در Fly، دستور CMD داکر را جایگزین میکند (در اینجا همان نقطه ورود کامپایلشده را مستقیماً با node dist/index.js gateway ... اجرا میکند)، بدون آنکه ENTRYPOINT را تغییر دهد؛ بنابراین فرایند همچنان زیر نظر tini اجرا میشود.
تنظیمات کلیدی:
| تنظیم | دلیل |
|---|---|
--bind lan |
به 0.0.0.0 متصل میشود تا پروکسی Fly بتواند به Gateway دسترسی پیدا کند |
--allow-unconfigured |
بدون فایل پیکربندی شروع میشود (بعداً آن را ایجاد میکنید) |
internal_port = 3000 |
برای بررسیهای سلامت Fly باید با --port 3000 (یا OPENCLAW_GATEWAY_PORT) مطابقت داشته باشد |
memory = "2048mb" |
۵۱۲ مگابایت بسیار کم است؛ ۲ گیگابایت توصیه میشود |
OPENCLAW_STATE_DIR = "/data" |
وضعیت را روی جلد پایدار نگه میدارد |
تنظیم رازها
# الزامی: توکن احراز هویت Gateway برای اتصال غیر از local loopbackfly secrets set OPENCLAW_GATEWAY_TOKEN=$(openssl rand -hex 32) # کلیدهای API ارائهدهنده مدلfly secrets set ANTHROPIC_API_KEY=example-anthropic-key-not-real # اختیاری: سایر ارائهدهندگانfly secrets set OPENAI_API_KEY=example-openai-key-not-realfly secrets set GOOGLE_API_KEY=... # توکنهای کانالfly secrets set DISCORD_BOT_TOKEN=example-discord-bot-tokenاتصالهای غیر از local loopback (--bind lan) به یک مسیر معتبر احراز هویت Gateway نیاز دارند. این مثال از OPENCLAW_GATEWAY_TOKEN استفاده میکند، اما gateway.auth.password یا یک استقرار پروکسی مورداعتماد با اتصال غیر از local loopback که بهدرستی پیکربندی شده باشد نیز این الزام را برآورده میکند. برای قرارداد SecretRef به مدیریت رازها مراجعه کنید.
با این توکنها مانند گذرواژه رفتار کنید. برای کلیدهای API و توکنها، متغیرهای محیطی/fly secrets را به فایل پیکربندی ترجیح دهید تا رازها خارج از openclaw.json باقی بمانند.
استقرار
fly deployنخستین استقرار، تصویر Docker را میسازد. پس از استقرار، آن را بررسی کنید:
fly statusfly logsپس از فعال شدن شنونده HTTP/WebSocket، راهاندازی Gateway پیام gateway ready را در گزارشها ثبت میکند. بررسی سلامت خود Fly مطابق fly.toml، internal_port = 3000 را پایش میکند؛ دستور HEALTHCHECK در تصویر Docker نیز مسیر /healthz را روی درگاه پیشفرض 18789 بررسی میکند که در اینجا استفاده نمیشود، زیرا این استقرار درگاه Gateway را با --port 3000 بازنویسی میکند.
ایجاد فایل پیکربندی
برای ایجاد یک پیکربندی مناسب، از طریق SSH وارد ماشین شوید:
fly ssh consolemkdir -p /datacat > /data/openclaw.json << 'EOF'{ "agents": { "defaults": { "model": { "primary": "anthropic/claude-opus-4-6", "fallbacks": ["anthropic/claude-sonnet-4-6", "openai/gpt-5.4"] }, "maxConcurrent": 4 }, "list": [ { "id": "main", "default": true } ] }, "auth": { "profiles": { "anthropic:default": { "mode": "token", "provider": "anthropic" }, "openai:default": { "mode": "token", "provider": "openai" } } }, "bindings": [ { "agentId": "main", "match": { "channel": "discord" } } ], "channels": { "discord": { "enabled": true, "groupPolicy": "allowlist", "guilds": { "YOUR_GUILD_ID": { "channels": { "general": { "allow": true } }, "requireMention": false } } } }, "gateway": { "mode": "local", "bind": "auto", "controlUi": { "allowedOrigins": [ "https://my-openclaw.fly.dev", "http://localhost:3000", "http://127.0.0.1:3000" ] } }, "meta": {}}EOFبا OPENCLAW_STATE_DIR=/data، مسیر پیکربندی /data/openclaw.json است.
https://my-openclaw.fly.dev را با مبدأ واقعی برنامه Fly خود جایگزین کنید. راهاندازی Gateway، مبدأهای محلی رابط کنترل را بر اساس مقادیر زمان اجرای --bind و --port مقداردهی اولیه میکند تا نخستین راهاندازی پیش از وجود پیکربندی انجام شود؛ اما دسترسی مرورگر از طریق Fly همچنان به مبدأ دقیق HTTPS فهرستشده در gateway.controlUi.allowedOrigins نیاز دارد.
توکن Discord میتواند از یکی از این دو منبع تأمین شود:
- متغیر محیطی
DISCORD_BOT_TOKEN(برای رازها توصیه میشود)؛ نیازی به افزودن آن به پیکربندی نیست، Gateway آن را خودکار میخواند - فایل پیکربندی
channels.discord.token
برای اعمال تغییرات، راهاندازی مجدد کنید:
exitfly machine restart <machine-id>دسترسی به Gateway
رابط کنترل
fly openیا به https://my-openclaw.fly.dev/ مراجعه کنید.
با راز مشترک پیکربندیشده احراز هویت کنید: توکن Gateway از OPENCLAW_GATEWAY_TOKEN، یا اگر احراز هویت را به گذرواژه تغییر دادهاید، گذرواژه خودتان.
گزارشها
fly logs # گزارشهای زندهfly logs --no-tail # گزارشهای اخیرکنسول SSH
fly ssh consoleعیبیابی
«برنامه روی نشانی مورد انتظار گوش نمیدهد»
Gateway بهجای 0.0.0.0 به 127.0.0.1 متصل شده است.
راهحل: --bind lan را به دستور فرایند خود در fly.toml اضافه کنید.
ناموفق بودن بررسیهای سلامت / رد شدن اتصال
Fly نمیتواند از طریق درگاه پیکربندیشده به Gateway دسترسی پیدا کند.
راهحل: مطمئن شوید internal_port با درگاه Gateway (--port 3000 یا OPENCLAW_GATEWAY_PORT=3000) مطابقت دارد.
مشکلات OOM / حافظه
کانتینر مرتباً راهاندازی مجدد یا متوقف میشود. نشانهها: SIGABRT، v8::internal::Runtime_AllocateInYoungGeneration یا راهاندازیهای مجدد بیصدا.
راهحل: حافظه را در fly.toml افزایش دهید:
[[vm]] memory = "2048mb"یا یک ماشین موجود را بهروزرسانی کنید:
fly machine update <machine-id> --vm-memory 2048 -y۵۱۲ مگابایت بسیار کم است. ۱ گیگابایت ممکن است کار کند، اما زیر بار یا با گزارشگیری پرجزئیات ممکن است با OOM مواجه شود. ۲ گیگابایت توصیه میشود.
مشکلات قفل Gateway
پس از راهاندازی مجدد کانتینر، Gateway بهدلیل خطاهای «از قبل در حال اجرا است» از شروع خودداری میکند.
فایل قفل تکنمونهای در <tmpdir>/openclaw-<uid>/gateway.<hash>.lock قرار دارد (در لینوکس: /tmp/openclaw-<uid>/gateway.<hash>.lock)، نه روی جلد پایدار /data؛ بنابراین راهاندازی مجدد کامل کانتینر معمولاً آن را همراه با بقیه سامانه فایل کانتینر پاک میکند. اگر قفل باقی بماند (برای مثال، در یک fly machine restart که سامانه فایل کانتینر را حفظ میکند) و مانع راهاندازی شود، آن را دستی حذف کنید:
fly ssh console --command "rm -f /tmp/openclaw-*/gateway.*.lock"fly machine restart <machine-id>خوانده نشدن پیکربندی
--allow-unconfigured فقط محافظ راهاندازی را دور میزند. این گزینه /data/openclaw.json را ایجاد یا ترمیم نمیکند؛ بنابراین مطمئن شوید پیکربندی واقعی شما وجود دارد و برای راهاندازی عادی Gateway محلی شامل "gateway": { "mode": "local" } است.
وجود پیکربندی را بررسی کنید:
fly ssh console --command "cat /data/openclaw.json"نوشتن پیکربندی از طریق SSH
fly ssh console -C از تغییر مسیر پوسته پشتیبانی نمیکند. برای نوشتن فایل پیکربندی:
# echo + tee (ارسال از محلی به دوردست از طریق لوله)echo '{"your":"config"}' | fly ssh console -C "tee /data/openclaw.json" # یا sftpfly sftp shell> put /local/path/config.json /data/openclaw.jsonاگر فایل از قبل وجود داشته باشد، ممکن است fly sftp ناموفق شود؛ ابتدا آن را حذف کنید:
fly ssh console --command "rm /data/openclaw.json"پایدار نماندن وضعیت
اگر پس از راهاندازی مجدد، نمایههای احراز هویت، وضعیت کانال/ارائهدهنده یا نشستها را از دست میدهید، دایرکتوری وضعیت بهجای جلد روی سامانه فایل کانتینر نوشته میشود.
راهحل: مطمئن شوید OPENCLAW_STATE_DIR=/data در fly.toml تنظیم شده است و دوباره استقرار دهید.
بهروزرسانی
git pullfly deployfly statusfly logsدر اینجا git pull + fly deploy مسیر تحت نظارت است: تصویر را از Dockerfile دوباره میسازد، بنابراین نسخه CLI/Gateway، تصویر پایه سیستمعامل و هرگونه تغییر Dockerfile همگی با هم بهروزرسانی میشوند. اجرای openclaw update درون کانتینر در حال اجرا، عملیات یکسانی نیست؛ زیرا تصویر بهصورت یک درخت dist/ ساختهشده با Docker عرضه میشود و نه نسخهبرداری .git دارد و نه نصب سراسری مدیریتشده با npm که بتواند آن را شناسایی کند. برای این فرایند در نصبهای سبک ماشین مجازی، به بهروزرسانی مراجعه کنید.
بهروزرسانی دستور ماشین
برای تغییر دستور راهاندازی بدون استقرار مجدد کامل:
fly machines listfly machine update <machine-id> --command "node dist/index.js gateway --port 3000 --bind lan" -y # یا همراه با افزایش حافظهfly machine update <machine-id> --vm-memory 2048 --command "node dist/index.js gateway --port 3000 --bind lan" -yاجرای بعدی fly deploy دستور ماشین را به مقدار موجود در fly.toml بازمیگرداند؛ پس از استقرار مجدد، تغییرات دستی را دوباره اعمال کنید.
استقرار خصوصی (سختسازیشده)
Fly بهطور پیشفرض IPهای عمومی اختصاص میدهد؛ بنابراین Gateway شما در https://your-app.fly.dev قابل دسترسی و برای پویشگرهای اینترنتی (Shodan، Censys و غیره) قابل کشف است.
برای استقرار سختسازیشده با بدون IP عمومی از deploy/fly.private.toml استفاده کنید: این فایل بخش [http_service] را حذف میکند، بنابراین هیچ ورودی عمومی تخصیص داده نمیشود.
چه زمانی از استقرار خصوصی استفاده کنید
- فقط تماسها/پیامهای خروجی (بدون Webhookهای ورودی)
- تونلهای ngrok یا Tailscale فراخوانیهای برگشتی Webhook را مدیریت میکنند
- دسترسی به Gateway بهجای مرورگر از طریق SSH، پروکسی یا WireGuard انجام میشود
- استقرار باید از پویشگرهای اینترنتی پنهان باشد
راهاندازی
fly deploy -c deploy/fly.private.tomlیا یک استقرار موجود را تبدیل کنید:
# فهرست IPهای فعلیfly ips list -a my-openclaw # آزادسازی IPهای عمومیfly ips release <public-ipv4> -a my-openclawfly ips release <public-ipv6> -a my-openclaw # تغییر به پیکربندی خصوصی تا استقرارهای آینده IP عمومی را دوباره تخصیص ندهندfly deploy -c deploy/fly.private.toml # تخصیص IPv6 فقط خصوصیfly ips allocate-v6 --private -a my-openclawپس از این، fly ips list باید فقط یک IP از نوع private را نشان دهد:
VERSION IP TYPE REGIONv6 fdaa:x:x:x:x::x private globalدسترسی به استقرار خصوصی
گزینه ۱: پروکسی محلی (سادهترین)
fly proxy 3000:3000 -a my-openclaw# نشانی http://localhost:3000 را در مرورگر باز کنیدگزینه ۲: VPN مبتنی بر WireGuard
fly wireguard create# آن را در یک کلاینت WireGuard وارد کنید، سپس از طریق IPv6 داخلی دسترسی پیدا کنید# نمونه: http://[fdaa:x:x:x:x::x]:3000گزینه ۳: فقط SSH
fly ssh console -a my-openclawWebhookها در استقرار خصوصی
برای فراخوانیهای برگشتی Webhook (Twilio، Telnyx و غیره) بدون قرار گرفتن در معرض دسترسی عمومی:
- تونل ngrok: ngrok را درون کانتینر یا بهصورت سایدکار اجرا کنید
- Tailscale Funnel: مسیرهای مشخصی را از طریق Tailscale در دسترس قرار دهید
- فقط خروجی: برخی ارائهدهندگان (مانند Twilio) برای تماسهای خروجی بدون Webhook کار میکنند
نمونه پیکربندی تماس صوتی با ngrok، در plugins.entries.voice-call.config:
{ plugins: { entries: { "voice-call": { enabled: true, config: { provider: "twilio", tunnel: { provider: "ngrok" }, webhookSecurity: { allowedHosts: ["example.ngrok.app"], }, }, }, }, },}تونل ngrok درون کانتینر اجرا میشود و بدون در معرض دسترسی عمومی قرار دادن خود برنامه Fly، یک نشانی عمومی Webhook فراهم میکند. مقدار webhookSecurity.allowedHosts را روی نام میزبان تونل تنظیم کنید تا سرآیندهای میزبانِ بازارسالشده پذیرفته شوند.
ملاحظات امنیتی
| جنبه | عمومی | خصوصی |
|---|---|---|
| اسکنرهای اینترنتی | قابل شناسایی | پنهان |
| حملات مستقیم | ممکن | مسدود |
| دسترسی به رابط کنترل | مرورگر | پروکسی/VPN |
| تحویل Webhook | مستقیم | از طریق تونل |
نکات
- Fly.io از معماری x86 استفاده میکند؛ Dockerfile با هر دو معماری x86 و ARM سازگار است.
- برای راهاندازی اولیه WhatsApp/Telegram، از
fly ssh consoleاستفاده کنید. - دادههای پایدار روی ولوم در مسیر
/dataقرار دارند. - Signal به signal-cli (یک CLI مبتنی بر Java) در ایمیج نیاز دارد؛ از یک ایمیج سفارشی استفاده کنید و حافظه را روی ۲ گیگابایت یا بیشتر نگه دارید.
هزینه
با پیکربندی توصیهشده (shared-cpu-2x و ۲ گیگابایت RAM)، بسته به میزان استفاده، هزینهای حدود ۱۰ تا ۱۵ دلار در ماه انتظار میرود؛ سطح رایگان بخشی از سهمیه پایه را پوشش میدهد. برای مشاهده نرخهای فعلی، به قیمتگذاری Fly.io مراجعه کنید.
گامهای بعدی
- کانالهای پیامرسانی را راهاندازی کنید: کانالها
- Gateway را پیکربندی کنید: پیکربندی Gateway
- OpenClaw را بهروز نگه دارید: بهروزرسانی