---
read_when:
    - تغییر اجرای پاسخ خودکار یا همزمانی
    - توضیح حالت‌های /queue یا رفتار هدایت پیام
summary: حالت‌های صف پاسخ خودکار، پیش‌فرض‌ها، و بازنویسی‌های مخصوص هر نشست
title: صف فرمان‌ها
x-i18n:
    generated_at: "2026-05-06T09:13:24Z"
    model: gpt-5.5
    provider: openai
    source_hash: 8f182195b740d678044a203387da6368df77ac2a6bb0eb29653bb8ea45264aaf
    source_path: concepts/queue.md
    workflow: 16
---

ما اجرای پاسخ خودکار ورودی (همه کانال‌ها) را از طریق یک صف کوچک درون‌پردازشی سریال‌سازی می‌کنیم تا از برخورد چند اجرای agent جلوگیری شود، در حالی که همچنان موازی‌سازی امن میان sessionها ممکن باشد.

## چرا

- اجرای پاسخ خودکار می‌تواند پرهزینه باشد (فراخوانی‌های LLM) و وقتی چند پیام ورودی با فاصله زمانی کم برسند، ممکن است با هم برخورد کنند.
- سریال‌سازی از رقابت بر سر منابع مشترک (فایل‌های session، لاگ‌ها، stdin مربوط به CLI) جلوگیری می‌کند و احتمال محدودیت نرخ از سمت upstream را کاهش می‌دهد.

## نحوه کار

- یک صف FIFO آگاه از lane، هر lane را با سقف هم‌زمانی قابل تنظیم تخلیه می‌کند (پیش‌فرض 1 برای laneهای پیکربندی‌نشده؛ مقدار پیش‌فرض main برابر 4 و subagent برابر 8 است).
- `runEmbeddedPiAgent` بر اساس **کلید session** (lane `session:<key>`) در صف قرار می‌گیرد تا تضمین شود برای هر session فقط یک اجرای فعال وجود دارد.
- سپس هر اجرای session در یک **lane سراسری** (به‌طور پیش‌فرض `main`) صف‌بندی می‌شود تا موازی‌سازی کلی با `agents.defaults.maxConcurrent` محدود شود.
- وقتی لاگ‌گیری مفصل فعال باشد، اجراهای صف‌شده اگر پیش از شروع بیش از حدود 2s منتظر مانده باشند، یک اعلان کوتاه منتشر می‌کنند.
- نشانگرهای تایپ همچنان بلافاصله هنگام قرار گرفتن در صف فعال می‌شوند (وقتی کانال پشتیبانی کند)، بنابراین تجربه کاربر هنگام انتظار برای نوبت خود تغییر نمی‌کند.

## پیش‌فرض‌ها

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

- `mode: "steer"`
- `debounceMs: 500`
- `cap: 20`
- `drop: "summarize"`

`steer` پیش‌فرض است چون نوبت model فعال را پاسخ‌گو نگه می‌دارد بدون اینکه اجرای session دوم را شروع کند. همه پیام‌های steering را که پیش از مرز بعدی model رسیده‌اند تخلیه می‌کند. اگر اجرای فعلی نتواند steering را بپذیرد، OpenClaw به یک ورودی صف followup برمی‌گردد.

## حالت‌های صف

پیام‌های ورودی می‌توانند اجرای فعلی را steer کنند، برای نوبت followup منتظر بمانند، یا هر دو را انجام دهند:

