Gateway

تکمیل‌های گفت‌وگوی OpenAI

Gateway می‌تواند یک سطح کوچک و سازگار با Chat Completions متعلق به OpenAI ارائه کند. این قابلیت به‌طور پیش‌فرض غیرفعال است.

پس از فعال‌سازی، همهٔ موارد زیر را روی همان پورت Gateway ارائه می‌کند (مالتی‌پلکس WS + HTTP):

روش مسیر
POST /v1/chat/completions
GET /v1/models
GET /v1/models/{id}
POST /v1/embeddings
POST /v1/responses

درخواست‌ها مانند اجرای عادی عامل Gateway اجرا می‌شوند (همان مسیر کد openclaw agent)؛ بنابراین مسیریابی، مجوزها و پیکربندی با Gateway شما مطابقت دارند.

فعال‌سازی نقطهٔ پایانی

json5
{  gateway: {    http: {      endpoints: {        chatCompletions: { enabled: true },      },    },  },}

برای غیرفعال‌سازی، enabled: false را تنظیم کنید (یا آن را حذف کنید).

مرز امنیتی (مهم)

این نقطهٔ پایانی را معادل دسترسی کامل اپراتور به نمونهٔ Gateway در نظر بگیرید:

  • توکن/گذرواژهٔ معتبر Gateway برای این نقطهٔ پایانی، معادل اعتبارنامهٔ مالک/اپراتور است، نه دامنه‌ای محدود برای هر کاربر.
  • درخواست‌ها از همان مسیر عامل صفحهٔ کنترلِ کنش‌های اپراتور مورداعتماد عبور می‌کنند؛ بنابراین اگر خط‌مشی عامل مقصد ابزارهای حساس را مجاز بداند، این نقطهٔ پایانی می‌تواند از آن‌ها استفاده کند.
  • آن را فقط روی loopback/tailnet/ورودی خصوصی نگه دارید. آن را در معرض اینترنت عمومی قرار ندهید.

ماتریس احراز هویت:

مسیر احراز هویت رفتار
gateway.auth.mode="token" یا "password" + Authorization: Bearer ... در اختیار داشتن راز مشترک Gateway را اثبات می‌کند. هر سرآیند x-openclaw-scopes را نادیده می‌گیرد و مجموعهٔ کامل دامنه‌های پیش‌فرض اپراتور را بازیابی می‌کند: operator.admin، operator.approvals، operator.pairing، operator.read، operator.talk.secrets، operator.write. نوبت‌های گفتگو را نوبت‌های فرستندهٔ مالک در نظر می‌گیرد.
HTTP مورداعتمادِ حامل هویت (احراز هویت trusted-proxy یا gateway.auth.mode="none" روی ورودی خصوصی) در صورت وجود، x-openclaw-scopes را رعایت می‌کند؛ در صورت نبود آن، به مجموعهٔ دامنه‌های پیش‌فرض اپراتور بازمی‌گردد. فقط زمانی معناشناسی مالک را از دست می‌دهد که فراخواننده صراحتاً دامنه‌ها را محدود و operator.admin را حذف کند. برای کنترل‌های سطح مالک مانند x-openclaw-model به operator.admin نیاز دارد.

به دامنه‌های اپراتور، امنیت و دسترسی از راه دور مراجعه کنید.

احراز هویت

از پیکربندی احراز هویت Gateway استفاده می‌کند (برای جزئیات این حالت، به احراز هویت پراکسی مورداعتماد مراجعه کنید):

حالت نحوهٔ احراز هویت
gateway.auth.mode="token" Authorization: Bearer <token>. از طریق gateway.auth.token یا OPENCLAW_GATEWAY_TOKEN تنظیم کنید.
gateway.auth.mode="password" Authorization: Bearer <password>. از طریق gateway.auth.password یا OPENCLAW_GATEWAY_PASSWORD تنظیم کنید.
gateway.auth.mode="trusted-proxy" از طریق پراکسی پیکربندی‌شدهٔ آگاه از هویت مسیریابی کنید؛ این پراکسی سرآیندهای هویت موردنیاز را تزریق می‌کند. پراکسی‌های loopback روی همان میزبان به gateway.auth.trustedProxy.allowLoopback = true صریح نیاز دارند.
gateway.auth.mode="none" نیازی به سرآیند احراز هویت نیست (فقط ورودی خصوصی).

