Sessions and memory

موتور حافظهٔ QMD

QMD یک سایدکار جست‌وجوی local-first است که در کنار OpenClaw اجرا می‌شود. این ابزار BM25، جست‌وجوی برداری، و بازرتبه‌بندی را در یک باینری واحد ترکیب می‌کند و می‌تواند محتوایی فراتر از فایل‌های حافظه فضای کاری شما را نمایه‌سازی کند.

آنچه نسبت به داخلی اضافه می‌کند

  • بازرتبه‌بندی و گسترش پرس‌وجو برای بازیابی بهتر.
  • نمایه‌سازی دایرکتوری‌های اضافی -- مستندات پروژه، یادداشت‌های تیم، هر چیزی روی دیسک.
  • نمایه‌سازی رونوشت‌های نشست -- بازیابی گفت‌وگوهای قبلی.
  • کاملا محلی -- با بسته زمان اجرای اختیاری node-llama-cpp اجرا می‌شود و مدل‌های GGUF را به‌طور خودکار دانلود می‌کند.
  • بازگشت خودکار -- اگر QMD در دسترس نباشد، OpenClaw بی‌وقفه به موتور داخلی برمی‌گردد.

شروع کار

پیش‌نیازها

  • QMD را نصب کنید: npm install -g @tobilu/qmd یا bun install -g @tobilu/qmd
  • بیلد SQLite که افزونه‌ها را مجاز می‌کند (brew install sqlite در macOS).
  • QMD باید در PATH مربوط به Gateway باشد.
  • macOS و Linux بدون تنظیمات اضافی کار می‌کنند. Windows از طریق WSL2 بهترین پشتیبانی را دارد.

فعال‌سازی

{
  memory: {
    backend: "qmd",
  },
}

OpenClaw یک خانه QMD خودبسنده زیر ~/.openclaw/agents/<agentId>/qmd/ ایجاد می‌کند و چرخه عمر سایدکار را به‌طور خودکار مدیریت می‌کند -- مجموعه‌ها، به‌روزرسانی‌ها، و اجرای embedding برای شما انجام می‌شوند. این حالت شکل‌های فعلی مجموعه QMD و پرس‌وجوی MCP را ترجیح می‌دهد، اما همچنان در صورت نیاز به پرچم‌های الگوی مجموعه جایگزین و نام‌های قدیمی‌تر ابزار MCP برمی‌گردد. همگام‌سازی زمان راه‌اندازی همچنین وقتی یک مجموعه QMD قدیمی‌تر با همان نام هنوز وجود دارد، مجموعه‌های مدیریت‌شده کهنه را دوباره به الگوهای متعارفشان بازمی‌سازد.

نحوه کار سایدکار

  • OpenClaw از فایل‌های حافظه فضای کاری شما و هر memory.qmd.paths پیکربندی‌شده مجموعه می‌سازد، سپس هنگام باز شدن مدیر QMD و به‌صورت دوره‌ای پس از آن (به‌طور پیش‌فرض هر ۵ دقیقه) qmd update را اجرا می‌کند. این بازخوانی‌ها از طریق زیرفرایندهای QMD اجرا می‌شوند، نه خزش فایل‌سیستم درون‌فرایندی. حالت‌های معنایی همچنین qmd embed را اجرا می‌کنند.
  • مجموعه پیش‌فرض فضای کاری، MEMORY.md به‌علاوه درخت memory/ را دنبال می‌کند. memory.md با حروف کوچک به‌عنوان فایل حافظه ریشه نمایه‌سازی نمی‌شود.
  • اسکنر خود QMD مسیرهای مخفی و دایرکتوری‌های رایج وابستگی/بیلد مانند .git، .cache، node_modules، vendor، dist، و build را نادیده می‌گیرد. راه‌اندازی Gateway به‌طور پیش‌فرض QMD را مقداردهی اولیه نمی‌کند، بنابراین بوت سرد از وارد کردن زمان اجرای حافظه یا ایجاد ناظر بلندمدت پیش از نخستین استفاده از حافظه جلوگیری می‌کند.
  • اگر با این حال بازخوانی هنگام شروع Gateway را می‌خواهید، memory.qmd.update.startup را روی idle یا immediate تنظیم کنید. بازخوانی اختیاری هنگام شروع، به‌جای ایجاد ناظر کامل و بلندمدت درون‌فرایندی، از مسیر زیرفرایند یک‌باره QMD استفاده می‌کند.
  • جست‌وجوها از searchMode پیکربندی‌شده استفاده می‌کنند (پیش‌فرض: search؛ همچنین از vsearch و query پشتیبانی می‌کند). search فقط BM25 است، بنابراین OpenClaw در این حالت بررسی‌های آمادگی برداری معنایی و نگهداری embedding را رد می‌کند. اگر حالتی شکست بخورد، OpenClaw با qmd query دوباره تلاش می‌کند.
  • با نسخه‌های QMD که فیلترهای چندمجموعه‌ای را اعلام می‌کنند، OpenClaw مجموعه‌های هم‌منبع را در یک فراخوانی جست‌وجوی QMD گروه‌بندی می‌کند. نسخه‌های قدیمی‌تر QMD مسیر بازگشت سازگار به‌ازای هر مجموعه را نگه می‌دارند.
  • اگر QMD کاملا شکست بخورد، OpenClaw به موتور داخلی SQLite برمی‌گردد. تلاش‌های تکراری در نوبت‌های چت پس از شکست در باز کردن، برای مدت کوتاهی عقب‌نشینی می‌کنند تا نبود باینری یا خرابی وابستگی سایدکار باعث توفان تلاش مجدد نشود؛ openclaw memory status و بررسی‌های یک‌باره CLI همچنان QMD را مستقیما دوباره بررسی می‌کنند.