- `steer`: پیام‌های steering را در runtime فعال صف‌بندی می‌کند. Pi همه پیام‌های steering معلق را **بعد از اینکه نوبت فعلی assistant اجرای tool callهای خود را تمام کرد** و پیش از فراخوانی LLM بعدی تحویل می‌دهد؛ Codex app-server یک `turn/steer` دسته‌ای دریافت می‌کند. اگر اجرا به‌طور فعال streaming نکند یا steering در دسترس نباشد، OpenClaw به یک ورودی صف followup برمی‌گردد.
- `queue` (legacy): steering قدیمی یکی‌در‌هر‌بار. Pi در هر مرز model یک پیام steering صف‌شده را تحویل می‌دهد؛ Codex app-server درخواست‌های جداگانه `turn/steer` دریافت می‌کند. مگر اینکه به رفتار سریال‌سازی‌شده قبلی نیاز داشته باشید، `steer` را ترجیح دهید.
- `followup`: هر پیام را برای یک نوبت agent بعدی پس از پایان اجرای فعلی در صف قرار می‌دهد.
- `collect`: پیام‌های صف‌شده را پس از پنجره سکوت در یک نوبت followup **واحد** ادغام می‌کند. اگر پیام‌ها کانال‌ها/threadهای متفاوتی را هدف بگیرند، برای حفظ routing به‌صورت جداگانه تخلیه می‌شوند.
- `steer-backlog` (یا `steer+backlog`): اکنون steer می‌کند **و** همان پیام را برای یک نوبت followup حفظ می‌کند.
- `interrupt` (legacy): اجرای فعال آن session را لغو می‌کند، سپس جدیدترین پیام را اجرا می‌کند.

Steer-backlog یعنی می‌توانید پس از اجرای steer‌شده یک پاسخ followup دریافت کنید، بنابراین سطح‌های streaming ممکن است شبیه تکرار به نظر برسند. اگر برای هر پیام ورودی یک پاسخ می‌خواهید، `collect`/`steer` را ترجیح دهید.

برای زمان‌بندی و رفتار وابستگی ویژه runtime، [صف Steering](/fa/concepts/queue-steering) را ببینید. برای فرمان صریح `/steer <message>`، [Steer](/fa/tools/steer) را ببینید.

به‌صورت سراسری یا برای هر کانال از طریق `messages.queue` پیکربندی کنید:

```json5
{
  messages: {
    queue: {
      mode: "steer",
      debounceMs: 500,
      cap: 20,
      drop: "summarize",
      byChannel: { discord: "collect" },
    },
  },
}
```

## گزینه‌های صف

گزینه‌ها روی `followup`، `collect` و `steer-backlog` اعمال می‌شوند (و وقتی steering به followup برمی‌گردد، روی `steer` یا `queue` legacy نیز اعمال می‌شوند):

- `debounceMs`: پنجره سکوت پیش از تخلیه followupهای صف‌شده. اعداد تنها بر حسب میلی‌ثانیه هستند؛ واحدهای `ms`، `s`، `m`، `h` و `d` توسط گزینه‌های `/queue` پذیرفته می‌شوند.
- `cap`: بیشینه پیام‌های صف‌شده برای هر session. مقدارهای کمتر از `1` نادیده گرفته می‌شوند.
- `drop: "summarize"`: پیش‌فرض. ورودی‌های صف‌شده قدیمی‌تر را در صورت نیاز حذف می‌کند، خلاصه‌های فشرده را نگه می‌دارد و آن‌ها را به‌عنوان یک prompt followup ساختگی تزریق می‌کند.
- `drop: "old"`: ورودی‌های صف‌شده قدیمی‌تر را در صورت نیاز، بدون حفظ خلاصه‌ها حذف می‌کند.
- `drop: "new"`: وقتی صف از قبل پر است، جدیدترین پیام را رد می‌کند.

پیش‌فرض‌ها: `debounceMs: 500`، `cap: 20`، `drop: summarize`.

## اولویت

برای انتخاب حالت، OpenClaw این ترتیب را resolve می‌کند:

1. override درون‌خطی یا ذخیره‌شده برای هر session مربوط به `/queue`.
2. `messages.queue.byChannel.<channel>`.
3. `messages.queue.mode`.
4. پیش‌فرض `steer`.

برای گزینه‌ها، گزینه‌های درون‌خطی یا ذخیره‌شده `/queue` بر config اولویت دارند. سپس debounce ویژه کانال (`messages.queue.debounceMsByChannel`)، پیش‌فرض‌های debounce مربوط به Plugin، گزینه‌های سراسری `messages.queue` و پیش‌فرض‌های داخلی اعمال می‌شوند. `cap` و `drop` گزینه‌های سراسری/session هستند، نه کلیدهای config برای هر کانال.