نکات:

  • فراخواننده‌های روی همان میزبان که در یک Gateway با trusted-proxy پراکسی را دور می‌زنند، می‌توانند مستقیماً از gateway.auth.password / OPENCLAW_GATEWAY_PASSWORD به‌عنوان مسیر جایگزین استفاده کنند. هرگونه شواهد سرآیند Forwarded، X-Forwarded-* یا X-Real-IP باعث می‌شود درخواست همچنان در مسیر trusted-proxy باقی بماند.
  • اگر gateway.auth.rateLimit پیکربندی شده باشد و تلاش‌های احراز هویت بیش‌ازحد شکست بخورند، نقطهٔ پایانی 429 را با سرآیند Retry-After برمی‌گرداند.

زمان استفاده از این نقطهٔ پایانی

  • وقتی یکپارچه‌سازی شما صرفاً سطح اپراتور/کلاینت دیگری برای همان Gateway است، این گزینه را به افزودن کانال داخلی جدید ترجیح دهید.
  • برای کلاینت‌های موبایل بومی که مستقیماً به Gateway راه دور متصل می‌شوند، WebChat یا پروتکل Gateway را با جریان راه‌اندازی اولیهٔ دستگاه جفت‌شده/توکن دستگاه ترجیح دهید تا دستگاه به توکن/گذرواژهٔ HTTP مشترک نیاز نداشته باشد.
  • هنگام یکپارچه‌سازی شبکهٔ پیام‌رسان خارجی با کاربران، اتاق‌ها، تحویل Webhook یا انتقال خروجی مختص خود، به‌جای آن یک Plugin کانال بسازید. به ساخت Pluginها مراجعه کنید.

قرارداد مدل عامل‌محور

OpenClaw فیلد model متعلق به OpenAI را نه به‌عنوان شناسهٔ خام مدل ارائه‌دهنده، بلکه به‌عنوان مقصد عامل در نظر می‌گیرد.

مقدار model مسیریابی به
openclaw عامل پیش‌فرض پیکربندی‌شده
openclaw/default عامل پیش‌فرض پیکربندی‌شده (نام مستعار پایدار؛ حتی اگر شناسهٔ واقعی عامل پیش‌فرض بین محیط‌ها تغییر کند، می‌توان آن را با خیال راحت به‌صورت ثابت در کد قرار داد)
openclaw/<agentId> یا openclaw:<agentId> عامل مشخص
agent:<agentId> عامل مشخص (نام مستعار سازگاری)

سرآیندهای اختیاری درخواست:

سرآیند اثر
x-openclaw-model: <provider/model-or-bare-id> مدل پشتیبان عامل انتخاب‌شده را بازنویسی می‌کند. فراخواننده‌های bearer با راز مشترک می‌توانند مستقیماً از این مورد استفاده کنند؛ فراخواننده‌های حامل هویت (trusted-proxy یا ورودی خصوصی بدون احراز هویت همراه با x-openclaw-scopes) به operator.admin نیاز دارند، در غیر این صورت 403 missing scope: operator.admin.
x-openclaw-agent-id: <agentId> بازنویسی سازگاری برای انتخاب عامل.
x-openclaw-session-key: <sessionKey> مسیریابی صریح نشست. اگر از فضای نام داخلی رزروشده (subagent:، cron:، acp:) استفاده کند، با 400 invalid_request_error رد می‌شود.
x-openclaw-message-channel: <channel> زمینهٔ کانال ورودی مصنوعی را برای اعلان‌ها/خط‌مشی‌های آگاه از کانال تنظیم می‌کند.

/v1/models مقصدهای عامل سطح‌بالا (openclaw، openclaw/default، openclaw/<agentId>) را فهرست می‌کند، نه مدل‌های ارائه‌دهندهٔ پشتیبان و نه زیرعامل‌ها؛ زیرعامل‌ها توپولوژی اجرای داخلی باقی می‌مانند. اگر x-openclaw-model را حذف کنید، عامل انتخاب‌شده با مدل عادی پیکربندی‌شدهٔ خود اجرا می‌شود.

/v1/embeddings از همان شناسه‌های model مقصد عامل استفاده می‌کند. برای انتخاب یک مدل تعبیه‌سازی مشخص، x-openclaw-model را ارسال کنید (از فراخواننده‌ای با راز مشترک یا فراخواننده‌ای حامل هویت با operator.admin)؛ در غیر این صورت، درخواست از تنظیم عادی تعبیه‌سازی عامل انتخاب‌شده استفاده می‌کند.