کارایی جست‌وجو و سازگاری

OpenClaw مسیر جست‌وجوی QMD را با نصب‌های فعلی و قدیمی‌تر QMD سازگار نگه می‌دارد.

هنگام راه‌اندازی، OpenClaw متن راهنمای QMD نصب‌شده را برای هر مدیر یک‌بار بررسی می‌کند. اگر باینری پشتیبانی از چند فیلتر مجموعه را اعلام کند، OpenClaw همه مجموعه‌های هم‌منبع را با یک فرمان جست‌وجو می‌کند:

qmd search "router notes" --json -n 10 -c memory-root-main -c memory-dir-main

این کار از شروع یک زیرفرایند QMD برای هر مجموعه حافظه پایدار جلوگیری می‌کند. مجموعه‌های رونوشت نشست در گروه منبع خودشان باقی می‌مانند، بنابراین جست‌وجوهای ترکیبی memory + sessions همچنان ورودی متنوع‌ساز نتیجه را از هر دو منبع دریافت می‌کنند.

بیلدهای قدیمی‌تر QMD فقط یک فیلتر مجموعه را می‌پذیرند. وقتی OpenClaw یکی از آن بیلدها را تشخیص می‌دهد، مسیر سازگاری را نگه می‌دارد و هر مجموعه را پیش از ادغام و حذف موارد تکراری، جداگانه جست‌وجو می‌کند.

برای بررسی دستی قرارداد نصب‌شده، اجرا کنید:

qmd --help | grep -i collection

راهنمای فعلی QMD می‌گوید فیلترهای مجموعه می‌توانند یک یا چند مجموعه را هدف بگیرند. راهنمای قدیمی‌تر معمولا یک مجموعه واحد را توصیف می‌کند.

بازنویسی‌های مدل

متغیرهای محیطی مدل QMD بدون تغییر از فرایند Gateway عبور می‌کنند، بنابراین می‌توانید QMD را به‌صورت سراسری بدون افزودن پیکربندی جدید OpenClaw تنظیم کنید:

export QMD_EMBED_MODEL="hf:Qwen/Qwen3-Embedding-0.6B-GGUF/Qwen3-Embedding-0.6B-Q8_0.gguf"
export QMD_RERANK_MODEL="/absolute/path/to/reranker.gguf"
export QMD_GENERATE_MODEL="/absolute/path/to/generator.gguf"

پس از تغییر مدل embedding، embeddingها را دوباره اجرا کنید تا نمایه با فضای برداری جدید مطابق شود.

نمایه‌سازی مسیرهای اضافی

QMD را به دایرکتوری‌های اضافی اشاره دهید تا قابل جست‌وجو شوند:

{
  memory: {
    backend: "qmd",
    qmd: {
      paths: [{ name: "docs", path: "~/notes", pattern: "**/*.md" }],
    },
  },
}

بریده‌های مسیرهای اضافی در نتایج جست‌وجو به‌صورت qmd/<collection>/<relative-path> ظاهر می‌شوند. memory_get این پیشوند را می‌فهمد و از ریشه مجموعه درست می‌خواند.

نمایه‌سازی رونوشت‌های نشست

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

{
  memory: {
    backend: "qmd",
    qmd: {
      sessions: { enabled: true },
    },
  },
}

رونوشت‌ها به‌صورت نوبت‌های پاک‌سازی‌شده User/Assistant به یک مجموعه اختصاصی QMD زیر ~/.openclaw/agents/<id>/qmd/sessions/ صادر می‌شوند.

دامنه جست‌وجو

به‌طور پیش‌فرض، نتایج جست‌وجوی QMD در نشست‌های مستقیم و کانالی نمایش داده می‌شوند (نه گروه‌ها). برای تغییر این مورد، memory.qmd.scope را پیکربندی کنید:

{
  memory: {
    qmd: {
      scope: {
        default: "deny",
        rules: [{ action: "allow", match: { chatType: "direct" } }],
      },
    },
  },
}

