الحالة
مواصفة تنفيذ مسودة.الهدف
جعل حزمة أداة تطبيق الخادم الخاصة بـ Codex تحترم عقد دورة حياة محرك السياق نفسه في OpenClaw الذي تحترمه بالفعل دورات OpenClaw المضمّنة. يجب أن تظل الجلسة التي تستخدم المزوّد/النموذجagentRuntime.id: "codex" أو نموذج codex/* تتيح لـ Plugin محرك السياق المحدد، مثل lossless-claw، التحكم في تجميع السياق، واستيعاب ما بعد الدورة، والصيانة، وسياسة Compaction على مستوى OpenClaw بقدر ما تسمح به حدود تطبيق الخادم في Codex.
غير الأهداف
- لا تُعد تنفيذ الأجزاء الداخلية لتطبيق الخادم في Codex.
- لا تجعل Compaction الأصلي لسلسلة Codex ينتج ملخص
lossless-claw. - لا تطلب من النماذج غير Codex استخدام أداة Codex.
- لا تغيّر سلوك جلسات ACP/acpx. هذه المواصفة مخصصة فقط لمسار أداة الوكيل المضمّن غير ACP.
- لا تجعل Plugins الجهات الخارجية تسجل مصانع امتدادات تطبيق الخادم في Codex؛ يظل حد الثقة الحالي الخاص بـ Plugin المضمّن دون تغيير.
البنية الحالية
تحل حلقة التشغيل المضمّنة محرك السياق المهيأ مرة واحدة لكل تشغيل قبل اختيار أداة منخفضة المستوى ملموسة:src/agents/embedded-agent-runner/run.ts- تهيّئ Plugins محرك السياق
- تستدعي
resolveContextEngine(params.config) - تمرر
contextEngineوcontextTokenBudgetإلىrunEmbeddedAttemptWithBackend(...)
runEmbeddedAttemptWithBackend(...) إلى أداة الوكيل المحددة:
src/agents/embedded-agent-runner/run/backend.tssrc/agents/harness/selection.ts
extensions/codex/index.tsextensions/codex/harness.ts
EmbeddedRunAttemptParams التي تتلقاها محاولات OpenClaw المدمجة:
extensions/codex/src/app-server/run-attempt.ts
thread/start وthread/resume وturn/start، ويمكنها مراقبة الإشعارات، لكنها لا تستطيع تغيير مخزن السلاسل الداخلي في Codex أو أداة Compaction الأصلية.
الفجوة الحالية
تستدعي محاولات OpenClaw المدمجة دورة حياة محرك السياق مباشرة:- التمهيد/الصيانة قبل المحاولة
- التجميع قبل استدعاء النموذج
- afterTurn أو الاستيعاب بعد المحاولة
- الصيانة بعد دورة ناجحة
- Compaction محرك السياق للمحركات التي تملك Compaction
src/agents/embedded-agent-runner/run/attempt.tssrc/agents/embedded-agent-runner/run/attempt.context-engine-helpers.tssrc/agents/embedded-agent-runner/context-engine-maintenance.ts
params.contextEngine.bootstrap أو params.contextEngine.assemble أو params.contextEngine.afterTurn أو params.contextEngine.ingestBatch أو params.contextEngine.ingest أو
params.contextEngine.maintain.
كود Codex ذي الصلة:
extensions/codex/src/app-server/run-attempt.tsextensions/codex/src/app-server/thread-lifecycle.tsextensions/codex/src/app-server/event-projector.tsextensions/codex/src/app-server/compact.ts
السلوك المطلوب
بالنسبة إلى دورات أداة Codex، يجب أن تحافظ OpenClaw على دورة الحياة هذه:- قراءة نص جلسة OpenClaw المنعكس.
- تمهيد محرك السياق النشط عند وجود ملف جلسة سابق.
- تشغيل صيانة التمهيد عند توفرها.
- تجميع السياق باستخدام محرك السياق النشط.
- تحويل السياق المجمّع إلى مدخلات متوافقة مع Codex.
- بدء سلسلة Codex أو استئنافها بتعليمات مطوّر تتضمن أي
systemPromptAdditionمن محرك السياق. - بدء دورة Codex بالموجّه المجمّع المواجه للمستخدم.
- عكس نتيجة Codex مرة أخرى إلى نص OpenClaw.
- استدعاء
afterTurnإذا كان منفذًا، وإلاingestBatch/ingest، باستخدام لقطة النص المنعكس. - تشغيل صيانة الدورة بعد الدورات الناجحة غير المُجهضة.
- الحفاظ على إشارات Compaction الأصلية في Codex وخطافات Compaction في OpenClaw.
قيود التصميم
يظل تطبيق الخادم في Codex هو المصدر المعتمد لحالة السلسلة الأصلية
يمتلك Codex سلسلته الأصلية وأي سجل داخلي ممتد. يجب ألا تحاول OpenClaw تعديل السجل الداخلي لتطبيق الخادم إلا عبر استدعاءات البروتوكول المدعومة. يظل انعكاس نص OpenClaw هو المصدر لميزات OpenClaw:- سجل المحادثة
- البحث
- مسك دفاتر
/newو/reset - تبديل النموذج أو الأداة مستقبلًا
- حالة Plugin محرك السياق
يجب إسقاط تجميع محرك السياق في مدخلات Codex
تعيد واجهة محرك السياقAgentMessage[] في OpenClaw، لا رقعة سلسلة Codex. يقبل turn/start في تطبيق الخادم في Codex إدخال المستخدم الحالي، بينما يقبل thread/start وthread/resume تعليمات المطوّر.
لذلك يحتاج التنفيذ إلى طبقة إسقاط. يجب أن تتجنب النسخة الأولى الآمنة الادعاء بأنها تستطيع استبدال سجل Codex الداخلي. يجب أن تحقن السياق المجمّع كمادة حتمية للموجّه/تعليمات المطوّر حول الدورة الحالية.
استقرار ذاكرة التخزين المؤقت للموجّه مهم
بالنسبة إلى محركات مثل lossless-claw، يجب أن يكون السياق المجمّع حتميًا للمدخلات غير المتغيرة. لا تضف طوابع زمنية أو معرفات عشوائية أو ترتيبًا غير حتمي إلى نص السياق المُولّد.لا تتغير دلالات اختيار وقت التشغيل
يبقى اختيار الأداة كما هو:runtime: "openclaw"يحدد أداة OpenClaw المدمجةruntime: "codex"يحدد أداة Codex المسجلةruntime: "auto"يتيح لأدوات Plugins المطالبة بالمزوّدين المدعومين- تشغيلات
autoغير المطابقة تستخدم أداة OpenClaw المدمجة
خطة التنفيذ
1. تصدير أو نقل مساعدين قابلين لإعادة الاستخدام لمحاولات محرك السياق
اليوم يعيش مساعدو دورة الحياة القابلون لإعادة الاستخدام ضمن مشغّل الوكيل المضمّن:src/agents/embedded-agent-runner/run/attempt.context-engine-helpers.tssrc/agents/embedded-agent-runner/run/attempt.prompt-helpers.tssrc/agents/embedded-agent-runner/context-engine-maintenance.ts
src/agents/harness/context-engine-lifecycle.ts
runAttemptContextEngineBootstrapassembleAttemptContextEnginefinalizeAttemptContextEngineTurnbuildAfterTurnRuntimeContextbuildAfterTurnRuntimeContextFromUsage- غلافًا صغيرًا حول
runContextEngineMaintenance
bootstrapHarnessContextEngineassembleHarnessContextEnginefinalizeHarnessContextEngineTurnbuildHarnessContextEngineRuntimeContextrunHarnessContextEngineMaintenance
2. إضافة مساعد إسقاط سياق Codex
أضف وحدة جديدة:extensions/codex/src/app-server/context-engine-projection.ts
- قبول
AgentMessage[]المجمّعة، والسجل المنعكس الأصلي، والموجّه الحالي. - تحديد أي سياق ينتمي إلى تعليمات المطوّر مقابل إدخال المستخدم الحالي.
- الحفاظ على موجّه المستخدم الحالي بصفته الطلب النهائي القابل للتنفيذ.
- عرض الرسائل السابقة بتنسيق ثابت وصريح.
- تجنب البيانات الوصفية المتقلبة.
- ضع
systemPromptAdditionفي تعليمات المطوّر. - ضع سياق النص المجمّع قبل الموجّه الحالي في
promptText. - صنّفه بوضوح كسياق مجمّع من OpenClaw.
- أبقِ الموجّه الحالي أخيرًا.
- استبعد موجّه المستخدم الحالي المكرر إذا كان يظهر بالفعل في الذيل.
3. ربط التمهيد قبل بدء سلسلة Codex
فيextensions/codex/src/app-server/run-attempt.ts:
- اقرأ سجل الجلسة المنعكس كما يحدث اليوم.
- حدد ما إذا كان ملف الجلسة موجودًا قبل هذا التشغيل. فضّل مساعدًا يتحقق من
fs.stat(params.sessionFile)قبل كتابات الانعكاس. - افتح
SessionManagerأو استخدم محوّل مدير جلسة ضيقًا إذا كان المساعد يتطلبه. - استدعِ مساعد التمهيد المحايد عند وجود
params.contextEngine.
sessionKey نفسه الذي يستخدمه جسر أدوات Codex وانعكاس النص. يحسب Codex اليوم sandboxSessionKey من params.sessionKey أو params.sessionId؛ استخدم ذلك باتساق ما لم يوجد سبب للحفاظ على params.sessionKey الخام.
4. ربط التجميع قبل thread/start / thread/resume وturn/start
في runCodexAppServerAttempt:
- ابنِ الأدوات الديناميكية أولًا، لكي يرى محرك السياق أسماء الأدوات الفعلية المتاحة.
- اقرأ سجل الجلسة المنعكس.
- شغّل
assemble(...)لمحرك السياق عند وجودparams.contextEngine. - أسقط النتيجة المجمّعة في:
- إضافة تعليمات المطوّر
- نص الموجّه لـ
turn/start
- احسب تعليمات المطوّر الأساسية باستخدام
buildDeveloperInstructions(params) - طبّق تجميع/إسقاط محرك السياق
- شغّل
before_prompt_buildبالموجّه/تعليمات المطوّر المسقطة
systemPromptAddition من محرك السياق على موجّه النظام النهائي بعد خط أنابيب الموجّه الخاص بها. الثابت المهم هو أن يحصل كل من محرك السياق والخطافات على ترتيب حتمي وموثق.
الترتيب الموصى به للتنفيذ الأول:
buildDeveloperInstructions(params)assemble()لمحرك السياق- إلحاق/إضافة
systemPromptAdditionإلى تعليمات المطوّر - إسقاط الرسائل المجمّعة في نص الموجّه
resolveAgentHarnessBeforePromptBuildResult(...)- تمرير تعليمات المطوّر النهائية إلى
startOrResumeThread(...) - تمرير نص الموجّه النهائي إلى
buildTurnStartParams(...)
5. الحفاظ على تنسيق مستقر لذاكرة التخزين المؤقت للموجّه
يجب أن ينتج مساعد الإسقاط خرجًا مستقرًا على مستوى البايت للمدخلات المتطابقة:- ترتيب رسائل ثابت
- تسميات أدوار ثابتة
- بلا طوابع زمنية مولّدة
- بلا تسرب لترتيب مفاتيح الكائنات
- بلا محددات عشوائية
- بلا معرفات لكل تشغيل
6. ربط ما بعد الدورة بعد انعكاس النص
يبنيCodexAppServerEventProjector في Codex لقطة messagesSnapshot محلية للدورة
الحالية. تكتب mirrorTranscriptBestEffort(...) تلك اللقطة في مرآة نص OpenClaw.
بعد نجاح النسخ إلى المرآة أو فشله، استدعِ المنهي الخاص بمحرك السياق باستخدام أفضل
لقطة رسائل متاحة:
- فضّل سياق الجلسة المنسوخ بالكامل إلى المرآة بعد الكتابة، لأن
afterTurnيتوقع لقطة الجلسة، وليس الدورة الحالية فقط. - ارجع إلى
historyMessages + result.messagesSnapshotإذا تعذر إعادة فتح ملف الجلسة.
afterTurn مع اللقطة الاحتياطية مع ذلك، لكن سجّل
أن محرك السياق يستوعب البيانات من بيانات الدورة الاحتياطية.
7. طبّع الاستخدام وسياق وقت تشغيل ذاكرة تخزين المطالبات المؤقتة
تتضمن نتائج Codex استخداما مطبعا من إشعارات رموز خادم التطبيق عندما تكون متاحة. مرّر ذلك الاستخدام إلى سياق وقت تشغيل محرك السياق. إذا كشف خادم تطبيق Codex لاحقا تفاصيل قراءة/كتابة ذاكرة التخزين المؤقت، فحوّلها إلىContextEnginePromptCacheInfo. إلى ذلك الحين، احذف promptCache بدلا من
اختراع أصفار.
8. سياسة Compaction
يوجد نظاما Compaction:compact()الخاص بمحرك سياق OpenClawthread/compact/startالأصلي الخاص بخادم تطبيق Codex
/compact وCompaction الصريح في OpenClaw
عندما يكون لمحرك السياق المحدد info.ownsCompaction === true، يجب أن يفضّل
Compaction الصريح في OpenClaw نتيجة compact() الخاصة بمحرك السياق لمرآة نص
OpenClaw وحالة Plugin.
عندما يكون لحزمة Codex المحددة ربط مؤشر ترابط أصلي، قد نطلب أيضا Compaction
الأصلي من Codex للحفاظ على سلامة مؤشر ترابط خادم التطبيق، لكن يجب الإبلاغ عن
ذلك كإجراء خلفية منفصل في التفاصيل.
السلوك الموصى به:
- إذا كان
contextEngine.info.ownsCompaction === true:- استدعِ
compact()الخاص بمحرك السياق أولا - ثم استدعِ Compaction الأصلي من Codex بأفضل جهد عند وجود ربط مؤشر ترابط
- أعد نتيجة محرك السياق باعتبارها النتيجة الأساسية
- ضمّن حالة Compaction الأصلي من Codex في
details.codexNativeCompaction
- استدعِ
- إذا لم يكن محرك السياق النشط يملك Compaction:
- حافظ على سلوك Compaction الأصلي الحالي في Codex
extensions/codex/src/app-server/compact.ts أو
تغليفه من مسار Compaction العام، بحسب موضع استدعاء
maybeCompactAgentHarnessSession(...).
أحداث contextCompaction الأصلية من Codex أثناء الدورة
قد يصدر Codex أحداث عناصر contextCompaction أثناء الدورة. أبقِ إصدار خطاف
Compaction قبل/بعد الحالي في event-projector.ts، لكن لا تتعامل معه على أنه
Compaction مكتمل لمحرك السياق.
بالنسبة إلى المحركات التي تملك Compaction، أصدر تشخيصا صريحا عندما ينفذ Codex
Compaction الأصلي على أي حال:
- اسم التدفق/الحدث: تدفق
compactionالحالي مقبول - التفاصيل:
{ backend: "codex-app-server", ownsCompaction: true }
9. إعادة ضبط الجلسة وسلوك الربط
يمسحreset(...) الحالي في حزمة Codex ربط خادم تطبيق Codex من ملف جلسة
OpenClaw. حافظ على هذا السلوك.
تأكد أيضا من استمرار حدوث تنظيف حالة محرك السياق عبر مسارات دورة حياة جلسة
OpenClaw الحالية. لا تضف تنظيفا خاصا بـ Codex إلا إذا كانت دورة حياة محرك السياق
لا تلتقط حاليا أحداث إعادة الضبط/الحذف لكل الحزم.
10. معالجة الأخطاء
اتبع دلالات OpenClaw المضمنة:- تحذر إخفاقات التمهيد وتستمر
- تحذر إخفاقات التجميع وتعود إلى رسائل/مطالبة مسار المعالجة غير المجمعة
- تحذر إخفاقات
afterTurn/الاستيعاب وتضع علامة على فشل الإنهاء بعد الدورة - لا تعمل الصيانة إلا بعد الدورات الناجحة وغير الملغاة وغير دورات التنازل
- يجب عدم إعادة محاولة أخطاء Compaction كمطالبات جديدة
- إذا فشل إسقاط السياق، فحذّر وارجع إلى المطالبة الأصلية.
- إذا فشلت مرآة النص، فحاول مع ذلك إنهاء محرك السياق باستخدام الرسائل الاحتياطية.
- إذا فشل Compaction الأصلي من Codex بعد نجاح Compaction الخاص بمحرك السياق، فلا تفشل Compaction الكامل في OpenClaw عندما يكون محرك السياق هو الأساسي.
خطة الاختبار
اختبارات الوحدة
أضف اختبارات ضمنextensions/codex/src/app-server:
-
run-attempt.context-engine.test.ts- يستدعي Codex الدالة
bootstrapعند وجود ملف جلسة. - يستدعي Codex الدالة
assembleمع الرسائل المنعكسة، وميزانية الرموز، وأسماء الأدوات، ووضع الاستشهادات، ومعرّف النموذج، والموجّه. - يتم تضمين
systemPromptAdditionفي تعليمات المطوّر. - تُسقط الرسائل المجمّعة في الموجّه قبل الطلب الحالي.
- يستدعي Codex الدالة
afterTurnبعد انعكاس النص المنسوخ. - من دون
afterTurn، يستدعي Codex الدالةingestBatchأوingestلكل رسالة. - تعمل صيانة الدور بعد الأدوار الناجحة.
- لا تعمل صيانة الدور عند خطأ الموجّه أو الإجهاض أو إجهاض التسليم.
- يستدعي Codex الدالة
-
context-engine-projection.test.ts- مخرجات مستقرة للمدخلات المتطابقة
- عدم تكرار الموجّه الحالي عندما يتضمن السجل المجمّع ذلك
- يتعامل مع السجل الفارغ
- يحافظ على ترتيب الأدوار
- يتضمن إضافة موجّه النظام في تعليمات المطوّر فقط
-
compact.context-engine.test.ts- النتيجة الأساسية لمحرك السياق المالك لها الأولوية
- تظهر حالة Compaction الأصلية في Codex ضمن التفاصيل عند محاولة تنفيذها أيضًا
- لا يؤدي فشل Codex الأصلي إلى فشل Compaction لمحرك السياق المالك
- يحافظ محرك السياق غير المالك على سلوك Compaction الأصلي الحالي
الاختبارات الحالية المطلوب تحديثها
extensions/codex/src/app-server/run-attempt.test.tsإن وُجد، وإلا أقرب اختبارات تشغيل Codex app-server.extensions/codex/src/app-server/event-projector.test.tsفقط إذا تغيرت تفاصيل حدث Compaction.- ينبغي ألا يحتاج
src/agents/harness/selection.test.tsإلى تغييرات إلا إذا تغير سلوك الإعدادات؛ ويجب أن يبقى مستقرًا. - يجب أن تستمر اختبارات محرك السياق المضمنة في المرور من دون تغيير.
اختبارات التكامل / الاختبارات الحية
أضف أو وسّع اختبارات الدخان الحية لحزمة Codex:- اضبط
plugins.slots.contextEngineعلى محرك اختبار - اضبط
agents.defaults.modelعلى نموذجcodex/* - اضبط
agentRuntime.id = "codex"للمزوّد/النموذج - تأكد من أن محرك الاختبار لاحظ:
- bootstrap
- assemble
- afterTurn أو ingest
- maintenance
قابلية الملاحظة
أضف سجلات تصحيح حول استدعاءات دورة حياة محرك السياق في Codex:codex context engine bootstrap started/completed/failedcodex context engine assemble appliedcodex context engine finalize completed/failedcodex context engine maintenance skippedمع السببcodex native compaction completed alongside context-engine compaction
sessionIdsessionKeyمنقّح أو محذوف وفقًا لممارسة التسجيل الحاليةengineIdthreadIdturnIdassembledMessageCountestimatedTokenshasSystemPromptAddition
الترحيل / التوافق
يجب أن يكون هذا متوافقًا مع الإصدارات السابقة:- إذا لم يتم إعداد أي محرك سياق، فيجب أن يكون سلوك محرك السياق القديم مكافئًا لسلوك حزمة Codex الحالي.
- إذا فشلت
assembleالخاصة بمحرك السياق، فيجب أن يواصل Codex عبر مسار الموجّه الأصلي. - يجب أن تظل ارتباطات خيوط Codex الحالية صالحة.
- يجب ألا يتضمن أخذ بصمة الأدوات الديناميكية مخرجات محرك السياق؛ وإلا فقد يفرض كل تغيير في السياق إنشاء خيط Codex جديد. يجب أن يؤثر كتالوج الأدوات فقط في بصمة الأدوات الديناميكية.
أسئلة مفتوحة
-
هل يجب حقن السياق المجمّع بالكامل في موجّه المستخدم، أم بالكامل
في تعليمات المطوّر، أم تقسيمه؟
التوصية: التقسيم. ضع
systemPromptAdditionفي تعليمات المطوّر؛ وضع سياق النص المنسوخ المجمّع في غلاف موجّه المستخدم. يطابق هذا بروتوكول Codex الحالي بأفضل شكل من دون تعديل سجل الخيط الأصلي. - هل يجب تعطيل Compaction الأصلي في Codex عندما يملك محرك سياق عملية Compaction؟ التوصية: لا، ليس في البداية. قد يظل Compaction الأصلي في Codex ضروريًا لإبقاء خيط app-server حيًا. لكن يجب الإبلاغ عنه بوصفه Compaction أصليًا في Codex، لا بوصفه Compaction لمحرك السياق.
-
هل يجب تشغيل
before_prompt_buildقبل تجميع محرك السياق أم بعده؟ التوصية: بعد إسقاط محرك السياق في Codex، حتى ترى خطافات الحزمة العامة الموجّه/تعليمات المطوّر الفعلية التي سيتلقاها Codex. إذا تطلب تكافؤ الحزمة المضمنة العكس، فقم بترميز الترتيب المختار في الاختبارات ووثّقه هنا. - هل يمكن أن يقبل Codex app-server تجاوزًا منظّمًا للسياق/السجل في المستقبل؟ غير معروف. إذا كان ذلك ممكنًا، فاستبدل طبقة الإسقاط النصي بذلك البروتوكول وأبقِ استدعاءات دورة الحياة من دون تغيير.
معايير القبول
- يستدعي دور حزمة مضمنة
codex/*دورة حياة assemble لمحرك السياق المحدد. - تؤثر
systemPromptAdditionالخاصة بمحرك السياق في تعليمات مطوّر Codex. - يؤثر السياق المجمّع في مُدخل دور Codex بشكل حتمي.
- تستدعي أدوار Codex الناجحة
afterTurnأو بديل ingest. - تشغّل أدوار Codex الناجحة صيانة دور محرك السياق.
- لا تشغّل الأدوار الفاشلة/المجهضة/المجهضة عند التسليم صيانة الدور.
- تبقى Compaction المملوكة لمحرك السياق أساسية لحالة OpenClaw/Plugin.
- تبقى Compaction الأصلية في Codex قابلة للتدقيق بوصفها سلوك Codex أصليًا.
- لا يتغير سلوك محرك السياق في الحزمة المضمنة الحالية.
- لا يتغير سلوك حزمة Codex الحالي عندما لا يتم تحديد محرك سياق غير قديم أو عندما يفشل التجميع.