رفتار نشست

به‌طور پیش‌فرض، نقطهٔ پایانی برای هر درخواست بدون حالت است (در هر فراخوانی، یک کلید نشست جدید تولید می‌شود).

اگر درخواست شامل رشتهٔ user متعلق به OpenAI باشد، Gateway یک کلید نشست پایدار از آن استخراج می‌کند تا فراخوانی‌های تکراری بتوانند یک نشست عامل را به‌اشتراک بگذارند. برای برنامه‌های سفارشی، در هر رشتهٔ مکالمه از همان مقدار user دوباره استفاده کنید؛ مگر اینکه بخواهید چند مکالمه/دستگاه یک نشست OpenClaw را به‌اشتراک بگذارند، از شناسه‌های سطح حساب استفاده نکنید. فقط وقتی به کنترل مسیریابی صریح میان چند کلاینت/رشته نیاز دارید از x-openclaw-session-key استفاده کنید؛ کلیدهای متعلق به برنامه باید از فضاهای نام رزروشدهٔ بالا اجتناب کنند.

محدودیت‌های درخواست

این نقطهٔ پایانی از محدودیت‌های داخلی 20 MB برای بدنهٔ هر درخواست، 8 بخش image_url از جدیدترین پیام کاربر و 20 MB دادهٔ تصویری رمزگشایی‌شدهٔ تجمعی استفاده می‌کند. خط‌مشی منبع تصویر همچنان در gateway.http.endpoints.chatCompletions.images قابل پیکربندی است:

json5
{  gateway: {    http: {      endpoints: {        chatCompletions: {          enabled: true,          images: {            allowUrl: false,            urlAllowlist: ["cdn.example.com", "*.assets.example.com"],            allowedMimes: [              "image/jpeg",              "image/png",              "image/gif",              "image/webp",              "image/heic",              "image/heif",            ],            maxBytes: 10485760,            maxRedirects: 3,            timeoutMs: 10000,          },        },      },    },  },}

تنظیمات پیش‌فرض تصویر:

کلید پیش‌فرض
images.allowUrl false (بخش‌های image_url با منبع URL، مگر در صورت فعال‌سازی، رد می‌شوند)
images.maxBytes 10MB برای هر تصویر
images.maxRedirects 3
images.timeoutMs 10s

منابع image_url با فرمت HEIC/HEIF پذیرفته می‌شوند و پیش از تحویل به ارائه‌دهنده، از طریق پردازشگر تصویر مشترک OpenClaw ‏(Rastermill) به JPEG تبدیل می‌شوند؛ این پردازشگر برای فرمت‌هایی که به پشتیبانی کُدک خارجی نیاز دارند، از یک مبدل سیستمی (sips، ImageMagick، GraphicsMagick یا ffmpeg) به‌عنوان مسیر جایگزین استفاده می‌کند.

نکتهٔ امنیتی: قرار دادن نام میزبان در فهرست مجاز، مسدودسازی IPهای خصوصی/داخلی را دور نمی‌زند. برای Gatewayهای در معرض اینترنت، علاوه بر محافظ‌های سطح برنامه، کنترل‌های خروجی شبکه را اعمال کنید. به امنیت مراجعه کنید.

قرارداد ابزار گفتگو

/v1/chat/completions از زیرمجموعه‌ای از ابزارهای تابعی سازگار با کلاینت‌های رایج Chat متعلق به OpenAI پشتیبانی می‌کند.

فیلدهای درخواست پشتیبانی‌شده