## overrideهای هر session

- `/queue <mode>` را به‌عنوان یک فرمان مستقل بفرستید تا حالت برای session فعلی ذخیره شود.
- گزینه‌ها را می‌توان ترکیب کرد: `/queue collect debounce:0.5s cap:25 drop:summarize`
- `/queue default` یا `/queue reset`، override مربوط به session را پاک می‌کند.

## دامنه و تضمین‌ها

- روی اجرای agent پاسخ خودکار در همه کانال‌های ورودی که از خط لوله پاسخ Gateway استفاده می‌کنند اعمال می‌شود (WhatsApp web، Telegram، Slack، Discord، Signal، iMessage، webchat و غیره).
- lane پیش‌فرض (`main`) برای ورودی + Heartbeatهای اصلی در سطح پردازش است؛ برای اجازه دادن به چند session به‌صورت موازی، `agents.defaults.maxConcurrent` را تنظیم کنید.
- laneهای اضافی ممکن است وجود داشته باشند (مثلاً `cron`، `cron-nested`، `nested`، `subagent`) تا jobهای پس‌زمینه بتوانند بدون مسدود کردن پاسخ‌های ورودی به‌صورت موازی اجرا شوند. نوبت‌های agent کرون ایزوله‌شده هنگام اجرای داخلی agent خود که از `cron-nested` استفاده می‌کند، یک اسلات `cron` را نگه می‌دارند؛ هر دو از `cron.maxConcurrentRuns` استفاده می‌کنند. جریان‌های `nested` مشترک غیرکرون رفتار lane خود را حفظ می‌کنند. این اجراهای جداشده به‌عنوان [وظایف پس‌زمینه](/fa/automation/tasks) ردیابی می‌شوند.
- laneهای هر session تضمین می‌کنند که در هر لحظه فقط یک اجرای agent به یک session مشخص دست می‌زند.
- بدون وابستگی خارجی یا threadهای worker پس‌زمینه؛ فقط TypeScript + promiseها.

## عیب‌یابی

- اگر فرمان‌ها گیر کرده به نظر می‌رسند، لاگ‌های مفصل را فعال کنید و دنبال خطوط "queued for ...ms" بگردید تا تأیید کنید صف در حال تخلیه است.
- اگر به عمق صف نیاز دارید، لاگ‌های مفصل را فعال کنید و خطوط زمان‌بندی صف را زیر نظر بگیرید.
- اجراهای Codex app-server که یک turn را می‌پذیرند و سپس انتشار progress را متوقف می‌کنند، توسط adapter مربوط به Codex قطع می‌شوند تا lane فعال session بتواند آزاد شود، به‌جای اینکه منتظر timeout اجرای بیرونی بماند.
- وقتی diagnostics فعال باشد، sessionهایی که پس از `diagnostics.stuckSessionWarnMs` بدون هیچ پاسخ، tool، status، block یا پیشرفت ACP مشاهده‌شده در `processing` باقی می‌مانند، بر اساس فعالیت فعلی طبقه‌بندی می‌شوند. کار فعال به‌صورت `session.long_running` لاگ می‌شود؛ کار فعال بدون پیشرفت اخیر به‌صورت `session.stalled` لاگ می‌شود؛ `session.stuck` برای bookkeeping کهنه session بدون کار فعال رزرو شده است، و فقط همین مسیر می‌تواند lane مربوط به session آسیب‌دیده را آزاد کند تا کار صف‌شده تخلیه شود. diagnostics تکراری `session.stuck` تا وقتی session بدون تغییر بماند back off می‌کنند.

## مرتبط

- [مدیریت session](/fa/concepts/session)
- [صف Steering](/fa/concepts/queue-steering)
- [Steer](/fa/tools/steer)
- [سیاست retry](/fa/concepts/retry)