وقتی دامنه یک جست‌وجو را رد می‌کند، OpenClaw هشداری با کانال و نوع چت استخراج‌شده ثبت می‌کند تا اشکال‌زدایی نتایج خالی آسان‌تر شود.

ارجاع‌ها

وقتی memory.citations برابر auto یا on باشد، بریده‌های جست‌وجو یک پانوشت Source: <path#line> شامل می‌شوند. memory.citations = "off" را تنظیم کنید تا پانوشت حذف شود، در حالی که مسیر همچنان به‌صورت داخلی به عامل ارسال می‌شود.

زمان استفاده

QMD را زمانی انتخاب کنید که نیاز دارید:

  • بازرتبه‌بندی برای نتایج باکیفیت‌تر.
  • جست‌وجوی مستندات پروژه یا یادداشت‌های بیرون از فضای کاری.
  • بازیابی گفت‌وگوهای نشست‌های گذشته.
  • جست‌وجوی کاملا محلی بدون کلیدهای API.

برای راه‌اندازی‌های ساده‌تر، موتور داخلی بدون وابستگی‌های اضافی به‌خوبی کار می‌کند.

عیب‌یابی

QMD پیدا نشد؟ مطمئن شوید باینری در PATH مربوط به Gateway قرار دارد. اگر OpenClaw به‌صورت سرویس اجرا می‌شود، یک symlink بسازید: sudo ln -s ~/.bun/bin/qmd /usr/local/bin/qmd.

اگر qmd --version در شل شما کار می‌کند اما OpenClaw همچنان spawn qmd ENOENT گزارش می‌دهد، احتمالا فرایند Gateway نسبت به شل تعاملی شما PATH متفاوتی دارد. باینری را صریحا مشخص کنید:

{
  memory: {
    backend: "qmd",
    qmd: {
      command: "/absolute/path/to/qmd",
    },
  },
}

در محیطی که QMD نصب شده است از command -v qmd استفاده کنید، سپس با openclaw memory status --deep دوباره بررسی کنید.

نخستین جست‌وجو خیلی کند است؟ QMD در نخستین استفاده مدل‌های GGUF را دانلود می‌کند. با qmd query "test" و همان دایرکتوری‌های XDG که OpenClaw استفاده می‌کند، از پیش گرم کنید.

زیرفرایندهای زیاد QMD هنگام جست‌وجو؟ در صورت امکان QMD را به‌روزرسانی کنید. OpenClaw فقط وقتی QMD نصب‌شده پشتیبانی از چند فیلتر -c را اعلام کند، برای جست‌وجوهای چندمجموعه‌ای هم‌منبع از یک فرایند استفاده می‌کند؛ در غیر این صورت برای درستی، مسیر بازگشت قدیمی‌تر به‌ازای هر مجموعه را نگه می‌دارد.

QMD فقط BM25 هنوز سعی می‌کند llama.cpp را بسازد؟ memory.qmd.searchMode = "search" را تنظیم کنید. OpenClaw این حالت را فقط واژگانی در نظر می‌گیرد، بررسی‌های وضعیت برداری QMD یا نگهداری embedding را اجرا نمی‌کند، و بررسی‌های آمادگی معنایی را به راه‌اندازی‌های vsearch یا query واگذار می‌کند.

جست‌وجو timeout می‌شود؟ memory.qmd.limits.timeoutMs را افزایش دهید (پیش‌فرض: 4000ms). برای سخت‌افزار کندتر آن را روی 120000 تنظیم کنید.

نتایج خالی در چت‌های گروهی؟ memory.qmd.scope را بررسی کنید -- پیش‌فرض فقط نشست‌های مستقیم و کانالی را مجاز می‌کند.

جست‌وجوی حافظه ریشه ناگهان بیش از حد گسترده شده است؟ Gateway را دوباره راه‌اندازی کنید یا منتظر همگام‌سازی شروع بعدی بمانید. OpenClaw وقتی تعارض هم‌نام را تشخیص می‌دهد، مجموعه‌های مدیریت‌شده کهنه را دوباره به الگوهای متعارف MEMORY.md و memory/ بازمی‌سازد.

مخزن‌های موقت قابل مشاهده در فضای کاری باعث ENAMETOOLONG یا خرابی نمایه‌سازی می‌شوند؟ پیمایش QMD در حال حاضر به‌جای قواعد symlink داخلی OpenClaw، رفتار اسکنر زیربنایی QMD را دنبال می‌کند. تا زمانی که QMD پیمایش ایمن در برابر چرخه یا کنترل‌های حذف صریح را ارائه کند، checkoutهای موقت monorepo را زیر دایرکتوری‌های مخفی مانند .tmp/ یا بیرون از ریشه‌های QMD نمایه‌شده نگه دارید.

پیکربندی

برای سطح کامل پیکربندی (memory.qmd.*)، حالت‌های جست‌وجو، بازه‌های به‌روزرسانی، قواعد دامنه، و همه تنظیمات دیگر، مرجع پیکربندی حافظه را ببینید.

مرتبط