فیلد توضیحات
tools آرایه‌ای از { "type": "function", "function": { ... } }
tool_choice "auto"، "none"، "required" یا { "type": "function", "function": { "name": "..." } }
messages[*].role: "tool" نوبت‌های پیگیری
messages[*].tool_call_id نتیجهٔ یک ابزار را به فراخوانی قبلی آن ابزار متصل می‌کند
max_completion_tokens عدد؛ سقف مجموع توکن‌های تکمیل در هر فراخوانی (شامل توکن‌های استدلال). نام فعلی فیلد؛ هنگامی‌که این فیلد و max_tokens هر دو ارسال شوند، از این فیلد استفاده می‌شود.
max_tokens عدد؛ نام مستعار قدیمی که در صورت وجود max_completion_tokens نادیده گرفته می‌شود.
temperature عددی از 0 تا 2؛ به‌صورت بهترین تلاش به ارائه‌دهندهٔ بالادستی ارسال می‌شود. اگر خارج از محدوده باشد، 400 invalid_request_error.
top_p عددی از 0 تا 1؛ به‌صورت بهترین تلاش. اگر خارج از محدوده باشد، 400 invalid_request_error.
frequency_penalty عددی از -2.0 تا 2.0؛ به‌صورت بهترین تلاش. اگر خارج از محدوده باشد، 400 invalid_request_error.
presence_penalty عددی از -2.0 تا 2.0؛ به‌صورت بهترین تلاش. اگر خارج از محدوده باشد، 400 invalid_request_error.
seed عدد صحیح؛ به‌صورت بهترین تلاش. برای مقادیر غیرصحیح، 400 invalid_request_error.
stop رشته یا آرایه‌ای با حداکثر 4 رشته؛ به‌صورت بهترین تلاش. برای بیش از 4 دنباله یا ورودی‌های غیررشته‌ای/خالی، 400 invalid_request_error.

همهٔ فیلدهای نمونه‌برداری و سقف توکن از همان کانال پارامترهای جریان عامل عبور می‌کنند و به‌صورت بهترین تلاش ارسال می‌شوند:

  • سقف توکن: نام فیلد روی سیم را انتقال‌دهندهٔ ارائه‌دهنده انتخاب می‌کند: max_completion_tokens برای نقاط پایانی خانوادهٔ OpenAI و max_tokens برای ارائه‌دهندگانی که فقط نام قدیمی را می‌پذیرند (Mistral، Chutes).
  • stop به فیلد توقف انتقال‌دهنده نگاشت می‌شود: stop برای بک‌اندهای Chat Completions و stop_sequences برای Anthropic. API ‏OpenAI Responses پارامتر توقف ندارد؛ بنابراین stop روی مدل‌های مبتنی بر Responses اعمال نمی‌شود.
  • بک‌اند Codex Responses مبتنی بر ChatGPT از نمونه‌برداری ثابت سمت سرور استفاده می‌کند و پیش از رسیدن درخواست به آن بک‌اند، temperature/top_p (همراه با max_output_tokens، metadata، prompt_cache_retention و service_tier) را حذف می‌کند.

گونه‌های پشتیبانی‌نشده

در موارد زیر 400 invalid_request_error برمی‌گرداند:

  • tools غیرآرایه‌ای، ورودی‌های ابزار غیرفراخوانی یا نبود tool.function.name
  • گونه‌های tool_choice مانند allowed_tools و custom
  • مقادیر tool_choice.function.name که با هیچ‌یک از ابزارهای ارائه‌شده مطابقت ندارند

برای tool_choice: "required" و tool_choice سنجاق‌شده به تابع، نقطهٔ پایانی مجموعهٔ ابزارهای تابعی کلاینتِ در معرض نمایش را محدود می‌کند، به زمان اجرا دستور می‌دهد پیش از پاسخ‌گویی یک ابزار کلاینت را فراخوانی کند و اگر پاسخ عامل فاقد فراخوانی ساختاریافته و منطبق ابزار کلاینت باشد، خطا می‌دهد. این رفتار بر فهرست HTTP ‏tools ارائه‌شده توسط فراخواننده اعمال می‌شود، نه بر همهٔ ابزارهای داخلی عامل OpenClaw.

شکل پاسخ ابزار در حالت غیرجریانی

هنگامی‌که عامل ابزارها را فراخوانی می‌کند، پاسخ از این ساختار استفاده می‌کند:

  • choices[0].finish_reason = "tool_calls"
  • ورودی‌های choices[0].message.tool_calls[] با id، type: "function"، function.name، function.arguments (رشتهٔ JSON)
  • توضیحات دستیار پیش از فراخوانی ابزار، در choices[0].message.content (ممکن است خالی باشد)

شکل پاسخ ابزار در حالت جریانی

هنگامی‌که stream: true، فراخوانی‌های ابزار به‌صورت قطعه‌های افزایشی SSE می‌رسند: یک دلتای اولیهٔ نقش دستیار، دلتاهای اختیاری توضیحات دستیار، یک یا چند قطعهٔ delta.tool_calls حامل هویت ابزار و بخش‌های آرگومان، و سپس یک قطعهٔ نهایی با finish_reason: "tool_calls" و data: [DONE].

اگر stream_options.include_usage=true، پیش از [DONE] یک قطعهٔ پایانیِ میزان استفاده منتشر می‌شود.

حلقهٔ پیگیری ابزار

پس از دریافت tool_calls، تابع یا توابع درخواستی را اجرا کنید و یک درخواست پیگیری بفرستید که شامل پیام قبلی فراخوانی ابزارِ دستیار، به‌علاوهٔ یک یا چند پیام role: "tool" با tool_call_id منطبق باشد. این کار همان حلقهٔ استدلال عامل را برای تولید پاسخ نهایی ادامه می‌دهد.

جریان‌دهی (SSE)

برای دریافت رویدادهای ارسال‌شده از سرور، stream: true را تنظیم کنید:

  • Content-Type: text/event-stream
  • هر خط رویداد data: <json> است
  • جریان با data: [DONE] پایان می‌یابد

راه‌اندازی سریع Open WebUI

  • نشانی پایه: http://127.0.0.1:18789/v1
  • نشانی پایهٔ Docker در macOS: http://host.docker.internal:18789/v1
  • کلید API: توکن حامل Gateway شما
  • مدل: openclaw/default

رفتار مورد انتظار: GET /v1/models، openclaw/default را فهرست می‌کند و Open WebUI از آن به‌عنوان شناسهٔ مدل گفت‌وگو استفاده می‌کند. برای یک ارائه‌دهنده/مدل بک‌اند مشخص، مدل پیش‌فرض عادی عامل را تنظیم کنید یا x-openclaw-model را ارسال کنید (فراخوانندهٔ دارای راز مشترک، یا فراخوانندهٔ دارای هویت با operator.admin).

آزمایش سریع دود:

bash
curl -sS http://127.0.0.1:18789/v1/models \  -H 'Authorization: Bearer YOUR_TOKEN'

اگر این دستور openclaw/default را برگرداند، بیشتر پیکربندی‌های Open WebUI می‌توانند با همان نشانی پایه و توکن متصل شوند.

نمونه‌ها

نشست پایدار برای یک گفت‌وگوی برنامه:

bash
curl -sS http://127.0.0.1:18789/v1/chat/completions \  -H 'Authorization: Bearer YOUR_TOKEN' \  -H 'Content-Type: application/json' \  -d '{    "model": "openclaw/default",    "user": "conv:YOUR_CONVERSATION_ID",    "messages": [{"role":"user","content":"کارهای امروز من را خلاصه کن"}]  }'

برای ادامهٔ همان نشست عامل، در فراخوانی‌های بعدی مربوط به آن گفت‌وگو از همان مقدار user دوباره استفاده کنید.

غیرجریانی:

bash
curl -sS http://127.0.0.1:18789/v1/chat/completions \  -H 'Authorization: Bearer YOUR_TOKEN' \  -H 'Content-Type: application/json' \  -d '{    "model": "openclaw/default",    "messages": [{"role":"user","content":"سلام"}]  }'

جریانی:

bash
curl -N http://127.0.0.1:18789/v1/chat/completions \  -H 'Authorization: Bearer YOUR_TOKEN' \  -H 'Content-Type: application/json' \  -H 'x-openclaw-model: openai/gpt-5.4' \  -d '{    "model": "openclaw/research",    "stream": true,    "messages": [{"role":"user","content":"سلام"}]  }'

فهرست‌کردن مدل‌ها:

bash
curl -sS http://127.0.0.1:18789/v1/models \  -H 'Authorization: Bearer YOUR_TOKEN'

دریافت یک مدل:

bash
curl -sS http://127.0.0.1:18789/v1/models/openclaw%2Fdefault \  -H 'Authorization: Bearer YOUR_TOKEN'

ایجاد تعبیه‌ها:

bash
curl -sS http://127.0.0.1:18789/v1/embeddings \  -H 'Authorization: Bearer YOUR_TOKEN' \  -H 'Content-Type: application/json' \  -H 'x-openclaw-model: openai/text-embedding-3-small' \  -d '{    "model": "openclaw/default",    "input": ["آلفا", "بتا"]  }'

/v1/embeddings از input به‌صورت یک رشته یا آرایه‌ای از رشته‌ها پشتیبانی می‌کند.

مرتبط

Was this useful?
On this page

On this page