From 4000a07bb24d0c00d9d3cfd6d96ac6b531479ac4 Mon Sep 17 00:00:00 2001 From: "openclaw-docs-i18n[bot]" Date: Mon, 4 May 2026 18:26:17 +0000 Subject: [PATCH] chore(i18n): refresh th translations --- docs/th/channels/zalouser.md | 116 ++++---- docs/th/cli/daemon.md | 47 ++-- docs/th/cli/gateway.md | 324 +++++++++++----------- docs/th/cli/models.md | 186 +++++++------ docs/th/cli/proxy.md | 69 ++--- docs/th/gateway/cli-backends.md | 335 +++++++++++----------- docs/th/help/testing-live.md | 445 +++++++++++++++--------------- docs/th/plugins/hooks.md | 366 ++++++++++++------------ docs/th/plugins/sdk-overview.md | 344 +++++++++++------------ docs/th/security/network-proxy.md | 138 ++++----- docs/th/tools/thinking.md | 171 ++++++------ 11 files changed, 1281 insertions(+), 1260 deletions(-) diff --git a/docs/th/channels/zalouser.md b/docs/th/channels/zalouser.md index afb26a5f2..50a1e47e5 100644 --- a/docs/th/channels/zalouser.md +++ b/docs/th/channels/zalouser.md @@ -3,46 +3,46 @@ read_when: - การตั้งค่า Zalo Personal สำหรับ OpenClaw - การดีบักการเข้าสู่ระบบหรือโฟลว์ข้อความของ Zalo Personal summary: การรองรับบัญชีส่วนบุคคลของ Zalo ผ่าน zca-js แบบเนทีฟ (การเข้าสู่ระบบด้วย QR), ความสามารถ และการกำหนดค่า -title: Zalo ส่วนตัว +title: Zalo ส่วนบุคคล x-i18n: - generated_at: "2026-05-02T22:17:19Z" + generated_at: "2026-05-04T18:23:43Z" model: gpt-5.5 provider: openai - source_hash: 0096775e0017e504130f2e19e05ab8114eadb873a9e11f79ea8f0dd91297567f + source_hash: 0f6d27f0ca502e6426abe21d609efd0a168a0b6b0fafe8d52d59f1a717da1ed5 source_path: channels/zalouser.md workflow: 16 --- -สถานะ: ทดลอง การผสานรวมนี้ทำให้ **บัญชี Zalo ส่วนบุคคล** ทำงานอัตโนมัติผ่าน `zca-js` แบบเนทีฟภายใน OpenClaw +สถานะ: ทดลอง การผสานการทำงานนี้ทำให้ **บัญชี Zalo ส่วนตัว** ทำงานอัตโนมัติผ่าน `zca-js` แบบเนทีฟภายใน OpenClaw -นี่เป็นการผสานรวมแบบไม่เป็นทางการ และอาจทำให้บัญชีถูกระงับหรือแบนได้ ใช้งานโดยยอมรับความเสี่ยงเอง +นี่เป็นการผสานการทำงานที่ไม่เป็นทางการและอาจทำให้บัญชีถูกระงับหรือถูกแบนได้ ใช้งานโดยยอมรับความเสี่ยงเอง -## Plugin ที่บันเดิลมาให้ +## Plugin ที่บันเดิลมา -Zalo Personal จัดส่งเป็น Plugin ที่บันเดิลมาให้ใน OpenClaw รุ่นปัจจุบัน ดังนั้นบิลด์แบบแพ็กเกจปกติ +Zalo Personal มาพร้อมเป็น Plugin ที่บันเดิลมาใน OpenClaw รุ่นปัจจุบัน ดังนั้นบิลด์แบบแพ็กเกจปกติ จึงไม่ต้องติดตั้งแยกต่างหาก -หากคุณใช้บิลด์เก่าหรือการติดตั้งแบบกำหนดเองที่ไม่รวม Zalo Personal +หากคุณใช้บิลด์เก่ากว่าหรือการติดตั้งแบบกำหนดเองที่ไม่รวม Zalo Personal ให้ติดตั้งแพ็กเกจ npm โดยตรง: - ติดตั้งผ่าน CLI: `openclaw plugins install @openclaw/zalouser` -- เวอร์ชันที่ปักไว้: `openclaw plugins install @openclaw/zalouser@2026.5.2` -- หรือจากซอร์ส checkout: `openclaw plugins install ./path/to/local/zalouser-plugin` -- รายละเอียด: [Plugins](/th/tools/plugin) +- เวอร์ชันที่ปักหมุด: `openclaw plugins install @openclaw/zalouser@2026.5.2` +- หรือจากเช็กเอาต์ซอร์ส: `openclaw plugins install ./path/to/local/zalouser-plugin` +- รายละเอียด: [Plugin](/th/tools/plugin) ไม่จำเป็นต้องมีไบนารี CLI ภายนอก `zca`/`openzca` ## การตั้งค่าอย่างรวดเร็ว (สำหรับผู้เริ่มต้น) 1. ตรวจสอบว่า Plugin Zalo Personal พร้อมใช้งาน - - OpenClaw รุ่นแพ็กเกจปัจจุบันบันเดิลมาให้อยู่แล้ว - - การติดตั้งรุ่นเก่าหรือแบบกำหนดเองสามารถเพิ่มเองได้ด้วยคำสั่งด้านบน + - OpenClaw รุ่นแพ็กเกจปัจจุบันบันเดิลไว้แล้ว + - การติดตั้งเก่ากว่าหรือแบบกำหนดเองสามารถเพิ่มเองได้ด้วยคำสั่งด้านบน 2. เข้าสู่ระบบ (QR บนเครื่อง Gateway): - `openclaw channels login --channel zalouser` - - สแกนรหัส QR ด้วยแอปมือถือ Zalo -3. เปิดใช้งานช่องทาง: + - สแกนคิวอาร์โค้ดด้วยแอปมือถือ Zalo +3. เปิดใช้ช่องทาง: ```json5 { @@ -55,19 +55,19 @@ Zalo Personal จัดส่งเป็น Plugin ที่บันเดิ } ``` -4. รีสตาร์ต Gateway (หรือทำการตั้งค่าให้เสร็จ) -5. การเข้าถึง DM มีค่าเริ่มต้นเป็นการจับคู่ อนุมัติรหัสจับคู่ในการติดต่อครั้งแรก +4. รีสตาร์ท Gateway (หรือทำการตั้งค่าให้เสร็จ) +5. การเข้าถึง DM ใช้ค่าเริ่มต้นเป็นการจับคู่ อนุมัติรหัสจับคู่เมื่อมีการติดต่อครั้งแรก -## สิ่งนี้คืออะไร +## คืออะไร -- ทำงานทั้งหมดในโปรเซสผ่าน `zca-js` -- ใช้ตัวฟังเหตุการณ์แบบเนทีฟเพื่อรับข้อความขาเข้า +- ทำงานทั้งหมดภายในโปรเซสผ่าน `zca-js` +- ใช้ตัวรับฟังเหตุการณ์แบบเนทีฟเพื่อรับข้อความขาเข้า - ส่งคำตอบโดยตรงผ่าน JS API (ข้อความ/สื่อ/ลิงก์) -- ออกแบบมาสำหรับกรณีใช้งาน “บัญชีส่วนบุคคล” ที่ Zalo Bot API ไม่พร้อมใช้งาน +- ออกแบบมาสำหรับกรณีใช้งาน “บัญชีส่วนตัว” ที่ Zalo Bot API ไม่พร้อมใช้งาน ## การตั้งชื่อ -รหัสช่องทางคือ `zalouser` เพื่อระบุให้ชัดเจนว่าสิ่งนี้ทำให้ **บัญชีผู้ใช้ Zalo ส่วนบุคคล** ทำงานอัตโนมัติ (ไม่เป็นทางการ) เราสงวน `zalo` ไว้สำหรับการผสานรวม Zalo API อย่างเป็นทางการที่อาจมีในอนาคต +รหัสช่องทางคือ `zalouser` เพื่อระบุอย่างชัดเจนว่าสิ่งนี้ทำให้ **บัญชีผู้ใช้ Zalo ส่วนตัว** ทำงานอัตโนมัติ (ไม่เป็นทางการ) เราสงวน `zalo` ไว้สำหรับการผสานการทำงานกับ Zalo API อย่างเป็นทางการที่อาจมีในอนาคต ## การค้นหา ID (ไดเรกทอรี) @@ -79,16 +79,18 @@ openclaw directory peers list --channel zalouser --query "name" openclaw directory groups list --channel zalouser --query "work" ``` -## ขีดจำกัด +## ข้อจำกัด -- ข้อความขาออกจะถูกแบ่งเป็นชิ้นประมาณ 2000 อักขระ (ขีดจำกัดของไคลเอนต์ Zalo) -- การสตรีมถูกบล็อกเป็นค่าเริ่มต้น +- ข้อความขาออกถูกแบ่งเป็นชิ้นประมาณ 2000 อักขระ (ข้อจำกัดของไคลเอนต์ Zalo) +- การสตรีมถูกบล็อกตามค่าเริ่มต้น ## การควบคุมการเข้าถึง (DM) `channels.zalouser.dmPolicy` รองรับ: `pairing | allowlist | open | disabled` (ค่าเริ่มต้น: `pairing`) -`channels.zalouser.allowFrom` รับ ID ผู้ใช้หรือชื่อ ระหว่างการตั้งค่า ชื่อจะถูกแปลงเป็น ID โดยใช้การค้นหารายชื่อติดต่อในโปรเซสของ Plugin +`channels.zalouser.allowFrom` ควรใช้ ID ผู้ใช้ Zalo ที่เสถียร ระหว่างการตั้งค่าแบบโต้ตอบ ชื่อที่ป้อนสามารถแปลงเป็น ID ได้โดยใช้การค้นหารายชื่อติดต่อภายในโปรเซสของ Plugin + +หากชื่อดิบยังอยู่ในการกำหนดค่า ตอนเริ่มต้นระบบจะแปลงชื่อเฉพาะเมื่อเปิดใช้ `channels.zalouser.dangerouslyAllowNameMatching: true` เท่านั้น หากไม่มีการเลือกใช้นี้ การตรวจสอบผู้ส่งขณะรันไทม์จะใช้เฉพาะ ID และชื่อดิบจะถูกละเว้นสำหรับการอนุญาต อนุมัติผ่าน: @@ -97,16 +99,16 @@ openclaw directory groups list --channel zalouser --query "work" ## การเข้าถึงกลุ่ม (ไม่บังคับ) -- ค่าเริ่มต้น: `channels.zalouser.groupPolicy = "open"` (อนุญาตกลุ่ม) ใช้ `channels.defaults.groupPolicy` เพื่อแทนที่ค่าเริ่มต้นเมื่อไม่ได้ตั้งค่า -- จำกัดเป็น allowlist ด้วย: +- ค่าเริ่มต้น: `channels.zalouser.groupPolicy = "open"` (อนุญาตกลุ่ม) ใช้ `channels.defaults.groupPolicy` เพื่อแทนที่ค่าเริ่มต้นเมื่อยังไม่ได้ตั้งค่า +- จำกัดไว้ที่รายการอนุญาตด้วย: - `channels.zalouser.groupPolicy = "allowlist"` - - `channels.zalouser.groups` (คีย์ควรเป็น ID กลุ่มที่เสถียร ชื่อจะถูกแปลงเป็น ID เมื่อเริ่มต้นระบบเมื่อทำได้) - - `channels.zalouser.groupAllowFrom` (ควบคุมว่าผู้ส่งรายใดในกลุ่มที่อนุญาตสามารถทริกเกอร์บอตได้) + - `channels.zalouser.groups` (คีย์ควรเป็น ID กลุ่มที่เสถียร ชื่อจะถูกแปลงเป็น ID ตอนเริ่มต้นเท่านั้นเมื่อเปิดใช้ `channels.zalouser.dangerouslyAllowNameMatching: true`) + - `channels.zalouser.groupAllowFrom` (ควบคุมว่าผู้ส่งใดในกลุ่มที่อนุญาตสามารถเรียกบอตได้) - บล็อกทุกกลุ่ม: `channels.zalouser.groupPolicy = "disabled"` -- วิซาร์ดกำหนดค่าสามารถแจ้งให้ตั้งค่า allowlist ของกลุ่มได้ -- เมื่อเริ่มต้นระบบ OpenClaw จะแปลงชื่อกลุ่ม/ผู้ใช้ใน allowlist เป็น ID และบันทึกการแมปลงในล็อก -- การจับคู่ allowlist ของกลุ่มใช้เฉพาะ ID เป็นค่าเริ่มต้น ชื่อที่แปลงไม่ได้จะถูกละเว้นสำหรับการยืนยันสิทธิ์ เว้นแต่จะเปิดใช้งาน `channels.zalouser.dangerouslyAllowNameMatching: true` -- `channels.zalouser.dangerouslyAllowNameMatching: true` เป็นโหมดความเข้ากันได้สำหรับกรณีฉุกเฉินที่เปิดการจับคู่ชื่อกลุ่มที่เปลี่ยนแปลงได้อีกครั้ง +- วิซาร์ดกำหนดค่าสามารถถามรายการอนุญาตของกลุ่มได้ +- ตอนเริ่มต้น OpenClaw จะแปลงชื่อกลุ่ม/ผู้ใช้ในรายการอนุญาตเป็น ID และบันทึกการแมปเฉพาะเมื่อเปิดใช้ `channels.zalouser.dangerouslyAllowNameMatching: true` +- การจับคู่รายการอนุญาตของกลุ่มใช้เฉพาะ ID ตามค่าเริ่มต้น ชื่อที่แปลงไม่ได้จะถูกละเว้นสำหรับการตรวจสอบสิทธิ์ เว้นแต่เปิดใช้ `channels.zalouser.dangerouslyAllowNameMatching: true` +- `channels.zalouser.dangerouslyAllowNameMatching: true` คือโหมดความเข้ากันได้แบบ break-glass ที่เปิดการแปลงชื่อตอนเริ่มต้นที่เปลี่ยนแปลงได้และการจับคู่ชื่อกลุ่มขณะรันไทม์อีกครั้ง - หากไม่ได้ตั้งค่า `groupAllowFrom` รันไทม์จะย้อนกลับไปใช้ `allowFrom` สำหรับการตรวจสอบผู้ส่งในกลุ่ม - การตรวจสอบผู้ส่งใช้กับทั้งข้อความกลุ่มปกติและคำสั่งควบคุม (เช่น `/new`, `/reset`) @@ -127,15 +129,15 @@ openclaw directory groups list --channel zalouser --query "work" } ``` -### การควบคุมการกล่าวถึงในกลุ่ม +### การกั้นด้วยการเมนชันในกลุ่ม -- `channels.zalouser.groups..requireMention` ควบคุมว่าคำตอบในกลุ่มต้องมีการกล่าวถึงหรือไม่ -- ลำดับการแปลง: ID/ชื่อกลุ่มแบบตรงกันพอดี -> slug กลุ่มที่ normalize แล้ว -> `*` -> ค่าเริ่มต้น (`true`) -- สิ่งนี้ใช้กับทั้งกลุ่มใน allowlist และโหมดกลุ่มแบบเปิด -- การอ้างอิงข้อความของบอตนับเป็นการกล่าวถึงโดยนัยสำหรับการเปิดใช้งานในกลุ่ม -- คำสั่งควบคุมที่ได้รับอนุญาต (เช่น `/new`) สามารถข้ามการควบคุมการกล่าวถึงได้ -- เมื่อข้อความกลุ่มถูกข้ามเพราะต้องมีการกล่าวถึง OpenClaw จะจัดเก็บเป็นประวัติกลุ่มที่รอดำเนินการและรวมไว้ในข้อความกลุ่มครั้งถัดไปที่ถูกประมวลผล -- ขีดจำกัดประวัติกลุ่มมีค่าเริ่มต้นเป็น `messages.groupChat.historyLimit` (fallback `50`) คุณสามารถแทนที่รายบัญชีได้ด้วย `channels.zalouser.historyLimit` +- `channels.zalouser.groups..requireMention` ควบคุมว่าการตอบกลับในกลุ่มต้องมีการเมนชันหรือไม่ +- ลำดับการแปลง: ID/ชื่อกลุ่มแบบตรงกันทุกประการ -> สลักกลุ่มที่ทำให้เป็นมาตรฐานแล้ว -> `*` -> ค่าเริ่มต้น (`true`) +- สิ่งนี้ใช้กับทั้งกลุ่มที่อยู่ในรายการอนุญาตและโหมดกลุ่มแบบเปิด +- การอ้างอิงข้อความของบอตนับเป็นการเมนชันโดยนัยสำหรับการเปิดใช้งานในกลุ่ม +- คำสั่งควบคุมที่ได้รับอนุญาต (เช่น `/new`) สามารถข้ามการกั้นด้วยการเมนชันได้ +- เมื่อข้ามข้อความกลุ่มเพราะต้องมีการเมนชัน OpenClaw จะเก็บไว้เป็นประวัติกลุ่มที่รอดำเนินการและรวมไว้ในข้อความกลุ่มถัดไปที่ประมวลผล +- ขีดจำกัดประวัติกลุ่มใช้ค่าเริ่มต้นเป็น `messages.groupChat.historyLimit` (สำรองเป็น `50`) คุณสามารถแทนที่ต่อบัญชีได้ด้วย `channels.zalouser.historyLimit` ตัวอย่าง: @@ -155,7 +157,7 @@ openclaw directory groups list --channel zalouser --query "work" ## หลายบัญชี -บัญชีจะแมปกับโปรไฟล์ `zalouser` ในสถานะของ OpenClaw ตัวอย่าง: +บัญชีถูกแมปกับโปรไฟล์ `zalouser` ในสถานะ OpenClaw ตัวอย่าง: ```json5 { @@ -171,13 +173,13 @@ openclaw directory groups list --channel zalouser --query "work" } ``` -## การพิมพ์อยู่ รีแอ็กชัน และการยืนยันการส่งมอบ +## การพิมพ์ การตอบสนอง และการยืนยันการส่ง -- OpenClaw ส่งเหตุการณ์การพิมพ์อยู่ก่อนส่งคำตอบ (พยายามให้ดีที่สุด) -- รองรับการกระทำรีแอ็กชันข้อความ `react` สำหรับ `zalouser` ในการกระทำของช่องทาง - - ใช้ `remove: true` เพื่อลบอีโมจิรีแอ็กชันที่ระบุออกจากข้อความ - - ความหมายของรีแอ็กชัน: [รีแอ็กชัน](/th/tools/reactions) -- สำหรับข้อความขาเข้าที่มีข้อมูลเมตาเหตุการณ์ OpenClaw จะส่งการยืนยัน delivered + seen (พยายามให้ดีที่สุด) +- OpenClaw ส่งเหตุการณ์การพิมพ์ก่อนส่งคำตอบ (พยายามให้ดีที่สุด) +- รองรับการดำเนินการตอบสนองต่อข้อความ `react` สำหรับ `zalouser` ในการดำเนินการของช่องทาง + - ใช้ `remove: true` เพื่อลบอีโมจิตอบสนองเฉพาะจากข้อความ + - ความหมายของการตอบสนอง: [การตอบสนอง](/th/tools/reactions) +- สำหรับข้อความขาเข้าที่มีเมทาดาทาเหตุการณ์ OpenClaw จะส่งการยืนยันส่งถึงแล้ว + เห็นแล้ว (พยายามให้ดีที่สุด) ## การแก้ไขปัญหา @@ -186,19 +188,19 @@ openclaw directory groups list --channel zalouser --query "work" - `openclaw channels status --probe` - เข้าสู่ระบบใหม่: `openclaw channels logout --channel zalouser && openclaw channels login --channel zalouser` -**ไม่สามารถแปลงชื่อใน allowlist/กลุ่มได้:** +**แก้ชื่อในรายการอนุญาต/กลุ่มไม่ได้:** -- ใช้ ID ตัวเลขใน `allowFrom`/`groupAllowFrom`/`groups` หรือใช้ชื่อเพื่อน/กลุ่มแบบตรงกันพอดี +- ใช้ ID แบบตัวเลขใน `allowFrom`/`groupAllowFrom` และ ID กลุ่มที่เสถียรใน `groups` หากคุณตั้งใจต้องใช้ชื่อเพื่อน/กลุ่มที่ตรงกันทุกประการ ให้เปิดใช้ `channels.zalouser.dangerouslyAllowNameMatching: true` -**อัปเกรดมาจากการตั้งค่าเก่าที่ใช้ CLI:** +**อัปเกรดจากการตั้งค่าแบบเก่าที่ใช้ CLI:** -- ลบสมมติฐานเกี่ยวกับโปรเซส `zca` ภายนอกเก่าออก -- ตอนนี้ช่องทางทำงานภายใน OpenClaw อย่างสมบูรณ์โดยไม่ต้องใช้ไบนารี CLI ภายนอก +- ลบสมมติฐานเกี่ยวกับโปรเซส `zca` ภายนอกแบบเก่า +- ตอนนี้ช่องทางทำงานทั้งหมดภายใน OpenClaw โดยไม่มีไบนารี CLI ภายนอก ## ที่เกี่ยวข้อง - [ภาพรวมช่องทาง](/th/channels) — ช่องทางที่รองรับทั้งหมด -- [การจับคู่](/th/channels/pairing) — การยืนยันสิทธิ์ DM และโฟลว์การจับคู่ -- [กลุ่ม](/th/channels/groups) — พฤติกรรมแชตกลุ่มและการควบคุมการกล่าวถึง +- [การจับคู่](/th/channels/pairing) — การยืนยันตัวตน DM และโฟลว์การจับคู่ +- [กลุ่ม](/th/channels/groups) — พฤติกรรมแชตกลุ่มและการกั้นด้วยการเมนชัน - [การกำหนดเส้นทางช่องทาง](/th/channels/channel-routing) — การกำหนดเส้นทางเซสชันสำหรับข้อความ -- [ความปลอดภัย](/th/gateway/security) — โมเดลการเข้าถึงและการเพิ่มความแข็งแกร่ง +- [ความปลอดภัย](/th/gateway/security) — โมเดลการเข้าถึงและการเสริมความปลอดภัย diff --git a/docs/th/cli/daemon.md b/docs/th/cli/daemon.md index fbda67a7a..ee0634e72 100644 --- a/docs/th/cli/daemon.md +++ b/docs/th/cli/daemon.md @@ -1,14 +1,14 @@ --- read_when: - - คุณยังคงใช้ `openclaw daemon ...` ใน scripts + - คุณยังใช้ `openclaw daemon ...` ในสคริปต์ - คุณต้องใช้คำสั่งวงจรชีวิตของบริการ (install/start/stop/restart/status) summary: เอกสารอ้างอิง CLI สำหรับ `openclaw daemon` (นามแฝงเดิมสำหรับการจัดการบริการ Gateway) -title: ดีมอน +title: เดมอน x-i18n: - generated_at: "2026-05-02T22:17:29Z" + generated_at: "2026-05-04T18:23:47Z" model: gpt-5.5 provider: openai - source_hash: 3f11b75bf2781e69f6f59b23364f06cf359f9f24407f25f19b9d2186f7158512 + source_hash: f84e11fc50bdf38da518a8fcf415ae461a2688c2299f996eee384357c0d04a05 source_path: cli/daemon.md workflow: 16 --- @@ -17,7 +17,7 @@ x-i18n: นามแฝงเดิมสำหรับคำสั่งจัดการบริการ Gateway -`openclaw daemon ...` แมปไปยังส่วนติดต่อควบคุมบริการเดียวกันกับคำสั่งบริการ `openclaw gateway ...` +`openclaw daemon ...` แมปไปยังพื้นผิวควบคุมบริการเดียวกับคำสั่งบริการ `openclaw gateway ...` ## การใช้งาน @@ -32,40 +32,41 @@ openclaw daemon uninstall ## คำสั่งย่อย -- `status`: แสดงสถานะการติดตั้งบริการและตรวจสอบสุขภาพของ Gateway +- `status`: แสดงสถานะการติดตั้งบริการและตรวจสอบสุขภาพ Gateway - `install`: ติดตั้งบริการ (`launchd`/`systemd`/`schtasks`) -- `uninstall`: ลบบริการออก +- `uninstall`: ลบบริการ - `start`: เริ่มบริการ - `stop`: หยุดบริการ -- `restart`: รีสตาร์ทบริการ +- `restart`: รีสตาร์ตบริการ ## ตัวเลือกทั่วไป - `status`: `--url`, `--token`, `--password`, `--timeout`, `--no-probe`, `--require-rpc`, `--deep`, `--json` - `install`: `--port`, `--runtime `, `--token`, `--force`, `--json` -- `restart`: `--force`, `--wait `, `--json` +- `restart`: `--safe`, `--force`, `--wait `, `--json` - วงจรชีวิต (`uninstall|start|stop`): `--json` หมายเหตุ: -- `status` จะแก้ SecretRefs การยืนยันตัวตนที่กำหนดค่าไว้สำหรับการยืนยันตัวตนของการตรวจสอบเมื่อทำได้ -- หาก SecretRef การยืนยันตัวตนที่จำเป็นไม่สามารถแก้ได้ในเส้นทางคำสั่งนี้ `daemon status --json` จะรายงาน `rpc.authWarning` เมื่อการเชื่อมต่อ/การยืนยันตัวตนของการตรวจสอบล้มเหลว ให้ส่ง `--token`/`--password` อย่างชัดเจน หรือแก้แหล่งที่มาของความลับก่อน -- หากการตรวจสอบสำเร็จ คำเตือน auth-ref ที่ยังแก้ไม่ได้จะถูกระงับเพื่อหลีกเลี่ยงผลบวกลวง -- `status --deep` เพิ่มการสแกนบริการระดับระบบแบบพยายามอย่างดีที่สุด เมื่อพบบริการอื่นที่มีลักษณะคล้าย Gateway เอาต์พุตสำหรับมนุษย์จะแสดงคำแนะนำการล้างข้อมูลและเตือนว่าคำแนะนำปกติยังคงเป็นหนึ่ง Gateway ต่อหนึ่งเครื่อง -- บนการติดตั้ง Linux systemd การตรวจสอบ token-drift ของ `status` จะรวมทั้งแหล่งที่มาของยูนิต `Environment=` และ `EnvironmentFile=` -- การตรวจสอบ drift จะแก้ SecretRefs ของ `gateway.auth.token` โดยใช้ runtime env ที่รวมแล้ว (service command env ก่อน จากนั้น fallback ไปที่ process env) -- หาก token auth ไม่ได้เปิดใช้อย่างมีผล (ตั้งค่า `gateway.auth.mode` อย่างชัดเจนเป็น `password`/`none`/`trusted-proxy` หรือไม่ได้ตั้งค่า mode โดยที่ password สามารถชนะได้และไม่มีตัวเลือก token ใดชนะได้) การตรวจสอบ token-drift จะข้ามการแก้ config token -- เมื่อ token auth ต้องใช้ token และ `gateway.auth.token` ถูกจัดการด้วย SecretRef, `install` จะตรวจสอบว่า SecretRef แก้ได้ แต่จะไม่บันทึก token ที่แก้แล้วลงในเมทาดาทา environment ของบริการ -- หาก token auth ต้องใช้ token และ SecretRef ของ token ที่กำหนดค่าไว้ยังแก้ไม่ได้ การติดตั้งจะล้มเหลวแบบปิด -- หากกำหนดค่าทั้ง `gateway.auth.token` และ `gateway.auth.password` และไม่ได้ตั้งค่า `gateway.auth.mode` การติดตั้งจะถูกบล็อกจนกว่าจะตั้งค่า mode อย่างชัดเจน -- บน macOS, `install` จะเก็บ LaunchAgent plists ให้เฉพาะเจ้าของเท่านั้น และโหลดค่า environment ของบริการที่จัดการผ่านไฟล์และ wrapper ที่เฉพาะเจ้าของเท่านั้น แทนการ serialize API keys หรือ auth-profile env refs ลงใน `EnvironmentVariables` -- หากคุณตั้งใจเรียกใช้หลาย Gateway บนโฮสต์เดียว ให้แยกพอร์ต config/state และ workspaces ดู [/gateway#multiple-gateways-same-host](/th/gateway#multiple-gateways-same-host) +- `status` แปลงค่า SecretRefs ของการยืนยันตัวตนที่กำหนดค่าไว้สำหรับการยืนยันตัวตนของการตรวจสอบเมื่อทำได้ +- หาก SecretRef ของการยืนยันตัวตนที่จำเป็นไม่สามารถแปลงค่าได้ในเส้นทางคำสั่งนี้ `daemon status --json` จะรายงาน `rpc.authWarning` เมื่อการเชื่อมต่อหรือการยืนยันตัวตนของการตรวจสอบล้มเหลว ให้ส่ง `--token`/`--password` อย่างชัดเจน หรือแปลงค่าแหล่งที่มาของ secret ก่อน +- หากการตรวจสอบสำเร็จ คำเตือน auth-ref ที่ยังแปลงค่าไม่ได้จะถูกระงับเพื่อหลีกเลี่ยงผลบวกลวง +- `status --deep` เพิ่มการสแกนบริการระดับระบบแบบพยายามให้ดีที่สุด เมื่อพบบริการอื่นที่คล้าย Gateway เอาต์พุตสำหรับมนุษย์จะพิมพ์คำแนะนำการล้างข้อมูลและเตือนว่าคำแนะนำปกติยังคงเป็นหนึ่ง Gateway ต่อหนึ่งเครื่อง +- สำหรับการติดตั้ง systemd บน Linux การตรวจสอบ token-drift ของ `status` รวมทั้งแหล่งที่มาของยูนิต `Environment=` และ `EnvironmentFile=` +- การตรวจสอบ drift แปลงค่า SecretRefs ของ `gateway.auth.token` โดยใช้ runtime env ที่ผสานแล้ว (env ของคำสั่งบริการก่อน แล้วจึงใช้ process env เป็น fallback) +- หากการยืนยันตัวตนด้วยโทเค็นไม่ได้ทำงานอย่างมีผลจริง (ตั้งค่า `gateway.auth.mode` อย่างชัดเจนเป็น `password`/`none`/`trusted-proxy` หรือไม่ได้ตั้งค่าโหมดในกรณีที่รหัสผ่านสามารถชนะได้และไม่มีตัวเลือกโทเค็นใดชนะได้) การตรวจสอบ token-drift จะข้ามการแปลงค่าโทเค็นจากการกำหนดค่า +- เมื่อการยืนยันตัวตนด้วยโทเค็นต้องใช้โทเค็นและ `gateway.auth.token` จัดการโดย SecretRef, `install` จะตรวจสอบว่า SecretRef แปลงค่าได้ แต่จะไม่คงค่าโทเค็นที่แปลงแล้วไว้ในข้อมูลเมตา environment ของบริการ +- หากการยืนยันตัวตนด้วยโทเค็นต้องใช้โทเค็นและ SecretRef ของโทเค็นที่กำหนดค่าไว้ยังแปลงค่าไม่ได้ การติดตั้งจะล้มเหลวแบบปิด +- หากกำหนดค่าทั้ง `gateway.auth.token` และ `gateway.auth.password` และไม่ได้ตั้งค่า `gateway.auth.mode` การติดตั้งจะถูกบล็อกจนกว่าจะตั้งค่าโหมดอย่างชัดเจน +- บน macOS, `install` จะเก็บ plist ของ LaunchAgent ให้เฉพาะเจ้าของเท่านั้น และโหลดค่า environment ของบริการที่จัดการผ่านไฟล์และ wrapper ที่เฉพาะเจ้าของเท่านั้น แทนการซีเรียลไลซ์คีย์ API หรือ env refs ของ auth-profile ลงใน `EnvironmentVariables` +- หากคุณตั้งใจเรียกใช้ Gateway หลายตัวบนโฮสต์เดียว ให้แยกพอร์ต การกำหนดค่า/สถานะ และเวิร์กสเปซออกจากกัน ดู [/gateway#multiple-gateways-same-host](/th/gateway#multiple-gateways-same-host) +- `restart --safe` ขอให้ Gateway ที่กำลังทำงานอยู่ตรวจสอบงานที่ใช้งานอยู่ล่วงหน้าและกำหนดเวลารีสตาร์ตแบบรวมครั้งเดียวหลังจากงานที่ใช้งานอยู่หมดลง `restart` แบบธรรมดายังคงพฤติกรรมเดิมของตัวจัดการบริการไว้ ส่วน `--force` ยังคงเป็นเส้นทางบังคับทันที -## แนะนำให้ใช้ +## แนะนำ ใช้ [`openclaw gateway`](/th/cli/gateway) สำหรับเอกสารและตัวอย่างปัจจุบัน ## ที่เกี่ยวข้อง -- [ข้อมูลอ้างอิง CLI](/th/cli) +- [เอกสารอ้างอิง CLI](/th/cli) - [คู่มือปฏิบัติการ Gateway](/th/gateway) diff --git a/docs/th/cli/gateway.md b/docs/th/cli/gateway.md index 44f56fed8..d4db295e0 100644 --- a/docs/th/cli/gateway.md +++ b/docs/th/cli/gateway.md @@ -1,56 +1,56 @@ --- read_when: - การเรียกใช้ Gateway จาก CLI (สำหรับการพัฒนาหรือเซิร์ฟเวอร์) - - การดีบักการยืนยันตัวตนของ Gateway, โหมดการผูก, และการเชื่อมต่อ - - การค้นพบ Gateway ผ่าน Bonjour (DNS-SD แบบภายในเครือข่ายและแบบวงกว้าง) + - การดีบักการยืนยันตัวตนของ Gateway โหมดการผูก และการเชื่อมต่อ + - การค้นพบ Gateway ผ่าน Bonjour (ภายในเครือข่าย + DNS-SD แบบพื้นที่กว้าง) sidebarTitle: Gateway -summary: OpenClaw Gateway CLI (`openclaw gateway`) — เรียกใช้ สืบค้น และค้นหา Gateway +summary: OpenClaw Gateway CLI (`openclaw gateway`) — เรียกใช้ สืบค้น และค้นพบ Gateway title: Gateway x-i18n: - generated_at: "2026-05-02T22:17:36Z" + generated_at: "2026-05-04T18:23:49Z" model: gpt-5.5 provider: openai - source_hash: f7f948a8f0ee6e065afa02f354e690ad5cc4f71bdb8b8674f1b0396c439ab242 + source_hash: 310867c59148577f2e8ce6f708da6bce936e09243ce7fbe5daeb453c6b3b370d source_path: cli/gateway.md workflow: 16 --- -Gateway คือเซิร์ฟเวอร์ WebSocket ของ OpenClaw (ช่องทาง, โหนด, เซสชัน, hooks) คำสั่งย่อยในหน้านี้อยู่ภายใต้ `openclaw gateway …` +Gateway คือเซิร์ฟเวอร์ WebSocket ของ OpenClaw (ช่องทาง, โหนด, เซสชัน, hooks) คำสั่งย่อยในหน้านี้อยู่ภายใต้ `openclaw gateway …`. - + การตั้งค่า mDNS ภายในเครื่อง + DNS-SD แบบ wide-area - + วิธีที่ OpenClaw ประกาศและค้นหา gateways - - คีย์การกำหนดค่า gateway ระดับบนสุด + + คีย์การกำหนดค่า Gateway ระดับบนสุด ## เรียกใช้ Gateway -เรียกใช้กระบวนการ Gateway ภายในเครื่อง: +เรียกใช้โปรเซส Gateway ภายในเครื่อง: ```bash openclaw gateway ``` -นามแฝงสำหรับ foreground: +นามแฝงสำหรับการทำงานแบบ foreground: ```bash openclaw gateway run ``` - - - โดยค่าเริ่มต้น Gateway จะปฏิเสธการเริ่มต้น เว้นแต่จะตั้งค่า `gateway.mode=local` ไว้ใน `~/.openclaw/openclaw.json` ใช้ `--allow-unconfigured` สำหรับการรันเฉพาะกิจ/การพัฒนา - - คาดว่า `openclaw onboard --mode local` และ `openclaw setup` จะเขียน `gateway.mode=local` หากไฟล์มีอยู่แต่ไม่มี `gateway.mode` ให้ถือว่าเป็นการกำหนดค่าที่เสียหรือถูกเขียนทับ และซ่อมแซมแทนที่จะถือว่าเป็นโหมด local โดยนัย - - หากไฟล์มีอยู่และไม่มี `gateway.mode` Gateway จะถือว่านั่นเป็นความเสียหายของการกำหนดค่าที่น่าสงสัย และจะปฏิเสธการ "เดา local" ให้คุณ - - การ bind เกินกว่า loopback โดยไม่มี auth จะถูกบล็อก (ราวกั้นความปลอดภัย) - - `SIGUSR1` จะทริกเกอร์การรีสตาร์ทภายในกระบวนการเมื่อได้รับอนุญาต (`commands.restart` เปิดใช้งานโดยค่าเริ่มต้น; ตั้งค่า `commands.restart: false` เพื่อบล็อกการรีสตาร์ทด้วยตนเอง ขณะที่ gateway tool/config apply/update ยังได้รับอนุญาต) - - handler ของ `SIGINT`/`SIGTERM` จะหยุดกระบวนการ gateway แต่จะไม่กู้คืนสถานะเทอร์มินัลแบบกำหนดเองใดๆ หากคุณห่อ CLI ด้วย TUI หรืออินพุตแบบ raw-mode ให้กู้คืนเทอร์มินัลก่อนออก + + - โดยค่าเริ่มต้น Gateway จะปฏิเสธการเริ่มทำงาน เว้นแต่จะตั้งค่า `gateway.mode=local` ใน `~/.openclaw/openclaw.json` ใช้ `--allow-unconfigured` สำหรับการเรียกใช้งานแบบเฉพาะกิจ/เพื่อพัฒนา + - คาดว่า `openclaw onboard --mode local` และ `openclaw setup` จะเขียนค่า `gateway.mode=local` หากไฟล์มีอยู่แต่ไม่มี `gateway.mode` ให้ถือว่าเป็นการกำหนดค่าที่เสียหรือถูกเขียนทับ และซ่อมแซมแทนการสันนิษฐานโหมด local โดยปริยาย + - หากไฟล์มีอยู่และไม่มี `gateway.mode` Gateway จะถือว่านี่เป็นความเสียหายของการกำหนดค่าที่น่าสงสัย และจะปฏิเสธการ "เดา local" ให้คุณ + - การ bind เกิน loopback โดยไม่มี auth จะถูกบล็อก (แนวป้องกันด้านความปลอดภัย) + - `SIGUSR1` จะทริกเกอร์การรีสตาร์ทภายในโปรเซสเมื่อได้รับอนุญาต (`commands.restart` เปิดใช้งานตามค่าเริ่มต้น; ตั้ง `commands.restart: false` เพื่อบล็อกการรีสตาร์ทด้วยตนเอง ขณะที่ gateway tool/config apply/update ยังได้รับอนุญาต) + - ตัวจัดการ `SIGINT`/`SIGTERM` จะหยุดโปรเซส gateway แต่จะไม่คืนค่าสถานะเทอร์มินัลแบบกำหนดเองใดๆ หากคุณห่อหุ้ม CLI ด้วย TUI หรืออินพุต raw-mode ให้คืนค่าเทอร์มินัลก่อนออก @@ -64,13 +64,13 @@ openclaw gateway run โหมด bind ของ listener - การ override โหมด auth + แทนที่โหมด auth - การ override token (ตั้งค่า `OPENCLAW_GATEWAY_TOKEN` ให้กระบวนการด้วย) + แทนที่ token (ตั้งค่า `OPENCLAW_GATEWAY_TOKEN` สำหรับโปรเซสด้วย) - การ override password + แทนที่รหัสผ่าน อ่านรหัสผ่าน gateway จากไฟล์ @@ -82,69 +82,79 @@ openclaw gateway run รีเซ็ตการกำหนดค่า serve/funnel ของ Tailscale เมื่อปิด - อนุญาตให้เริ่ม gateway โดยไม่มี `gateway.mode=local` ใน config ข้าม guard การเริ่มต้นสำหรับ bootstrap เฉพาะกิจ/การพัฒนาเท่านั้น; ไม่เขียนหรือซ่อมแซมไฟล์ config + อนุญาตให้เริ่ม gateway โดยไม่มี `gateway.mode=local` ใน config ข้าม guard ตอนเริ่มต้นสำหรับการ bootstrap แบบเฉพาะกิจ/เพื่อพัฒนาเท่านั้น; ไม่เขียนหรือซ่อมแซมไฟล์ config - สร้าง dev config + workspace หากไม่มีอยู่ (ข้าม BOOTSTRAP.md) + สร้าง config สำหรับ dev + workspace หากยังไม่มี (ข้าม BOOTSTRAP.md) - รีเซ็ต dev config + credentials + sessions + workspace (ต้องใช้ `--dev`) + รีเซ็ต config สำหรับ dev + credentials + sessions + workspace (ต้องใช้ `--dev`) - ปิด listener ที่มีอยู่บนพอร์ตที่เลือกก่อนเริ่มต้น + ฆ่า listener ที่มีอยู่บนพอร์ตที่เลือกก่อนเริ่ม - บันทึกแบบละเอียด + logs แบบละเอียด - แสดงเฉพาะบันทึก CLI backend ในคอนโซล (และเปิดใช้งาน stdout/stderr) + แสดงเฉพาะ logs ของ backend CLI ในคอนโซล (และเปิดใช้งาน stdout/stderr) - รูปแบบบันทึก Websocket + รูปแบบ log ของ Websocket - นามแฝงของ `--ws-log compact` + นามแฝงสำหรับ `--ws-log compact` - บันทึกเหตุการณ์สตรีมโมเดลดิบลงใน jsonl + บันทึกเหตุการณ์ stream ดิบของ model ลงใน jsonl - พาธ jsonl ของสตรีมดิบ + path ของ raw stream jsonl +## รีสตาร์ท Gateway + +```bash +openclaw gateway restart +openclaw gateway restart --safe +openclaw gateway restart --force +``` + +`openclaw gateway restart --safe` จะขอให้ Gateway ที่กำลังทำงานอยู่ตรวจสอบงาน OpenClaw ที่ active ล่วงหน้าก่อนรีสตาร์ท หากมีการดำเนินการในคิว การส่งคำตอบ การรันแบบฝัง หรือการรันงานที่ active อยู่ Gateway จะรายงานตัวบล็อก รวมคำขอ safe restart ที่ซ้ำกัน และรีสตาร์ทเมื่อ active work ระบายหมดแล้ว `restart` แบบธรรมดายังคงพฤติกรรม service-manager เดิมไว้เพื่อความเข้ากันได้ ใช้ `--force` เฉพาะเมื่อคุณต้องการเส้นทาง override ทันทีอย่างชัดเจน + -`--password` แบบ inline อาจถูกเปิดเผยในรายการกระบวนการภายในเครื่อง ควรใช้ `--password-file`, env หรือ `gateway.auth.password` ที่มี SecretRef รองรับ +`--password` แบบ inline อาจถูกเปิดเผยในรายการโปรเซสภายในเครื่อง ควรใช้ `--password-file`, env หรือ `gateway.auth.password` ที่รองรับ SecretRef -### การทำโปรไฟล์เมื่อเริ่มต้น +### การทำโปรไฟล์ตอนเริ่มต้น -- ตั้งค่า `OPENCLAW_GATEWAY_STARTUP_TRACE=1` เพื่อบันทึกเวลาแต่ละเฟสระหว่างการเริ่มต้น Gateway รวมถึง delay ของ `eventLoopMax` ต่อเฟส และเวลา lookup-table ของ Plugin สำหรับ installed-index, manifest registry, startup planning และงาน owner-map -- ตั้งค่า `OPENCLAW_DIAGNOSTICS=timeline` พร้อม `OPENCLAW_DIAGNOSTICS_TIMELINE_PATH=` เพื่อเขียนไทม์ไลน์ diagnostics การเริ่มต้นแบบ JSONL ด้วยความพยายามเต็มที่สำหรับ QA harnesses ภายนอก คุณยังสามารถเปิดใช้ flag ด้วย `diagnostics.flags: ["timeline"]` ใน config ได้; path ยังต้องให้ผ่าน env เพิ่ม `OPENCLAW_DIAGNOSTICS_EVENT_LOOP=1` เพื่อรวมตัวอย่าง event-loop -- รัน `pnpm test:startup:gateway -- --runs 5 --warmup 1` เพื่อ benchmark การเริ่มต้น Gateway benchmark จะบันทึกเอาต์พุตแรกของกระบวนการ, `/healthz`, `/readyz`, เวลา startup trace, delay ของ event-loop และรายละเอียดเวลา lookup-table ของ Plugin +- ตั้ง `OPENCLAW_GATEWAY_STARTUP_TRACE=1` เพื่อบันทึกเวลาแต่ละเฟสระหว่างการเริ่มต้น Gateway รวมถึงความหน่วง `eventLoopMax` ต่อเฟส และเวลาของ lookup-table ของ Plugin สำหรับ installed-index, manifest registry, startup planning และงาน owner-map +- ตั้ง `OPENCLAW_DIAGNOSTICS=timeline` พร้อม `OPENCLAW_DIAGNOSTICS_TIMELINE_PATH=` เพื่อเขียนไทม์ไลน์ diagnostics ตอนเริ่มต้นแบบ JSONL ตามความพยายามที่ดีที่สุดสำหรับ harness QA ภายนอก คุณยังสามารถเปิดใช้ flag ด้วย `diagnostics.flags: ["timeline"]` ใน config ได้; path ยังคงต้องมาจาก env เพิ่ม `OPENCLAW_DIAGNOSTICS_EVENT_LOOP=1` เพื่อรวมตัวอย่าง event-loop +- เรียกใช้ `pnpm test:startup:gateway -- --runs 5 --warmup 1` เพื่อ benchmark การเริ่มต้น Gateway benchmark จะบันทึก output แรกของโปรเซส, `/healthz`, `/readyz`, เวลา startup trace, ความหน่วง event-loop และรายละเอียดเวลาของ lookup-table ของ Plugin -## สอบถาม Gateway ที่กำลังทำงาน +## สอบถาม Gateway ที่กำลังทำงานอยู่ คำสั่งสอบถามทั้งหมดใช้ WebSocket RPC - - - ค่าเริ่มต้น: อ่านได้สำหรับมนุษย์ (มีสีใน TTY) - - `--json`: JSON ที่อ่านได้โดยเครื่อง (ไม่มี styling/spinner) - - `--no-color` (หรือ `NO_COLOR=1`): ปิด ANSI โดยยังคง layout สำหรับมนุษย์ไว้ + + - ค่าเริ่มต้น: อ่านได้โดยมนุษย์ (มีสีใน TTY) + - `--json`: JSON ที่เครื่องอ่านได้ (ไม่มี styling/spinner) + - `--no-color` (หรือ `NO_COLOR=1`): ปิด ANSI โดยยังคง layout สำหรับมนุษย์ - + - `--url `: URL WebSocket ของ Gateway - `--token `: token ของ Gateway - `--password `: รหัสผ่านของ Gateway - `--timeout `: timeout/budget (แตกต่างกันตามคำสั่ง) - - `--expect-final`: รอการตอบกลับ "final" (การเรียก agent) + - `--expect-final`: รอ response แบบ "final" (agent calls) -เมื่อคุณตั้งค่า `--url` CLI จะไม่ fallback ไปยัง credentials จาก config หรือ environment ส่ง `--token` หรือ `--password` อย่างชัดเจน หากไม่มี credentials ที่ระบุอย่างชัดเจนจะถือเป็นข้อผิดพลาด +เมื่อคุณตั้ง `--url` CLI จะไม่ fallback ไปยัง credentials จาก config หรือ environment ส่ง `--token` หรือ `--password` อย่างชัดเจน การไม่มี credentials ที่ระบุอย่างชัดเจนถือเป็นข้อผิดพลาด ### `gateway health` @@ -153,11 +163,11 @@ openclaw gateway run openclaw gateway health --url ws://127.0.0.1:18789 ``` -endpoint HTTP `/healthz` คือ liveness probe: จะส่งค่ากลับเมื่อเซิร์ฟเวอร์สามารถตอบ HTTP ได้ endpoint HTTP `/readyz` เข้มงวดกว่าและจะยังเป็นสีแดงขณะที่ sidecar ของ Plugin ตอนเริ่มต้น, ช่องทาง หรือ hooks ที่กำหนดค่ายังอยู่ระหว่างปรับสถานะ การตอบกลับ readiness แบบละเอียดในเครื่องหรือที่ผ่านการยืนยันตัวตนแล้วจะมีบล็อก diagnostics `eventLoop` พร้อม delay ของ event-loop, การใช้งาน event-loop, อัตราส่วนแกน CPU และ flag `degraded` +endpoint HTTP `/healthz` เป็น liveness probe: จะคืนค่าเมื่อ server สามารถตอบ HTTP ได้ endpoint HTTP `/readyz` เข้มงวดกว่าและยังคงเป็นสีแดงขณะที่ startup plugin sidecars, channels หรือ configured hooks ยังอยู่ระหว่างการ settle responses ความพร้อมแบบละเอียดที่เป็น local หรือ authenticated จะมีบล็อก diagnostic `eventLoop` พร้อมความหน่วง event-loop, utilization ของ event-loop, อัตราส่วน CPU core และ flag `degraded` ### `gateway usage-cost` -ดึงสรุป usage-cost จากบันทึกเซสชัน +ดึงสรุป usage-cost จาก logs ของ session ```bash openclaw gateway usage-cost @@ -171,7 +181,7 @@ openclaw gateway usage-cost --json ### `gateway stability` -ดึงตัวบันทึกเสถียรภาพ diagnostics ล่าสุดจาก Gateway ที่กำลังทำงาน +ดึงตัวบันทึก diagnostic stability ล่าสุดจาก Gateway ที่กำลังทำงานอยู่ ```bash openclaw gateway stability @@ -182,35 +192,35 @@ openclaw gateway stability --json ``` - จำนวนเหตุการณ์ล่าสุดสูงสุดที่จะรวม (สูงสุด `1000`) + จำนวนสูงสุดของเหตุการณ์ล่าสุดที่จะรวม (สูงสุด `1000`) - กรองตามประเภทเหตุการณ์ diagnostics เช่น `payload.large` หรือ `diagnostic.memory.pressure` + กรองตามประเภทเหตุการณ์ diagnostic เช่น `payload.large` หรือ `diagnostic.memory.pressure` - รวมเฉพาะเหตุการณ์หลังจากหมายเลขลำดับ diagnostics + รวมเฉพาะเหตุการณ์หลังหมายเลขลำดับ diagnostic - อ่าน stability bundle ที่บันทึกไว้แทนการเรียก Gateway ที่กำลังทำงาน ใช้ `--bundle latest` (หรือแค่ `--bundle`) สำหรับ bundle ใหม่ล่าสุดใต้ state directory หรือส่งพาธ JSON ของ bundle โดยตรง + อ่าน stability bundle ที่บันทึกไว้แทนการเรียก Gateway ที่กำลังทำงานอยู่ ใช้ `--bundle latest` (หรือแค่ `--bundle`) สำหรับ bundle ใหม่ล่าสุดภายใต้ state directory หรือส่ง path ของ JSON bundle โดยตรง - เขียนไฟล์ zip diagnostics สำหรับ support ที่แชร์ได้แทนการพิมพ์รายละเอียด stability + เขียน zip diagnostics สำหรับ support ที่แชร์ได้แทนการพิมพ์รายละเอียด stability - พาธเอาต์พุตสำหรับ `--export` + path ของ output สำหรับ `--export` - - - ระเบียนจะเก็บ metadata เชิงปฏิบัติการ: ชื่อเหตุการณ์, จำนวน, ขนาด byte, ค่าการอ่านหน่วยความจำ, สถานะ queue/session, ชื่อช่องทาง/Plugin และสรุปเซสชันที่ redact แล้ว ระเบียนจะไม่เก็บข้อความแชท, webhook bodies, เอาต์พุตเครื่องมือ, request หรือ response bodies ดิบ, tokens, cookies, ค่าลับ, hostnames หรือ raw session ids ตั้งค่า `diagnostics.enabled: false` เพื่อปิดใช้งาน recorder ทั้งหมด - - เมื่อ Gateway ออกแบบ fatal, timeout ระหว่าง shutdown และการเริ่มต้นใหม่ล้มเหลว OpenClaw จะเขียน snapshot diagnostics เดียวกันไปยัง `~/.openclaw/logs/stability/openclaw-stability-*.json` เมื่อ recorder มีเหตุการณ์ ตรวจสอบ bundle ใหม่ล่าสุดด้วย `openclaw gateway stability --bundle latest`; `--limit`, `--type` และ `--since-seq` ยังใช้กับเอาต์พุต bundle ได้ด้วย + + - records จะเก็บ metadata เชิงปฏิบัติการ: ชื่อเหตุการณ์, จำนวน, ขนาด byte, ค่าอ่าน memory, สถานะ queue/session, ชื่อ channel/plugin และสรุป session ที่ถูก redacted แล้ว ไม่เก็บข้อความแชต, bodies ของ webhook, outputs ของ tool, bodies ดิบของ request หรือ response, tokens, cookies, ค่าลับ, hostnames หรือ ids ของ session ดิบ ตั้ง `diagnostics.enabled: false` เพื่อปิด recorder ทั้งหมด + - เมื่อ Gateway exits ร้ายแรง, shutdown timeouts และ restart startup failures, OpenClaw จะเขียน snapshot diagnostic เดียวกันไปยัง `~/.openclaw/logs/stability/openclaw-stability-*.json` เมื่อ recorder มีเหตุการณ์ ตรวจสอบ bundle ใหม่ล่าสุดด้วย `openclaw gateway stability --bundle latest`; `--limit`, `--type` และ `--since-seq` ใช้กับ output ของ bundle ด้วย ### `gateway diagnostics export` -เขียนไฟล์ zip diagnostics ภายในเครื่องที่ออกแบบมาเพื่อแนบกับรายงานบั๊ก สำหรับโมเดลความเป็นส่วนตัวและเนื้อหา bundle โปรดดู [Diagnostics Export](/th/gateway/diagnostics) +เขียน zip diagnostics ภายในเครื่องที่ออกแบบมาเพื่อแนบกับรายงาน bug สำหรับโมเดลความเป็นส่วนตัวและเนื้อหา bundle ดู [Diagnostics Export](/th/gateway/diagnostics) ```bash openclaw gateway diagnostics export @@ -219,13 +229,13 @@ openclaw gateway diagnostics export --json ``` - พาธ zip เอาต์พุต ค่าเริ่มต้นคือ support export ใต้ state directory + path ของ output zip ค่าเริ่มต้นคือ support export ภายใต้ state directory - จำนวนบรรทัดบันทึกที่ sanitize แล้วสูงสุดที่จะรวม + จำนวนบรรทัด log ที่ sanitized แล้วสูงสุดที่จะรวม - จำนวน byte บันทึกสูงสุดที่จะตรวจสอบ + จำนวน byte ของ log สูงสุดที่จะตรวจสอบ URL WebSocket ของ Gateway สำหรับ health snapshot @@ -237,22 +247,22 @@ openclaw gateway diagnostics export --json รหัสผ่านของ Gateway สำหรับ health snapshot - timeout ของ snapshot สถานะ/health + timeout ของ status/health snapshot ข้ามการค้นหา stability bundle ที่บันทึกไว้ - พิมพ์พาธที่เขียนแล้ว ขนาด และ manifest เป็น JSON + พิมพ์ path, size และ manifest ที่เขียนเป็น JSON -export มี manifest, สรุป Markdown, รูปทรง config, รายละเอียด config ที่ sanitize แล้ว, สรุปบันทึกที่ sanitize แล้ว, snapshot สถานะ/health ของ Gateway ที่ sanitize แล้ว และ stability bundle ใหม่ล่าสุดเมื่อมีอยู่ +export มี manifest, สรุป Markdown, shape ของ config, รายละเอียด config ที่ sanitized แล้ว, สรุป log ที่ sanitized แล้ว, snapshots status/health ของ Gateway ที่ sanitized แล้ว และ stability bundle ใหม่ล่าสุดเมื่อมีอยู่ -ออกแบบมาเพื่อแชร์ โดยจะเก็บรายละเอียดเชิงปฏิบัติการที่ช่วยในการ debug เช่น fields บันทึก OpenClaw ที่ปลอดภัย, ชื่อ subsystem, status codes, durations, โหมดที่กำหนดค่า, พอร์ต, plugin ids, provider ids, การตั้งค่าฟีเจอร์ที่ไม่ใช่ความลับ และข้อความบันทึกเชิงปฏิบัติการที่ redact แล้ว โดยจะละเว้นหรือ redact ข้อความแชท, webhook bodies, เอาต์พุตเครื่องมือ, credentials, cookies, ตัวระบุบัญชี/ข้อความ, ข้อความ prompt/instruction, hostnames และค่าลับ เมื่อข้อความรูปแบบ LogTape ดูเหมือนข้อความ payload ของผู้ใช้/แชท/เครื่องมือ export จะเก็บไว้เพียงว่าข้อความถูกละเว้นพร้อมจำนวน byte ของข้อความนั้น +ออกแบบมาเพื่อแชร์ได้ โดยเก็บรายละเอียดเชิงปฏิบัติการที่ช่วยในการ debugging เช่น ฟิลด์ log ของ OpenClaw ที่ปลอดภัย, ชื่อ subsystem, status codes, durations, modes ที่กำหนดค่าไว้, ports, plugin ids, provider ids, การตั้งค่า feature ที่ไม่ใช่ความลับ และข้อความ log เชิงปฏิบัติการที่ redacted แล้ว จะละเว้นหรือ redact ข้อความแชต, bodies ของ webhook, outputs ของ tool, credentials, cookies, identifiers ของ account/message, ข้อความ prompt/instruction, hostnames และค่าลับ เมื่อข้อความแบบ LogTape ดูเหมือนข้อความ payload ของ user/chat/tool, export จะเก็บเฉพาะว่าข้อความถูกละเว้นพร้อมจำนวน byte ของข้อความนั้น ### `gateway status` -`gateway status` แสดงบริการ Gateway (launchd/systemd/schtasks) พร้อม probe เพิ่มเติมของความสามารถด้าน connectivity/auth +`gateway status` แสดง service ของ Gateway (launchd/systemd/schtasks) พร้อม probe เสริมของ connectivity/auth capability ```bash openclaw gateway status @@ -261,63 +271,63 @@ openclaw gateway status --require-rpc ``` - เพิ่มเป้าหมาย probe ที่ระบุชัดเจน remote ที่กำหนดค่า + localhost ยังถูก probe อยู่ + เพิ่มเป้าหมายการตรวจสอบแบบชัดเจน รีโมตที่กำหนดค่าไว้ + localhost ยังคงถูกตรวจสอบอยู่ - auth ด้วย token สำหรับ probe + การยืนยันตัวตนด้วยโทเค็นสำหรับการตรวจสอบ - auth ด้วย password สำหรับ probe + การยืนยันตัวตนด้วยรหัสผ่านสำหรับการตรวจสอบ - timeout ของ probe + ระยะหมดเวลาของการตรวจสอบ - ข้าม connectivity probe (มุมมองเฉพาะ service) + ข้ามการตรวจสอบการเชื่อมต่อ (มุมมองเฉพาะบริการ) สแกนบริการระดับระบบด้วย - ยกระดับ connectivity probe ค่าเริ่มต้นให้เป็น read probe และออกด้วยค่าที่ไม่ใช่ศูนย์เมื่อ read probe นั้นล้มเหลว ไม่สามารถใช้ร่วมกับ `--no-probe` ได้ + ยกระดับการตรวจสอบการเชื่อมต่อเริ่มต้นเป็นการตรวจสอบแบบอ่าน และออกด้วยสถานะไม่เป็นศูนย์เมื่อการตรวจสอบแบบอ่านนั้นล้มเหลว ใช้ร่วมกับ `--no-probe` ไม่ได้ - - `gateway status` ยังคงพร้อมใช้งานสำหรับการวินิจฉัย แม้เมื่อการกำหนดค่า CLI ภายในเครื่องหายไปหรือไม่ถูกต้อง - - `gateway status` แบบค่าเริ่มต้นพิสูจน์สถานะบริการ การเชื่อมต่อ WebSocket และความสามารถด้านการตรวจสอบสิทธิ์ที่มองเห็นได้ในเวลาจับมือ ไม่ได้พิสูจน์การดำเนินการอ่าน/เขียน/ผู้ดูแลระบบ - - โพรบวินิจฉัยไม่แก้ไขข้อมูลสำหรับการตรวจสอบสิทธิ์อุปกรณ์ครั้งแรก: จะใช้โทเค็นอุปกรณ์ที่แคชไว้เดิมซ้ำเมื่อมีอยู่ แต่จะไม่สร้างตัวตนอุปกรณ์ CLI ใหม่หรือระเบียนการจับคู่อุปกรณ์แบบอ่านอย่างเดียวใหม่เพียงเพื่อตรวจสอบสถานะ - - `gateway status` จะแปลง SecretRefs การตรวจสอบสิทธิ์ที่กำหนดค่าไว้สำหรับการตรวจสอบสิทธิ์ของโพรบเมื่อทำได้ - - หาก SecretRef การตรวจสอบสิทธิ์ที่จำเป็นยังแปลงค่าไม่ได้ในเส้นทางคำสั่งนี้ `gateway status --json` จะรายงาน `rpc.authWarning` เมื่อการเชื่อมต่อ/การตรวจสอบสิทธิ์ของโพรบล้มเหลว; ส่ง `--token`/`--password` อย่างชัดเจน หรือแปลงค่าแหล่งข้อมูลลับก่อน - - หากโพรบสำเร็จ คำเตือน auth-ref ที่ยังแปลงค่าไม่ได้จะถูกระงับเพื่อหลีกเลี่ยงผลบวกลวง - - ใช้ `--require-rpc` ในสคริปต์และระบบอัตโนมัติเมื่อบริการที่กำลังฟังอยู่ยังไม่เพียงพอ และคุณต้องการให้การเรียก RPC ขอบเขตการอ่านทำงานปกติด้วย - - `--deep` เพิ่มการสแกนแบบพยายามอย่างดีที่สุดเพื่อค้นหาการติดตั้ง launchd/systemd/schtasks เพิ่มเติม เมื่อพบหลายบริการที่คล้าย gateway เอาต์พุตสำหรับมนุษย์จะแสดงคำแนะนำการล้างข้อมูลและเตือนว่าการตั้งค่าส่วนใหญ่ควรรันหนึ่ง gateway ต่อเครื่อง - - เอาต์พุตสำหรับมนุษย์รวมพาธบันทึกไฟล์ที่แปลงค่าแล้ว พร้อมสแนปช็อตพาธ/ความถูกต้องของการกำหนดค่า CLI เทียบกับบริการ เพื่อช่วยวินิจฉัยการเลื่อนของโปรไฟล์หรือไดเรกทอรีสถานะ + - `gateway status` ยังคงพร้อมใช้งานสำหรับการวินิจฉัย แม้ว่าการกำหนดค่า CLI ภายในเครื่องจะหายไปหรือไม่ถูกต้อง + - `gateway status` ค่าเริ่มต้นพิสูจน์สถานะบริการ การเชื่อมต่อ WebSocket และความสามารถด้านการยืนยันตัวตนที่เห็นได้ตอน handshake แต่ไม่ได้พิสูจน์การดำเนินการอ่าน/เขียน/ผู้ดูแลระบบ + - การตรวจสอบเพื่อวินิจฉัยไม่แก้ไขข้อมูลสำหรับการยืนยันตัวตนอุปกรณ์ครั้งแรก: จะใช้โทเค็นอุปกรณ์ที่แคชไว้แล้วซ้ำเมื่อมีอยู่ แต่จะไม่สร้างตัวตนอุปกรณ์ CLI ใหม่หรือระเบียนการจับคู่อุปกรณ์แบบอ่านอย่างเดียวใหม่เพียงเพื่อตรวจสอบสถานะ + - `gateway status` จะแก้ค่า SecretRefs ของการยืนยันตัวตนที่กำหนดค่าไว้สำหรับการยืนยันตัวตนของการตรวจสอบเมื่อทำได้ + - หาก SecretRef ของการยืนยันตัวตนที่จำเป็นแก้ค่าไม่ได้ในเส้นทางคำสั่งนี้ `gateway status --json` จะรายงาน `rpc.authWarning` เมื่อการเชื่อมต่อ/การยืนยันตัวตนของการตรวจสอบล้มเหลว ให้ส่ง `--token`/`--password` อย่างชัดเจน หรือแก้แหล่งที่มาของ secret ก่อน + - หากการตรวจสอบสำเร็จ คำเตือน auth-ref ที่แก้ค่าไม่ได้จะถูกระงับเพื่อหลีกเลี่ยงผลบวกเท็จ + - ใช้ `--require-rpc` ในสคริปต์และระบบอัตโนมัติเมื่อบริการที่กำลังรับฟังอย่างเดียวยังไม่เพียงพอ และคุณต้องการให้การเรียก RPC ขอบเขตอ่านทำงานปกติด้วย + - `--deep` เพิ่มการสแกนแบบ best-effort สำหรับการติดตั้ง launchd/systemd/schtasks เพิ่มเติม เมื่อพบหลายบริการที่คล้าย Gateway ผลลัพธ์สำหรับมนุษย์จะพิมพ์คำแนะนำการล้างข้อมูลและเตือนว่าการตั้งค่าส่วนใหญ่ควรรันหนึ่ง Gateway ต่อหนึ่งเครื่อง + - ผลลัพธ์สำหรับมนุษย์รวมพาธไฟล์บันทึกที่แก้ค่าแล้ว พร้อมสแนปชอตพาธ/ความถูกต้องของการกำหนดค่า CLI เทียบกับบริการ เพื่อช่วยวินิจฉัยการเลื่อนของโปรไฟล์หรือ state-dir - - ในการติดตั้ง Linux systemd การตรวจสอบการเลื่อนของการตรวจสอบสิทธิ์ของบริการจะอ่านค่าทั้ง `Environment=` และ `EnvironmentFile=` จากยูนิต (รวมถึง `%h`, พาธที่มีเครื่องหมายคำพูด, หลายไฟล์ และไฟล์เสริม `-`) - - การตรวจสอบการเลื่อนจะแปลงค่า SecretRefs ของ `gateway.auth.token` โดยใช้ env ขณะรันที่รวมแล้ว (env คำสั่งของบริการก่อน แล้วจึงใช้ env ของโปรเซสเป็นทางเลือกสำรอง) - - หากการตรวจสอบสิทธิ์ด้วยโทเค็นไม่ได้เปิดใช้งานอย่างมีผลจริง (ตั้งค่า `gateway.auth.mode` อย่างชัดเจนเป็น `password`/`none`/`trusted-proxy` หรือไม่ได้ตั้งค่า mode โดยที่รหัสผ่านอาจชนะและไม่มีตัวเลือกโทเค็นใดชนะได้) การตรวจสอบ token-drift จะข้ามการแปลงค่าโทเค็นใน config + - บนการติดตั้ง Linux systemd การตรวจสอบ auth drift ของบริการจะอ่านค่าทั้ง `Environment=` และ `EnvironmentFile=` จาก unit (รวมถึง `%h`, พาธที่อยู่ในเครื่องหมายคำพูด, หลายไฟล์ และไฟล์ `-` แบบไม่บังคับ) + - การตรวจสอบ drift จะแก้ค่า SecretRefs ของ `gateway.auth.token` โดยใช้ runtime env ที่ผสานแล้ว (env ของคำสั่งบริการก่อน จากนั้น fallback เป็น env ของ process) + - หากการยืนยันตัวตนด้วยโทเค็นไม่ได้เปิดใช้งานจริง (ตั้ง `gateway.auth.mode` เป็น `password`/`none`/`trusted-proxy` อย่างชัดเจน หรือไม่ได้ตั้ง mode โดยที่รหัสผ่านอาจชนะและไม่มี token candidate ที่ชนะได้) การตรวจสอบ token-drift จะข้ามการแก้ค่าโทเค็นจาก config ### `gateway probe` -`gateway probe` คือคำสั่ง "ดีบักทุกอย่าง" โดยจะโพรบเสมอ: +`gateway probe` คือคำสั่ง "ดีบักทุกอย่าง" โดยจะตรวจสอบเสมอ: -- gateway ระยะไกลที่คุณกำหนดค่าไว้ (ถ้าตั้งค่าไว้), และ -- localhost (loopback) **แม้ว่าจะกำหนดค่าระยะไกลไว้แล้วก็ตาม** +- Gateway รีโมตที่คุณกำหนดค่าไว้ (ถ้าตั้งไว้), และ +- localhost (loopback) **แม้ว่าจะกำหนดค่ารีโมตไว้ก็ตาม** -หากคุณส่ง `--url` เป้าหมายที่ระบุอย่างชัดเจนนั้นจะถูกเพิ่มไว้ก่อนทั้งสองรายการ เอาต์พุตสำหรับมนุษย์ติดป้ายเป้าหมายเป็น: +หากคุณส่ง `--url` เป้าหมายที่ระบุอย่างชัดเจนนั้นจะถูกเพิ่มไว้ก่อนทั้งสองรายการ ผลลัพธ์สำหรับมนุษย์จะติดป้ายกำกับเป้าหมายเป็น: - `URL (explicit)` - `Remote (configured)` หรือ `Remote (configured, inactive)` - `Local loopback` -หากมีหลาย gateway ที่เข้าถึงได้ ระบบจะแสดงทั้งหมด รองรับหลาย gateway เมื่อคุณใช้โปรไฟล์/พอร์ตที่แยกกัน (เช่น บอตกู้คืน) แต่การติดตั้งส่วนใหญ่ยังคงรัน gateway เดียว +หากเข้าถึงได้หลาย Gateway จะแสดงทั้งหมด รองรับหลาย Gateway เมื่อคุณใช้โปรไฟล์/พอร์ตที่แยกกัน (เช่น บอตกู้คืน) แต่การติดตั้งส่วนใหญ่ยังคงรัน Gateway เดียว ```bash @@ -328,68 +338,68 @@ openclaw gateway probe --json - `Reachable: yes` หมายความว่าอย่างน้อยหนึ่งเป้าหมายยอมรับการเชื่อมต่อ WebSocket - - `Capability: read-only|write-capable|admin-capable|pairing-pending|connect-only` รายงานสิ่งที่โพรบพิสูจน์ได้เกี่ยวกับการตรวจสอบสิทธิ์ ซึ่งแยกจากความสามารถในการเข้าถึง - - `Read probe: ok` หมายความว่าการเรียก RPC รายละเอียดขอบเขตการอ่าน (`health`/`status`/`system-presence`/`config.get`) สำเร็จด้วย - - `Read probe: limited - missing scope: operator.read` หมายความว่าเชื่อมต่อสำเร็จ แต่ RPC ขอบเขตการอ่านถูกจำกัด รายงานเป็นความสามารถในการเข้าถึงแบบ **ลดระดับ** ไม่ใช่ความล้มเหลวเต็มรูปแบบ - - `Read probe: failed` หลัง `Connect: ok` หมายความว่า Gateway ยอมรับการเชื่อมต่อ WebSocket แล้ว แต่การวินิจฉัยการอ่านที่ตามมาหมดเวลาหรือล้มเหลว นี่เป็นความสามารถในการเข้าถึงแบบ **ลดระดับ** เช่นกัน ไม่ใช่ Gateway ที่เข้าถึงไม่ได้ - - เช่นเดียวกับ `gateway status` โพรบจะใช้การตรวจสอบสิทธิ์อุปกรณ์ที่แคชไว้เดิมซ้ำ แต่ไม่สร้างตัวตนอุปกรณ์ครั้งแรกหรือสถานะการจับคู่ - - รหัสออกจะไม่เป็นศูนย์เฉพาะเมื่อไม่มีเป้าหมายที่โพรบแล้วเข้าถึงได้ + - `Capability: read-only|write-capable|admin-capable|pairing-pending|connect-only` รายงานสิ่งที่การตรวจสอบพิสูจน์ได้เกี่ยวกับการยืนยันตัวตน ซึ่งแยกจากความสามารถในการเข้าถึง + - `Read probe: ok` หมายความว่าการเรียก RPC รายละเอียดขอบเขตอ่าน (`health`/`status`/`system-presence`/`config.get`) ก็สำเร็จด้วย + - `Read probe: limited - missing scope: operator.read` หมายความว่าเชื่อมต่อสำเร็จ แต่ RPC ขอบเขตอ่านถูกจำกัด รายงานเป็นความสามารถในการเข้าถึงที่**เสื่อมระดับ** ไม่ใช่ความล้มเหลวทั้งหมด + - `Read probe: failed` หลัง `Connect: ok` หมายความว่า Gateway ยอมรับการเชื่อมต่อ WebSocket แล้ว แต่การวินิจฉัยแบบอ่านที่ตามมาหมดเวลาหรือล้มเหลว กรณีนี้ก็เป็นความสามารถในการเข้าถึงที่**เสื่อมระดับ** ไม่ใช่ Gateway ที่เข้าถึงไม่ได้ + - เช่นเดียวกับ `gateway status` การตรวจสอบจะใช้การยืนยันตัวตนอุปกรณ์ที่แคชไว้แล้วซ้ำ แต่จะไม่สร้างตัวตนอุปกรณ์หรือสถานะการจับคู่ครั้งแรก + - รหัสออกจะไม่เป็นศูนย์เฉพาะเมื่อไม่มีเป้าหมายที่ตรวจสอบใดเข้าถึงได้ - + ระดับบนสุด: - `ok`: อย่างน้อยหนึ่งเป้าหมายเข้าถึงได้ - - `degraded`: อย่างน้อยหนึ่งเป้าหมายยอมรับการเชื่อมต่อ แต่ไม่ได้ทำการวินิจฉัย RPC รายละเอียดเต็มรูปแบบจนเสร็จ - - `capability`: ความสามารถที่ดีที่สุดที่พบในเป้าหมายที่เข้าถึงได้ (`read_only`, `write_capable`, `admin_capable`, `pairing_pending`, `connected_no_operator_scope`, หรือ `unknown`) - - `primaryTargetId`: เป้าหมายที่ดีที่สุดให้ถือเป็นผู้ชนะที่ใช้งานอยู่ตามลำดับนี้: URL ที่ระบุอย่างชัดเจน, SSH tunnel, ระยะไกลที่กำหนดค่าไว้, แล้วจึง local loopback - - `warnings[]`: ระเบียนคำเตือนแบบพยายามอย่างดีที่สุด พร้อม `code`, `message` และ `targetIds` ที่เป็นทางเลือก - - `network`: คำใบ้ URL local loopback/tailnet ที่ได้จาก config ปัจจุบันและเครือข่ายของโฮสต์ - - `discovery.timeoutMs` และ `discovery.count`: งบเวลาการค้นหา/จำนวนผลลัพธ์จริงที่ใช้สำหรับรอบโพรบนี้ + - `degraded`: อย่างน้อยหนึ่งเป้าหมายยอมรับการเชื่อมต่อ แต่ทำการวินิจฉัย RPC รายละเอียดเต็มไม่เสร็จ + - `capability`: ความสามารถที่ดีที่สุดที่พบในเป้าหมายที่เข้าถึงได้ (`read_only`, `write_capable`, `admin_capable`, `pairing_pending`, `connected_no_operator_scope` หรือ `unknown`) + - `primaryTargetId`: เป้าหมายที่ดีที่สุดสำหรับถือเป็นผู้ชนะที่ใช้งานอยู่ตามลำดับนี้: URL ที่ระบุอย่างชัดเจน, อุโมงค์ SSH, รีโมตที่กำหนดค่าไว้, จากนั้น local loopback + - `warnings[]`: ระเบียนคำเตือนแบบ best-effort พร้อม `code`, `message` และ `targetIds` ที่ไม่บังคับ + - `network`: คำใบ้ URL ของ local loopback/tailnet ที่ได้จาก config ปัจจุบันและเครือข่ายของโฮสต์ + - `discovery.timeoutMs` และ `discovery.count`: งบประมาณ/จำนวนผลลัพธ์ของการค้นพบจริงที่ใช้สำหรับรอบการตรวจสอบนี้ ต่อเป้าหมาย (`targets[].connect`): - - `ok`: ความสามารถในการเข้าถึงหลังการเชื่อมต่อ + การจัดประเภทแบบลดระดับ - - `rpcOk`: RPC รายละเอียดเต็มรูปแบบสำเร็จ - - `scopeLimited`: RPC รายละเอียดล้มเหลวเนื่องจากขาดขอบเขต operator + - `ok`: ความสามารถในการเข้าถึงหลังการเชื่อมต่อ + การจำแนกแบบเสื่อมระดับ + - `rpcOk`: RPC รายละเอียดเต็มสำเร็จ + - `scopeLimited`: RPC รายละเอียดล้มเหลวเพราะขาดขอบเขต operator ต่อเป้าหมาย (`targets[].auth`): - - `role`: บทบาทการตรวจสอบสิทธิ์ที่รายงานใน `hello-ok` เมื่อมี + - `role`: บทบาทการยืนยันตัวตนที่รายงานใน `hello-ok` เมื่อมี - `scopes`: ขอบเขตที่ได้รับซึ่งรายงานใน `hello-ok` เมื่อมี - - `capability`: การจัดประเภทความสามารถด้านการตรวจสอบสิทธิ์ที่แสดงสำหรับเป้าหมายนั้น + - `capability`: การจำแนกความสามารถด้านการยืนยันตัวตนที่แสดงสำหรับเป้าหมายนั้น - - - `ssh_tunnel_failed`: การตั้งค่า SSH tunnel ล้มเหลว; คำสั่งย้อนกลับไปใช้โพรบโดยตรง - - `multiple_gateways`: มีมากกว่าหนึ่งเป้าหมายที่เข้าถึงได้; กรณีนี้ไม่ปกติ เว้นแต่คุณตั้งใจรันโปรไฟล์ที่แยกกัน เช่น บอตกู้คืน - - `auth_secretref_unresolved`: SecretRef การตรวจสอบสิทธิ์ที่กำหนดค่าไว้ไม่สามารถแปลงค่าสำหรับเป้าหมายที่ล้มเหลว - - `probe_scope_limited`: การเชื่อมต่อ WebSocket สำเร็จ แต่โพรบการอ่านถูกจำกัดเพราะขาด `operator.read` + + - `ssh_tunnel_failed`: การตั้งค่าอุโมงค์ SSH ล้มเหลว; คำสั่ง fallback ไปใช้การตรวจสอบโดยตรง + - `multiple_gateways`: เข้าถึงได้มากกว่าหนึ่งเป้าหมาย; กรณีนี้ไม่ปกติ เว้นแต่คุณตั้งใจรันโปรไฟล์ที่แยกกัน เช่น บอตกู้คืน + - `auth_secretref_unresolved`: SecretRef ของการยืนยันตัวตนที่กำหนดค่าไว้ไม่สามารถแก้ค่าได้สำหรับเป้าหมายที่ล้มเหลว + - `probe_scope_limited`: การเชื่อมต่อ WebSocket สำเร็จ แต่การตรวจสอบแบบอ่านถูกจำกัดเพราะไม่มี `operator.read` -#### ระยะไกลผ่าน SSH (ความสอดคล้องกับแอป Mac) +#### รีโมตผ่าน SSH (ความเท่าเทียมกับแอป Mac) -โหมด "Remote over SSH" ของแอป macOS ใช้ local port-forward เพื่อให้ gateway ระยะไกล (ซึ่งอาจผูกกับ loopback เท่านั้น) เข้าถึงได้ที่ `ws://127.0.0.1:` +โหมด "Remote over SSH" ของแอป macOS ใช้การส่งต่อพอร์ตภายในเครื่อง เพื่อให้ Gateway รีโมต (ซึ่งอาจ bind กับ loopback เท่านั้น) เข้าถึงได้ที่ `ws://127.0.0.1:` -รายการเทียบเท่าใน CLI: +คำสั่ง CLI ที่เทียบเท่า: ```bash openclaw gateway probe --ssh user@gateway-host ``` - `user@host` หรือ `user@host:port` (ค่าเริ่มต้นของพอร์ตคือ `22`) + `user@host` หรือ `user@host:port` (พอร์ตมีค่าเริ่มต้นเป็น `22`) - ไฟล์ตัวตน + ไฟล์ identity - เลือกโฮสต์ gateway ที่ค้นพบรายการแรกเป็นเป้าหมาย SSH จาก endpoint การค้นหาที่แปลงค่าแล้ว (`local.` บวกโดเมนพื้นที่กว้างที่กำหนดค่าไว้ หากมี) คำใบ้แบบ TXT เท่านั้นจะถูกละเว้น + เลือกโฮสต์ Gateway แรกที่ค้นพบเป็นเป้าหมาย SSH จาก endpoint การค้นพบที่แก้ค่าแล้ว (`local.` บวกโดเมน wide-area ที่กำหนดค่าไว้ หากมี) คำใบ้แบบ TXT-only จะถูกละเว้น -Config (เป็นทางเลือก ใช้เป็นค่าเริ่มต้น): +Config (ไม่บังคับ, ใช้เป็นค่าเริ่มต้น): - `gateway.remote.sshTarget` - `gateway.remote.sshIdentity` @@ -404,7 +414,7 @@ openclaw gateway call logs.tail --params '{"sinceMs": 60000}' ``` - สตริงออบเจ็กต์ JSON สำหรับ params + สตริงออบเจกต์ JSON สำหรับ params URL WebSocket ของ Gateway @@ -416,13 +426,13 @@ openclaw gateway call logs.tail --params '{"sinceMs": 60000}' รหัสผ่าน Gateway - งบเวลาหมดเวลา + งบประมาณระยะหมดเวลา - ใช้เป็นหลักสำหรับ RPC แบบ agent ที่สตรีมเหตุการณ์ระหว่างทางก่อน payload สุดท้าย + ใช้เป็นหลักสำหรับ RPC แบบ agent-style ที่สตรีมเหตุการณ์ขั้นกลางก่อน payload สุดท้าย - เอาต์พุต JSON ที่เครื่องอ่านได้ + ผลลัพธ์ JSON ที่เครื่องอ่านได้ @@ -442,8 +452,8 @@ openclaw gateway uninstall ### ติดตั้งด้วย wrapper ใช้ `--wrapper` เมื่อบริการที่จัดการต้องเริ่มผ่าน executable อื่น เช่น -shim ของตัวจัดการความลับหรือ helper สำหรับ run-as wrapper จะได้รับ args ปกติของ Gateway และ -รับผิดชอบในการ exec `openclaw` หรือ Node พร้อม args เหล่านั้นในท้ายที่สุด +secrets manager shim หรือตัวช่วย run-as wrapper จะได้รับ args ปกติของ Gateway และ +มีหน้าที่ exec `openclaw` หรือ Node พร้อม args เหล่านั้นในท้ายที่สุด ```bash cat > ~/.local/bin/openclaw-doppler <<'EOF' @@ -457,16 +467,16 @@ openclaw gateway install --wrapper ~/.local/bin/openclaw-doppler --force openclaw gateway restart ``` -คุณยังสามารถตั้งค่า wrapper ผ่าน environment ได้ `gateway install` ตรวจสอบว่าพาธเป็น -ไฟล์ executable, เขียน wrapper ลงใน `ProgramArguments` ของบริการ และคงค่า -`OPENCLAW_WRAPPER` ไว้ใน environment ของบริการสำหรับการติดตั้งใหม่แบบบังคับ การอัปเดต และการซ่อมแซมโดย doctor ภายหลัง +คุณยังสามารถตั้งค่า wrapper ผ่าน environment ได้ `gateway install` จะตรวจสอบว่าพาธเป็น +ไฟล์ executable, เขียน wrapper ลงใน `ProgramArguments` ของบริการ, และคงค่า +`OPENCLAW_WRAPPER` ใน environment ของบริการไว้สำหรับการติดตั้งใหม่แบบบังคับ การอัปเดต และการซ่อมแซมของ doctor ในภายหลัง ```bash OPENCLAW_WRAPPER="$HOME/.local/bin/openclaw-doppler" openclaw gateway install --force openclaw doctor ``` -หากต้องการลบ wrapper ที่คงค่าไว้ ให้ล้าง `OPENCLAW_WRAPPER` ระหว่างติดตั้งใหม่: +หากต้องการลบ wrapper ที่คงค่าไว้ ให้ล้าง `OPENCLAW_WRAPPER` ขณะติดตั้งใหม่: ```bash OPENCLAW_WRAPPER= openclaw gateway install --force @@ -481,41 +491,41 @@ openclaw gateway restart - `gateway uninstall|start|stop`: `--json` - - - ใช้ `gateway restart` เพื่อรีสตาร์ตบริการที่จัดการ อย่าต่อ `gateway stop` และ `gateway start` แทนการรีสตาร์ต; บน macOS, `gateway stop` ตั้งใจปิดใช้งาน LaunchAgent ก่อนหยุดมัน - - `gateway restart --wait 30s` แทนที่งบเวลาระบายงานก่อนรีสตาร์ตที่กำหนดค่าไว้สำหรับการรีสตาร์ตครั้งนั้น ตัวเลขเปล่าเป็นมิลลิวินาที; ยอมรับหน่วย เช่น `s`, `m` และ `h` ได้ `--wait 0` จะรอไม่มีกำหนด - - `gateway restart --force` ข้ามการระบายงานที่กำลังทำอยู่และรีสตาร์ตทันที ใช้เมื่อ operator ตรวจสอบตัวบล็อกงานที่แสดงไว้แล้วและต้องการให้ gateway กลับมาทันที - - คำสั่งวงจรชีวิตรองรับ `--json` สำหรับสคริปต์ + + - ใช้ `gateway restart` เพื่อรีสตาร์ทบริการที่จัดการ อย่าเชน `gateway stop` และ `gateway start` เป็นตัวแทนการรีสตาร์ท; บน macOS, `gateway stop` ตั้งใจปิดใช้งาน LaunchAgent ก่อนหยุด + - `gateway restart --wait 30s` จะแทนที่งบประมาณการ drain สำหรับรีสตาร์ทที่กำหนดค่าไว้สำหรับการรีสตาร์ทครั้งนั้น ตัวเลขล้วนคือมิลลิวินาที; รองรับหน่วยอย่าง `s`, `m` และ `h` `--wait 0` จะรอไม่มีกำหนด + - `gateway restart --force` ข้ามการ drain งานที่กำลังทำอยู่และรีสตาร์ททันที ใช้เมื่อ operator ตรวจสอบตัวบล็อกงานที่แสดงไว้แล้วและต้องการให้ Gateway กลับมาตอนนี้ + - คำสั่งวงจรชีวิตรับ `--json` สำหรับการเขียนสคริปต์ - - - เมื่อการตรวจสอบสิทธิ์ด้วยโทเค็นต้องการโทเค็นและ `gateway.auth.token` จัดการด้วย SecretRef, `gateway install` จะตรวจสอบว่า SecretRef แปลงค่าได้ แต่จะไม่คงค่าโทเค็นที่แปลงแล้วลงใน metadata environment ของบริการ - - หากการตรวจสอบสิทธิ์ด้วยโทเค็นต้องการโทเค็นและ SecretRef โทเค็นที่กำหนดค่าไว้ยังแปลงค่าไม่ได้ การติดตั้งจะล้มเหลวแบบปิดแทนการคงค่าข้อความธรรมดาสำรอง - - สำหรับการตรวจสอบสิทธิ์ด้วยรหัสผ่านบน `gateway run` ให้ใช้ `OPENCLAW_GATEWAY_PASSWORD`, `--password-file` หรือ `gateway.auth.password` ที่รองรับด้วย SecretRef แทน `--password` แบบ inline - - ในโหมดการตรวจสอบสิทธิ์ที่อนุมานได้ `OPENCLAW_GATEWAY_PASSWORD` เฉพาะเชลล์จะไม่ผ่อนคลายข้อกำหนดโทเค็นในการติดตั้ง; ใช้ config ที่คงทน (`gateway.auth.password` หรือ config `env`) เมื่อติดตั้งบริการที่จัดการ - - หากกำหนดค่าทั้ง `gateway.auth.token` และ `gateway.auth.password` และไม่ได้ตั้งค่า `gateway.auth.mode` การติดตั้งจะถูกบล็อกจนกว่าจะตั้งค่า mode อย่างชัดเจน + + - เมื่อการยืนยันตัวตนด้วยโทเค็นต้องใช้โทเค็นและ `gateway.auth.token` ถูกจัดการด้วย SecretRef, `gateway install` จะตรวจสอบว่า SecretRef แก้ค่าได้ แต่จะไม่คงค่าโทเค็นที่แก้แล้วไว้ใน metadata environment ของบริการ + - หากการยืนยันตัวตนด้วยโทเค็นต้องใช้โทเค็นและ SecretRef ของโทเค็นที่กำหนดค่าไว้แก้ค่าไม่ได้ การติดตั้งจะล้มเหลวแบบปิด แทนที่จะคงค่า plaintext fallback + - สำหรับการยืนยันตัวตนด้วยรหัสผ่านบน `gateway run` ให้ใช้ `OPENCLAW_GATEWAY_PASSWORD`, `--password-file` หรือ `gateway.auth.password` ที่รองรับด้วย SecretRef แทน `--password` แบบ inline + - ในโหมดการยืนยันตัวตนที่อนุมานได้ `OPENCLAW_GATEWAY_PASSWORD` เฉพาะ shell จะไม่ผ่อนคลายข้อกำหนดโทเค็นสำหรับการติดตั้ง; ใช้ config ที่คงทน (`gateway.auth.password` หรือ config `env`) เมื่อติดตั้งบริการที่จัดการ + - หากกำหนดค่าทั้ง `gateway.auth.token` และ `gateway.auth.password` และไม่ได้ตั้ง `gateway.auth.mode` การติดตั้งจะถูกบล็อกจนกว่าจะตั้ง mode อย่างชัดเจน -## ค้นหา gateway (Bonjour) +## ค้นหา Gateway (Bonjour) `gateway discover` สแกนหา beacon ของ Gateway (`_openclaw-gw._tcp`) -- Multicast DNS-SD: `local.` -- Unicast DNS-SD (Wide-Area Bonjour): เลือกโดเมน (ตัวอย่าง: `openclaw.internal.`) และตั้งค่า split DNS + เซิร์ฟเวอร์ DNS; ดู [Bonjour](/th/gateway/bonjour) +- DNS-SD แบบมัลติคาสต์: `local.` +- DNS-SD แบบยูนิคาสต์ (Wide-Area Bonjour): เลือกโดเมน (ตัวอย่าง: `openclaw.internal.`) และตั้งค่า split DNS + เซิร์ฟเวอร์ DNS; ดู [Bonjour](/th/gateway/bonjour) -เฉพาะ gateway ที่เปิดใช้งานการค้นหา Bonjour (ค่าเริ่มต้น) เท่านั้นที่จะประกาศ beacon +เฉพาะ Gateway ที่เปิดใช้การค้นพบผ่าน Bonjour (ค่าเริ่มต้น) เท่านั้นที่จะประกาศบีคอน -ระเบียนการค้นหา Wide-Area รวม (TXT): +เรคคอร์ดการค้นพบแบบพื้นที่กว้างประกอบด้วย (TXT): -- `role` (คำใบ้บทบาท gateway) -- `transport` (คำใบ้ transport เช่น `gateway`) +- `role` (คำใบ้บทบาทของ Gateway) +- `transport` (คำใบ้ทรานสปอร์ต เช่น `gateway`) - `gatewayPort` (พอร์ต WebSocket โดยปกติคือ `18789`) -- `sshPort` (เป็นทางเลือก; clients ตั้งค่าเป้าหมาย SSH เริ่มต้นเป็น `22` เมื่อไม่มีค่านี้) -- `tailnetDns` (ชื่อโฮสต์ MagicDNS เมื่อมี) -- `gatewayTls` / `gatewayTlsSha256` (เปิดใช้งาน TLS + ลายนิ้วมือใบรับรอง) -- `cliPath` (คำใบ้การติดตั้งระยะไกลที่เขียนไปยังโซนพื้นที่กว้าง) +- `sshPort` (ไม่บังคับ; ไคลเอ็นต์ตั้งค่าเป้าหมาย SSH เริ่มต้นเป็น `22` เมื่อไม่มีค่านี้) +- `tailnetDns` (ชื่อโฮสต์ MagicDNS เมื่อพร้อมใช้งาน) +- `gatewayTls` / `gatewayTlsSha256` (เปิดใช้ TLS + ลายนิ้วมือใบรับรอง) +- `cliPath` (คำใบ้การติดตั้งระยะไกลที่เขียนลงในโซนพื้นที่กว้าง) ### `gateway discover` @@ -524,10 +534,10 @@ openclaw gateway discover ``` - ระยะหมดเวลาต่อคำสั่ง (เรียกดู/แก้ไขชื่อ) + เวลาหมดเวลาต่อคำสั่ง (browse/resolve) - เอาต์พุตที่เครื่องอ่านได้ (ปิดใช้การจัดรูปแบบ/สปินเนอร์ด้วย) + เอาต์พุตที่เครื่องอ่านได้ (ปิดการจัดสไตล์/ตัวหมุนด้วย) ตัวอย่าง: @@ -538,13 +548,13 @@ openclaw gateway discover --json | jq '.beacons[].wsUrl' ``` -- CLI จะสแกน `local.` รวมถึงโดเมนเครือข่ายวงกว้างที่กำหนดค่าไว้เมื่อเปิดใช้งาน -- `wsUrl` ในเอาต์พุต JSON มาจากปลายทางบริการที่แก้ไขได้ ไม่ได้มาจากคำใบ้แบบ TXT เท่านั้น เช่น `lanHost` หรือ `tailnetDns` -- บน mDNS `local.` จะเผยแพร่ `sshPort` และ `cliPath` เฉพาะเมื่อ `discovery.mdns.mode` เป็น `full` เท่านั้น ส่วน DNS-SD เครือข่ายวงกว้างยังคงเขียน `cliPath`; `sshPort` ยังคงเป็นค่าทางเลือกที่นั่นเช่นกัน +- CLI จะสแกน `local.` พร้อมกับโดเมนพื้นที่กว้างที่กำหนดค่าไว้เมื่อเปิดใช้โดเมนนั้น +- `wsUrl` ในเอาต์พุต JSON มาจากปลายทางบริการที่ resolve ได้ ไม่ได้มาจากคำใบ้แบบ TXT เท่านั้น เช่น `lanHost` หรือ `tailnetDns` +- บน mDNS ของ `local.` จะบรอดแคสต์ `sshPort` และ `cliPath` เฉพาะเมื่อ `discovery.mdns.mode` เป็น `full` เท่านั้น DNS-SD แบบพื้นที่กว้างยังคงเขียน `cliPath`; และ `sshPort` ก็ยังไม่บังคับเช่นกัน ## ที่เกี่ยวข้อง -- [เอกสารอ้างอิง CLI](/th/cli) +- [ข้อมูลอ้างอิง CLI](/th/cli) - [คู่มือปฏิบัติการ Gateway](/th/gateway) diff --git a/docs/th/cli/models.md b/docs/th/cli/models.md index a64a7df19..6e6976fe1 100644 --- a/docs/th/cli/models.md +++ b/docs/th/cli/models.md @@ -1,27 +1,27 @@ --- read_when: - - คุณต้องการเปลี่ยนโมเดลเริ่มต้นหรือดูสถานะการตรวจสอบสิทธิ์ของผู้ให้บริการ + - คุณต้องการเปลี่ยนโมเดลเริ่มต้นหรือดูสถานะการยืนยันตัวตนของผู้ให้บริการ - คุณต้องการสแกนโมเดล/ผู้ให้บริการที่พร้อมใช้งาน และดีบักโปรไฟล์การยืนยันตัวตน -summary: ข้อมูลอ้างอิง CLI สำหรับ `openclaw models` (status/list/set/scan, นามแฝง, กลไกสำรอง, การรับรองความถูกต้อง) +summary: ข้อมูลอ้างอิง CLI สำหรับ `openclaw models` (status/list/set/scan, นามแฝง, กลไกสำรอง, การยืนยันตัวตน) title: โมเดล x-i18n: - generated_at: "2026-05-01T10:14:39Z" + generated_at: "2026-05-04T18:23:48Z" model: gpt-5.5 provider: openai - source_hash: 538d3e4808329737fdc044dc6e14e5c7c78052e75d8a8b3b257b1ebd821c84d1 + source_hash: dc7842f02e29aa0ac2ae88f3d42bba71f1890a58ab22d818dbee0585bc562fea source_path: cli/models.md workflow: 16 --- # `openclaw models` -การค้นหา การสแกน และการกำหนดค่าโมเดล (โมเดลเริ่มต้น ตัวสำรอง โปรไฟล์การยืนยันตัวตน) +การค้นหา การสแกน และการกำหนดค่าโมเดล (โมเดลเริ่มต้น ตัวสำรอง โปรไฟล์การรับรองความถูกต้อง) ที่เกี่ยวข้อง: - ผู้ให้บริการ + โมเดล: [โมเดล](/th/providers/models) -- แนวคิดการเลือกโมเดล + คำสั่ง slash `/models`: [แนวคิดโมเดล](/th/concepts/models) -- การตั้งค่าการยืนยันตัวตนของผู้ให้บริการ: [เริ่มต้นใช้งาน](/th/start/getting-started) +- แนวคิดการเลือกโมเดล + คำสั่ง slash `/models`: [แนวคิดเกี่ยวกับโมเดล](/th/concepts/models) +- การตั้งค่าการรับรองความถูกต้องของผู้ให้บริการ: [เริ่มต้นใช้งาน](/th/start/getting-started) ## คำสั่งทั่วไป @@ -32,82 +32,82 @@ openclaw models set openclaw models scan ``` -`openclaw models status` แสดงค่าเริ่มต้น/ตัวสำรองที่ resolve แล้ว พร้อมภาพรวมการยืนยันตัวตน +`openclaw models status` แสดงค่าเริ่มต้น/ตัวสำรองที่ resolve แล้ว พร้อมภาพรวมการรับรองความถูกต้อง เมื่อมีสแนปช็อตการใช้งานของผู้ให้บริการ ส่วนสถานะ OAuth/คีย์ API จะรวม -หน้าต่างการใช้งานของผู้ให้บริการและสแนปช็อตโควตา +หน้าต่างการใช้งานของผู้ให้บริการและสแนปช็อตโควตาไว้ด้วย ผู้ให้บริการหน้าต่างการใช้งานปัจจุบัน: Anthropic, GitHub Copilot, Gemini CLI, OpenAI -Codex, MiniMax, Xiaomi และ z.ai การยืนยันตัวตนสำหรับการใช้งานมาจาก hook เฉพาะผู้ให้บริการ -เมื่อมีให้ใช้งาน ไม่เช่นนั้น OpenClaw จะ fallback ไปยังข้อมูลประจำตัว OAuth/คีย์ API -ที่ตรงกันจากโปรไฟล์การยืนยันตัวตน env หรือ config -ในเอาต์พุต `--json` นั้น `auth.providers` คือภาพรวมผู้ให้บริการที่รับรู้ env/config/store -ส่วน `auth.oauth` คือสถานะสุขภาพของโปรไฟล์ auth-store เท่านั้น -เพิ่ม `--probe` เพื่อเรียกใช้ probe การยืนยันตัวตนแบบ live กับแต่ละโปรไฟล์ผู้ให้บริการที่กำหนดค่าไว้ -Probe เป็นคำขอจริง (อาจใช้ token และทำให้เกิด rate limit) -ใช้ `--agent ` เพื่อตรวจสอบสถานะโมเดล/การยืนยันตัวตนของ agent ที่กำหนดค่าไว้ เมื่อละไว้ -คำสั่งจะใช้ `OPENCLAW_AGENT_DIR`/`PI_CODING_AGENT_DIR` หากตั้งค่าไว้ ไม่เช่นนั้นจะใช้ +Codex, MiniMax, Xiaomi และ z.ai การรับรองความถูกต้องของการใช้งานมาจาก hook เฉพาะผู้ให้บริการ +เมื่อมีให้ใช้งาน มิฉะนั้น OpenClaw จะ fallback ไปใช้ข้อมูลรับรอง OAuth/คีย์ API ที่ตรงกัน +จากโปรไฟล์การรับรองความถูกต้อง env หรือ config +ในเอาต์พุต `--json`, `auth.providers` คือภาพรวมผู้ให้บริการที่รับรู้ env/config/store +ขณะที่ `auth.oauth` คือสถานะความสมบูรณ์ของโปรไฟล์ใน auth-store เท่านั้น +เพิ่ม `--probe` เพื่อเรียกใช้ probe การรับรองความถูกต้องแบบ live กับโปรไฟล์ผู้ให้บริการที่กำหนดค่าไว้แต่ละรายการ +Probe คือคำขอจริง (อาจใช้ token และทำให้เกิด rate limit) +ใช้ `--agent ` เพื่อตรวจสอบสถานะโมเดล/การรับรองความถูกต้องของ agent ที่กำหนดค่าไว้ เมื่อไม่ระบุ +คำสั่งจะใช้ `OPENCLAW_AGENT_DIR`/`PI_CODING_AGENT_DIR` ถ้ามีการตั้งค่าไว้ มิฉะนั้นจะใช้ agent เริ่มต้นที่กำหนดค่าไว้ -แถว probe อาจมาจากโปรไฟล์การยืนยันตัวตน ข้อมูลประจำตัว env หรือ `models.json` +แถว probe อาจมาจากโปรไฟล์การรับรองความถูกต้อง ข้อมูลรับรอง env หรือ `models.json` หมายเหตุ: - `models set ` รับ `provider/model` หรือ alias -- `models list` เป็นแบบอ่านอย่างเดียว: จะอ่าน config, โปรไฟล์การยืนยันตัวตน, สถานะ catalog - ที่มีอยู่ และแถว catalog ที่ผู้ให้บริการเป็นเจ้าของ แต่จะไม่เขียนทับ - `models.json` -- คอลัมน์ `Auth` เป็นระดับผู้ให้บริการและอ่านอย่างเดียว ค่านี้คำนวณจาก metadata - โปรไฟล์การยืนยันตัวตนในเครื่อง, marker ของ env, คีย์ผู้ให้บริการที่กำหนดค่าไว้, marker - ของผู้ให้บริการในเครื่อง, marker ของ AWS Bedrock env/profile และ metadata synthetic-auth ของ Plugin; - ค่านี้จะไม่โหลด runtime ของผู้ให้บริการ, อ่าน secret จาก keychain, เรียก API - ของผู้ให้บริการ หรือพิสูจน์ความพร้อมในการรันจริงแบบรายโมเดลอย่างแม่นยำ -- `models list --all --provider ` อาจรวมแถว catalog แบบ static ที่ผู้ให้บริการเป็นเจ้าของ - จาก manifest ของ Plugin หรือ metadata catalog ของผู้ให้บริการที่ bundle มา แม้คุณ - ยังไม่ได้ยืนยันตัวตนกับผู้ให้บริการนั้นก็ตาม แถวเหล่านั้นจะยังแสดงเป็น - ไม่พร้อมใช้งานจนกว่าจะกำหนดค่าการยืนยันตัวตนที่ตรงกัน -- `models list` ทำให้ control plane ยังตอบสนองได้ในขณะที่การค้นพบ catalog - ของผู้ให้บริการทำงานช้า มุมมองเริ่มต้นและมุมมองที่กำหนดค่าไว้จะ fallback ไปยังแถวโมเดลที่กำหนดค่าไว้หรือ - สร้างแบบ synthetic หลังรอช่วงสั้น ๆ และปล่อยให้การค้นพบทำงานต่อใน - เบื้องหลัง ใช้ `--all` เมื่อคุณต้องการ catalog ที่ค้นพบทั้งหมดแบบครบถ้วนจริง - และยินดีรอการค้นพบของผู้ให้บริการ -- `models list --all` แบบกว้างจะ merge แถว catalog จาก manifest ทับแถว registry +- `models list` เป็นแบบอ่านอย่างเดียว: อ่าน config, โปรไฟล์การรับรองความถูกต้อง, สถานะแค็ตตาล็อกที่มีอยู่ + และแถวแค็ตตาล็อกที่ผู้ให้บริการเป็นเจ้าของ แต่จะไม่เขียน + `models.json` ใหม่ +- คอลัมน์ `Auth` เป็นระดับผู้ให้บริการและอ่านอย่างเดียว ค่านี้คำนวณจาก + metadata โปรไฟล์การรับรองความถูกต้องภายในเครื่อง, marker ของ env, คีย์ผู้ให้บริการที่กำหนดค่าไว้, marker ของ local-provider, + marker ของ env/profile ของ AWS Bedrock และ metadata synthetic-auth ของ Plugin; + ค่านี้จะไม่โหลด runtime ของผู้ให้บริการ อ่านความลับจาก keychain เรียก API ของผู้ให้บริการ + หรือพิสูจน์ความพร้อมในการเรียกใช้งานแบบรายโมเดลอย่างแม่นยำ +- `models list --all --provider ` อาจรวมแถวแค็ตตาล็อก static ที่ผู้ให้บริการเป็นเจ้าของ + จาก manifest ของ Plugin หรือ metadata แค็ตตาล็อกผู้ให้บริการที่ bundle มา แม้ว่าคุณ + ยังไม่ได้รับรองความถูกต้องกับผู้ให้บริการนั้นก็ตาม แถวเหล่านั้นยังคงแสดงเป็น + ใช้งานไม่ได้จนกว่าจะกำหนดค่าการรับรองความถูกต้องที่ตรงกัน +- `models list` ทำให้ control plane ตอบสนองได้ดีขณะที่การค้นพบแค็ตตาล็อกของผู้ให้บริการ + ทำงานช้า มุมมองเริ่มต้นและมุมมองที่กำหนดค่าไว้จะ fallback ไปใช้แถวโมเดลที่กำหนดค่าไว้หรือ + แถวโมเดลสังเคราะห์หลังจากรอเป็นเวลาสั้น ๆ และปล่อยให้การค้นพบทำงานต่อจนเสร็จใน + เบื้องหลัง ใช้ `--all` เมื่อคุณต้องการแค็ตตาล็อกที่ค้นพบแบบเต็มที่แม่นยำ + และยินดีรอการค้นพบจากผู้ให้บริการ +- `models list --all` แบบกว้างจะผสานแถวแค็ตตาล็อกจาก manifest ทับแถวจาก registry โดยไม่โหลด hook เสริม runtime ของผู้ให้บริการ fast path ของ manifest ที่กรองตามผู้ให้บริการ - ใช้เฉพาะผู้ให้บริการที่ทำเครื่องหมายเป็น `static`; ผู้ให้บริการที่ทำเครื่องหมายเป็น `refreshable` - จะยังอิง registry/cache และเพิ่มแถว manifest เป็นส่วนเสริม ส่วน - ผู้ให้บริการที่ทำเครื่องหมายเป็น `runtime` จะยังอยู่กับการค้นพบผ่าน registry/runtime -- `models list` แยก metadata โมเดลดั้งเดิมออกจาก runtime cap อย่างชัดเจน ในเอาต์พุตตาราง - `Ctx` แสดง `contextTokens/contextWindow` เมื่อ runtime cap ที่มีผล - แตกต่างจาก native context window; แถว JSON จะรวม `contextTokens` - เมื่อผู้ให้บริการเปิดเผย cap นั้น + ใช้เฉพาะผู้ให้บริการที่ถูกทำเครื่องหมายเป็น `static`; ผู้ให้บริการที่ถูกทำเครื่องหมายเป็น `refreshable` + จะยังคงอิง registry/cache และเพิ่มแถว manifest เป็นส่วนเสริม ขณะที่ + ผู้ให้บริการที่ถูกทำเครื่องหมายเป็น `runtime` จะยังคงใช้การค้นพบผ่าน registry/runtime +- `models list` แยก metadata โมเดลดั้งเดิมออกจากขีดจำกัด runtime อย่างชัดเจน ในเอาต์พุตตาราง + `Ctx` จะแสดง `contextTokens/contextWindow` เมื่อขีดจำกัด runtime ที่มีผล + แตกต่างจาก context window ดั้งเดิม; แถว JSON จะรวม `contextTokens` + เมื่อผู้ให้บริการเปิดเผยขีดจำกัดนั้น - `models list --provider ` กรองตาม id ของผู้ให้บริการ เช่น `moonshot` หรือ - `openai-codex` ค่านี้ไม่รับป้ายแสดงผลจากตัวเลือกผู้ให้บริการแบบโต้ตอบ + `openai-codex` ไม่รับ label ที่แสดงจากตัวเลือกผู้ให้บริการแบบโต้ตอบ เช่น `Moonshot AI` -- ref ของโมเดลถูก parse โดยแยกที่ `/` ตัว **แรก** หาก ID โมเดลมี `/` (สไตล์ OpenRouter) ให้รวม prefix ผู้ให้บริการด้วย (ตัวอย่าง: `openrouter/moonshotai/kimi-k2`) -- หากคุณละผู้ให้บริการ OpenClaw จะ resolve อินพุตเป็น alias ก่อน จากนั้น - เป็นการจับคู่ผู้ให้บริการที่กำหนดค่าไว้แบบไม่ซ้ำสำหรับ model id นั้นตรง ๆ และหลังจากนั้นเท่านั้น +- refs ของโมเดลถูก parse โดยแยกที่ `/` **ตัวแรก** หาก ID โมเดลมี `/` (แบบ OpenRouter) ให้ใส่ prefix ผู้ให้บริการด้วย (ตัวอย่าง: `openrouter/moonshotai/kimi-k2`) +- หากคุณละผู้ให้บริการไว้ OpenClaw จะ resolve อินพุตเป็น alias ก่อน จากนั้น + เป็นรายการที่ตรงกับผู้ให้บริการที่กำหนดค่าไว้แบบไม่ซ้ำสำหรับ model id ที่ตรงกันนั้น และหลังจากนั้นเท่านั้น จึง fallback ไปยังผู้ให้บริการเริ่มต้นที่กำหนดค่าไว้พร้อมคำเตือน deprecation หากผู้ให้บริการนั้นไม่เปิดเผยโมเดลเริ่มต้นที่กำหนดค่าไว้อีกต่อไป OpenClaw - จะ fallback ไปยังผู้ให้บริการ/โมเดลที่กำหนดค่าไว้รายการแรกแทนการแสดง - ค่าเริ่มต้นของผู้ให้บริการที่ถูกลบไปและล้าสมัย -- `models status` อาจแสดง `marker()` ในเอาต์พุตการยืนยันตัวตนสำหรับ placeholder ที่ไม่ใช่ secret (เช่น `OPENAI_API_KEY`, `secretref-managed`, `minimax-oauth`, `oauth:chutes`, `ollama-local`) แทนการ mask เป็น secret + จะ fallback ไปยังผู้ให้บริการ/โมเดลที่กำหนดค่าไว้รายการแรกแทนที่จะแสดง + ค่าเริ่มต้นของผู้ให้บริการที่ถูกลบซึ่งค้างอยู่ +- `models status` อาจแสดง `marker()` ในเอาต์พุตการรับรองความถูกต้องสำหรับ placeholder ที่ไม่ใช่ความลับ (เช่น `OPENAI_API_KEY`, `secretref-managed`, `minimax-oauth`, `oauth:chutes`, `ollama-local`) แทนการ mask เป็นความลับ -### สแกนโมเดล +### การสแกนโมเดล -`models scan` อ่าน catalog `:free` สาธารณะของ OpenRouter และจัดอันดับ candidate สำหรับ -ใช้เป็น fallback ตัว catalog เองเป็นสาธารณะ ดังนั้นการสแกนแบบ metadata-only จึงไม่จำเป็นต้องมี +`models scan` อ่านแค็ตตาล็อก `:free` สาธารณะของ OpenRouter และจัดอันดับ candidate สำหรับ +การใช้เป็น fallback ตัวแค็ตตาล็อกเป็นสาธารณะ ดังนั้นการสแกนแบบ metadata-only จึงไม่ต้องใช้ คีย์ OpenRouter -โดยค่าเริ่มต้น OpenClaw จะพยายาม probe การรองรับ tool และ image ด้วยการเรียกโมเดลแบบ live -หากไม่ได้กำหนดค่าคีย์ OpenRouter คำสั่งจะ fallback ไปยังเอาต์พุตแบบ metadata-only -และอธิบายว่าโมเดล `:free` ยังต้องใช้ `OPENROUTER_API_KEY` สำหรับ +ตามค่าเริ่มต้น OpenClaw จะพยายาม probe การรองรับเครื่องมือและรูปภาพด้วยการเรียกโมเดลแบบ live +หากไม่ได้กำหนดค่าคีย์ OpenRouter คำสั่งจะ fallback เป็นเอาต์พุตแบบ metadata-only +และอธิบายว่าโมเดล `:free` ยังคงต้องใช้ `OPENROUTER_API_KEY` สำหรับ probe และ inference ตัวเลือก: -- `--no-probe` (metadata เท่านั้น; ไม่ค้นหา config/secret) +- `--no-probe` (เฉพาะ metadata; ไม่ค้นหา config/ความลับ) - `--min-params ` - `--max-age-days ` - `--provider ` - `--max-candidates ` -- `--timeout ` (timeout ของคำขอ catalog และต่อ probe) +- `--timeout ` (timeout ของคำขอแค็ตตาล็อกและแต่ละ probe) - `--concurrency ` - `--yes` - `--no-input` @@ -116,7 +116,7 @@ probe และ inference - `--json` `--set-default` และ `--set-image` ต้องใช้ probe แบบ live; ผลลัพธ์การสแกนแบบ metadata-only -เป็นข้อมูลประกอบและจะไม่ถูกนำไปใช้กับ config +มีไว้เพื่อให้ข้อมูลและจะไม่นำไปใช้กับ config ### สถานะโมเดล @@ -125,19 +125,19 @@ probe และ inference - `--json` - `--plain` - `--check` (exit 1=หมดอายุ/ขาดหาย, 2=ใกล้หมดอายุ) -- `--probe` (probe แบบ live ของโปรไฟล์การยืนยันตัวตนที่กำหนดค่าไว้) +- `--probe` (probe แบบ live ของโปรไฟล์การรับรองความถูกต้องที่กำหนดค่าไว้) - `--probe-provider ` (probe ผู้ให้บริการหนึ่งราย) -- `--probe-profile ` (ทำซ้ำหรือใช้ id โปรไฟล์แบบคั่นด้วยจุลภาค) +- `--probe-profile ` (ระบุซ้ำหรือใช้ id โปรไฟล์คั่นด้วยจุลภาค) - `--probe-timeout ` - `--probe-concurrency ` - `--probe-max-tokens ` -- `--agent ` (id agent ที่กำหนดค่าไว้; override `OPENCLAW_AGENT_DIR`/`PI_CODING_AGENT_DIR`) +- `--agent ` (id ของ agent ที่กำหนดค่าไว้; แทนที่ `OPENCLAW_AGENT_DIR`/`PI_CODING_AGENT_DIR`) -`--json` สงวน stdout ไว้สำหรับ payload JSON diagnostics ของโปรไฟล์การยืนยันตัวตน, ผู้ให้บริการ -และการเริ่มต้นจะถูกส่งไปที่ stderr เพื่อให้สคริปต์สามารถ pipe stdout ตรง -เข้าเครื่องมืออย่าง `jq` ได้ +`--json` สงวน stdout ไว้สำหรับ payload JSON การวินิจฉัยโปรไฟล์การรับรองความถูกต้อง ผู้ให้บริการ +และการเริ่มต้นระบบจะถูกส่งไปยัง stderr เพื่อให้สคริปต์สามารถ pipe stdout โดยตรง +เข้าเครื่องมือเช่น `jq` -bucket สถานะ Probe: +กลุ่มสถานะ probe: - `ok` - `auth` @@ -148,14 +148,15 @@ bucket สถานะ Probe: - `unknown` - `no_model` -กรณีรายละเอียด/รหัสเหตุผลของ Probe ที่คาดได้: +กรณีรายละเอียด/reason-code ของ probe ที่ควรคาดไว้: -- `excluded_by_auth_order`: มีโปรไฟล์ที่จัดเก็บไว้ แต่ `auth.order.` แบบ explicit - ละไว้ ดังนั้น probe จึงรายงานการยกเว้นแทนที่จะลองใช้โปรไฟล์นั้น +- `excluded_by_auth_order`: มีโปรไฟล์ที่จัดเก็บอยู่ แต่ `auth.order.` แบบ explicit + ละโปรไฟล์นั้นไว้ ดังนั้น probe จึงรายงานการยกเว้นแทนที่จะ + ลองใช้โปรไฟล์นั้น - `missing_credential`, `invalid_expires`, `expired`, `unresolved_ref`: - มีโปรไฟล์อยู่แต่ไม่เข้าเกณฑ์/resolve ไม่ได้ -- `no_model`: มีการยืนยันตัวตนของผู้ให้บริการ แต่ OpenClaw ไม่สามารถ resolve candidate - โมเดลที่ probe ได้สำหรับผู้ให้บริการนั้น + มีโปรไฟล์อยู่แต่ไม่มีสิทธิ์ใช้/resolve ไม่ได้ +- `no_model`: มีการรับรองความถูกต้องของผู้ให้บริการ แต่ OpenClaw ไม่สามารถ resolve + candidate โมเดลที่ probe ได้สำหรับผู้ให้บริการนั้น ## Alias + fallback @@ -164,49 +165,56 @@ openclaw models aliases list openclaw models fallbacks list ``` -## โปรไฟล์การยืนยันตัวตน +## โปรไฟล์การรับรองความถูกต้อง ```bash openclaw models auth add +openclaw models auth list [--provider ] [--json] openclaw models auth login --provider openclaw models auth setup-token --provider openclaw models auth paste-token ``` -`models auth add` เป็นตัวช่วยยืนยันตัวตนแบบโต้ตอบ สามารถเปิด flow การยืนยันตัวตนของผู้ให้บริการ -(OAuth/คีย์ API) หรือนำทางคุณไปสู่การวาง token ด้วยตนเอง ขึ้นอยู่กับ +`models auth add` คือ helper การรับรองความถูกต้องแบบโต้ตอบ สามารถเริ่ม flow การรับรองความถูกต้องของผู้ให้บริการ +(OAuth/คีย์ API) หรือแนะนำให้คุณ paste token ด้วยตนเอง ขึ้นอยู่กับ ผู้ให้บริการที่คุณเลือก -`models auth login` เรียกใช้ flow การยืนยันตัวตนของ Plugin ผู้ให้บริการ (OAuth/คีย์ API) ใช้ +`models auth list` แสดงรายการโปรไฟล์การรับรองความถูกต้องที่บันทึกไว้สำหรับ agent ที่เลือกโดยไม่ +พิมพ์ token, คีย์ API หรือข้อมูลลับ OAuth ใช้ `--provider ` เพื่อ +กรองให้เหลือผู้ให้บริการเดียว เช่น `openai-codex` และใช้ `--json` สำหรับสคริปต์ + +`models auth login` เรียกใช้ flow การรับรองความถูกต้องของ Plugin ผู้ให้บริการ (OAuth/คีย์ API) ใช้ `openclaw plugins list` เพื่อดูว่ามีผู้ให้บริการใดติดตั้งอยู่ -ใช้ `openclaw models auth --agent ` เพื่อเขียนผลการยืนยันตัวตนไปยัง -store ของ agent ที่กำหนดค่าไว้โดยเฉพาะ flag parent `--agent` จะถูกใช้งานโดย -`add`, `login`, `setup-token`, `paste-token` และ `login-github-copilot` +ใช้ `openclaw models auth --agent ` เพื่อเขียนผลลัพธ์การรับรองความถูกต้องไปยัง +store ของ agent ที่กำหนดค่าไว้เฉพาะ flag `--agent` ของ parent จะถูกนำไปใช้โดย +`add`, `list`, `login`, `setup-token`, `paste-token` และ +`login-github-copilot` ตัวอย่าง: ```bash openclaw models auth login --provider openai-codex --set-default +openclaw models auth list --provider openai-codex ``` หมายเหตุ: - `setup-token` และ `paste-token` ยังคงเป็นคำสั่ง token ทั่วไปสำหรับผู้ให้บริการ - ที่เปิดเผยวิธีการยืนยันตัวตนด้วย token + ที่เปิดเผยวิธีรับรองความถูกต้องด้วย token - `setup-token` ต้องใช้ TTY แบบโต้ตอบและเรียกใช้วิธี token-auth ของผู้ให้บริการ - (ค่าเริ่มต้นเป็นวิธี `setup-token` ของผู้ให้บริการนั้นเมื่อเปิดเผย + (ค่าเริ่มต้นคือวิธี `setup-token` ของผู้ให้บริการนั้นเมื่อมีการเปิดเผย ไว้) - `paste-token` รับสตริง token ที่สร้างจากที่อื่นหรือจาก automation -- `paste-token` ต้องใช้ `--provider`, จะแจ้งให้ป้อนค่า token และเขียน - ลงใน id โปรไฟล์เริ่มต้น `:manual` เว้นแต่คุณส่ง +- `paste-token` ต้องใช้ `--provider`, prompt ให้กรอกค่า token และเขียน + ไปยัง id โปรไฟล์เริ่มต้น `:manual` เว้นแต่คุณจะส่ง `--profile-id` -- `paste-token --expires-in ` จัดเก็บเวลาหมดอายุ token แบบ absolute จาก - ระยะเวลาแบบ relative เช่น `365d` หรือ `12h` -- หมายเหตุเกี่ยวกับ Anthropic: พนักงาน Anthropic แจ้งเราว่าการใช้งาน Claude CLI แบบ OpenClaw ได้รับอนุญาตอีกครั้ง ดังนั้น OpenClaw จึงถือว่าการ reuse Claude CLI และการใช้งาน `claude -p` ได้รับการอนุมัติสำหรับ integration นี้ เว้นแต่ Anthropic จะเผยแพร่นโยบายใหม่ -- Anthropic `setup-token` / `paste-token` ยังคงพร้อมใช้งานในฐานะเส้นทาง token ของ OpenClaw ที่รองรับ แต่ตอนนี้ OpenClaw ชอบการ reuse Claude CLI และ `claude -p` เมื่อมีให้ใช้งาน +- `paste-token --expires-in ` จัดเก็บเวลาหมดอายุ token แบบสัมบูรณ์จาก + ระยะเวลาแบบสัมพัทธ์ เช่น `365d` หรือ `12h` +- หมายเหตุ Anthropic: เจ้าหน้าที่ Anthropic แจ้งเราว่าการใช้งาน Claude CLI แบบ OpenClaw ได้รับอนุญาตอีกครั้ง ดังนั้น OpenClaw จึงถือว่าการใช้ Claude CLI ซ้ำและการใช้ `claude -p` ได้รับอนุญาตสำหรับการผสานรวมนี้ เว้นแต่ Anthropic จะเผยแพร่นโยบายใหม่ +- Anthropic `setup-token` / `paste-token` ยังคงมีให้ใช้งานเป็นเส้นทาง token ของ OpenClaw ที่รองรับ แต่ตอนนี้ OpenClaw จะชอบการใช้ Claude CLI ซ้ำและ `claude -p` เมื่อมีให้ใช้งาน ## ที่เกี่ยวข้อง - [ข้อมูลอ้างอิง CLI](/th/cli) - [การเลือกโมเดล](/th/concepts/model-providers) -- [การสลับโมเดลเมื่อขัดข้อง](/th/concepts/model-failover) +- [การ failover ของโมเดล](/th/concepts/model-failover) diff --git a/docs/th/cli/proxy.md b/docs/th/cli/proxy.md index d0d194d67..61dd47c1f 100644 --- a/docs/th/cli/proxy.md +++ b/docs/th/cli/proxy.md @@ -1,36 +1,36 @@ --- read_when: - - คุณต้องตรวจสอบยืนยันการกำหนดเส้นทางพร็อกซีที่ผู้ปฏิบัติการจัดการก่อนการปรับใช้ + - คุณต้องตรวจสอบความถูกต้องของการกำหนดเส้นทางพร็อกซีที่จัดการโดยผู้ปฏิบัติการก่อนการปรับใช้ - คุณต้องจับทราฟฟิกการรับส่งข้อมูลของ OpenClaw ภายในเครื่องเพื่อการดีบัก - - คุณต้องการตรวจสอบเซสชันพร็อกซีดีบัก บล็อบ หรือพรีเซ็ตคิวรีในตัว -summary: ข้อมูลอ้างอิง CLI สำหรับ `openclaw proxy` รวมถึงการตรวจสอบพร็อกซีที่จัดการโดยผู้ปฏิบัติการและตัวตรวจสอบการจับพร็อกซีดีบักภายในเครื่อง + - คุณต้องการตรวจสอบเซสชันพร็อกซีสำหรับดีบัก บล็อบ หรือพรีเซ็ตคิวรีที่มีในตัว +summary: ข้อมูลอ้างอิง CLI สำหรับ `openclaw proxy` รวมถึงการตรวจสอบพร็อกซีที่จัดการโดยผู้ปฏิบัติงานและตัวตรวจสอบการจับข้อมูลพร็อกซีดีบักภายในเครื่อง title: พร็อกซี x-i18n: - generated_at: "2026-05-04T07:03:12Z" + generated_at: "2026-05-04T18:23:58Z" model: gpt-5.5 provider: openai - source_hash: 9589bedafb97c31bcb6536a04307cd0c6550e1f307693bd4401785d79f34a1eb + source_hash: 092c4e946dcab5e78e37d6fc77bb067b7a649368f8571fa127e462a85fa14ce5 source_path: cli/proxy.md workflow: 16 --- # `openclaw proxy` -ตรวจสอบความถูกต้องของการกำหนดเส้นทางพร็อกซีที่ผู้ปฏิบัติงานจัดการ หรือเรียกใช้พร็อกซีดีบักแบบระบุชัดภายในเครื่อง -และตรวจสอบทราฟฟิกที่บันทึกไว้ +ตรวจสอบความถูกต้องของการกำหนดเส้นทางพร็อกซีที่ผู้ปฏิบัติการจัดการ หรือเรียกใช้พร็อกซีดีบักแบบระบุชัดเจนในเครื่อง +และตรวจสอบทราฟฟิกที่จับไว้ -ใช้ `validate` เพื่อตรวจสอบล่วงหน้าพร็อกซีส่งต่อที่ผู้ปฏิบัติงานจัดการก่อนเปิดใช้ +ใช้ `validate` เพื่อตรวจสอบพร็อกซีส่งต่อที่ผู้ปฏิบัติการจัดการล่วงหน้าก่อนเปิดใช้ การกำหนดเส้นทางพร็อกซีของ OpenClaw คำสั่งอื่นเป็นเครื่องมือดีบักสำหรับ -การตรวจสอบในระดับการขนส่ง: สามารถเริ่มพร็อกซีภายในเครื่อง เรียกใช้คำสั่งลูก -พร้อมเปิดการบันทึก แสดงรายการเซสชันการบันทึก ค้นหารูปแบบทราฟฟิกทั่วไป อ่าน -บล็อบที่บันทึกไว้ และล้างข้อมูลการบันทึกภายในเครื่อง +การตรวจสอบระดับทรานสปอร์ต: สามารถเริ่มพร็อกซีในเครื่อง เรียกใช้คำสั่งลูก +โดยเปิดการจับข้อมูล แสดงรายการเซสชันการจับข้อมูล คิวรีรูปแบบทราฟฟิกทั่วไป อ่าน +blob ที่จับไว้ และล้างข้อมูลการจับข้อมูลในเครื่อง ## คำสั่ง ```bash openclaw proxy start [--host ] [--port ] openclaw proxy run [--host ] [--port ] -- -openclaw proxy validate [--json] [--proxy-url ] [--allowed-url ] [--denied-url ] [--timeout-ms ] +openclaw proxy validate [--json] [--proxy-url ] [--allowed-url ] [--denied-url ] [--apns-reachable] [--apns-authority ] [--timeout-ms ] openclaw proxy coverage openclaw proxy sessions [--limit ] openclaw proxy query --preset [--session ] @@ -40,29 +40,34 @@ openclaw proxy purge ## ตรวจสอบความถูกต้อง -`openclaw proxy validate` ตรวจสอบ URL พร็อกซีที่ผู้ปฏิบัติงานจัดการซึ่งมีผลใช้งาน จาก -`--proxy-url`, การกำหนดค่า หรือ `OPENCLAW_PROXY_URL` โดยรายงานปัญหาการกำหนดค่าเมื่อ -ไม่มีพร็อกซีที่เปิดใช้งานและกำหนดค่าไว้ ใช้ `--proxy-url` สำหรับการตรวจสอบล่วงหน้าแบบครั้งเดียว -ก่อนเปลี่ยนการกำหนดค่า โดยค่าเริ่มต้น ระบบจะตรวจสอบว่าปลายทางสาธารณะสำเร็จ -ผ่านพร็อกซี และพร็อกซีไม่สามารถเข้าถึงคานารี loopback ชั่วคราวได้ -ปลายทางที่กำหนดเองซึ่งคาดว่าจะถูกปฏิเสธจะปิดเมื่อไม่ผ่าน: การตอบกลับ HTTP และความล้มเหลว -ของการขนส่งที่กำกวมจะถือว่าไม่ผ่านทั้งคู่ เว้นแต่คุณจะสามารถตรวจสอบสัญญาณการปฏิเสธ -เฉพาะการปรับใช้แยกต่างหากได้ +`openclaw proxy validate` ตรวจสอบ URL พร็อกซีที่ผู้ปฏิบัติการจัดการซึ่งมีผลจริงจาก +`--proxy-url`, การกำหนดค่า หรือ `OPENCLAW_PROXY_URL` โดยจะรายงานปัญหาการกำหนดค่าเมื่อ +ไม่มีการเปิดใช้และกำหนดค่าพร็อกซีไว้; ใช้ `--proxy-url` สำหรับการตรวจสอบล่วงหน้าแบบครั้งเดียว +ก่อนเปลี่ยนการกำหนดค่า ตามค่าเริ่มต้น ระบบจะตรวจสอบว่าปลายทางสาธารณะสำเร็จ +ผ่านพร็อกซี และพร็อกซีไม่สามารถเข้าถึง canary แบบ loopback ชั่วคราวได้ +ปลายทางที่กำหนดเองซึ่งถูกปฏิเสธจะเป็นแบบ fail-closed: การตอบกลับ HTTP และความล้มเหลว +ของทรานสปอร์ตที่กำกวมจะถือว่าล้มเหลวทั้งคู่ เว้นแต่คุณจะสามารถตรวจสอบสัญญาณการปฏิเสธ +เฉพาะการปรับใช้แยกต่างหากได้ เพิ่ม `--apns-reachable` เพื่อเปิดทันเนล APNs HTTP/2 CONNECT +ผ่านพร็อกซีและยืนยันว่า sandbox APNs ตอบสนองด้วย; โพรบใช้ +โทเค็นผู้ให้บริการที่ตั้งใจให้ไม่ถูกต้อง ดังนั้นการตอบกลับ APNs `403 InvalidProviderToken` +จึงเป็นสัญญาณการเข้าถึงที่สำเร็จ ตัวเลือก: - `--json`: พิมพ์ JSON ที่เครื่องอ่านได้ -- `--proxy-url `: ตรวจสอบ URL พร็อกซีนี้แทนการกำหนดค่าหรือตัวแปรสภาพแวดล้อม +- `--proxy-url `: ตรวจสอบ URL พร็อกซีนี้แทนการกำหนดค่าหรือ env - `--allowed-url `: เพิ่มปลายทางที่คาดว่าจะสำเร็จผ่านพร็อกซี ทำซ้ำเพื่อตรวจสอบหลายปลายทาง - `--denied-url `: เพิ่มปลายทางที่คาดว่าจะถูกพร็อกซีบล็อก ทำซ้ำเพื่อตรวจสอบหลายปลายทาง -- `--timeout-ms `: ระยะหมดเวลาต่อคำขอ หน่วยเป็นมิลลิวินาที +- `--apns-reachable`: ตรวจสอบด้วยว่า sandbox APNs HTTP/2 เข้าถึงได้ผ่านพร็อกซี +- `--apns-authority `: authority ของ APNs ที่จะโพรบด้วย `--apns-reachable` (ค่าเริ่มต้นคือ `https://api.sandbox.push.apple.com`; production คือ `https://api.push.apple.com`) +- `--timeout-ms `: ระยะหมดเวลาต่อคำขอเป็นมิลลิวินาที -ดู [พร็อกซีเครือข่าย](/th/security/network-proxy) สำหรับแนวทางการปรับใช้และความหมาย -ของการปฏิเสธ +ดู [พร็อกซีเครือข่าย](/th/security/network-proxy) สำหรับแนวทางการปรับใช้และ +ความหมายของการปฏิเสธ -## พรีเซ็ตการค้นหา +## พรีเซ็ตการคิวรี -`openclaw proxy query --preset ` ยอมรับ: +`openclaw proxy query --preset ` รับค่า: - `double-sends` - `retry-storms` @@ -74,13 +79,13 @@ openclaw proxy purge ## หมายเหตุ - `start` ใช้ค่าเริ่มต้นเป็น `127.0.0.1` เว้นแต่จะตั้งค่า `--host` -- `run` เริ่มพร็อกซีดีบักภายในเครื่องแล้วจึงเรียกใช้คำสั่งหลัง `--` -- การส่งต่อไปยังต้นทางโดยตรงของพร็อกซีดีบักจะเปิดซ็อกเก็ตต้นทางเพื่อการวินิจฉัย เมื่อโหมดพร็อกซีที่ OpenClaw จัดการเปิดใช้งานอยู่ การส่งต่อโดยตรงสำหรับคำขอพร็อกซีและอุโมงค์ CONNECT จะถูกปิดใช้งานตามค่าเริ่มต้น ตั้งค่า `OPENCLAW_DEBUG_PROXY_ALLOW_DIRECT_CONNECT_WITH_MANAGED_PROXY=1` เฉพาะสำหรับการวินิจฉัยภายในเครื่องที่ได้รับอนุมัติแล้วเท่านั้น -- `validate` ออกด้วยรหัส 1 เมื่อการกำหนดค่าพร็อกซีหรือการตรวจสอบปลายทางล้มเหลว -- การบันทึกเป็นข้อมูลดีบักภายในเครื่อง ใช้ `openclaw proxy purge` เมื่อดำเนินการเสร็จ +- `run` เริ่มพร็อกซีดีบักในเครื่อง แล้วจึงเรียกใช้คำสั่งหลัง `--` +- การส่งต่ออัปสตรีมโดยตรงของพร็อกซีดีบักจะเปิดซ็อกเก็ตอัปสตรีมสำหรับการวินิจฉัย เมื่อโหมดพร็อกซีที่ OpenClaw จัดการเปิดใช้งาน การส่งต่อโดยตรงสำหรับคำขอพร็อกซีและทันเนล CONNECT จะปิดใช้งานตามค่าเริ่มต้น; ตั้งค่า `OPENCLAW_DEBUG_PROXY_ALLOW_DIRECT_CONNECT_WITH_MANAGED_PROXY=1` เฉพาะสำหรับการวินิจฉัยในเครื่องที่ได้รับอนุมัติเท่านั้น +- `validate` ออกด้วยโค้ด 1 เมื่อการกำหนดค่าพร็อกซีหรือการตรวจสอบปลายทางล้มเหลว +- ข้อมูลการจับเป็นข้อมูลดีบักในเครื่อง; ใช้ `openclaw proxy purge` เมื่อเสร็จสิ้น ## ที่เกี่ยวข้อง -- [อ้างอิง CLI](/th/cli) +- [ข้อมูลอ้างอิง CLI](/th/cli) - [พร็อกซีเครือข่าย](/th/security/network-proxy) -- [การยืนยันตัวตนของพร็อกซีที่เชื่อถือได้](/th/gateway/trusted-proxy-auth) +- [การยืนยันตัวตนพร็อกซีที่เชื่อถือได้](/th/gateway/trusted-proxy-auth) diff --git a/docs/th/gateway/cli-backends.md b/docs/th/gateway/cli-backends.md index 192a323be..6619ee801 100644 --- a/docs/th/gateway/cli-backends.md +++ b/docs/th/gateway/cli-backends.md @@ -1,45 +1,45 @@ --- read_when: - - คุณต้องการตัวเลือกสำรองที่เชื่อถือได้เมื่อผู้ให้บริการ API ล้มเหลว - - คุณกำลังใช้งาน Codex CLI หรือ CLI AI อื่น ๆ ภายในเครื่อง และต้องการนำมาใช้ซ้ำ - - คุณต้องการทำความเข้าใจบริดจ์ลูปแบ็ก MCP สำหรับการเข้าถึงเครื่องมือแบ็กเอนด์ของ CLI -summary: 'แบ็กเอนด์ CLI: ทางสำรอง AI CLI ในเครื่องพร้อมบริดจ์เครื่องมือ MCP แบบเลือกใช้ได้' + - คุณต้องการทางเลือกสำรองที่เชื่อถือได้เมื่อผู้ให้บริการ API ล้มเหลว + - คุณกำลังใช้งาน Codex CLI หรือ CLI ปัญญาประดิษฐ์ภายในเครื่องอื่น ๆ และต้องการนำมาใช้ซ้ำ + - คุณต้องการทำความเข้าใจสะพานเชื่อมลูปแบ็ก MCP สำหรับการเข้าถึงเครื่องมือแบ็กเอนด์ของ CLI +summary: 'แบ็กเอนด์ CLI: ตัวสำรอง AI CLI ภายในเครื่องพร้อมบริดจ์เครื่องมือ MCP แบบเลือกใช้ได้' title: แบ็กเอนด์ CLI x-i18n: - generated_at: "2026-05-02T10:15:23Z" + generated_at: "2026-05-04T18:23:53Z" model: gpt-5.5 provider: openai - source_hash: f343469d6a42dc6146196355dc2ba3feed045515c3d8446941b90971aadc9a16 + source_hash: 55534c48c5e226857b9320fd369416583e5c2efc80eabd4746f939afdd027dc1 source_path: gateway/cli-backends.md workflow: 16 --- -OpenClaw สามารถเรียกใช้ **AI CLI ภายในเครื่อง** เป็น **แผนสำรองแบบข้อความเท่านั้น** เมื่อผู้ให้บริการ API ล่ม, -ถูกจำกัดอัตรา, หรือทำงานผิดปกติชั่วคราว สิ่งนี้ตั้งใจให้อยู่ในแนวทางอนุรักษ์นิยม: +OpenClaw สามารถรัน **AI CLI ภายในเครื่อง** เป็น **เส้นทางสำรองแบบข้อความเท่านั้น** เมื่อผู้ให้บริการ API ล่ม, +ถูกจำกัดอัตรา, หรือทำงานผิดปกติชั่วคราว แนวทางนี้ตั้งใจให้ระมัดระวัง: -- **เครื่องมือของ OpenClaw จะไม่ถูกฉีดเข้าไปโดยตรง** แต่แบ็กเอนด์ที่มี `bundleMcp: true` - สามารถรับเครื่องมือ Gateway ผ่านบริดจ์ MCP แบบ loopback ได้ +- **เครื่องมือ OpenClaw จะไม่ถูกฉีดเข้าโดยตรง** แต่ backend ที่มี `bundleMcp: true` + สามารถรับเครื่องมือ Gateway ผ่านบริดจ์ MCP แบบ local loopback ได้ - **การสตรีม JSONL** สำหรับ CLI ที่รองรับ -- **รองรับเซสชัน** (เพื่อให้เทิร์นติดตามต่อเนื่องสอดคล้องกัน) -- **ส่งรูปภาพผ่านได้** หาก CLI รับพาธรูปภาพ +- **รองรับเซสชัน** (เพื่อให้รอบสนทนาต่อเนื่องยังสอดคล้องกัน) +- **สามารถส่งรูปภาพผ่านได้** หาก CLI ยอมรับพาธรูปภาพ -สิ่งนี้ออกแบบมาเป็น **ตาข่ายนิรภัย** มากกว่าจะเป็นเส้นทางหลัก ใช้เมื่อคุณ -ต้องการคำตอบข้อความที่ “ใช้งานได้เสมอ” โดยไม่ต้องพึ่งพา API ภายนอก +สิ่งนี้ออกแบบมาเป็น **ตาข่ายนิรภัย** มากกว่าเส้นทางหลัก ใช้เมื่อคุณ +ต้องการคำตอบแบบข้อความที่ “ใช้งานได้เสมอ” โดยไม่ต้องพึ่ง API ภายนอก -หากคุณต้องการรันไทม์ฮาร์เนสเต็มรูปแบบที่มีการควบคุมเซสชัน ACP, งานพื้นหลัง, -การผูกเธรด/บทสนทนา, และเซสชันเขียนโค้ดภายนอกแบบคงอยู่ ให้ใช้ -[ACP Agents](/th/tools/acp-agents) แทน แบ็กเอนด์ CLI ไม่ใช่ ACP +หากคุณต้องการ runtime แบบ harness เต็มรูปแบบพร้อมการควบคุมเซสชัน ACP, งานเบื้องหลัง, +การผูกเธรด/การสนทนา, และเซสชันเขียนโค้ดภายนอกแบบถาวร ให้ใช้ +[ACP Agents](/th/tools/acp-agents) แทน backend แบบ CLI ไม่ใช่ ACP -## เริ่มต้นอย่างรวดเร็วสำหรับผู้เริ่มต้น +## เริ่มต้นอย่างง่ายสำหรับมือใหม่ -คุณสามารถใช้ Codex CLI **โดยไม่ต้องมีการตั้งค่าใดๆ** (Plugin OpenAI ที่รวมมาให้ -จะลงทะเบียนแบ็กเอนด์เริ่มต้น): +คุณสามารถใช้ Codex CLI **โดยไม่ต้องมี config ใดๆ** (OpenAI Plugin ที่บันเดิลมา +จะลงทะเบียน backend เริ่มต้นไว้): ```bash openclaw agent --message "hi" --model codex-cli/gpt-5.5 ``` -หาก Gateway ของคุณทำงานภายใต้ launchd/systemd และ PATH มีค่าน้อยที่สุด ให้เพิ่มเพียง +หาก gateway ของคุณรันภายใต้ launchd/systemd และ PATH มีค่าน้อยที่สุด ให้เพิ่มเฉพาะ พาธคำสั่ง: ```json5 @@ -56,16 +56,16 @@ openclaw agent --message "hi" --model codex-cli/gpt-5.5 } ``` -เท่านี้ก็พอ ไม่ต้องใช้คีย์ และไม่ต้องมีการตั้งค่า auth เพิ่มเติมนอกเหนือจาก CLI เอง +เท่านี้ก็พอ ไม่ต้องใช้คีย์ ไม่ต้องมี config ยืนยันตัวตนเพิ่มเติมนอกเหนือจากตัว CLI เอง -หากคุณใช้แบ็กเอนด์ CLI ที่รวมมาให้เป็น **ผู้ให้บริการข้อความหลัก** บน -โฮสต์ Gateway ตอนนี้ OpenClaw จะโหลด Plugin ที่รวมมาให้ซึ่งเป็นเจ้าของโดยอัตโนมัติ เมื่อการตั้งค่าของคุณ -อ้างอิงแบ็กเอนด์นั้นอย่างชัดเจนใน model ref หรือภายใต้ +หากคุณใช้ backend แบบ CLI ที่บันเดิลมาเป็น **ผู้ให้บริการข้อความหลัก** บน +โฮสต์ gateway ตอนนี้ OpenClaw จะโหลด Plugin ที่บันเดิลมาและเป็นเจ้าของ backend นั้นให้อัตโนมัติเมื่อ config ของคุณ +อ้างถึง backend นั้นอย่างชัดเจนใน model ref หรือภายใต้ `agents.defaults.cliBackends` -## การใช้เป็นแผนสำรอง +## การใช้เป็นเส้นทางสำรอง -เพิ่มแบ็กเอนด์ CLI เข้าไปในรายการแผนสำรองของคุณ เพื่อให้ทำงานเฉพาะเมื่อโมเดลหลักล้มเหลว: +เพิ่ม backend แบบ CLI เข้าไปในรายการสำรองของคุณ เพื่อให้รันเฉพาะเมื่อโมเดลหลักล้มเหลว: ```json5 { @@ -86,26 +86,26 @@ openclaw agent --message "hi" --model codex-cli/gpt-5.5 หมายเหตุ: -- หากคุณใช้ `agents.defaults.models` (allowlist) คุณต้องรวมโมเดลแบ็กเอนด์ CLI ของคุณไว้ในนั้นด้วย -- หากผู้ให้บริการหลักล้มเหลว (auth, rate limits, timeouts) OpenClaw จะ - ลองใช้แบ็กเอนด์ CLI ถัดไป +- หากคุณใช้ `agents.defaults.models` (allowlist) คุณต้องใส่โมเดล backend แบบ CLI ของคุณไว้ที่นั่นด้วย +- หากผู้ให้บริการหลักล้มเหลว (การยืนยันตัวตน, การจำกัดอัตรา, timeout) OpenClaw จะ + ลอง backend แบบ CLI ถัดไป -## ภาพรวมการตั้งค่า +## ภาพรวมการกำหนดค่า -แบ็กเอนด์ CLI ทั้งหมดอยู่ภายใต้: +backend แบบ CLI ทั้งหมดอยู่ภายใต้: ``` agents.defaults.cliBackends ``` แต่ละรายการใช้ **provider id** เป็นคีย์ (เช่น `codex-cli`, `my-cli`) -provider id จะกลายเป็นฝั่งซ้ายของ model ref ของคุณ: +provider id จะกลายเป็นด้านซ้ายของ model ref ของคุณ: ``` / ``` -### ตัวอย่างการตั้งค่า +### ตัวอย่างการกำหนดค่า ```json5 { @@ -147,46 +147,52 @@ provider id จะกลายเป็นฝั่งซ้ายของ mode ## วิธีทำงาน -1. **เลือกแบ็กเอนด์** ตามคำนำหน้าผู้ให้บริการ (`codex-cli/...`) -2. **สร้าง system prompt** โดยใช้พรอมป์ OpenClaw เดียวกัน + บริบทเวิร์กสเปซ +1. **เลือก backend** ตาม prefix ของผู้ให้บริการ (`codex-cli/...`) +2. **สร้าง system prompt** โดยใช้ prompt ของ OpenClaw ชุดเดียวกัน + บริบท workspace 3. **เรียกใช้ CLI** พร้อม session id (หากรองรับ) เพื่อให้ประวัติยังคงสอดคล้องกัน - แบ็กเอนด์ `claude-cli` ที่รวมมาให้จะคงกระบวนการ Claude stdio ไว้ต่อหนึ่ง - เซสชัน OpenClaw และส่งเทิร์นติดตามผ่าน stream-json stdin -4. **แยกวิเคราะห์เอาต์พุต** (JSON หรือข้อความธรรมดา) แล้วคืนข้อความสุดท้าย -5. **คง session id ไว้** ต่อแบ็กเอนด์ เพื่อให้เทิร์นติดตามใช้เซสชัน CLI เดิมซ้ำ + backend `claude-cli` ที่บันเดิลมาจะคง process Claude stdio ไว้ต่อ + เซสชัน OpenClaw และส่งรอบสนทนาต่อเนื่องผ่าน stream-json stdin +4. **แยกวิเคราะห์ output** (JSON หรือข้อความธรรมดา) แล้วส่งข้อความสุดท้ายกลับ +5. **บันทึก session id แบบถาวร** ต่อ backend เพื่อให้รอบสนทนาต่อเนื่องใช้เซสชัน CLI เดิมซ้ำ -แบ็กเอนด์ Anthropic `claude-cli` ที่รวมมาให้ได้รับการรองรับอีกครั้ง เจ้าหน้าที่ Anthropic -แจ้งเราว่าการใช้งาน Claude CLI แบบ OpenClaw ได้รับอนุญาตอีกครั้ง ดังนั้น OpenClaw จึงถือว่าการใช้งาน -`claude -p` ได้รับการอนุมัติสำหรับการผสานรวมนี้ เว้นแต่ Anthropic จะเผยแพร่ +backend Anthropic `claude-cli` ที่บันเดิลมารองรับอีกครั้งแล้ว เจ้าหน้าที่ Anthropic +บอกเราว่าการใช้งาน Claude CLI แบบ OpenClaw ได้รับอนุญาตอีกครั้ง ดังนั้น OpenClaw จึงถือว่า +การใช้งาน `claude -p` ได้รับอนุญาตสำหรับการผสานรวมนี้ เว้นแต่ Anthropic จะเผยแพร่ นโยบายใหม่ -แบ็กเอนด์ OpenAI `codex-cli` ที่รวมมาให้จะส่ง system prompt ของ OpenClaw ผ่าน -การ override การตั้งค่า `model_instructions_file` ของ Codex (`-c -model_instructions_file="..."`) Codex ไม่เปิดเผยแฟล็กแบบ Claude -`--append-system-prompt` ดังนั้น OpenClaw จึงเขียนพรอมป์ที่ประกอบแล้วลงใน +backend OpenAI `codex-cli` ที่บันเดิลมาจะส่ง system prompt ของ OpenClaw ผ่าน +config override `model_instructions_file` ของ Codex (`-c +model_instructions_file="..."`) Codex ไม่มี flag แบบ Claude +`--append-system-prompt` ดังนั้น OpenClaw จะเขียน prompt ที่ประกอบแล้วลงใน ไฟล์ชั่วคราวสำหรับแต่ละเซสชัน Codex CLI ใหม่ -แบ็กเอนด์ Anthropic `claude-cli` ที่รวมมาให้รับสแนปช็อต Skills ของ OpenClaw -สองทาง: แค็ตตาล็อก Skills ของ OpenClaw แบบกระชับใน system prompt ที่ต่อท้าย และ -Plugin Claude Code ชั่วคราวที่ส่งด้วย `--plugin-dir` Plugin นี้มี -เฉพาะ Skills ที่เข้าเกณฑ์สำหรับเอเจนต์/เซสชันนั้น ดังนั้นตัวแก้ไข Skills ดั้งเดิมของ Claude Code -จะเห็นชุดที่กรองแล้วชุดเดียวกับที่ OpenClaw จะประกาศใน -พรอมป์แทน การ override env/API key ของ Skill ยังถูก OpenClaw นำไปใช้กับ -สภาพแวดล้อมของกระบวนการลูกสำหรับการรัน +backend Anthropic `claude-cli` ที่บันเดิลมารับสแนปช็อต Skills ของ OpenClaw +สองทาง: แค็ตตาล็อก Skills ของ OpenClaw แบบกะทัดรัดใน system prompt ที่ append เข้าไป และ +Claude Code Plugin ชั่วคราวที่ส่งด้วย `--plugin-dir` Plugin มีเฉพาะ +Skills ที่เข้าเงื่อนไขสำหรับ agent/เซสชันนั้น ดังนั้นตัว resolver Skills แบบ native ของ Claude Code +จะเห็นชุดที่กรองแล้วเดียวกันกับที่ OpenClaw จะโฆษณาไว้ใน +prompt แทน ค่า override ของ env/API key สำหรับ Skill ยังคงถูก OpenClaw นำไปใช้กับ +สภาพแวดล้อมของ process ลูกสำหรับการรัน -Claude CLI ยังมีโหมดสิทธิ์แบบไม่โต้ตอบของตัวเอง OpenClaw แมปสิ่งนั้น -กับนโยบาย exec ที่มีอยู่แทนการเพิ่มการตั้งค่าเฉพาะ Claude: เมื่อ -นโยบาย exec ที่ร้องขอและมีผลคือ YOLO (`tools.exec.security: "full"` และ +Claude CLI ยังมีโหมดสิทธิ์แบบ noninteractive ของตัวเองด้วย OpenClaw map โหมดนั้น +เข้ากับนโยบาย exec ที่มีอยู่ แทนที่จะเพิ่ม config เฉพาะ Claude: เมื่อ +นโยบาย exec ที่ร้องขอมีผลเป็น YOLO (`tools.exec.security: "full"` และ `tools.exec.ask: "off"`) OpenClaw จะเพิ่ม `--permission-mode bypassPermissions` -การตั้งค่า `agents.list[].tools.exec` รายเอเจนต์จะแทนที่ `tools.exec` ส่วนกลางสำหรับ -เอเจนต์นั้น หากต้องการบังคับโหมด Claude อื่น ให้ตั้งค่า raw backend args อย่างชัดเจน +การตั้งค่า `agents.list[].tools.exec` ราย agent จะแทนที่ `tools.exec` ส่วนกลางสำหรับ +agent นั้น หากต้องการบังคับโหมด Claude อื่น ให้ตั้งค่า raw backend args อย่างชัดเจน เช่น `--permission-mode default` หรือ `--permission-mode acceptEdits` ภายใต้ `agents.defaults.cliBackends.claude-cli.args` และ `resumeArgs` ที่ตรงกัน -ก่อนที่ OpenClaw จะใช้แบ็กเอนด์ `claude-cli` ที่รวมมาให้ได้ Claude Code เอง -ต้องล็อกอินอยู่แล้วบนโฮสต์เดียวกัน: +backend Anthropic `claude-cli` ที่บันเดิลมายัง map ระดับ OpenClaw `/think` +ไปยัง flag native `--effort` ของ Claude Code สำหรับระดับที่ไม่ใช่ off ด้วย `minimal` และ +`low` map เป็น `low`, `adaptive` และ `medium` map เป็น `medium`, และ `high`, +`xhigh`, และ `max` map โดยตรง backend แบบ CLI อื่นต้องให้ Plugin ที่เป็นเจ้าของ +ประกาศ argv mapper ที่เทียบเท่าก่อน `/think` จึงจะส่งผลต่อ CLI ที่ spawn ได้ + +ก่อนที่ OpenClaw จะใช้ backend `claude-cli` ที่บันเดิลมาได้ ตัว Claude Code เอง +ต้องล็อกอินไว้แล้วบนโฮสต์เดียวกัน: ```bash claude auth login @@ -194,101 +200,102 @@ claude auth status --text openclaw models auth login --provider anthropic --method cli --set-default ``` -ใช้ `agents.defaults.cliBackends.claude-cli.command` เฉพาะเมื่อไบนารี `claude` +ใช้ `agents.defaults.cliBackends.claude-cli.command` เฉพาะเมื่อ binary `claude` ไม่ได้อยู่บน `PATH` อยู่แล้ว ## เซสชัน -- หาก CLI รองรับเซสชัน ให้ตั้งค่า `sessionArg` (เช่น `--session-id`) หรือ +- หาก CLI รองรับเซสชัน ให้ตั้ง `sessionArg` (เช่น `--session-id`) หรือ `sessionArgs` (placeholder `{sessionId}`) เมื่อจำเป็นต้องแทรก ID - ลงในหลายแฟล็ก -- หาก CLI ใช้ **คำสั่งย่อย resume** ที่มีแฟล็กต่างกัน ให้ตั้งค่า - `resumeArgs` (แทนที่ `args` เมื่อ resume) และอาจตั้งค่า `resumeOutput` + ลงในหลาย flag +- หาก CLI ใช้ **resume subcommand** พร้อม flag ที่แตกต่างกัน ให้ตั้ง + `resumeArgs` (แทนที่ `args` เมื่อ resume) และอาจตั้ง `resumeOutput` (สำหรับการ resume ที่ไม่ใช่ JSON) - `sessionMode`: - - `always`: ส่ง session id เสมอ (UUID ใหม่หากยังไม่มีที่จัดเก็บไว้) - - `existing`: ส่ง session id เฉพาะเมื่อเคยจัดเก็บไว้ก่อนหน้า + - `always`: ส่ง session id เสมอ (UUID ใหม่หากยังไม่มีที่บันทึกไว้) + - `existing`: ส่ง session id เฉพาะเมื่อเคยบันทึกไว้ก่อนหน้า - `none`: ไม่ส่ง session id เลย - `claude-cli` มีค่าเริ่มต้นเป็น `liveSession: "claude-stdio"`, `output: "jsonl"`, - และ `input: "stdin"` เพื่อให้เทิร์นติดตามใช้กระบวนการ Claude สดซ้ำขณะที่ - ยังทำงานอยู่ stdio แบบอุ่นเป็นค่าเริ่มต้นแล้วในตอนนี้ รวมถึงสำหรับการตั้งค่าแบบกำหนดเอง - ที่ละเว้นฟิลด์ transport หาก Gateway รีสตาร์ตหรือกระบวนการที่ idle - ออก OpenClaw จะ resume จาก session id ของ Claude ที่จัดเก็บไว้ session - id ที่จัดเก็บไว้จะถูกตรวจสอบกับทรานสคริปต์โปรเจกต์ที่อ่านได้และมีอยู่ก่อน - resume ดังนั้นการผูกแบบ phantom จะถูกล้างด้วย `reason=transcript-missing` + และ `input: "stdin"` เพื่อให้รอบสนทนาต่อเนื่องใช้ process Claude แบบ live ซ้ำขณะที่ + ยังทำงานอยู่ ตอนนี้ warm stdio เป็นค่าเริ่มต้นแล้ว รวมถึงสำหรับ config แบบกำหนดเอง + ที่ละเว้น field transport หาก Gateway รีสตาร์ตหรือ process ที่ idle + ออกไป OpenClaw จะ resume จาก session id ของ Claude ที่เก็บไว้ session + id ที่เก็บไว้จะถูกตรวจสอบกับ transcript โปรเจกต์ที่มีอยู่และอ่านได้ก่อน + resume ดังนั้นการผูกที่เป็นภาพลวงจะถูกล้างด้วย `reason=transcript-missing` แทนที่จะเริ่มเซสชัน Claude CLI ใหม่อย่างเงียบๆ ภายใต้ `--resume` -- เซสชันสดของ Claude จะคงตัวป้องกันเอาต์พุต JSONL แบบมีขอบเขต ค่าเริ่มต้นอนุญาตได้ถึง - 8 MiB และ 20,000 บรรทัด JSONL ดิบต่อเทิร์น เทิร์น Claude ที่ใช้เครื่องมือหนักสามารถเพิ่ม - ค่าเหล่านี้ต่อแบ็กเอนด์ได้ด้วย +- เซสชัน Claude แบบ live จะเก็บ guard output JSONL แบบมีขอบเขต ค่าเริ่มต้นอนุญาตสูงสุด + 8 MiB และ 20,000 บรรทัด JSONL ดิบต่อรอบสนทนา รอบสนทนา Claude ที่ใช้เครื่องมือหนักสามารถเพิ่ม + ได้ราย backend ด้วย `agents.defaults.cliBackends.claude-cli.reliability.outputLimits.maxTurnRawChars` - และ `maxTurnLines`; OpenClaw จะจำกัดการตั้งค่าเหล่านั้นไว้ที่ 64 MiB และ 100,000 + และ `maxTurnLines`; OpenClaw จะ clamp การตั้งค่าเหล่านั้นไว้ที่ 64 MiB และ 100,000 บรรทัด -- เซสชัน CLI ที่จัดเก็บไว้คือความต่อเนื่องที่ผู้ให้บริการเป็นเจ้าของ การรีเซ็ตเซสชันรายวัน +- เซสชัน CLI ที่เก็บไว้เป็นความต่อเนื่องที่ผู้ให้บริการเป็นเจ้าของ การ reset เซสชันรายวัน โดยนัยจะไม่ตัดเซสชันเหล่านั้น; `/reset` และนโยบาย `session.reset` ที่ชัดเจนยังคง ทำเช่นนั้น -หมายเหตุเกี่ยวกับการทำให้เป็นลำดับ: +หมายเหตุเรื่อง serialization: -- `serialize: true` ทำให้การรันในเลนเดียวกันเรียงตามลำดับ -- CLI ส่วนใหญ่ทำให้เป็นลำดับบนเลนผู้ให้บริการเดียว -- OpenClaw จะยกเลิกการใช้เซสชัน CLI ที่จัดเก็บไว้ซ้ำเมื่อ auth identity ที่เลือกเปลี่ยนไป, - รวมถึง auth profile id ที่เปลี่ยน, static API key, static token, หรือ OAuth - account identity เมื่อ CLI เปิดเผยค่าใดค่าหนึ่ง การหมุนเวียน OAuth access และ refresh token - จะไม่ตัดเซสชัน CLI ที่จัดเก็บไว้ หาก CLI ไม่เปิดเผย +- `serialize: true` รักษาลำดับการรันในเลนเดียวกัน +- CLI ส่วนใหญ่ serialize บนเลนผู้ให้บริการเดียว +- OpenClaw จะเลิกใช้เซสชัน CLI ที่เก็บไว้ซ้ำเมื่อ identity การยืนยันตัวตนที่เลือกเปลี่ยน + รวมถึง auth profile id, static API key, static token, หรือ identity + บัญชี OAuth ที่เปลี่ยนไปเมื่อ CLI เปิดเผยให้ใช้ การหมุน access token และ refresh token + ของ OAuth จะไม่ตัดเซสชัน CLI ที่เก็บไว้ หาก CLI ไม่เปิดเผย OAuth account id ที่เสถียร OpenClaw จะให้ CLI นั้นบังคับใช้สิทธิ์ resume เอง -## บทนำแผนสำรองจากเซสชัน claude-cli +## prelude สำรองจากเซสชัน claude-cli -เมื่อความพยายามของ `claude-cli` fail over ไปยัง candidate ที่ไม่ใช่ CLI ใน -[`agents.defaults.model.fallbacks`](/th/concepts/model-failover) OpenClaw จะเติม seed -ความพยายามถัดไปด้วย context prelude ที่เก็บเกี่ยวจากทรานสคริปต์ JSONL ภายในเครื่องของ Claude Code -ที่ `~/.claude/projects/` หากไม่มี seed นี้ ผู้ให้บริการแผนสำรอง -จะเริ่มแบบเย็น เพราะทรานสคริปต์เซสชันของ OpenClaw เองว่างเปล่า +เมื่อความพยายาม `claude-cli` fail over ไปยังตัวเลือกที่ไม่ใช่ CLI ใน +[`agents.defaults.model.fallbacks`](/th/concepts/model-failover) OpenClaw จะ seed +ความพยายามถัดไปด้วย context prelude ที่เก็บจาก transcript JSONL ภายในเครื่องของ Claude Code +ที่ `~/.claude/projects/` หากไม่มี seed นี้ ผู้ให้บริการสำรอง +จะเริ่มแบบไม่มีบริบท เพราะ transcript เซสชันของ OpenClaw เองว่างเปล่า สำหรับการรัน `claude-cli` -- prelude จะเลือกสรุป `/compact` ล่าสุดหรือ marker `compact_boundary` - ก่อน แล้วต่อท้ายเทิร์นหลัง boundary ล่าสุดจนถึงงบประมาณอักขระ - เทิร์นก่อน boundary จะถูกทิ้ง เพราะสรุปนั้นแทนเทิร์นเหล่านั้นแล้ว -- บล็อกเครื่องมือจะถูกรวมเป็นคำใบ้แบบกระชับ `(tool call: name)` และ - `(tool result: …)` เพื่อรักษางบประมาณพรอมป์อย่างซื่อตรง สรุปจะถูก - ระบุว่า `(truncated)` หากเกินขนาด -- แผนสำรอง `claude-cli` ไป `claude-cli` ที่เป็นผู้ให้บริการเดียวกันจะพึ่งพา +- prelude จะเลือก summary `/compact` ล่าสุดหรือ marker `compact_boundary` + ก่อน จากนั้น append รอบสนทนาหลัง boundary ล่าสุดเท่าที่ char + budget อนุญาต รอบสนทนาก่อน boundary จะถูกทิ้ง เพราะ summary แทน + รอบสนทนาเหล่านั้นอยู่แล้ว +- บล็อกเครื่องมือจะถูกรวมเป็น hint แบบกะทัดรัด `(tool call: name)` และ + `(tool result: …)` เพื่อรักษา prompt budget ให้ตรงจริง summary จะถูก + ติดป้าย `(truncated)` หากล้น +- fallback จาก `claude-cli` ไป `claude-cli` ที่เป็นผู้ให้บริการเดียวกันพึ่งพา `--resume` ของ Claude เองและข้าม prelude -- seed จะใช้การตรวจสอบพาธไฟล์เซสชัน Claude ที่มีอยู่ซ้ำ ดังนั้น - จึงไม่สามารถอ่านพาธโดยพลการได้ +- seed ใช้การตรวจสอบพาธ session-file ของ Claude ที่มีอยู่ซ้ำ ดังนั้น + จึงไม่สามารถอ่านพาธใดๆ ตามอำเภอใจได้ ## รูปภาพ (ส่งผ่าน) -หาก CLI ของคุณรับพาธรูปภาพ ให้ตั้งค่า `imageArg`: +หาก CLI ของคุณยอมรับพาธรูปภาพ ให้ตั้ง `imageArg`: ```json5 imageArg: "--image", imageMode: "repeat" ``` -OpenClaw จะเขียนรูปภาพ base64 ลงในไฟล์ชั่วคราว หากตั้งค่า `imageArg` ไว้ พาธเหล่านั้น -จะถูกส่งเป็น args ของ CLI หากไม่มี `imageArg` OpenClaw จะต่อท้าย -พาธไฟล์เข้ากับพรอมป์ (path injection) ซึ่งเพียงพอสำหรับ CLI ที่โหลด -ไฟล์ภายในเครื่องจากพาธธรรมดาโดยอัตโนมัติ +OpenClaw จะเขียนรูปภาพ base64 ลงไฟล์ชั่วคราว หากตั้ง `imageArg` ไว้ +พาธเหล่านั้นจะถูกส่งเป็น arg ของ CLI หากไม่มี `imageArg` OpenClaw จะ append +พาธไฟล์เข้าไปใน prompt (path injection) ซึ่งเพียงพอสำหรับ CLI ที่โหลด +ไฟล์ภายในเครื่องอัตโนมัติจากพาธธรรมดา ## อินพุต / เอาต์พุต - `output: "json"` (ค่าเริ่มต้น) จะพยายามแยกวิเคราะห์ JSON และดึงข้อความ + session id -- สำหรับเอาต์พุต JSON ของ Gemini CLI OpenClaw จะอ่านข้อความตอบกลับจาก `response` และ - usage จาก `stats` เมื่อ `usage` ไม่มีหรือว่าง -- `output: "jsonl"` จะแยกวิเคราะห์สตรีม JSONL (เช่น Codex CLI `--json`) และดึงข้อความเอเจนต์สุดท้ายพร้อมตัวระบุเซสชัน - เมื่อมี +- สำหรับ output JSON ของ Gemini CLI OpenClaw จะอ่านข้อความตอบกลับจาก `response` และ + usage จาก `stats` เมื่อ `usage` หายไปหรือว่าง +- `output: "jsonl"` แยกวิเคราะห์สตรีม JSONL (เช่น Codex CLI `--json`) และดึงข้อความ agent สุดท้ายพร้อม session + identifier เมื่อมี - `output: "text"` ถือว่า stdout เป็นคำตอบสุดท้าย โหมดอินพุต: -- `input: "arg"` (ค่าเริ่มต้น) ส่งพรอมป์เป็น arg สุดท้ายของ CLI -- `input: "stdin"` ส่งพรอมป์ผ่าน stdin -- หากพรอมป์ยาวมากและตั้งค่า `maxPromptArgChars` ไว้ จะใช้ stdin +- `input: "arg"` (ค่าเริ่มต้น) ส่ง prompt เป็น arg สุดท้ายของ CLI +- `input: "stdin"` ส่ง prompt ผ่าน stdin +- หาก prompt ยาวมากและตั้ง `maxPromptArgChars` ไว้ จะใช้ stdin -## ค่าเริ่มต้น (Plugin เป็นเจ้าของ) +## ค่าเริ่มต้น (เป็นของ Plugin) -Plugin OpenAI ที่รวมมาให้ยังลงทะเบียนค่าเริ่มต้นสำหรับ `codex-cli` ด้วย: +OpenAI Plugin ที่บันเดิลมายังลงทะเบียนค่าเริ่มต้นสำหรับ `codex-cli` ด้วย: - `command: "codex"` - `args: ["exec","--json","--color","never","--sandbox","workspace-write","--skip-git-repo-check"]` @@ -299,7 +306,7 @@ Plugin OpenAI ที่รวมมาให้ยังลงทะเบีย - `imageArg: "--image"` - `sessionMode: "existing"` -Plugin Google ที่รวมมาให้ยังลงทะเบียนค่าเริ่มต้นสำหรับ `google-gemini-cli` ด้วย: +Google Plugin ที่บันเดิลมายังลงทะเบียนค่าเริ่มต้นสำหรับ `google-gemini-cli` ด้วย: - `command: "gemini"` - `args: ["--output-format", "json", "--prompt", "{prompt}"]` @@ -316,26 +323,26 @@ Plugin Google ที่รวมมาให้ยังลงทะเบีย หมายเหตุ JSON ของ Gemini CLI: -- ข้อความตอบกลับจะอ่านจากฟิลด์ JSON `response` -- Usage จะ fallback ไปที่ `stats` เมื่อ `usage` ไม่มีหรือว่าง -- `stats.cached` จะถูก normalize เป็น OpenClaw `cacheRead` -- หาก `stats.input` ไม่มี OpenClaw จะ derive input tokens จาก +- ข้อความตอบกลับถูกอ่านจากฟิลด์ JSON `response` +- การใช้งานจะ fallback ไปที่ `stats` เมื่อ `usage` ไม่มีอยู่หรือว่างเปล่า +- `stats.cached` ถูก normalize เป็น OpenClaw `cacheRead` +- หาก `stats.input` หายไป OpenClaw จะคำนวณโทเค็นอินพุตจาก `stats.input_tokens - stats.cached` -Override เฉพาะเมื่อจำเป็น (ที่พบบ่อย: พาธ `command` แบบ absolute) +Override เฉพาะเมื่อจำเป็นเท่านั้น (ที่พบบ่อย: พาธ `command` แบบสัมบูรณ์) ## ค่าเริ่มต้นที่ Plugin เป็นเจ้าของ -ค่าเริ่มต้นของแบ็กเอนด์ CLI ตอนนี้เป็นส่วนหนึ่งของพื้นผิว Plugin: +ค่าเริ่มต้นของแบ็กเอนด์ CLI เป็นส่วนหนึ่งของพื้นผิว Plugin แล้ว: -- Plugin ลงทะเบียนรายการเหล่านี้ด้วย `api.registerCliBackend(...)` -- แบ็กเอนด์ `id` จะกลายเป็นคำนำหน้าผู้ให้บริการในข้อมูลอ้างอิงโมเดล -- การกำหนดค่าของผู้ใช้ใน `agents.defaults.cliBackends.` ยังคงแทนที่ค่าเริ่มต้นของ Plugin -- การล้างการกำหนดค่าเฉพาะแบ็กเอนด์ยังคงเป็นของ Plugin ผ่าน hook เสริม - `normalizeConfig` +- Plugin ลงทะเบียนด้วย `api.registerCliBackend(...)` +- `id` ของแบ็กเอนด์จะกลายเป็น prefix ของ provider ในการอ้างอิงโมเดล +- การกำหนดค่าผู้ใช้ใน `agents.defaults.cliBackends.` ยังคง override ค่าเริ่มต้นของ Plugin +- การล้างการกำหนดค่าเฉพาะแบ็กเอนด์ยังคงเป็นของ Plugin ผ่าน hook + `normalizeConfig` แบบไม่บังคับ -Plugin ที่ต้องการชิมความเข้ากันได้ของพรอมป์/ข้อความขนาดเล็กสามารถประกาศ -การแปลงข้อความแบบสองทิศทางได้โดยไม่ต้องแทนที่ผู้ให้บริการหรือแบ็กเอนด์ CLI: +Plugin ที่ต้องการ shim ความเข้ากันได้ของพรอมป์/ข้อความขนาดเล็กสามารถประกาศ +การแปลงข้อความสองทิศทางได้โดยไม่ต้องแทนที่ provider หรือแบ็กเอนด์ CLI: ```typescript api.registerTextTransforms({ @@ -352,64 +359,64 @@ api.registerTextTransforms({ }); ``` -`input` เขียน system prompt และ user prompt ที่ส่งไปยัง CLI ใหม่ `output` -เขียนเดลตาของผู้ช่วยที่สตรีมมาและข้อความสุดท้ายที่แยกวิเคราะห์แล้วใหม่ ก่อนที่ OpenClaw จะจัดการ -เครื่องหมายควบคุมและการส่งมอบผ่านช่องทางของตัวเอง +`input` เขียนพรอมป์ระบบและพรอมป์ผู้ใช้ที่ส่งให้ CLI ใหม่ `output` +เขียน streamed assistant deltas และข้อความสุดท้ายที่ parse แล้วใหม่ ก่อนที่ OpenClaw จะจัดการ +control markers และการส่งมอบไปยังช่องทางของตัวเอง -สำหรับ CLI ที่ปล่อย JSONL ซึ่งเข้ากันได้กับ Claude Code stream-json ให้ตั้งค่า +สำหรับ CLI ที่ปล่อย JSONL ที่เข้ากันได้กับ Claude Code stream-json ให้ตั้งค่า `jsonlDialect: "claude-stream-json"` ในการกำหนดค่าของแบ็กเอนด์นั้น -## โอเวอร์เลย์ MCP แบบบันเดิล +## overlay MCP แบบบันเดิล -แบ็กเอนด์ CLI **ไม่ได้** รับการเรียกเครื่องมือ OpenClaw โดยตรง แต่แบ็กเอนด์สามารถ -เลือกใช้โอเวอร์เลย์การกำหนดค่า MCP ที่สร้างขึ้นด้วย `bundleMcp: true` +แบ็กเอนด์ CLI จะ **ไม่ได้** รับ tool calls ของ OpenClaw โดยตรง แต่แบ็กเอนด์สามารถ +เลือกใช้ overlay การกำหนดค่า MCP ที่สร้างขึ้นได้ด้วย `bundleMcp: true` พฤติกรรมที่บันเดิลอยู่ในปัจจุบัน: -- `claude-cli`: ไฟล์การกำหนดค่า MCP แบบเข้มงวดที่สร้างขึ้น -- `codex-cli`: การแทนที่การกำหนดค่าแบบอินไลน์สำหรับ `mcp_servers`; เซิร์ฟเวอร์ - OpenClaw loopback ที่สร้างขึ้นจะถูกทำเครื่องหมายด้วยโหมดอนุมัติเครื่องมือต่อเซิร์ฟเวอร์ของ Codex - เพื่อให้การเรียก MCP ไม่ค้างที่พรอมป์อนุมัติในเครื่อง +- `claude-cli`: ไฟล์กำหนดค่า MCP แบบเข้มงวดที่สร้างขึ้น +- `codex-cli`: การ override การกำหนดค่าแบบ inline สำหรับ `mcp_servers`; เซิร์ฟเวอร์ + loopback ของ OpenClaw ที่สร้างขึ้นจะถูกทำเครื่องหมายด้วยโหมดอนุมัติเครื่องมือต่อเซิร์ฟเวอร์ของ Codex + เพื่อให้การเรียก MCP ไม่หยุดค้างที่พรอมป์อนุมัติในเครื่อง - `google-gemini-cli`: ไฟล์การตั้งค่าระบบ Gemini ที่สร้างขึ้น -เมื่อเปิดใช้ bundle MCP แล้ว OpenClaw จะ: +เมื่อเปิดใช้ bundle MCP OpenClaw จะ: -- สร้างเซิร์ฟเวอร์ HTTP MCP แบบ loopback ที่เปิดเผยเครื่องมือ Gateway ให้กับกระบวนการ CLI -- ยืนยันตัวตนของบริดจ์ด้วยโทเค็นต่อเซสชัน (`OPENCLAW_MCP_TOKEN`) -- จำกัดขอบเขตการเข้าถึงเครื่องมือไว้ที่บริบทเซสชัน บัญชี และช่องทางปัจจุบัน -- โหลดเซิร์ฟเวอร์ bundle-MCP ที่เปิดใช้สำหรับเวิร์กสเปซปัจจุบัน -- รวมเซิร์ฟเวอร์เหล่านั้นกับรูปแบบการกำหนดค่า/การตั้งค่า MCP ของแบ็กเอนด์ที่มีอยู่ -- เขียนการกำหนดค่าการเปิดใช้งานใหม่โดยใช้โหมดการผสานรวมที่แบ็กเอนด์เป็นเจ้าของจากส่วนขยายเจ้าของ +- spawn เซิร์ฟเวอร์ HTTP MCP แบบ loopback ที่เปิดเผยเครื่องมือ Gateway ให้กับกระบวนการ CLI +- ตรวจสอบสิทธิ์ bridge ด้วยโทเค็นต่อเซสชัน (`OPENCLAW_MCP_TOKEN`) +- จำกัดขอบเขตการเข้าถึงเครื่องมือไว้ที่บริบทของเซสชัน บัญชี และช่องทางปัจจุบัน +- โหลดเซิร์ฟเวอร์ bundle-MCP ที่เปิดใช้สำหรับ workspace ปัจจุบัน +- ผสานเซิร์ฟเวอร์เหล่านั้นกับรูปแบบการกำหนดค่า/การตั้งค่า MCP ของแบ็กเอนด์ที่มีอยู่ +- เขียนการกำหนดค่าการเปิดใช้งานใหม่โดยใช้โหมด integration ที่แบ็กเอนด์เป็นเจ้าของจากส่วนขยายเจ้าของ -ถ้าไม่มีเซิร์ฟเวอร์ MCP ที่เปิดใช้ OpenClaw ยังคงแทรกการกำหนดค่าแบบเข้มงวดเมื่อ -แบ็กเอนด์เลือกใช้ bundle MCP เพื่อให้การรันเบื้องหลังยังคงแยกโดดเดี่ยว +หากไม่มีเซิร์ฟเวอร์ MCP ที่เปิดใช้ OpenClaw ยังคง inject การกำหนดค่าแบบเข้มงวดเมื่อ +แบ็กเอนด์เลือกใช้ bundle MCP เพื่อให้การรันเบื้องหลังยังคงถูกแยกออกจากกัน -รันไทม์ MCP ที่บันเดิลและมีขอบเขตตามเซสชันจะถูกแคชเพื่อนำกลับมาใช้ภายในเซสชัน จากนั้น +runtime MCP แบบบันเดิลที่มีขอบเขตตามเซสชันจะถูกแคชไว้เพื่อนำกลับมาใช้ซ้ำภายในเซสชัน จากนั้น ถูกเก็บกวาดหลังจากไม่มีการใช้งานเป็นเวลา `mcp.sessionIdleTtlMs` มิลลิวินาที (ค่าเริ่มต้น 10 -นาที; ตั้งค่าเป็น `0` เพื่อปิดใช้) การรันแบบฝังครั้งเดียว เช่น การตรวจสอบ auth, -การสร้าง slug และคำขอเรียกคืน active-memory จะทำความสะอาดเมื่อการรันสิ้นสุด เพื่อให้กระบวนการลูกแบบ stdio -และสตรีม Streamable HTTP/SSE ไม่อยู่เกินอายุของการรัน +นาที; ตั้งค่า `0` เพื่อปิดใช้) การรันแบบฝังตัวครั้งเดียว เช่น auth probes, +การสร้าง slug และคำขอ recall active-memory จะล้างข้อมูลเมื่อการรันสิ้นสุด เพื่อไม่ให้ stdio +children และสตรีม Streamable HTTP/SSE มีอายุยาวกว่าการรัน ## ข้อจำกัด -- **ไม่มีการเรียกเครื่องมือ OpenClaw โดยตรง** OpenClaw ไม่แทรกการเรียกเครื่องมือเข้าไปใน - โปรโตคอลแบ็กเอนด์ CLI แบ็กเอนด์จะเห็นเครื่องมือ Gateway ก็ต่อเมื่อเลือกใช้ - `bundleMcp: true` เท่านั้น -- **การสตรีมขึ้นอยู่กับแบ็กเอนด์** บางแบ็กเอนด์สตรีม JSONL; บางแบ็กเอนด์บัฟเฟอร์ +- **ไม่มี tool calls ของ OpenClaw โดยตรง** OpenClaw ไม่ inject tool calls เข้าไปใน + โปรโตคอลแบ็กเอนด์ CLI แบ็กเอนด์จะเห็นเครื่องมือ Gateway เฉพาะเมื่อเลือกใช้ + `bundleMcp: true` +- **Streaming ขึ้นอยู่กับแบ็กเอนด์** บางแบ็กเอนด์ stream JSONL; บางแบ็กเอนด์ buffer จนกว่าจะออก -- **เอาต์พุตแบบมีโครงสร้าง** ขึ้นอยู่กับรูปแบบ JSON ของ CLI -- **เซสชัน Codex CLI** ทำงานต่อผ่านเอาต์พุตข้อความ (ไม่มี JSONL) ซึ่งมีโครงสร้างน้อยกว่า - การรัน `--json` เริ่มต้น เซสชัน OpenClaw ยังคงทำงานได้ตามปกติ +- **Structured outputs** ขึ้นอยู่กับรูปแบบ JSON ของ CLI +- **เซสชัน Codex CLI** resume ผ่านเอาต์พุตข้อความ (ไม่มี JSONL) ซึ่งมีโครงสร้างน้อยกว่า + การรัน `--json` ครั้งแรก เซสชัน OpenClaw ยังคงทำงานได้ตามปกติ ## การแก้ไขปัญหา - **ไม่พบ CLI**: ตั้งค่า `command` เป็นพาธเต็ม -- **ชื่อโมเดลไม่ถูกต้อง**: ใช้ `modelAliases` เพื่อแมป `provider/model` → โมเดล CLI +- **ชื่อโมเดลไม่ถูกต้อง**: ใช้ `modelAliases` เพื่อ map `provider/model` → โมเดล CLI - **ไม่มีความต่อเนื่องของเซสชัน**: ตรวจสอบให้แน่ใจว่าตั้งค่า `sessionArg` แล้ว และ `sessionMode` ไม่ใช่ - `none` (ปัจจุบัน Codex CLI ยังไม่สามารถทำงานต่อด้วยเอาต์พุต JSON ได้) + `none` (ขณะนี้ Codex CLI ยังไม่สามารถ resume ด้วยเอาต์พุต JSON ได้) - **รูปภาพถูกละเว้น**: ตั้งค่า `imageArg` (และตรวจสอบว่า CLI รองรับพาธไฟล์) ## ที่เกี่ยวข้อง -- [คู่มือปฏิบัติการ Gateway](/th/gateway) -- [โมเดลภายในเครื่อง](/th/gateway/local-models) +- [คู่มือการดำเนินงาน Gateway](/th/gateway) +- [โมเดลในเครื่อง](/th/gateway/local-models) diff --git a/docs/th/help/testing-live.md b/docs/th/help/testing-live.md index 4c5d85ac1..d0fc08b0d 100644 --- a/docs/th/help/testing-live.md +++ b/docs/th/help/testing-live.md @@ -1,35 +1,35 @@ --- read_when: - - กำลังเรียกใช้การทดสอบ smoke ของเมทริกซ์โมเดลจริง / แบ็กเอนด์ CLI / ACP / media-provider - - การดีบักการค้นหาข้อมูลรับรองสำหรับการทดสอบจริง - - การเพิ่มการทดสอบแบบสดเฉพาะผู้ให้บริการใหม่ + - การรันการทดสอบเบื้องต้นสำหรับเมทริกซ์โมเดลสด / แบ็กเอนด์ CLI / ACP / media-provider + - การดีบักการระบุข้อมูลรับรองสำหรับการทดสอบสด + - การเพิ่มการทดสอบสดเฉพาะผู้ให้บริการใหม่ sidebarTitle: Live tests -summary: 'การทดสอบแบบสด (ที่แตะเครือข่าย): เมทริกซ์โมเดล, แบ็กเอนด์ CLI, ACP, ผู้ให้บริการสื่อ, ข้อมูลรับรอง' +summary: 'การทดสอบแบบใช้งานจริง (ที่มีการติดต่อเครือข่าย): เมทริกซ์โมเดล, แบ็กเอนด์ CLI, ACP, ผู้ให้บริการสื่อ, ข้อมูลประจำตัว' title: 'การทดสอบ: ชุดทดสอบแบบใช้งานจริง' x-i18n: - generated_at: "2026-05-03T10:12:42Z" + generated_at: "2026-05-04T18:24:03Z" model: gpt-5.5 provider: openai - source_hash: 4057d8875fa3404108e89e4381c1dd14e96abbc2af13c4934fc6c0dbf878fc00 + source_hash: 03b8ca6348137a55c8d5f67c9c166a130a75a744f6a433cb00496756b29d7016 source_path: help/testing-live.md workflow: 16 --- -สำหรับการเริ่มต้นอย่างรวดเร็ว, QA runner, ชุดทดสอบ unit/integration และ Docker flow โปรดดู +สำหรับ quick start, ตัวรัน QA, ชุดทดสอบ unit/integration และโฟลว์ Docker โปรดดู [การทดสอบ](/th/help/testing) หน้านี้ครอบคลุมชุดทดสอบ **live** (ที่แตะเครือข่าย): -เมทริกซ์โมเดล, CLI backend, ACP และการทดสอบ live ของผู้ให้บริการสื่อ รวมถึง -การจัดการข้อมูลประจำตัว +เมทริกซ์โมเดล, แบ็กเอนด์ CLI, ACP และการทดสอบ live ของ media-provider รวมถึง +การจัดการข้อมูลรับรอง -## Live: คำสั่ง smoke ของโปรไฟล์ local +## Live: คำสั่ง smoke สำหรับโปรไฟล์ภายในเครื่อง -ให้ source `~/.profile` ก่อนตรวจสอบ live แบบเฉพาะกิจ เพื่อให้คีย์ของผู้ให้บริการและ path ของเครื่องมือ local -ตรงกับ shell ของคุณ: +Source `~/.profile` ก่อนการตรวจ live แบบ ad hoc เพื่อให้คีย์ผู้ให้บริการและพาธเครื่องมือภายในเครื่อง +ตรงกับเชลล์ของคุณ: ```bash source ~/.profile ``` -media smoke ที่ปลอดภัย: +Smoke สื่อที่ปลอดภัย: ```bash pnpm openclaw infer tts convert --local --json \ @@ -37,102 +37,102 @@ pnpm openclaw infer tts convert --local --json \ --output /tmp/openclaw-live-smoke.mp3 ``` -smoke ตรวจความพร้อมของ voice-call ที่ปลอดภัย: +Smoke ความพร้อมของสายสนทนาด้วยเสียงที่ปลอดภัย: ```bash pnpm openclaw voicecall setup --json pnpm openclaw voicecall smoke --to "+15555550123" ``` -`voicecall smoke` เป็นการ dry run เว้นแต่จะมี `--yes` อยู่ด้วย ใช้ `--yes` เฉพาะเมื่อ -คุณตั้งใจจะโทรแจ้งเตือนจริง สำหรับ Twilio, Telnyx และ -Plivo การตรวจความพร้อมที่สำเร็จต้องมี URL ของ Webhook สาธารณะ fallback แบบ -local loopback/ส่วนตัวเท่านั้นจะถูกปฏิเสธตามการออกแบบ +`voicecall smoke` เป็นการ dry run เว้นแต่จะมี `--yes` อยู่ด้วย ใช้ `--yes` เฉพาะ +เมื่อคุณตั้งใจจะโทรแจ้งเตือนจริงเท่านั้น สำหรับ Twilio, Telnyx และ +Plivo การตรวจความพร้อมที่สำเร็จต้องใช้ Webhook URL สาธารณะ; fallback แบบ local-only +loopback/private จะถูกปฏิเสธโดยตั้งใจ -## Live: การ sweep ความสามารถของ Node Android +## Live: การกวาดความสามารถของ Android Node - การทดสอบ: `src/gateway/android-node.capabilities.live.test.ts` - สคริปต์: `pnpm android:test:integration` -- เป้าหมาย: เรียก **ทุกคำสั่งที่ประกาศอยู่ในปัจจุบัน** โดย Node Android ที่เชื่อมต่ออยู่ และยืนยันพฤติกรรมตามสัญญาของคำสั่ง +- เป้าหมาย: เรียกใช้ **ทุกคำสั่งที่ประกาศไว้ในปัจจุบัน** โดย Android Node ที่เชื่อมต่ออยู่ และยืนยันพฤติกรรมตามสัญญาของคำสั่ง - ขอบเขต: - - การตั้งค่าล่วงหน้า/ด้วยตนเอง (ชุดทดสอบนี้ไม่ติดตั้ง/รัน/จับคู่แอป) - - การตรวจสอบ `node.invoke` ของ Gateway ทีละคำสั่งสำหรับ Node Android ที่เลือก + - การตั้งค่าล่วงหน้า/แบบแมนนวล (ชุดทดสอบนี้ไม่ติดตั้ง/รัน/จับคู่แอป) + - การตรวจสอบ gateway `node.invoke` แบบทีละคำสั่งสำหรับ Android Node ที่เลือก - การตั้งค่าล่วงหน้าที่จำเป็น: - - แอป Android เชื่อมต่อและจับคู่กับ Gateway แล้ว - - คงแอปไว้ใน foreground - - ให้สิทธิ์/ยินยอมการจับภาพสำหรับความสามารถที่คุณคาดว่าจะผ่านแล้ว + - แอป Android เชื่อมต่อและจับคู่กับ gateway แล้ว + - เปิดแอปไว้ใน foreground + - ให้สิทธิ์/ยินยอมการจับภาพแล้วสำหรับความสามารถที่คุณคาดว่าจะผ่าน - การ override เป้าหมายแบบไม่บังคับ: - `OPENCLAW_ANDROID_NODE_ID` หรือ `OPENCLAW_ANDROID_NODE_NAME` - `OPENCLAW_ANDROID_GATEWAY_URL` / `OPENCLAW_ANDROID_GATEWAY_TOKEN` / `OPENCLAW_ANDROID_GATEWAY_PASSWORD` -- รายละเอียดการตั้งค่า Android แบบเต็ม: [แอป Android](/th/platforms/android) +- รายละเอียดการตั้งค่า Android ทั้งหมด: [แอป Android](/th/platforms/android) -## Live: model smoke (คีย์โปรไฟล์) +## Live: smoke โมเดล (คีย์โปรไฟล์) -การทดสอบ live แบ่งเป็นสองชั้นเพื่อให้เราแยกความล้มเหลวได้: +การทดสอบ Live แบ่งเป็นสองชั้นเพื่อให้เราแยกความล้มเหลวได้: -- “โมเดลโดยตรง” บอกเราว่าผู้ให้บริการ/โมเดลสามารถตอบได้จริงด้วยคีย์ที่ให้มา -- “Gateway smoke” บอกเราว่า pipeline gateway+agent แบบเต็มทำงานสำหรับโมเดลนั้น (session, ประวัติ, เครื่องมือ, นโยบาย sandbox ฯลฯ) +- “Direct model” บอกเราว่าผู้ให้บริการ/โมเดลสามารถตอบได้จริงด้วยคีย์ที่ให้มา +- “Gateway smoke” บอกเราว่า pipeline gateway+agent แบบเต็มทำงานสำหรับโมเดลนั้น (sessions, history, tools, sandbox policy ฯลฯ) -### ชั้นที่ 1: การ completion ของโมเดลโดยตรง (ไม่มี gateway) +### ชั้นที่ 1: Direct model completion (ไม่มี gateway) - การทดสอบ: `src/agents/models.profiles.live.test.ts` - เป้าหมาย: - แจกแจงโมเดลที่ค้นพบ - - ใช้ `getApiKeyForModel` เพื่อเลือกโมเดลที่คุณมีข้อมูลประจำตัว - - รัน completion ขนาดเล็กต่อโมเดล (และ regression แบบเจาะจงเมื่อจำเป็น) -- วิธีเปิดใช้งาน: - - `pnpm test:live` (หรือ `OPENCLAW_LIVE_TEST=1` หากเรียกใช้ Vitest โดยตรง) -- ตั้ง `OPENCLAW_LIVE_MODELS=modern` (หรือ `all` ซึ่งเป็น alias สำหรับ modern) เพื่อรันชุดทดสอบนี้จริง มิฉะนั้นจะข้ามเพื่อให้ `pnpm test:live` โฟกัสที่ gateway smoke + - ใช้ `getApiKeyForModel` เพื่อเลือกโมเดลที่คุณมีข้อมูลรับรอง + - รัน completion ขนาดเล็กต่อโมเดล (และ regression เฉพาะจุดเมื่อจำเป็น) +- วิธีเปิดใช้: + - `pnpm test:live` (หรือ `OPENCLAW_LIVE_TEST=1` หากเรียก Vitest โดยตรง) +- ตั้งค่า `OPENCLAW_LIVE_MODELS=modern` (หรือ `all` ซึ่งเป็น alias สำหรับ modern) เพื่อรันชุดทดสอบนี้จริง มิฉะนั้นจะข้ามเพื่อให้ `pnpm test:live` โฟกัสที่ gateway smoke - วิธีเลือกโมเดล: - `OPENCLAW_LIVE_MODELS=modern` เพื่อรัน allowlist สมัยใหม่ (Opus/Sonnet 4.6+, GPT-5.2 + Codex, Gemini 3, DeepSeek V4, GLM 4.7, MiniMax M2.7, Grok 4.3) - `OPENCLAW_LIVE_MODELS=all` เป็น alias สำหรับ allowlist สมัยใหม่ - - หรือ `OPENCLAW_LIVE_MODELS="openai/gpt-5.5,openai-codex/gpt-5.5,anthropic/claude-opus-4-6,..."` (allowlist คั่นด้วยจุลภาค) - - การ sweep แบบ modern/all ใช้ขีดจำกัด high-signal ที่คัดสรรไว้เป็นค่าเริ่มต้น ตั้ง `OPENCLAW_LIVE_MAX_MODELS=0` สำหรับการ sweep modern แบบครบถ้วน หรือจำนวนบวกสำหรับขีดจำกัดที่เล็กลง - - การ sweep แบบครบถ้วนใช้ `OPENCLAW_LIVE_TEST_TIMEOUT_MS` สำหรับ timeout ของการทดสอบ direct-model ทั้งหมด ค่าเริ่มต้น: 60 นาที - - probe แบบ direct-model รันด้วย parallelism 20 ทางเป็นค่าเริ่มต้น ตั้ง `OPENCLAW_LIVE_MODEL_CONCURRENCY` เพื่อ override + - หรือ `OPENCLAW_LIVE_MODELS="openai/gpt-5.5,openai-codex/gpt-5.5,anthropic/claude-opus-4-6,..."` (comma allowlist) + - การกวาดแบบ modern/all มีค่าเริ่มต้นเป็นเพดาน curated ที่ให้สัญญาณสูง; ตั้งค่า `OPENCLAW_LIVE_MAX_MODELS=0` สำหรับการกวาด modern แบบครอบคลุมทั้งหมด หรือใช้จำนวนบวกสำหรับเพดานที่เล็กลง + - การกวาดแบบครอบคลุมทั้งหมดใช้ `OPENCLAW_LIVE_TEST_TIMEOUT_MS` เป็น timeout ของการทดสอบ direct-model ทั้งหมด ค่าเริ่มต้น: 60 นาที + - probe แบบ direct-model รันด้วย parallelism 20 ทางเป็นค่าเริ่มต้น; ตั้งค่า `OPENCLAW_LIVE_MODEL_CONCURRENCY` เพื่อ override - วิธีเลือกผู้ให้บริการ: - - `OPENCLAW_LIVE_PROVIDERS="google,google-antigravity,google-gemini-cli"` (allowlist คั่นด้วยจุลภาค) + - `OPENCLAW_LIVE_PROVIDERS="google,google-antigravity,google-gemini-cli"` (comma allowlist) - คีย์มาจากที่ใด: - - โดยค่าเริ่มต้น: profile store และ fallback จาก env - - ตั้ง `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับใช้เฉพาะ **profile store** -- เหตุผลที่สิ่งนี้มีอยู่: - - แยก “API ของผู้ให้บริการเสีย / คีย์ไม่ถูกต้อง” ออกจาก “pipeline ของ gateway agent เสีย” - - มี regression ขนาดเล็กแบบแยกส่วน (ตัวอย่าง: OpenAI Responses/Codex Responses reasoning replay + flow ของ tool-call) + - ค่าเริ่มต้น: profile store และ env fallback + - ตั้งค่า `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับใช้เฉพาะ **profile store** +- เหตุผลที่มีสิ่งนี้: + - แยก “provider API เสีย / คีย์ไม่ถูกต้อง” ออกจาก “gateway agent pipeline เสีย” + - มี regression ขนาดเล็กและแยกส่วน (ตัวอย่าง: OpenAI Responses/Codex Responses reasoning replay + โฟลว์ tool-call) ### ชั้นที่ 2: Gateway + dev agent smoke (สิ่งที่ "@openclaw" ทำจริง) - การทดสอบ: `src/gateway/gateway-models.profiles.live.test.ts` - เป้าหมาย: - - เริ่ม gateway ภายใน process + - เปิด gateway แบบ in-process - สร้าง/patch session `agent:dev:*` (override โมเดลต่อการรัน) - - วนผ่านโมเดลที่มีคีย์และยืนยันว่า: - - การตอบกลับ “มีความหมาย” (ไม่มีเครื่องมือ) - - การเรียกใช้เครื่องมือจริงทำงานได้ (read probe) - - probe เครื่องมือเพิ่มเติมแบบไม่บังคับ (exec+read probe) - - path regression ของ OpenAI (tool-call-only → follow-up) ยังทำงาน + - วนผ่าน models-with-keys และยืนยันว่า: + - การตอบสนอง “มีความหมาย” (ไม่มี tools) + - การเรียก tool จริงทำงาน (read probe) + - probe tool เพิ่มเติมแบบไม่บังคับ (exec+read probe) + - พาธ regression ของ OpenAI (tool-call-only → follow-up) ยังทำงาน - รายละเอียด probe (เพื่อให้คุณอธิบายความล้มเหลวได้เร็ว): - - `read` probe: การทดสอบเขียนไฟล์ nonce ใน workspace และขอให้ agent `read` ไฟล์นั้น แล้ว echo nonce กลับมา - - `exec+read` probe: การทดสอบขอให้ agent ใช้ `exec` เขียน nonce ลงในไฟล์ temp แล้ว `read` กลับมา - - image probe: การทดสอบแนบ PNG ที่สร้างขึ้น (แมว + โค้ดสุ่ม) และคาดว่าโมเดลจะคืนค่า `cat ` - - อ้างอิง implementation: `src/gateway/gateway-models.profiles.live.test.ts` และ `src/gateway/live-image-probe.ts` -- วิธีเปิดใช้งาน: - - `pnpm test:live` (หรือ `OPENCLAW_LIVE_TEST=1` หากเรียกใช้ Vitest โดยตรง) + - `read` probe: การทดสอบเขียนไฟล์ nonce ใน workspace และขอให้ agent `read` ไฟล์นั้นและ echo nonce กลับมา + - `exec+read` probe: การทดสอบขอให้ agent ใช้ `exec` เขียน nonce ลงในไฟล์ชั่วคราว แล้ว `read` กลับมา + - image probe: การทดสอบแนบ PNG ที่สร้างขึ้น (cat + โค้ดสุ่ม) และคาดว่าโมเดลจะคืนค่า `cat ` + - อ้างอิงการใช้งาน: `src/gateway/gateway-models.profiles.live.test.ts` และ `src/gateway/live-image-probe.ts` +- วิธีเปิดใช้: + - `pnpm test:live` (หรือ `OPENCLAW_LIVE_TEST=1` หากเรียก Vitest โดยตรง) - วิธีเลือกโมเดล: - ค่าเริ่มต้น: allowlist สมัยใหม่ (Opus/Sonnet 4.6+, GPT-5.2 + Codex, Gemini 3, DeepSeek V4, GLM 4.7, MiniMax M2.7, Grok 4.3) - `OPENCLAW_LIVE_GATEWAY_MODELS=all` เป็น alias สำหรับ allowlist สมัยใหม่ - - หรือตั้ง `OPENCLAW_LIVE_GATEWAY_MODELS="provider/model"` (หรือรายการคั่นด้วยจุลภาค) เพื่อจำกัดขอบเขต - - การ sweep gateway แบบ modern/all ใช้ขีดจำกัด high-signal ที่คัดสรรไว้เป็นค่าเริ่มต้น ตั้ง `OPENCLAW_LIVE_GATEWAY_MAX_MODELS=0` สำหรับการ sweep modern แบบครบถ้วน หรือจำนวนบวกสำหรับขีดจำกัดที่เล็กลง -- วิธีเลือกผู้ให้บริการ (หลีกเลี่ยง “OpenRouter ทั้งหมด”): - - `OPENCLAW_LIVE_GATEWAY_PROVIDERS="google,google-antigravity,google-gemini-cli,openai,anthropic,zai,minimax"` (allowlist คั่นด้วยจุลภาค) -- probe เครื่องมือ + รูปภาพเปิดอยู่เสมอในการทดสอบ live นี้: + - หรือตั้งค่า `OPENCLAW_LIVE_GATEWAY_MODELS="provider/model"` (หรือรายการคั่นด้วยจุลภาค) เพื่อจำกัดขอบเขต + - การกวาด gateway แบบ modern/all มีค่าเริ่มต้นเป็นเพดาน curated ที่ให้สัญญาณสูง; ตั้งค่า `OPENCLAW_LIVE_GATEWAY_MAX_MODELS=0` สำหรับการกวาด modern แบบครอบคลุมทั้งหมด หรือใช้จำนวนบวกสำหรับเพดานที่เล็กลง +- วิธีเลือกผู้ให้บริการ (หลีกเลี่ยง “OpenRouter everything”): + - `OPENCLAW_LIVE_GATEWAY_PROVIDERS="google,google-antigravity,google-gemini-cli,openai,anthropic,zai,minimax"` (comma allowlist) +- Tool + image probes เปิดอยู่เสมอในการทดสอบ live นี้: - `read` probe + `exec+read` probe (tool stress) - - image probe รันเมื่อโมเดลประกาศว่ารองรับอินพุตรูปภาพ - - Flow (ระดับสูง): + - image probe จะรันเมื่อโมเดลประกาศว่ารองรับอินพุตรูปภาพ + - โฟลว์ (ระดับสูง): - การทดสอบสร้าง PNG ขนาดเล็กที่มี “CAT” + โค้ดสุ่ม (`src/gateway/live-image-probe.ts`) - ส่งผ่าน `agent` `attachments: [{ mimeType: "image/png", content: "" }]` - Gateway แยกวิเคราะห์ attachments เป็น `images[]` (`src/gateway/server-methods/agent.ts` + `src/gateway/chat-attachments.ts`) - - agent ที่ฝังอยู่ส่งข้อความผู้ใช้แบบ multimodal ไปยังโมเดล - - Assertion: คำตอบมี `cat` + โค้ด (ความทนทาน OCR: อนุญาตให้ผิดพลาดเล็กน้อย) + - Embedded agent ส่งต่อข้อความผู้ใช้แบบ multimodal ไปยังโมเดล + - Assertion: คำตอบมี `cat` + โค้ด (ความทนทาน OCR: อนุญาตข้อผิดพลาดเล็กน้อย) หากต้องการดูว่าคุณทดสอบอะไรได้บนเครื่องของคุณ (และ id `provider/model` ที่แน่นอน) ให้รัน: @@ -144,27 +144,27 @@ openclaw models list --json -## Live: CLI backend smoke (Claude, Codex, Gemini หรือ CLI local อื่น ๆ) +## Live: smoke แบ็กเอนด์ CLI (Claude, Codex, Gemini หรือ CLI ภายในเครื่องอื่น) - การทดสอบ: `src/gateway/gateway-cli-backend.live.test.ts` -- เป้าหมาย: ตรวจสอบ pipeline Gateway + agent โดยใช้ CLI backend แบบ local โดยไม่แตะ config เริ่มต้นของคุณ -- ค่าเริ่มต้นของ smoke เฉพาะ backend อยู่กับ definition `cli-backend.ts` ของ Plugin เจ้าของ -- เปิดใช้งาน: - - `pnpm test:live` (หรือ `OPENCLAW_LIVE_TEST=1` หากเรียกใช้ Vitest โดยตรง) +- เป้าหมาย: ตรวจสอบ pipeline Gateway + agent โดยใช้แบ็กเอนด์ CLI ภายในเครื่อง โดยไม่แตะ config เริ่มต้นของคุณ +- ค่าเริ่มต้นของ smoke เฉพาะแบ็กเอนด์อยู่กับ definition `cli-backend.ts` ของ Plugin เจ้าของ +- เปิดใช้: + - `pnpm test:live` (หรือ `OPENCLAW_LIVE_TEST=1` หากเรียก Vitest โดยตรง) - `OPENCLAW_LIVE_CLI_BACKEND=1` - ค่าเริ่มต้น: - ผู้ให้บริการ/โมเดลเริ่มต้น: `claude-cli/claude-sonnet-4-6` - - พฤติกรรม command/args/image มาจาก metadata ของ CLI backend Plugin เจ้าของ + - พฤติกรรม command/args/image มาจาก metadata ของ Plugin แบ็กเอนด์ CLI เจ้าของ - Override (ไม่บังคับ): - `OPENCLAW_LIVE_CLI_BACKEND_MODEL="codex-cli/gpt-5.5"` - `OPENCLAW_LIVE_CLI_BACKEND_COMMAND="/full/path/to/codex"` - `OPENCLAW_LIVE_CLI_BACKEND_ARGS='["exec","--json","--color","never","--sandbox","read-only","--skip-git-repo-check"]'` - - `OPENCLAW_LIVE_CLI_BACKEND_IMAGE_PROBE=1` เพื่อส่ง attachment รูปภาพจริง (path จะถูกใส่เข้าไปใน prompt) สูตร Docker ปิดค่านี้เป็นค่าเริ่มต้น เว้นแต่จะร้องขออย่างชัดเจน - - `OPENCLAW_LIVE_CLI_BACKEND_IMAGE_ARG="--image"` เพื่อส่ง path ไฟล์รูปภาพเป็น CLI args แทนการฉีดเข้า prompt - - `OPENCLAW_LIVE_CLI_BACKEND_IMAGE_MODE="repeat"` (หรือ `"list"`) เพื่อควบคุมวิธีส่ง image args เมื่อตั้ง `IMAGE_ARG` - - `OPENCLAW_LIVE_CLI_BACKEND_RESUME_PROBE=1` เพื่อส่ง turn ที่สองและตรวจสอบ flow การ resume - - `OPENCLAW_LIVE_CLI_BACKEND_MODEL_SWITCH_PROBE=1` เพื่อเลือกใช้ probe ความต่อเนื่องใน session เดียวกันจาก Claude Sonnet -> Opus เมื่อโมเดลที่เลือกสนับสนุนเป้าหมายการ switch สูตร Docker ปิดค่านี้เป็นค่าเริ่มต้นเพื่อความน่าเชื่อถือโดยรวม - - `OPENCLAW_LIVE_CLI_BACKEND_MCP_PROBE=1` เพื่อเลือกใช้ probe MCP/tool loopback สูตร Docker ปิดค่านี้เป็นค่าเริ่มต้น เว้นแต่จะร้องขออย่างชัดเจน + - `OPENCLAW_LIVE_CLI_BACKEND_IMAGE_PROBE=1` เพื่อส่ง attachment รูปภาพจริง (พาธจะถูก inject เข้าไปใน prompt) สูตร Docker ปิดค่านี้เป็นค่าเริ่มต้นเว้นแต่จะร้องขออย่างชัดเจน + - `OPENCLAW_LIVE_CLI_BACKEND_IMAGE_ARG="--image"` เพื่อส่งพาธไฟล์รูปภาพเป็น CLI args แทนการ inject ใน prompt + - `OPENCLAW_LIVE_CLI_BACKEND_IMAGE_MODE="repeat"` (หรือ `"list"`) เพื่อควบคุมวิธีส่ง image args เมื่อมีการตั้งค่า `IMAGE_ARG` + - `OPENCLAW_LIVE_CLI_BACKEND_RESUME_PROBE=1` เพื่อส่ง turn ที่สองและตรวจสอบโฟลว์ resume + - `OPENCLAW_LIVE_CLI_BACKEND_MODEL_SWITCH_PROBE=1` เพื่อเลือกใช้ probe ความต่อเนื่องใน session เดียวกัน Claude Sonnet -> Opus เมื่อโมเดลที่เลือก รองรับเป้าหมายการสลับ สูตร Docker ปิดค่านี้เป็นค่าเริ่มต้นเพื่อความเสถียรโดยรวม + - `OPENCLAW_LIVE_CLI_BACKEND_MCP_PROBE=1` เพื่อเลือกใช้ probe MCP/tool loopback สูตร Docker ปิดค่านี้เป็นค่าเริ่มต้นเว้นแต่จะร้องขออย่างชัดเจน ตัวอย่าง: @@ -174,17 +174,17 @@ OPENCLAW_LIVE_CLI_BACKEND=1 \ pnpm test:live src/gateway/gateway-cli-backend.live.test.ts ``` -smoke config Gemini MCP ราคาถูก: +Smoke config Gemini MCP ราคาถูก: ```bash OPENCLAW_LIVE_TEST=1 \ pnpm test:live src/agents/cli-runner/bundle-mcp.gemini.live.test.ts ``` -สิ่งนี้ไม่ได้ขอให้ Gemini สร้างคำตอบ แต่จะเขียน system -settings เดียวกับที่ OpenClaw ส่งให้ Gemini จากนั้นรัน `gemini --debug mcp list` เพื่อพิสูจน์ว่า server -ที่บันทึกไว้เป็น `transport: "streamable-http"` ถูก normalize เป็น shape HTTP MCP ของ Gemini -และสามารถเชื่อมต่อกับ server MCP แบบ streamable-HTTP local ได้ +สิ่งนี้ไม่ได้ขอให้ Gemini สร้างคำตอบ แต่เขียนการตั้งค่า system เดียวกับที่ +OpenClaw ให้ Gemini จากนั้นรัน `gemini --debug mcp list` เพื่อพิสูจน์ว่า +server `transport: "streamable-http"` ที่บันทึกไว้ถูก normalize เป็นรูปแบบ HTTP MCP +ของ Gemini และเชื่อมต่อกับ server MCP แบบ streamable-HTTP ภายในเครื่องได้ สูตร Docker: @@ -192,7 +192,7 @@ settings เดียวกับที่ OpenClaw ส่งให้ Gemini pnpm test:docker:live-cli-backend ``` -สูตร Docker สำหรับผู้ให้บริการรายเดียว: +สูตร Docker แบบผู้ให้บริการเดียว: ```bash pnpm test:docker:live-cli-backend:claude @@ -203,30 +203,39 @@ pnpm test:docker:live-cli-backend:gemini หมายเหตุ: -- Docker runner อยู่ที่ `scripts/test-live-cli-backend-docker.sh` -- มันรัน live CLI-backend smoke ภายใน image Docker ของ repo ในฐานะผู้ใช้ `node` ที่ไม่ใช่ root -- มัน resolve metadata ของ CLI smoke จากส่วนขยายเจ้าของ จากนั้นติดตั้งแพ็กเกจ Linux CLI ที่ตรงกัน (`@anthropic-ai/claude-code`, `@openai/codex` หรือ `@google/gemini-cli`) ลงใน prefix ที่เขียนได้และมี cache ที่ `OPENCLAW_DOCKER_CLI_TOOLS_DIR` (ค่าเริ่มต้น: `~/.cache/openclaw/docker-cli-tools`) -- `pnpm test:docker:live-cli-backend:claude-subscription` ต้องใช้ portable Claude Code subscription OAuth ผ่าน `~/.claude/.credentials.json` ที่มี `claudeAiOauth.subscriptionType` หรือ `CLAUDE_CODE_OAUTH_TOKEN` จาก `claude setup-token` โดยจะพิสูจน์ direct `claude -p` ใน Docker ก่อน จากนั้นรัน Gateway CLI-backend สอง turn โดยไม่เก็บ env var ของ Anthropic API-key lane subscription นี้ปิด probe Claude MCP/tool และรูปภาพเป็นค่าเริ่มต้น เพราะปัจจุบัน Claude route การใช้งานแอปของบุคคลที่สามผ่านการคิดค่าบริการการใช้งานเพิ่มเติมแทนขีดจำกัดปกติของแผน subscription -- live CLI-backend smoke ตอนนี้ทดสอบ flow end-to-end เดียวกันสำหรับ Claude, Codex และ Gemini: turn ข้อความ, turn จำแนกรูปภาพ จากนั้นเรียก tool MCP `cron` ที่ตรวจสอบผ่าน gateway CLI +- ตัวรัน Docker อยู่ที่ `scripts/test-live-cli-backend-docker.sh` +- มันรัน smoke แบ็กเอนด์ CLI แบบ live ภายในอิมเมจ Docker ของ repo ในฐานะผู้ใช้ `node` ที่ไม่ใช่ root +- มัน resolve metadata ของ CLI smoke จาก extension เจ้าของ จากนั้นติดตั้งแพ็กเกจ Linux CLI ที่ตรงกัน (`@anthropic-ai/claude-code`, `@openai/codex` หรือ `@google/gemini-cli`) ลงใน prefix ที่เขียนได้และมี cache ที่ `OPENCLAW_DOCKER_CLI_TOOLS_DIR` (ค่าเริ่มต้น: `~/.cache/openclaw/docker-cli-tools`) +- `pnpm test:docker:live-cli-backend:claude-subscription` ต้องใช้ OAuth สำหรับ subscription Claude Code แบบพกพาผ่าน `~/.claude/.credentials.json` ที่มี `claudeAiOauth.subscriptionType` หรือ `CLAUDE_CODE_OAUTH_TOKEN` จาก `claude setup-token` โดยจะพิสูจน์ `claude -p` โดยตรงใน Docker ก่อน จากนั้นรันสอง turn ของแบ็กเอนด์ CLI ของ Gateway โดยไม่เก็บ env vars ของ Anthropic API-key โหมด subscription นี้ปิด probe Claude MCP/tool และ image เป็นค่าเริ่มต้น เพราะปัจจุบัน Claude route การใช้งานแอป third-party ผ่านการคิดค่าใช้งานเพิ่มเติม แทนขีดจำกัดแพ็กเกจ subscription ปกติ +- ตอนนี้ smoke แบ็กเอนด์ CLI แบบ live ใช้โฟลว์ end-to-end เดียวกันสำหรับ Claude, Codex และ Gemini: text turn, image classification turn แล้วจึงเรียก tool MCP `cron` ที่ตรวจสอบผ่าน gateway CLI - smoke เริ่มต้นของ Claude ยัง patch session จาก Sonnet เป็น Opus และตรวจสอบว่า session ที่ resume แล้วยังจำ note ก่อนหน้าได้ -## Live: ACP bind smoke (`/acp spawn ... --bind here`) +## Live: ความสามารถในการเข้าถึงพร็อกซี APNs HTTP/2 -- ทดสอบ: `src/gateway/gateway-acp-bind.live.test.ts` -- เป้าหมาย: ตรวจสอบโฟลว์ bind การสนทนา ACP จริงกับ ACP agent แบบ live: - - ส่ง `/acp spawn --bind here` - - bind การสนทนาช่องทางข้อความสังเคราะห์ในตำแหน่งเดิม - - ส่งการติดตามผลปกติในการสนทนาเดียวกันนั้น - - ตรวจสอบว่าการติดตามผลไปอยู่ใน transcript ของเซสชัน ACP ที่ถูก bind แล้ว +- การทดสอบ: `src/infra/push-apns-http2.live.test.ts` +- เป้าหมาย: tunnel ผ่านพร็อกซี HTTP CONNECT ภายในเครื่องไปยัง endpoint APNs sandbox ของ Apple, ส่งคำขอตรวจสอบ APNs HTTP/2 และยืนยันว่าการตอบกลับจริง `403 InvalidProviderToken` ของ Apple กลับมาผ่านพาธพร็อกซี - เปิดใช้: + - `OPENCLAW_LIVE_TEST=1 OPENCLAW_LIVE_APNS_REACHABILITY=1 pnpm test:live src/infra/push-apns-http2.live.test.ts` +- Timeout แบบไม่บังคับ: + - `OPENCLAW_LIVE_APNS_TIMEOUT_MS=30000` + +## Live: smoke การ bind ACP (`/acp spawn ... --bind here`) + +- การทดสอบ: `src/gateway/gateway-acp-bind.live.test.ts` +- เป้าหมาย: ตรวจสอบโฟลว์ bind บทสนทนา ACP จริงกับเอเจนต์ ACP แบบ live: + - ส่ง `/acp spawn --bind here` + - bind บทสนทนาช่องทางข้อความสังเคราะห์ไว้ที่เดิม + - ส่งการติดตามผลปกติในบทสนทนาเดียวกันนั้น + - ตรวจสอบว่าการติดตามผลเข้าไปอยู่ในทรานสคริปต์ของเซสชัน ACP ที่ถูก bind แล้ว +- เปิดใช้งาน: - `pnpm test:live src/gateway/gateway-acp-bind.live.test.ts` - `OPENCLAW_LIVE_ACP_BIND=1` - ค่าเริ่มต้น: - - ACP agents ใน Docker: `claude,codex,gemini` - - ACP agent สำหรับ `pnpm test:live ...` โดยตรง: `claude` - - ช่องทางสังเคราะห์: บริบทการสนทนาแบบ DM ของ Slack + - เอเจนต์ ACP ใน Docker: `claude,codex,gemini` + - เอเจนต์ ACP สำหรับ `pnpm test:live ...` โดยตรง: `claude` + - ช่องทางสังเคราะห์: บริบทบทสนทนาแบบ Slack DM - แบ็กเอนด์ ACP: `acpx` -- การแทนที่: +- การ override: - `OPENCLAW_LIVE_ACP_BIND_AGENT=claude` - `OPENCLAW_LIVE_ACP_BIND_AGENT=codex` - `OPENCLAW_LIVE_ACP_BIND_AGENT=droid` @@ -240,9 +249,9 @@ pnpm test:docker:live-cli-backend:gemini - `OPENCLAW_LIVE_ACP_BIND_REQUIRE_CRON=1` - `OPENCLAW_LIVE_ACP_BIND_PARENT_MODEL=openai/gpt-5.5` - หมายเหตุ: - - เลนนี้ใช้พื้นผิว `chat.send` ของ gateway พร้อมฟิลด์ originating-route สังเคราะห์สำหรับผู้ดูแลเท่านั้น เพื่อให้การทดสอบสามารถแนบบริบทช่องทางข้อความได้โดยไม่แสร้งว่าส่งออกไปภายนอก - - เมื่อไม่ได้ตั้งค่า `OPENCLAW_LIVE_ACP_BIND_AGENT_COMMAND` การทดสอบจะใช้ registry agent ในตัวของ Plugin `acpx` ที่ฝังไว้สำหรับ ACP harness agent ที่เลือก - - การสร้าง MCP สำหรับ Cron ของเซสชันที่ถูก bind เป็นแบบพยายามให้ดีที่สุดโดยค่าเริ่มต้น เพราะ ACP harness ภายนอกอาจยกเลิกการเรียก MCP หลังจากหลักฐาน bind/image ผ่านแล้ว ตั้งค่า `OPENCLAW_LIVE_ACP_BIND_REQUIRE_CRON=1` เพื่อทำให้การ probe Cron หลัง bind นั้นเข้มงวด + - เลนนี้ใช้พื้นผิว `chat.send` ของ gateway พร้อมฟิลด์ originating-route สังเคราะห์แบบ admin-only เพื่อให้การทดสอบแนบบริบทช่องทางข้อความได้โดยไม่ต้องแสร้งว่าส่งออกไปภายนอกจริง + - เมื่อไม่ได้ตั้งค่า `OPENCLAW_LIVE_ACP_BIND_AGENT_COMMAND` การทดสอบจะใช้รีจิสทรีเอเจนต์ในตัวของ Plugin `acpx` แบบฝังตัวสำหรับเอเจนต์ harness ACP ที่เลือกไว้ + - การสร้าง MCP ของ Cron เซสชันที่ถูก bind เป็นแบบพยายามให้ดีที่สุดโดยค่าเริ่มต้น เพราะ harness ACP ภายนอกอาจยกเลิกการเรียก MCP หลังจาก proof ของการ bind/ภาพผ่านแล้ว ตั้งค่า `OPENCLAW_LIVE_ACP_BIND_REQUIRE_CRON=1` เพื่อทำให้ probe Cron หลัง bind นั้นเข้มงวด ตัวอย่าง: @@ -258,7 +267,7 @@ OPENCLAW_LIVE_ACP_BIND=1 \ pnpm test:docker:live-acp-bind ``` -สูตร Docker สำหรับ agent เดียว: +สูตร Docker สำหรับเอเจนต์เดียว: ```bash pnpm test:docker:live-acp-bind:claude @@ -271,35 +280,30 @@ pnpm test:docker:live-acp-bind:opencode หมายเหตุ Docker: - Docker runner อยู่ที่ `scripts/test-live-acp-bind-docker.sh` -- โดยค่าเริ่มต้น จะรัน ACP bind smoke กับ live CLI agents แบบรวมตามลำดับ: `claude`, `codex`, แล้วจึง `gemini` -- ใช้ `OPENCLAW_LIVE_ACP_BIND_AGENTS=claude`, `OPENCLAW_LIVE_ACP_BIND_AGENTS=codex`, `OPENCLAW_LIVE_ACP_BIND_AGENTS=droid`, `OPENCLAW_LIVE_ACP_BIND_AGENTS=gemini` หรือ `OPENCLAW_LIVE_ACP_BIND_AGENTS=opencode` เพื่อจำกัดเมทริกซ์ -- สคริปต์จะ source `~/.profile`, จัดเตรียมวัสดุ auth ของ CLI ที่ตรงกันเข้าไปในคอนเทนเนอร์ แล้วติดตั้ง live CLI ที่ร้องขอ (`@anthropic-ai/claude-code`, `@openai/codex`, Factory Droid ผ่าน `https://app.factory.ai/cli`, `@google/gemini-cli` หรือ `opencode-ai`) หากยังไม่มี แบ็กเอนด์ ACP เองคือแพ็กเกจ `acpx/runtime` ที่ฝังไว้จาก Plugin `acpx` อย่างเป็นทางการ -- ตัวแปร Docker สำหรับ Droid จะจัดเตรียม `~/.factory` สำหรับการตั้งค่า ส่งต่อ `FACTORY_API_KEY` และต้องใช้ API key นั้น เพราะการ auth แบบ Factory OAuth/keyring ในเครื่องไม่สามารถพกพาเข้าไปในคอนเทนเนอร์ได้ โดยใช้รายการ registry ในตัวของ ACPX คือ `droid exec --output-format acp` -- ตัวแปร Docker สำหรับ OpenCode เป็นเลน regression สำหรับ agent เดียวแบบเข้มงวด โดยเขียนโมเดลเริ่มต้น `OPENCODE_CONFIG_CONTENT` ชั่วคราวจาก `OPENCLAW_LIVE_ACP_BIND_OPENCODE_MODEL` (ค่าเริ่มต้น `opencode/kimi-k2.6`) หลังจาก source `~/.profile` และ `pnpm test:docker:live-acp-bind:opencode` ต้องมี transcript ของผู้ช่วยที่ถูก bind แทนที่จะยอมรับการข้ามหลัง bind แบบทั่วไป -- การเรียก CLI `acpx` โดยตรงเป็นเพียงเส้นทางแบบ manual/workaround สำหรับเปรียบเทียบพฤติกรรมภายนอก Gateway เท่านั้น ACP bind smoke บน Docker ทดสอบแบ็กเอนด์ runtime `acpx` ที่ฝังไว้ของ OpenClaw +- โดยค่าเริ่มต้น จะรัน ACP bind smoke กับเอเจนต์ CLI แบบ live รวมตามลำดับ: `claude`, `codex` แล้วจึง `gemini` +- ใช้ `OPENCLAW_LIVE_ACP_BIND_AGENTS=claude`, `OPENCLAW_LIVE_ACP_BIND_AGENTS=codex`, `OPENCLAW_LIVE_ACP_BIND_AGENTS=droid`, `OPENCLAW_LIVE_ACP_BIND_AGENTS=gemini` หรือ `OPENCLAW_LIVE_ACP_BIND_AGENTS=opencode` เพื่อจำกัดเมทริกซ์ให้แคบลง +- จะ source `~/.profile`, เตรียม auth material ของ CLI ที่ตรงกันลงในคอนเทนเนอร์ แล้วติดตั้ง CLI แบบ live ที่ร้องขอ (`@anthropic-ai/claude-code`, `@openai/codex`, Factory Droid ผ่าน `https://app.factory.ai/cli`, `@google/gemini-cli` หรือ `opencode-ai`) หากยังไม่มี แบ็กเอนด์ ACP เองคือแพ็กเกจ `acpx/runtime` แบบฝังตัวจาก Plugin `acpx` อย่างเป็นทางการ +- ตัวแปร Docker ของ Droid จะเตรียม `~/.factory` สำหรับการตั้งค่า, ส่งต่อ `FACTORY_API_KEY` และต้องมี API key นั้น เพราะ auth แบบ Factory OAuth/keyring ในเครื่องไม่สามารถพกพาเข้าไปในคอนเทนเนอร์ได้ โดยใช้รายการรีจิสทรีในตัวของ ACPX คือ `droid exec --output-format acp` +- ตัวแปร Docker ของ OpenCode เป็นเลน regression เอเจนต์เดียวแบบเข้มงวด โดยจะเขียนโมเดลเริ่มต้นชั่วคราว `OPENCODE_CONFIG_CONTENT` จาก `OPENCLAW_LIVE_ACP_BIND_OPENCODE_MODEL` (ค่าเริ่มต้น `opencode/kimi-k2.6`) หลังจาก source `~/.profile` และ `pnpm test:docker:live-acp-bind:opencode` ต้องมีทรานสคริปต์ผู้ช่วยที่ถูก bind แทนการยอมรับการข้ามหลัง bind แบบทั่วไป +- การเรียก CLI `acpx` โดยตรงเป็นเพียงเส้นทาง manual/workaround สำหรับเปรียบเทียบพฤติกรรมนอก Gateway เท่านั้น ACP bind smoke ของ Docker ทดสอบแบ็กเอนด์ runtime `acpx` แบบฝังตัวของ OpenClaw ## Live: Codex app-server harness smoke -- เป้าหมาย: ตรวจสอบ Codex harness ที่ Plugin เป็นเจ้าของผ่านเมธอด gateway - `agent` ปกติ: - - โหลด Plugin `codex` ที่ bundle มา +- เป้าหมาย: ตรวจสอบ harness Codex ที่ Plugin เป็นเจ้าของผ่านเมธอด `agent` ของ gateway ปกติ: + - โหลด Plugin `codex` ที่ bundled มา - เลือก `OPENCLAW_AGENT_RUNTIME=codex` - - ส่ง turn แรกของ gateway agent ไปที่ `openai/gpt-5.5` พร้อมบังคับใช้ Codex harness - - ส่ง turn ที่สองไปยังเซสชัน OpenClaw เดียวกัน และตรวจสอบว่า thread ของ app-server - สามารถ resume ได้ + - ส่งเทิร์นแรกของเอเจนต์ gateway ไปยัง `openai/gpt-5.5` โดยบังคับใช้ harness Codex + - ส่งเทิร์นที่สองไปยังเซสชัน OpenClaw เดิมและตรวจสอบว่า thread ของ app-server สามารถ resume ได้ - รัน `/codex status` และ `/codex models` ผ่านเส้นทางคำสั่ง gateway เดียวกัน - - เลือกรัน shell probes แบบสิทธิ์ยกระดับที่ Guardian ตรวจทานแล้วสองรายการ: คำสั่งที่ไม่เป็นอันตรายหนึ่งคำสั่งซึ่งควรได้รับการอนุมัติ และการอัปโหลด fake-secret หนึ่งรายการซึ่งควรถูกปฏิเสธเพื่อให้ agent ถามกลับ -- ทดสอบ: `src/gateway/gateway-codex-harness.live.test.ts` -- เปิดใช้: `OPENCLAW_LIVE_CODEX_HARNESS=1` + - เลือกรัน probe shell แบบ escalated ที่ผ่านการตรวจสอบโดย Guardian สองรายการ: คำสั่งที่ไม่เป็นอันตรายซึ่งควรถูกอนุมัติ และการอัปโหลด fake-secret ที่ควรถูกปฏิเสธเพื่อให้เอเจนต์ถามกลับ +- การทดสอบ: `src/gateway/gateway-codex-harness.live.test.ts` +- เปิดใช้งาน: `OPENCLAW_LIVE_CODEX_HARNESS=1` - โมเดลเริ่มต้น: `openai/gpt-5.5` -- image probe แบบเลือกได้: `OPENCLAW_LIVE_CODEX_HARNESS_IMAGE_PROBE=1` -- MCP/tool probe แบบเลือกได้: `OPENCLAW_LIVE_CODEX_HARNESS_MCP_PROBE=1` -- Guardian probe แบบเลือกได้: `OPENCLAW_LIVE_CODEX_HARNESS_GUARDIAN_PROBE=1` -- smoke ใช้ `agentRuntime.id: "codex"` เพื่อให้ Codex harness ที่เสียไม่สามารถ - ผ่านได้ด้วยการ fallback ไปที่ PI อย่างเงียบ ๆ -- Auth: auth ของ Codex app-server จากการล็อกอิน subscription ของ Codex ในเครื่อง Docker - smokes ยังสามารถให้ `OPENAI_API_KEY` สำหรับ probes ที่ไม่ใช่ Codex เมื่อเกี่ยวข้อง - รวมถึงคัดลอก `~/.codex/auth.json` และ `~/.codex/config.toml` แบบเลือกได้ +- probe รูปภาพแบบเลือกได้: `OPENCLAW_LIVE_CODEX_HARNESS_IMAGE_PROBE=1` +- probe MCP/tool แบบเลือกได้: `OPENCLAW_LIVE_CODEX_HARNESS_MCP_PROBE=1` +- probe Guardian แบบเลือกได้: `OPENCLAW_LIVE_CODEX_HARNESS_GUARDIAN_PROBE=1` +- smoke ใช้ `agentRuntime.id: "codex"` เพื่อให้ harness Codex ที่เสียไม่สามารถผ่านได้โดยเงียบ ๆ ด้วยการ fallback ไปยัง PI +- Auth: auth ของ Codex app-server จากการเข้าสู่ระบบ subscription ของ Codex ในเครื่อง Docker smokes ยังสามารถให้ `OPENAI_API_KEY` สำหรับ probe ที่ไม่ใช่ Codex เมื่อเกี่ยวข้อง รวมถึงคัดลอก `~/.codex/auth.json` และ `~/.codex/config.toml` แบบเลือกได้ สูตรในเครื่อง: @@ -323,66 +327,59 @@ pnpm test:docker:live-codex-harness หมายเหตุ Docker: - Docker runner อยู่ที่ `scripts/test-live-codex-harness-docker.sh` -- สคริปต์จะ source `~/.profile` ที่ mount ไว้ ส่งผ่าน `OPENAI_API_KEY` คัดลอกไฟล์ auth ของ Codex CLI - เมื่อมี ติดตั้ง `@openai/codex` ลงใน npm - prefix ที่ mount ไว้และเขียนได้ จัดเตรียม source tree แล้วรันเฉพาะการทดสอบ live ของ Codex-harness -- Docker เปิดใช้ image, MCP/tool และ Guardian probes โดยค่าเริ่มต้น ตั้งค่า - `OPENCLAW_LIVE_CODEX_HARNESS_IMAGE_PROBE=0` หรือ - `OPENCLAW_LIVE_CODEX_HARNESS_MCP_PROBE=0` หรือ - `OPENCLAW_LIVE_CODEX_HARNESS_GUARDIAN_PROBE=0` เมื่อคุณต้องการรัน debug - ที่แคบลง -- Docker ใช้การกำหนดค่า runtime ของ Codex ที่ชัดเจนเหมือนกัน ดังนั้น aliases เดิมหรือการ fallback ของ PI - จึงไม่สามารถซ่อน regression ของ Codex harness ได้ +- จะ source `~/.profile` ที่ mount ไว้, ส่งผ่าน `OPENAI_API_KEY`, คัดลอกไฟล์ auth ของ Codex CLI เมื่อมี, ติดตั้ง `@openai/codex` ลงใน npm prefix ที่ mount แบบเขียนได้, เตรียม source tree แล้วรันเฉพาะการทดสอบ live ของ Codex-harness +- Docker เปิดใช้ probe รูปภาพ, MCP/tool และ Guardian โดยค่าเริ่มต้น ตั้งค่า `OPENCLAW_LIVE_CODEX_HARNESS_IMAGE_PROBE=0` หรือ `OPENCLAW_LIVE_CODEX_HARNESS_MCP_PROBE=0` หรือ `OPENCLAW_LIVE_CODEX_HARNESS_GUARDIAN_PROBE=0` เมื่อคุณต้องการรัน debug ที่แคบลง +- Docker ใช้การตั้งค่า runtime Codex แบบชัดเจนเดียวกัน ดังนั้น alias เก่าหรือการ fallback ไปยัง PI จึงไม่สามารถซ่อน regression ของ harness Codex ได้ ### สูตร live ที่แนะนำ -allowlists ที่แคบและชัดเจนเร็วที่สุดและมีความ flaky น้อยที่สุด: +allowlist ที่แคบและชัดเจนเร็วที่สุดและ flaky น้อยที่สุด: -- โมเดลเดียว โดยตรง (ไม่มี gateway): +- โมเดลเดียว, โดยตรง (ไม่มี gateway): - `OPENCLAW_LIVE_MODELS="openai/gpt-5.5" pnpm test:live src/agents/models.profiles.live.test.ts` -- โมเดลเดียว gateway smoke: +- โมเดลเดียว, gateway smoke: - `OPENCLAW_LIVE_GATEWAY_MODELS="openai/gpt-5.5" pnpm test:live src/gateway/gateway-models.profiles.live.test.ts` -- การเรียก tool ข้ามหลาย providers: +- การเรียก tool ข้ามหลาย provider: - `OPENCLAW_LIVE_GATEWAY_MODELS="openai/gpt-5.5,openai-codex/gpt-5.5,anthropic/claude-opus-4-6,google/gemini-3-flash-preview,deepseek/deepseek-v4-flash,zai/glm-5.1,minimax/MiniMax-M2.7" pnpm test:live src/gateway/gateway-models.profiles.live.test.ts` -- เน้น Google (Gemini API key + Antigravity): +- โฟกัส Google (Gemini API key + Antigravity): - Gemini (API key): `OPENCLAW_LIVE_GATEWAY_MODELS="google/gemini-3-flash-preview" pnpm test:live src/gateway/gateway-models.profiles.live.test.ts` - Antigravity (OAuth): `OPENCLAW_LIVE_GATEWAY_MODELS="google-antigravity/claude-opus-4-6-thinking,google-antigravity/gemini-3-pro-high" pnpm test:live src/gateway/gateway-models.profiles.live.test.ts` - Google adaptive thinking smoke: - - หาก keys ในเครื่องอยู่ใน shell profile: `source ~/.profile` + - หากคีย์ในเครื่องอยู่ใน shell profile: `source ~/.profile` - ค่าเริ่มต้น dynamic ของ Gemini 3: `pnpm openclaw qa manual --provider-mode live-frontier --model google/gemini-3.1-pro-preview --alt-model google/gemini-3.1-pro-preview --message '/think adaptive Reply exactly: GEMINI_ADAPTIVE_OK' --timeout-ms 180000` - - budget แบบ dynamic ของ Gemini 2.5: `pnpm openclaw qa manual --provider-mode live-frontier --model google/gemini-2.5-flash --alt-model google/gemini-2.5-flash --message '/think adaptive Reply exactly: GEMINI25_ADAPTIVE_OK' --timeout-ms 180000` + - budget dynamic ของ Gemini 2.5: `pnpm openclaw qa manual --provider-mode live-frontier --model google/gemini-2.5-flash --alt-model google/gemini-2.5-flash --message '/think adaptive Reply exactly: GEMINI25_ADAPTIVE_OK' --timeout-ms 180000` หมายเหตุ: - `google/...` ใช้ Gemini API (API key) -- `google-antigravity/...` ใช้ bridge ของ Antigravity OAuth (endpoint ของ agent แบบ Cloud Code Assist) -- `google-gemini-cli/...` ใช้ Gemini CLI ในเครื่องของคุณ (มี auth แยกต่างหากและรายละเอียดเครื่องมือเฉพาะตัว) +- `google-antigravity/...` ใช้ bridge Antigravity OAuth (endpoint เอเจนต์แบบ Cloud Code Assist) +- `google-gemini-cli/...` ใช้ Gemini CLI ในเครื่องของคุณ (มี auth และข้อเฉพาะของ tooling แยกต่างหาก) - Gemini API เทียบกับ Gemini CLI: - - API: OpenClaw เรียก Gemini API ที่ Google โฮสต์ผ่าน HTTP (API key / profile auth); นี่คือสิ่งที่ผู้ใช้ส่วนใหญ่หมายถึงเมื่อพูดถึง “Gemini” - - CLI: OpenClaw shell out ไปยังไบนารี `gemini` ในเครื่อง; มี auth ของตัวเองและอาจทำงานต่างกัน (การรองรับ streaming/tool/version skew) + - API: OpenClaw เรียก Gemini API ที่ Google โฮสต์ผ่าน HTTP (API key / profile auth); นี่คือสิ่งที่ผู้ใช้ส่วนใหญ่หมายถึงเมื่อพูดว่า “Gemini” + - CLI: OpenClaw shell out ไปยังไบนารี `gemini` ในเครื่อง; มี auth ของตัวเองและอาจมีพฤติกรรมต่างกัน (streaming/การรองรับ tool/version skew) ## Live: เมทริกซ์โมเดล (สิ่งที่เราครอบคลุม) -ไม่มี “รายการโมเดล CI” แบบตายตัว (live เป็น opt-in) แต่โมเดลเหล่านี้คือโมเดลที่ **แนะนำ** ให้ครอบคลุมเป็นประจำบนเครื่อง dev ที่มี keys +ไม่มี “รายการโมเดล CI” แบบตายตัว (live เป็นแบบ opt-in) แต่นี่คือโมเดล **ที่แนะนำ** ให้ครอบคลุมเป็นประจำบนเครื่องพัฒนาที่มีคีย์ -### ชุด smoke สมัยใหม่ (การเรียก tool + image) +### ชุด smoke สมัยใหม่ (การเรียก tool + รูปภาพ) -นี่คือการรัน “common models” ที่เราคาดว่าจะรักษาให้ทำงานต่อไป: +นี่คือการรัน “โมเดลทั่วไป” ที่เราคาดว่าจะรักษาให้ทำงานต่อไปได้: - OpenAI (ไม่ใช่ Codex): `openai/gpt-5.5` - OpenAI Codex OAuth: `openai-codex/gpt-5.5` - Anthropic: `anthropic/claude-opus-4-6` (หรือ `anthropic/claude-sonnet-4-6`) -- Google (Gemini API): `google/gemini-3.1-pro-preview` และ `google/gemini-3-flash-preview` (หลีกเลี่ยงโมเดล Gemini 2.x รุ่นเก่า) +- Google (Gemini API): `google/gemini-3.1-pro-preview` และ `google/gemini-3-flash-preview` (หลีกเลี่ยงโมเดล Gemini 2.x ที่เก่ากว่า) - Google (Antigravity): `google-antigravity/claude-opus-4-6-thinking` และ `google-antigravity/gemini-3-flash` - DeepSeek: `deepseek/deepseek-v4-flash` และ `deepseek/deepseek-v4-pro` - Z.AI (GLM): `zai/glm-5.1` - MiniMax: `minimax/MiniMax-M2.7` -รัน gateway smoke พร้อม tools + image: +รัน gateway smoke พร้อม tool + รูปภาพ: `OPENCLAW_LIVE_GATEWAY_MODELS="openai/gpt-5.5,openai-codex/gpt-5.5,anthropic/claude-opus-4-6,google/gemini-3.1-pro-preview,google/gemini-3-flash-preview,google-antigravity/claude-opus-4-6-thinking,google-antigravity/gemini-3-flash,deepseek/deepseek-v4-flash,zai/glm-5.1,minimax/MiniMax-M2.7" pnpm test:live src/gateway/gateway-models.profiles.live.test.ts` ### Baseline: การเรียก tool (Read + Exec แบบเลือกได้) @@ -399,63 +396,63 @@ allowlists ที่แคบและชัดเจนเร็วที่ส ความครอบคลุมเพิ่มเติมแบบเลือกได้ (มีไว้ก็ดี): - xAI: `xai/grok-4.3` (หรือรุ่นล่าสุดที่มี) -- Mistral: `mistral/`… (เลือกโมเดลที่รองรับ “tools” หนึ่งตัวที่คุณเปิดใช้ไว้) +- Mistral: `mistral/`… (เลือกโมเดลที่รองรับ “tools” หนึ่งรายการที่คุณเปิดใช้ไว้) - Cerebras: `cerebras/`… (หากคุณมีสิทธิ์เข้าถึง) - LM Studio: `lmstudio/`… (ในเครื่อง; การเรียก tool ขึ้นกับโหมด API) -### Vision: การส่ง image (attachment → multimodal message) +### Vision: การส่งรูปภาพ (attachment → ข้อความ multimodal) -รวมโมเดลที่รองรับ image อย่างน้อยหนึ่งตัวไว้ใน `OPENCLAW_LIVE_GATEWAY_MODELS` (ตัวแปรที่รองรับ vision ของ Claude/Gemini/OpenAI เป็นต้น) เพื่อทดสอบ image probe +รวมโมเดลที่รองรับรูปภาพอย่างน้อยหนึ่งรายการใน `OPENCLAW_LIVE_GATEWAY_MODELS` (เช่น ตัวแปร Claude/Gemini/OpenAI ที่รองรับ vision) เพื่อทดสอบ image probe -### Aggregators / gateways ทางเลือก +### Aggregators / gateway ทางเลือก -หากคุณเปิดใช้ keys ไว้ เรายังรองรับการทดสอบผ่าน: +หากคุณเปิดใช้คีย์ไว้ เรายังรองรับการทดสอบผ่าน: -- OpenRouter: `openrouter/...` (หลายร้อยโมเดล; ใช้ `openclaw models scan` เพื่อค้นหาตัวเลือกที่รองรับ tool+image) +- OpenRouter: `openrouter/...` (โมเดลหลายร้อยรายการ; ใช้ `openclaw models scan` เพื่อค้นหาผู้สมัครที่รองรับ tool+image) - OpenCode: `opencode/...` สำหรับ Zen และ `opencode-go/...` สำหรับ Go (auth ผ่าน `OPENCODE_API_KEY` / `OPENCODE_ZEN_API_KEY`) -providers เพิ่มเติมที่คุณสามารถรวมไว้ในเมทริกซ์ live (หากคุณมี creds/config): +provider เพิ่มเติมที่คุณสามารถรวมในเมทริกซ์ live (หากคุณมี creds/config): - ในตัว: `openai`, `openai-codex`, `anthropic`, `google`, `google-vertex`, `google-antigravity`, `google-gemini-cli`, `zai`, `openrouter`, `opencode`, `opencode-go`, `xai`, `groq`, `cerebras`, `mistral`, `github-copilot` -- ผ่าน `models.providers` (endpoints แบบกำหนดเอง): `minimax` (cloud/API) รวมถึง proxy ที่เข้ากันได้กับ OpenAI/Anthropic ใด ๆ (LM Studio, vLLM, LiteLLM เป็นต้น) +- ผ่าน `models.providers` (endpoint แบบกำหนดเอง): `minimax` (cloud/API) รวมถึง proxy ที่เข้ากันได้กับ OpenAI/Anthropic ใด ๆ (LM Studio, vLLM, LiteLLM ฯลฯ) -อย่า hardcode "all models" ใน docs รายการที่ authoritative คือสิ่งที่ `discoverModels(...)` คืนค่าบนเครื่องของคุณ บวกกับ keys ที่มีอยู่ +อย่า hardcode "all models" ในเอกสาร รายการที่ authoritative คือสิ่งที่ `discoverModels(...)` คืนค่าบนเครื่องของคุณบวกกับคีย์ที่มีอยู่ ## ข้อมูลประจำตัว (ห้าม commit) -การทดสอบ live ค้นหาข้อมูลประจำตัวในวิธีเดียวกับที่ CLI ใช้ ผลในทางปฏิบัติ: +การทดสอบ live ค้นพบข้อมูลประจำตัวในแบบเดียวกับที่ CLI ทำ ผลกระทบเชิงปฏิบัติคือ: -- หาก CLI ใช้งานได้ การทดสอบแบบสดควรพบคีย์เดียวกัน -- หากการทดสอบแบบสดแจ้งว่า “ไม่มีข้อมูลรับรอง” ให้ดีบักด้วยวิธีเดียวกับที่คุณใช้ดีบัก `openclaw models list` / การเลือกโมเดล +- หาก CLI ใช้งานได้ การทดสอบแบบ live ควรพบคีย์เดียวกัน +- หากการทดสอบแบบ live แจ้งว่า “ไม่มี creds” ให้ดีบักแบบเดียวกับที่คุณดีบัก `openclaw models list` / การเลือกโมเดล -- โปรไฟล์การยืนยันตัวตนต่อเอเจนต์: `~/.openclaw/agents//agent/auth-profiles.json` (นี่คือความหมายของ “คีย์โปรไฟล์” ในการทดสอบแบบสด) +- โปรไฟล์ auth ราย agent: `~/.openclaw/agents//agent/auth-profiles.json` (นี่คือความหมายของ “profile keys” ในการทดสอบแบบ live) - การกำหนดค่า: `~/.openclaw/openclaw.json` (หรือ `OPENCLAW_CONFIG_PATH`) -- ไดเรกทอรีสถานะเดิม: `~/.openclaw/credentials/` (ถูกคัดลอกเข้าไปในโฮมทดสอบแบบสดที่จัดเตรียมไว้เมื่อมีอยู่ แต่ไม่ใช่ที่เก็บคีย์โปรไฟล์หลัก) -- การรันแบบสดภายในเครื่องจะคัดลอกการกำหนดค่าที่ใช้งานอยู่, ไฟล์ `auth-profiles.json` ต่อเอเจนต์, `credentials/` เดิม และไดเรกทอรีการยืนยันตัวตน CLI ภายนอกที่รองรับ เข้าไปในโฮมทดสอบชั่วคราวโดยค่าเริ่มต้น; โฮมสดที่จัดเตรียมไว้จะข้าม `workspace/` และ `sandboxes/` และการแทนที่พาธ `agents.*.workspace` / `agentDir` จะถูกตัดออก เพื่อให้โพรบไม่แตะ workspace จริงบนโฮสต์ของคุณ +- ไดเรกทอรีสถานะเดิม: `~/.openclaw/credentials/` (ถูกคัดลอกเข้าไปใน live home ที่จัดเตรียมไว้เมื่อมีอยู่ แต่ไม่ใช่ที่เก็บ profile-key หลัก) +- การรันแบบ live ในเครื่องจะคัดลอกการกำหนดค่าที่ใช้งานอยู่, ไฟล์ `auth-profiles.json` ราย agent, `credentials/` เดิม, และไดเรกทอรี auth ของ CLI ภายนอกที่รองรับไปยัง test home ชั่วคราวโดยค่าเริ่มต้น; live home ที่จัดเตรียมไว้จะข้าม `workspace/` และ `sandboxes/`, และจะลบการ override พาธ `agents.*.workspace` / `agentDir` เพื่อให้ probe ไม่แตะ workspace จริงบน host ของคุณ -หากคุณต้องการพึ่งพาคีย์ env (เช่น export ไว้ใน `~/.profile` ของคุณ) ให้รันการทดสอบภายในเครื่องหลังจาก `source ~/.profile` หรือใช้ Docker runners ด้านล่าง (สามารถ mount `~/.profile` เข้าไปในคอนเทนเนอร์ได้) +หากคุณต้องการพึ่งพา env keys (เช่น export ไว้ใน `~/.profile` ของคุณ) ให้รันการทดสอบในเครื่องหลังจาก `source ~/.profile` หรือใช้ Docker runners ด้านล่าง (ซึ่งสามารถ mount `~/.profile` เข้าไปใน container ได้) -## Deepgram live (การถอดเสียงจากเสียง) +## Deepgram live (การถอดเสียงจาก audio) - การทดสอบ: `extensions/deepgram/audio.live.test.ts` - เปิดใช้: `DEEPGRAM_API_KEY=... DEEPGRAM_LIVE_TEST=1 pnpm test:live extensions/deepgram/audio.live.test.ts` -## BytePlus coding plan live +## แผนการเขียนโค้ด BytePlus live - การทดสอบ: `extensions/byteplus/live.test.ts` - เปิดใช้: `BYTEPLUS_API_KEY=... BYTEPLUS_LIVE_TEST=1 pnpm test:live extensions/byteplus/live.test.ts` -- การแทนที่โมเดลแบบไม่บังคับ: `BYTEPLUS_CODING_MODEL=ark-code-latest` +- การ override โมเดลแบบไม่บังคับ: `BYTEPLUS_CODING_MODEL=ark-code-latest` -## ComfyUI workflow media live +## สื่อ workflow ComfyUI live - การทดสอบ: `extensions/comfy/comfy.live.test.ts` - เปิดใช้: `OPENCLAW_LIVE_TEST=1 COMFY_LIVE_TEST=1 pnpm test:live -- extensions/comfy/comfy.live.test.ts` - ขอบเขต: - - ทดสอบพาธรูปภาพ วิดีโอ และ `music_generate` ของ comfy ที่รวมมา - - ข้ามแต่ละความสามารถ เว้นแต่จะกำหนดค่า `plugins.entries.comfy.config.` ไว้ - - มีประโยชน์หลังจากเปลี่ยนการส่ง workflow ของ comfy, การ polling, การดาวน์โหลด หรือการลงทะเบียน plugin + - ทดสอบพาธ comfy image, video และ `music_generate` ที่ bundled มา + - ข้ามแต่ละ capability เว้นแต่จะกำหนดค่า `plugins.entries.comfy.config.` ไว้ + - มีประโยชน์หลังจากเปลี่ยนการส่ง workflow ของ comfy, polling, downloads หรือการลงทะเบียน Plugin ## Image generation live @@ -463,14 +460,14 @@ providers เพิ่มเติมที่คุณสามารถรว - คำสั่ง: `pnpm test:live test/image-generation.runtime.live.test.ts` - Harness: `pnpm test:live:media image` - ขอบเขต: - - แจกแจง plugin ผู้ให้บริการสร้างรูปภาพที่ลงทะเบียนไว้ทุกตัว - - โหลด env vars ของผู้ให้บริการที่ขาดจาก login shell ของคุณ (`~/.profile`) ก่อนโพรบ - - ใช้คีย์ API แบบสด/env ก่อนโปรไฟล์การยืนยันตัวตนที่จัดเก็บไว้โดยค่าเริ่มต้น เพื่อไม่ให้คีย์ทดสอบเก่าใน `auth-profiles.json` บดบังข้อมูลรับรองจริงจาก shell - - ข้ามผู้ให้บริการที่ไม่มี auth/profile/model ที่ใช้งานได้ - - รันผู้ให้บริการแต่ละรายที่กำหนดค่าไว้ผ่าน runtime การสร้างรูปภาพร่วม: + - แจกแจงทุก Plugin ผู้ให้บริการ image-generation ที่ลงทะเบียนไว้ + - โหลด provider env vars ที่ขาดหายจาก login shell ของคุณ (`~/.profile`) ก่อน probe + - ใช้ API keys จาก live/env ก่อน auth profiles ที่จัดเก็บไว้โดยค่าเริ่มต้น ดังนั้น test keys ที่เก่าใน `auth-profiles.json` จะไม่บดบัง credentials จริงจาก shell + - ข้าม providers ที่ไม่มี auth/profile/model ที่ใช้งานได้ + - รัน provider ที่กำหนดค่าไว้แต่ละตัวผ่าน runtime image-generation ที่ใช้ร่วมกัน: - `:generate` - - `:edit` เมื่อผู้ให้บริการประกาศว่ารองรับการแก้ไข -- ผู้ให้บริการที่รวมมาในปัจจุบันซึ่งครอบคลุม: + - `:edit` เมื่อ provider ประกาศว่ารองรับ edit +- Providers ที่ bundled อยู่ในปัจจุบันซึ่งครอบคลุม: - `deepinfra` - `fal` - `google` @@ -484,10 +481,10 @@ providers เพิ่มเติมที่คุณสามารถรว - `OPENCLAW_LIVE_IMAGE_GENERATION_PROVIDERS="deepinfra"` - `OPENCLAW_LIVE_IMAGE_GENERATION_MODELS="openai/gpt-image-2,google/gemini-3.1-flash-image-preview,openrouter/google/gemini-3.1-flash-image-preview,xai/grok-imagine-image"` - `OPENCLAW_LIVE_IMAGE_GENERATION_CASES="google:flash-generate,google:pro-edit,openrouter:generate,xai:default-generate,xai:default-edit"` -- พฤติกรรมการยืนยันตัวตนแบบไม่บังคับ: - - `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับการยืนยันตัวตนจากที่เก็บโปรไฟล์และละเว้นการแทนที่แบบ env-only +- พฤติกรรม auth แบบไม่บังคับ: + - `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับใช้ auth จาก profile-store และละเว้นการ override แบบ env-only -สำหรับพาธ CLI ที่เผยแพร่ ให้เพิ่ม smoke `infer` หลังจากการทดสอบแบบสดของผู้ให้บริการ/runtime ผ่านแล้ว: +สำหรับพาธ CLI ที่จัดส่ง ให้เพิ่ม smoke `infer` หลังจากการทดสอบแบบ live ของ provider/runtime ผ่านแล้ว: ```bash OPENCLAW_LIVE_TEST=1 OPENCLAW_LIVE_INFER_CLI_TEST=1 pnpm test:live -- test/image-generation.infer-cli.live.test.ts @@ -499,7 +496,7 @@ openclaw infer image generate \ --json ``` -สิ่งนี้ครอบคลุมการแยกวิเคราะห์อาร์กิวเมนต์ CLI, การแก้ค่าการกำหนดค่า/เอเจนต์เริ่มต้น, การเปิดใช้งาน plugin ที่รวมมา, runtime การสร้างรูปภาพร่วม และคำขอผู้ให้บริการแบบสด คาดว่าการพึ่งพาของ Plugin จะพร้อมก่อนโหลด runtime +สิ่งนี้ครอบคลุมการ parse อาร์กิวเมนต์ของ CLI, การ resolve config/default-agent, การเปิดใช้งาน Plugin ที่ bundled, runtime image-generation ที่ใช้ร่วมกัน และคำขอ provider แบบ live คาดว่า dependencies ของ Plugin จะต้องมีอยู่ก่อนโหลด runtime ## Music generation live @@ -507,23 +504,23 @@ openclaw infer image generate \ - เปิดใช้: `OPENCLAW_LIVE_TEST=1 pnpm test:live -- extensions/music-generation-providers.live.test.ts` - Harness: `pnpm test:live:media music` - ขอบเขต: - - ทดสอบพาธผู้ให้บริการสร้างเพลงร่วมที่รวมมา + - ทดสอบพาธ provider music-generation แบบ bundled ที่ใช้ร่วมกัน - ปัจจุบันครอบคลุม Google และ MiniMax - - โหลด env vars ของผู้ให้บริการจาก login shell ของคุณ (`~/.profile`) ก่อนโพรบ - - ใช้คีย์ API แบบสด/env ก่อนโปรไฟล์การยืนยันตัวตนที่จัดเก็บไว้โดยค่าเริ่มต้น เพื่อไม่ให้คีย์ทดสอบเก่าใน `auth-profiles.json` บดบังข้อมูลรับรองจริงจาก shell - - ข้ามผู้ให้บริการที่ไม่มี auth/profile/model ที่ใช้งานได้ - - รันทั้งสองโหมด runtime ที่ประกาศไว้เมื่อพร้อมใช้งาน: - - `generate` ด้วยอินพุตที่มีเฉพาะ prompt - - `edit` เมื่อผู้ให้บริการประกาศ `capabilities.edit.enabled` - - ความครอบคลุมของ shared-lane ปัจจุบัน: + - โหลด provider env vars จาก login shell ของคุณ (`~/.profile`) ก่อน probe + - ใช้ API keys จาก live/env ก่อน auth profiles ที่จัดเก็บไว้โดยค่าเริ่มต้น ดังนั้น test keys ที่เก่าใน `auth-profiles.json` จะไม่บดบัง credentials จริงจาก shell + - ข้าม providers ที่ไม่มี auth/profile/model ที่ใช้งานได้ + - รัน runtime modes ที่ประกาศไว้ทั้งสองแบบเมื่อมี: + - `generate` ด้วย input ที่มีเฉพาะ prompt + - `edit` เมื่อ provider ประกาศ `capabilities.edit.enabled` + - ความครอบคลุม shared-lane ปัจจุบัน: - `google`: `generate`, `edit` - `minimax`: `generate` - - `comfy`: ไฟล์ Comfy live แยกต่างหาก ไม่ใช่ sweep ร่วมนี้ + - `comfy`: ไฟล์ Comfy live แยกต่างหาก ไม่ใช่ sweep ที่ใช้ร่วมกันนี้ - การจำกัดขอบเขตแบบไม่บังคับ: - `OPENCLAW_LIVE_MUSIC_GENERATION_PROVIDERS="google,minimax"` - `OPENCLAW_LIVE_MUSIC_GENERATION_MODELS="google/lyria-3-clip-preview,minimax/music-2.6"` -- พฤติกรรมการยืนยันตัวตนแบบไม่บังคับ: - - `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับการยืนยันตัวตนจากที่เก็บโปรไฟล์และละเว้นการแทนที่แบบ env-only +- พฤติกรรม auth แบบไม่บังคับ: + - `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับใช้ auth จาก profile-store และละเว้นการ override แบบ env-only ## Video generation live @@ -531,43 +528,43 @@ openclaw infer image generate \ - เปิดใช้: `OPENCLAW_LIVE_TEST=1 pnpm test:live -- extensions/video-generation-providers.live.test.ts` - Harness: `pnpm test:live:media video` - ขอบเขต: - - ทดสอบพาธผู้ให้บริการสร้างวิดีโอร่วมที่รวมมา - - ใช้ค่าเริ่มต้นเป็นพาธ smoke ที่ปลอดภัยสำหรับ release: ผู้ให้บริการที่ไม่ใช่ FAL, คำขอ text-to-video หนึ่งรายการต่อผู้ให้บริการ, prompt กุ้งล็อบสเตอร์ความยาวหนึ่งวินาที และเพดานการทำงานต่อผู้ให้บริการจาก `OPENCLAW_LIVE_VIDEO_GENERATION_TIMEOUT_MS` (`180000` โดยค่าเริ่มต้น) - - ข้าม FAL โดยค่าเริ่มต้น เพราะ latency ของคิวฝั่งผู้ให้บริการอาจกินเวลา release มากเกินไป; ส่ง `--video-providers fal` หรือ `OPENCLAW_LIVE_VIDEO_GENERATION_PROVIDERS="fal"` เพื่อรันอย่างชัดเจน - - โหลด env vars ของผู้ให้บริการจาก login shell ของคุณ (`~/.profile`) ก่อนโพรบ - - ใช้คีย์ API แบบสด/env ก่อนโปรไฟล์การยืนยันตัวตนที่จัดเก็บไว้โดยค่าเริ่มต้น เพื่อไม่ให้คีย์ทดสอบเก่าใน `auth-profiles.json` บดบังข้อมูลรับรองจริงจาก shell - - ข้ามผู้ให้บริการที่ไม่มี auth/profile/model ที่ใช้งานได้ + - ทดสอบพาธ provider video-generation แบบ bundled ที่ใช้ร่วมกัน + - ค่าเริ่มต้นคือพาธ smoke ที่ปลอดภัยสำหรับ release: providers ที่ไม่ใช่ FAL, คำขอ text-to-video หนึ่งรายการต่อ provider, prompt รูป lobster ความยาวหนึ่งวินาที และขีดจำกัด operation ราย provider จาก `OPENCLAW_LIVE_VIDEO_GENERATION_TIMEOUT_MS` (`180000` โดยค่าเริ่มต้น) + - ข้าม FAL โดยค่าเริ่มต้นเพราะ latency ของ queue ฝั่ง provider อาจครอบงำเวลา release; ส่ง `--video-providers fal` หรือ `OPENCLAW_LIVE_VIDEO_GENERATION_PROVIDERS="fal"` เพื่อรันอย่างชัดเจน + - โหลด provider env vars จาก login shell ของคุณ (`~/.profile`) ก่อน probe + - ใช้ API keys จาก live/env ก่อน auth profiles ที่จัดเก็บไว้โดยค่าเริ่มต้น ดังนั้น test keys ที่เก่าใน `auth-profiles.json` จะไม่บดบัง credentials จริงจาก shell + - ข้าม providers ที่ไม่มี auth/profile/model ที่ใช้งานได้ - รันเฉพาะ `generate` โดยค่าเริ่มต้น - - ตั้งค่า `OPENCLAW_LIVE_VIDEO_GENERATION_FULL_MODES=1` เพื่อรันโหมด transform ที่ประกาศไว้ด้วยเมื่อพร้อมใช้งาน: - - `imageToVideo` เมื่อผู้ให้บริการประกาศ `capabilities.imageToVideo.enabled` และผู้ให้บริการ/โมเดลที่เลือกยอมรับอินพุตรูปภาพภายในเครื่องที่มี buffer รองรับใน sweep ร่วม - - `videoToVideo` เมื่อผู้ให้บริการประกาศ `capabilities.videoToVideo.enabled` และผู้ให้บริการ/โมเดลที่เลือกยอมรับอินพุตวิดีโอภายในเครื่องที่มี buffer รองรับใน sweep ร่วม - - ผู้ให้บริการ `imageToVideo` ที่ประกาศแล้วแต่ถูกข้ามในปัจจุบันใน sweep ร่วม: - - `vydra` เพราะ `veo3` ที่รวมมาเป็น text-only และ `kling` ที่รวมมาต้องใช้ URL รูปภาพระยะไกล - - ความครอบคลุมเฉพาะผู้ให้บริการ Vydra: + - ตั้งค่า `OPENCLAW_LIVE_VIDEO_GENERATION_FULL_MODES=1` เพื่อรัน transform modes ที่ประกาศไว้ด้วยเมื่อมี: + - `imageToVideo` เมื่อ provider ประกาศ `capabilities.imageToVideo.enabled` และ provider/model ที่เลือกยอมรับ input รูปภาพในเครื่องแบบ buffer-backed ใน shared sweep + - `videoToVideo` เมื่อ provider ประกาศ `capabilities.videoToVideo.enabled` และ provider/model ที่เลือกยอมรับ input วิดีโอในเครื่องแบบ buffer-backed ใน shared sweep + - Providers `imageToVideo` ที่ประกาศไว้แต่ถูกข้ามในปัจจุบันใน shared sweep: + - `vydra` เพราะ `veo3` ที่ bundled เป็น text-only และ `kling` ที่ bundled ต้องใช้ URL รูปภาพระยะไกล + - ความครอบคลุมเฉพาะ provider ของ Vydra: - `OPENCLAW_LIVE_TEST=1 OPENCLAW_LIVE_VYDRA_VIDEO=1 pnpm test:live -- extensions/vydra/vydra.live.test.ts` - ไฟล์นั้นรัน text-to-video ของ `veo3` พร้อม lane ของ `kling` ที่ใช้ fixture URL รูปภาพระยะไกลโดยค่าเริ่มต้น - - ความครอบคลุม `videoToVideo` แบบสดในปัจจุบัน: + - ความครอบคลุม live ของ `videoToVideo` ปัจจุบัน: - `runway` เฉพาะเมื่อโมเดลที่เลือกคือ `runway/gen4_aleph` - - ผู้ให้บริการ `videoToVideo` ที่ประกาศแล้วแต่ถูกข้ามในปัจจุบันใน sweep ร่วม: - - `alibaba`, `qwen`, `xai` เพราะพาธเหล่านั้นในปัจจุบันต้องใช้ URL อ้างอิง `http(s)` / MP4 ระยะไกล - - `google` เพราะ lane Gemini/Veo ร่วมปัจจุบันใช้อินพุตภายในเครื่องที่มี buffer รองรับ และพาธนั้นไม่ถูกยอมรับใน sweep ร่วม - - `openai` เพราะ lane ร่วมปัจจุบันไม่มีการรับประกันการเข้าถึง video inpaint/remix เฉพาะ org + - Providers `videoToVideo` ที่ประกาศไว้แต่ถูกข้ามในปัจจุบันใน shared sweep: + - `alibaba`, `qwen`, `xai` เพราะพาธเหล่านั้นปัจจุบันต้องใช้ URL อ้างอิง `http(s)` / MP4 ระยะไกล + - `google` เพราะ lane Gemini/Veo ที่ใช้ร่วมกันในปัจจุบันใช้ input ในเครื่องแบบ buffer-backed และพาธนั้นไม่ถูกรับใน shared sweep + - `openai` เพราะ shared lane ปัจจุบันไม่มีการรับประกันสิทธิ์เข้าถึง video inpaint/remix เฉพาะ org - การจำกัดขอบเขตแบบไม่บังคับ: - `OPENCLAW_LIVE_VIDEO_GENERATION_PROVIDERS="deepinfra,google,openai,runway"` - `OPENCLAW_LIVE_VIDEO_GENERATION_MODELS="google/veo-3.1-fast-generate-preview,openai/sora-2,runway/gen4_aleph"` - - `OPENCLAW_LIVE_VIDEO_GENERATION_SKIP_PROVIDERS=""` เพื่อรวมผู้ให้บริการทุกตัวใน sweep เริ่มต้น รวมถึง FAL - - `OPENCLAW_LIVE_VIDEO_GENERATION_TIMEOUT_MS=60000` เพื่อลดเพดานการทำงานของผู้ให้บริการแต่ละรายสำหรับการรัน smoke แบบเร่งรัด -- พฤติกรรมการยืนยันตัวตนแบบไม่บังคับ: - - `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับการยืนยันตัวตนจากที่เก็บโปรไฟล์และละเว้นการแทนที่แบบ env-only + - `OPENCLAW_LIVE_VIDEO_GENERATION_SKIP_PROVIDERS=""` เพื่อรวมทุก provider ใน sweep ค่าเริ่มต้น รวมถึง FAL + - `OPENCLAW_LIVE_VIDEO_GENERATION_TIMEOUT_MS=60000` เพื่อลดขีดจำกัด operation ของแต่ละ provider สำหรับการรัน smoke แบบเร่งรัด +- พฤติกรรม auth แบบไม่บังคับ: + - `OPENCLAW_LIVE_REQUIRE_PROFILE_KEYS=1` เพื่อบังคับใช้ auth จาก profile-store และละเว้นการ override แบบ env-only ## Media live harness - คำสั่ง: `pnpm test:live:media` - วัตถุประสงค์: - - รันชุดทดสอบสดของรูปภาพ เพลง และวิดีโอร่วมผ่าน entrypoint แบบ repo-native เดียว - - โหลด env vars ของผู้ให้บริการที่ขาดจาก `~/.profile` โดยอัตโนมัติ - - จำกัดขอบเขตแต่ละชุดทดสอบให้เหลือเฉพาะผู้ให้บริการที่ปัจจุบันมี auth ที่ใช้งานได้โดยค่าเริ่มต้นโดยอัตโนมัติ - - ใช้ `scripts/test-live.mjs` ซ้ำ เพื่อให้พฤติกรรม Heartbeat และโหมดเงียบสอดคล้องกัน + - รันชุดทดสอบ live ของ image, music และ video ที่ใช้ร่วมกันผ่าน entrypoint แบบ repo-native เดียว + - โหลด provider env vars ที่ขาดหายจาก `~/.profile` อัตโนมัติ + - จำกัดแต่ละชุดโดยอัตโนมัติให้เหลือ providers ที่มี auth ใช้งานได้ในปัจจุบันโดยค่าเริ่มต้น + - ใช้ `scripts/test-live.mjs` ซ้ำ ดังนั้นพฤติกรรม Heartbeat และ quiet-mode จึงสอดคล้องกัน - ตัวอย่าง: - `pnpm test:live:media` - `pnpm test:live:media image video --providers openai,google,minimax` diff --git a/docs/th/plugins/hooks.md b/docs/th/plugins/hooks.md index 74b96da12..949b33c7c 100644 --- a/docs/th/plugins/hooks.md +++ b/docs/th/plugins/hooks.md @@ -6,25 +6,25 @@ read_when: summary: 'ฮุกของ Plugin: ดักจับเหตุการณ์วงจรชีวิตของเอเจนต์ เครื่องมือ ข้อความ เซสชัน และ Gateway' title: ฮุกของ Plugin x-i18n: - generated_at: "2026-05-03T21:36:02Z" + generated_at: "2026-05-04T18:24:05Z" model: gpt-5.5 provider: openai - source_hash: 2c4ed060f1b89917e1f2f46d2da9448cd562edbcd6ce03bc9b1a83da3ed9a591 + source_hash: 37c7273036463c87e478db5678822b676c89447caee65f2f3f47a45194d1e37b source_path: plugins/hooks.md workflow: 16 --- -ฮุกของ Plugin เป็นจุดขยายแบบ in-process สำหรับ Plugin ของ OpenClaw ใช้เมื่อ -Plugin ต้องตรวจสอบหรือเปลี่ยนแปลงการรันของเอเจนต์ การเรียกเครื่องมือ โฟลว์ข้อความ -วงจรชีวิตของเซสชัน การกำหนดเส้นทางเอเจนต์ย่อย การติดตั้ง หรือการเริ่มต้น Gateway +ฮุกของ Plugin เป็นจุดขยายในโปรเซสสำหรับ Plugin ของ OpenClaw ใช้ฮุกเหล่านี้ +เมื่อ Plugin ต้องตรวจสอบหรือเปลี่ยนการรันของเอเจนต์ การเรียกเครื่องมือ โฟลว์ข้อความ +วงจรชีวิตเซสชัน การกำหนดเส้นทาง subagent การติดตั้ง หรือการเริ่มต้น Gateway -ใช้ [ฮุกภายใน](/th/automation/hooks) แทนเมื่อคุณต้องการสคริปต์ `HOOK.md` ขนาดเล็ก -ที่ติดตั้งโดยโอเปอเรเตอร์ สำหรับคำสั่งและเหตุการณ์ของ Gateway เช่น +ให้ใช้ [ฮุกภายใน](/th/automation/hooks) แทน เมื่อคุณต้องการสคริปต์ `HOOK.md` +ขนาดเล็กที่ติดตั้งโดยผู้ปฏิบัติงานสำหรับเหตุการณ์คำสั่งและ Gateway เช่น `/new`, `/reset`, `/stop`, `agent:bootstrap` หรือ `gateway:startup` ## เริ่มต้นอย่างรวดเร็ว -ลงทะเบียนฮุกของ Plugin แบบมีชนิดด้วย `api.on(...)` จากจุดเข้าของ Plugin: +ลงทะเบียนฮุก Plugin แบบมีชนิดด้วย `api.on(...)` จาก entry ของ Plugin ของคุณ: ```typescript import { definePluginEntry } from "openclaw/plugin-sdk/plugin-entry"; @@ -56,18 +56,18 @@ export default definePluginEntry({ }); ``` -ตัวจัดการฮุกจะรันตามลำดับทีละตัวโดยเรียง `priority` จากมากไปน้อย ฮุกที่มี priority -เท่ากันจะคงลำดับการลงทะเบียนไว้ +ตัวจัดการฮุกจะรันตามลำดับทีละตัวโดยเรียง `priority` จากมากไปน้อย ฮุกที่มี priority เท่ากัน +จะคงลำดับการลงทะเบียนไว้ -`api.on(name, handler, opts?)` รับ: +`api.on(name, handler, opts?)` รับค่า: -- `priority` — ลำดับของตัวจัดการ (ค่าที่สูงกว่าจะรันก่อน) -- `timeoutMs` — งบเวลาต่อฮุกแบบไม่บังคับ เมื่อกำหนดไว้ ตัวรันฮุกจะยกเลิก - ตัวจัดการนั้นหลังงบเวลาหมดลงและทำต่อกับตัวถัดไป แทนที่จะปล่อยให้งานตั้งค่าหรือการเรียกคืนที่ช้า - ใช้ timeout ของโมเดลที่ผู้เรียกกำหนดไว้จนหมด ละไว้เพื่อใช้ timeout เริ่มต้นสำหรับการสังเกต/การตัดสินใจที่ - ตัวรันฮุกใช้โดยทั่วไป +- `priority` — การจัดลำดับตัวจัดการ (ค่าสูงกว่าจะรันก่อน) +- `timeoutMs` — งบเวลาต่อฮุกที่เป็นตัวเลือก เมื่อตั้งค่าไว้ ตัวรันฮุกจะยกเลิกตัวจัดการนั้น + หลังงบเวลาหมดลงและดำเนินการต่อกับตัวถัดไป แทนที่จะปล่อยให้งานตั้งค่าหรือเรียกคืนข้อมูลที่ช้า + ใช้เวลา timeout ของโมเดลที่ผู้เรียกกำหนดไว้ เว้นค่าไว้เพื่อใช้ timeout เริ่มต้นสำหรับการสังเกต/การตัดสินใจ + ที่ตัวรันฮุกใช้อย่างทั่วไป -โอเปอเรเตอร์ยังสามารถตั้งงบเวลาของฮุกได้โดยไม่ต้องแพตช์โค้ดของ Plugin: +ผู้ปฏิบัติงานยังสามารถตั้งงบเวลาของฮุกได้โดยไม่ต้องแพตช์โค้ด Plugin: ```json { @@ -87,70 +87,69 @@ export default definePluginEntry({ } ``` -`hooks.timeouts.` จะ override `hooks.timeoutMs` ซึ่ง override ค่า -`api.on(..., { timeoutMs })` ที่ผู้เขียน Plugin กำหนดไว้ แต่ละค่าที่กำหนดต้องเป็น -จำนวนเต็มบวกไม่เกิน 600000 มิลลิวินาที ควรใช้การ override รายฮุกสำหรับฮุกที่ทราบว่าช้า -เพื่อไม่ให้ Plugin หนึ่งได้งบเวลายาวขึ้นทุกที่ +`hooks.timeouts.` จะแทนที่ `hooks.timeoutMs` ซึ่งจะแทนที่ค่า +`api.on(..., { timeoutMs })` ที่ผู้เขียน Plugin ระบุ ค่าแต่ละรายการที่กำหนดต้องเป็น +จำนวนเต็มบวกไม่เกิน 600000 มิลลิวินาที ควรใช้การ override ต่อฮุกสำหรับฮุกที่ทราบว่าช้า +เพื่อไม่ให้ Plugin หนึ่งได้งบเวลาที่ยาวขึ้นในทุกที่ -แต่ละฮุกจะได้รับ `event.context.pluginConfig` ซึ่งเป็นคอนฟิกที่ resolve แล้วสำหรับ -Plugin ที่ลงทะเบียนตัวจัดการนั้น ใช้สำหรับการตัดสินใจของฮุกที่ต้องใช้ -ตัวเลือกปัจจุบันของ Plugin; OpenClaw ฉีดค่านี้ต่อหนึ่งตัวจัดการโดยไม่ mutate -อ็อบเจ็กต์เหตุการณ์ร่วมที่ Plugin อื่นเห็น +แต่ละฮุกจะได้รับ `event.context.pluginConfig` ซึ่งเป็น config ที่ resolve แล้วสำหรับ +Plugin ที่ลงทะเบียนตัวจัดการนั้น ใช้ค่านี้สำหรับการตัดสินใจของฮุกที่ต้องใช้ตัวเลือก Plugin +ปัจจุบัน OpenClaw จะ inject ค่านี้ต่อหนึ่งตัวจัดการโดยไม่ mutate ออบเจ็กต์เหตุการณ์ร่วม +ที่ Plugin อื่นเห็น ## แค็ตตาล็อกฮุก -ฮุกถูกจัดกลุ่มตามพื้นผิวที่ขยาย ชื่อที่เป็น **ตัวหนา** รับ -ผลลัพธ์การตัดสินใจได้ (บล็อก ยกเลิก override หรือขออนุมัติ); รายการอื่นทั้งหมด -ใช้สำหรับสังเกตเท่านั้น +ฮุกถูกจัดกลุ่มตามพื้นผิวที่ฮุกขยาย ชื่อที่เป็น **ตัวหนา** รับผลลัพธ์การตัดสินใจได้ +(บล็อก ยกเลิก override หรือต้องขออนุมัติ) ส่วนที่เหลือทั้งหมดเป็นแบบสังเกตเท่านั้น **เทิร์นของเอเจนต์** -- `before_model_resolve` — override ผู้ให้บริการหรือโมเดลก่อนโหลดข้อความเซสชัน -- `agent_turn_prepare` — ใช้การฉีดเทิร์นของ Plugin ที่เข้าคิวไว้และเพิ่มบริบทในเทิร์นเดียวกันก่อนฮุกพรอมป์ -- `before_prompt_build` — เพิ่มบริบทแบบไดนามิกหรือข้อความ system prompt ก่อนการเรียกโมเดล -- `before_agent_start` — เฟสรวมเพื่อความเข้ากันได้เท่านั้น; ควรใช้สองฮุกข้างต้น -- **`before_agent_reply`** — ลัดวงจรเทิร์นโมเดลด้วยคำตอบสังเคราะห์หรือความเงียบ -- **`before_agent_finalize`** — ตรวจสอบคำตอบสุดท้ายตามธรรมชาติและขอให้โมเดลรันเพิ่มอีกหนึ่งรอบ +- `before_model_resolve` — override provider หรือ model ก่อนโหลดข้อความเซสชัน +- `agent_turn_prepare` — ใช้การ inject เทิร์นของ Plugin ที่เข้าคิวไว้และเพิ่มบริบทในเทิร์นเดียวกันก่อนฮุก prompt +- `before_prompt_build` — เพิ่มบริบทแบบไดนามิกหรือข้อความ system-prompt ก่อนเรียกโมเดล +- `before_agent_start` — เฟสรวมเพื่อความเข้ากันได้เท่านั้น ควรใช้สองฮุกข้างต้น +- **`before_agent_reply`** — ตัดเทิร์นของโมเดลให้จบก่อนด้วย reply สังเคราะห์หรือความเงียบ +- **`before_agent_finalize`** — ตรวจสอบคำตอบสุดท้ายตามธรรมชาติและขอให้โมเดลรันอีกหนึ่งรอบ - `agent_end` — สังเกตข้อความสุดท้าย สถานะความสำเร็จ และระยะเวลาการรัน -- `heartbeat_prompt_contribution` — เพิ่มบริบทสำหรับ Heartbeat เท่านั้นสำหรับ Plugin ตรวจสอบพื้นหลังและวงจรชีวิต +- `heartbeat_prompt_contribution` — เพิ่มบริบทเฉพาะ Heartbeat สำหรับ Plugin ตรวจสอบเบื้องหลังและวงจรชีวิต -**การสังเกตการสนทนา** +**การสังเกตบทสนทนา** -- `model_call_started` / `model_call_ended` — สังเกตเมตาดาต้าของการเรียกผู้ให้บริการ/โมเดลที่ผ่านการทำให้ปลอดภัยแล้ว เวลา ผลลัพธ์ และแฮช request-id แบบมีขอบเขต โดยไม่มีเนื้อหาพรอมป์หรือคำตอบ -- `llm_input` — สังเกตอินพุตของผู้ให้บริการ (system prompt, prompt, ประวัติ) -- `llm_output` — สังเกตเอาต์พุตของผู้ให้บริการ +- `model_call_started` / `model_call_ended` — สังเกตเมตาดาต้าการเรียก provider/model ที่ sanitize แล้ว เวลา ผลลัพธ์ และแฮช request-id แบบจำกัด โดยไม่มีเนื้อหา prompt หรือ response +- `llm_input` — สังเกต input ของ provider (system prompt, prompt, history) +- `llm_output` — สังเกต output ของ provider **เครื่องมือ** -- **`before_tool_call`** — เขียน params ของเครื่องมือใหม่ บล็อกการดำเนินการ หรือขออนุมัติ -- `after_tool_call` — สังเกตผลลัพธ์ของเครื่องมือ ข้อผิดพลาด และระยะเวลา -- **`tool_result_persist`** — เขียนข้อความของ assistant ที่สร้างจากผลลัพธ์เครื่องมือใหม่ -- **`before_message_write`** — ตรวจสอบหรือบล็อกการเขียนข้อความที่กำลังดำเนินอยู่ (พบได้น้อย) +- **`before_tool_call`** — เขียน params ของเครื่องมือใหม่ บล็อกการทำงาน หรือขออนุมัติ +- `after_tool_call` — สังเกตผลลัพธ์เครื่องมือ ข้อผิดพลาด และระยะเวลา +- **`tool_result_persist`** — เขียนข้อความ assistant ที่สร้างจากผลลัพธ์เครื่องมือใหม่ +- **`before_message_write`** — ตรวจสอบหรือบล็อกการเขียนข้อความที่กำลังดำเนินอยู่ (พบไม่บ่อย) **ข้อความและการส่งมอบ** -- **`inbound_claim`** — claim ข้อความขาเข้าก่อนการกำหนดเส้นทางเอเจนต์ (คำตอบสังเคราะห์) +- **`inbound_claim`** — claim ข้อความขาเข้าก่อนการกำหนดเส้นทางเอเจนต์ (reply สังเคราะห์) - `message_received` — สังเกตเนื้อหาขาเข้า ผู้ส่ง เธรด และเมตาดาต้า - **`message_sending`** — เขียนเนื้อหาขาออกใหม่หรือยกเลิกการส่งมอบ - `message_sent` — สังเกตความสำเร็จหรือความล้มเหลวของการส่งมอบขาออก -- **`before_dispatch`** — ตรวจสอบหรือเขียน dispatch ขาออกใหม่ก่อนส่งต่อให้ช่องทาง -- **`reply_dispatch`** — เข้าร่วมใน pipeline การ dispatch คำตอบสุดท้าย +- **`before_dispatch`** — ตรวจสอบหรือเขียน dispatch ขาออกใหม่ก่อนส่งต่อให้ channel +- **`reply_dispatch`** — เข้าร่วม pipeline การ dispatch reply ขั้นสุดท้าย **เซสชันและ Compaction** -- `session_start` / `session_end` — ติดตามขอบเขตวงจรชีวิตของเซสชัน -- `before_compaction` / `after_compaction` — สังเกตหรือใส่หมายเหตุให้รอบ Compaction +- `session_start` / `session_end` — ติดตามขอบเขตวงจรชีวิตเซสชัน +- `before_compaction` / `after_compaction` — สังเกตหรือใส่ annotation ให้รอบ Compaction - `before_reset` — สังเกตเหตุการณ์รีเซ็ตเซสชัน (`/reset`, การรีเซ็ตผ่านโปรแกรม) -**เอเจนต์ย่อย** +**Subagents** -- `subagent_spawning` / `subagent_delivery_target` / `subagent_spawned` / `subagent_ended` — ประสานการกำหนดเส้นทางเอเจนต์ย่อยและการส่งมอบเมื่อเสร็จสิ้น +- `subagent_spawning` / `subagent_delivery_target` / `subagent_spawned` / `subagent_ended` — ประสานการกำหนดเส้นทาง subagent และการส่งมอบเมื่อเสร็จสิ้น **วงจรชีวิต** - `gateway_start` / `gateway_stop` — เริ่มหรือหยุดบริการที่ Plugin เป็นเจ้าของพร้อมกับ Gateway -- `cron_changed` — สังเกตการเปลี่ยนแปลงวงจรชีวิต Cron ที่ Gateway เป็นเจ้าของ (เพิ่ม อัปเดต ลบ เริ่มต้น เสร็จสิ้น กำหนดเวลา) -- **`before_install`** — ตรวจสอบการสแกนการติดตั้ง Skills หรือ Plugin และบล็อกได้ตามต้องการ +- `cron_changed` — สังเกตการเปลี่ยนแปลงวงจรชีวิต Cron ที่ Gateway เป็นเจ้าของ (เพิ่ม อัปเดต ลบ เริ่ม เสร็จสิ้น ตั้งเวลา) +- **`before_install`** — ตรวจสอบการสแกนติดตั้ง Skills หรือ Plugin และเลือกบล็อกได้ ## นโยบายการเรียกเครื่องมือ @@ -158,12 +157,12 @@ Plugin ที่ลงทะเบียนตัวจัดการนั้ - `event.toolName` - `event.params` -- `event.runId` แบบไม่บังคับ -- `event.toolCallId` แบบไม่บังคับ +- `event.runId` ที่เป็นตัวเลือก +- `event.toolCallId` ที่เป็นตัวเลือก - ฟิลด์บริบท เช่น `ctx.agentId`, `ctx.sessionKey`, `ctx.sessionId`, - `ctx.runId`, `ctx.jobId` (ตั้งค่าในการรันที่ขับเคลื่อนด้วย Cron) และ `ctx.trace` สำหรับการวินิจฉัย + `ctx.runId`, `ctx.jobId` (ตั้งค่าในการรันที่ขับเคลื่อนด้วย Cron) และ `ctx.trace` สำหรับวินิจฉัย -สามารถส่งคืน: +สามารถ return: ```typescript type BeforeToolCallResult = { @@ -186,88 +185,100 @@ type BeforeToolCallResult = { กฎ: -- `block: true` เป็นสถานะสิ้นสุดและข้ามตัวจัดการ priority ต่ำกว่า -- `block: false` ถือว่าไม่มีการตัดสินใจ -- `params` เขียนพารามิเตอร์ของเครื่องมือใหม่สำหรับการดำเนินการ -- `requireApproval` หยุดการรันเอเจนต์ชั่วคราวและขอผู้ใช้ผ่านการอนุมัติของ Plugin +- `block: true` เป็นสถานะสุดท้ายและข้ามตัวจัดการที่มี priority ต่ำกว่า +- `block: false` จะถือว่าไม่มีการตัดสินใจ +- `params` เขียนพารามิเตอร์เครื่องมือใหม่สำหรับการดำเนินการ +- `requireApproval` หยุดการรันเอเจนต์ชั่วคราวและถามผู้ใช้ผ่านการอนุมัติของ Plugin คำสั่ง `/approve` สามารถอนุมัติได้ทั้ง exec และการอนุมัติของ Plugin -- `block: true` จาก priority ต่ำกว่ายังสามารถบล็อกได้หลังฮุก priority สูงกว่า - ขออนุมัติแล้ว -- `onResolution` ได้รับการตัดสินใจอนุมัติที่ resolve แล้ว — `allow-once`, +- `block: true` ที่มี priority ต่ำกว่ายังสามารถบล็อกได้หลังจากฮุกที่มี priority สูงกว่าขออนุมัติแล้ว +- `onResolution` ได้รับการตัดสินใจอนุมัติที่ resolve แล้ว ได้แก่ `allow-once`, `allow-always`, `deny`, `timeout` หรือ `cancelled` -Plugin ที่มาพร้อมระบบซึ่งต้องใช้นโยบายระดับโฮสต์สามารถลงทะเบียนนโยบายเครื่องมือที่เชื่อถือได้ +Plugin ที่ bundled ซึ่งต้องใช้นโยบายระดับโฮสต์สามารถลงทะเบียนนโยบายเครื่องมือที่เชื่อถือได้ ด้วย `api.registerTrustedToolPolicy(...)` นโยบายเหล่านี้รันก่อนฮุก -`before_tool_call` ทั่วไปและก่อนการตัดสินใจของ Plugin ภายนอก ใช้เฉพาะ -สำหรับด่านที่โฮสต์เชื่อถือ เช่น นโยบาย workspace การบังคับใช้งบประมาณ หรือ -ความปลอดภัยของ workflow ที่สงวนไว้ Plugin ภายนอกควรใช้ฮุก `before_tool_call` -ตามปกติ +`before_tool_call` ปกติและก่อนการตัดสินใจของ Plugin ภายนอก ใช้เฉพาะกับ gate ที่โฮสต์เชื่อถือ +เช่น นโยบาย workspace การบังคับใช้งบประมาณ หรือความปลอดภัยของ workflow ที่สงวนไว้ +Plugin ภายนอกควรใช้ฮุก `before_tool_call` ปกติ -### การคงอยู่ของผลลัพธ์เครื่องมือ +### การ persist ผลลัพธ์เครื่องมือ -ผลลัพธ์เครื่องมือสามารถมี `details` แบบมีโครงสร้างสำหรับการเรนเดอร์ UI การวินิจฉัย -การกำหนดเส้นทางสื่อ หรือเมตาดาต้าที่ Plugin เป็นเจ้าของ ให้ถือว่า `details` เป็นเมตาดาต้ารันไทม์ -ไม่ใช่เนื้อหาพรอมป์: +ผลลัพธ์เครื่องมือสามารถมี `details` แบบมีโครงสร้างสำหรับการแสดงผลใน UI การวินิจฉัย +การกำหนดเส้นทางสื่อ หรือเมตาดาต้าที่ Plugin เป็นเจ้าของ ให้ถือว่า `details` เป็นเมตาดาต้า runtime +ไม่ใช่เนื้อหา prompt: -- OpenClaw ตัด `toolResult.details` ออกก่อน replay ไปยังผู้ให้บริการและอินพุตของ Compaction +- OpenClaw จะลบ `toolResult.details` ก่อน replay ไปยัง provider และก่อน input ของ Compaction เพื่อไม่ให้เมตาดาต้ากลายเป็นบริบทของโมเดล -- รายการเซสชันที่ persist จะเก็บเฉพาะ `details` แบบมีขอบเขต details ที่ใหญ่เกินไปจะถูก - แทนที่ด้วยสรุปแบบกะทัดรัดและ `persistedDetailsTruncated: true` +- รายการเซสชันที่ persist แล้วจะเก็บเฉพาะ `details` แบบจำกัด ข้อมูล details ที่ใหญ่เกินไปจะถูก + แทนที่ด้วยสรุปขนาดกะทัดรัดและ `persistedDetailsTruncated: true` - `tool_result_persist` และ `before_message_write` รันก่อน cap การ persist ขั้นสุดท้าย - ฮุกยังควรรักษา `details` ที่ส่งคืนให้มีขนาดเล็กและหลีกเลี่ยง - การวางข้อความที่เกี่ยวข้องกับพรอมป์ไว้เฉพาะใน `details`; ให้วางเอาต์พุตเครื่องมือที่โมเดลเห็นได้ - ใน `content` + ฮุกยังควรรักษา `details` ที่ return ให้มีขนาดเล็กและหลีกเลี่ยงการวางข้อความที่เกี่ยวข้องกับ prompt + ไว้เฉพาะใน `details`; ให้วาง output ของเครื่องมือที่โมเดลมองเห็นได้ไว้ใน `content` -## ฮุกพรอมป์และโมเดล +## ฮุก prompt และโมเดล ใช้ฮุกเฉพาะเฟสสำหรับ Plugin ใหม่: -- `before_model_resolve`: ได้รับเฉพาะพรอมป์ปัจจุบันและเมตาดาต้า - ไฟล์แนบ ส่งคืน `providerOverride` หรือ `modelOverride` -- `agent_turn_prepare`: ได้รับพรอมป์ปัจจุบัน ข้อความเซสชันที่เตรียมไว้ - และการฉีดที่เข้าคิวแบบใช้ครั้งเดียวที่ drain สำหรับเซสชันนี้ ส่งคืน +- `before_model_resolve`: รับเฉพาะ prompt ปัจจุบันและเมตาดาต้า attachment + return `providerOverride` หรือ `modelOverride` +- `agent_turn_prepare`: รับ prompt ปัจจุบัน ข้อความเซสชันที่เตรียมไว้ + และการ inject ที่เข้าคิวแบบใช้ครั้งเดียวพอดีซึ่งถูก drain สำหรับเซสชันนี้ return `prependContext` หรือ `appendContext` -- `before_prompt_build`: ได้รับพรอมป์ปัจจุบันและข้อความเซสชัน - ส่งคืน `prependContext`, `appendContext`, `systemPrompt`, +- `before_prompt_build`: รับ prompt ปัจจุบันและข้อความเซสชัน + return `prependContext`, `appendContext`, `systemPrompt`, `prependSystemContext` หรือ `appendSystemContext` -- `heartbeat_prompt_contribution`: รันเฉพาะสำหรับเทิร์น Heartbeat และส่งคืน - `prependContext` หรือ `appendContext` มีไว้สำหรับตัวตรวจสอบพื้นหลัง +- `heartbeat_prompt_contribution`: รันเฉพาะเทิร์น Heartbeat และ return + `prependContext` หรือ `appendContext` มีไว้สำหรับตัวตรวจสอบเบื้องหลัง ที่ต้องสรุปสถานะปัจจุบันโดยไม่เปลี่ยนเทิร์นที่ผู้ใช้เริ่มต้น -`before_agent_start` ยังคงอยู่เพื่อความเข้ากันได้ ควรใช้ฮุกที่ชัดเจนข้างต้น -เพื่อให้ Plugin ของคุณไม่ต้องพึ่งพาเฟสรวมแบบเดิม +`before_agent_start` ยังคงอยู่เพื่อความเข้ากันได้ ควรใช้ฮุกแบบชัดเจนข้างต้น +เพื่อให้ Plugin ของคุณไม่ต้องพึ่งพาเฟสรวมแบบ legacy -`before_agent_start` และ `agent_end` รวม `event.runId` เมื่อ OpenClaw สามารถ -ระบุการรันที่ใช้งานอยู่ได้ ค่าเดียวกันยังพร้อมใช้งานที่ `ctx.runId` +`before_agent_start` และ `agent_end` จะมี `event.runId` เมื่อ OpenClaw สามารถ +ระบุการรันที่ active ได้ ค่าเดียวกันยังมีใน `ctx.runId` ด้วย การรันที่ขับเคลื่อนด้วย Cron ยังเปิดเผย `ctx.jobId` (id ของงาน Cron ต้นทาง) เพื่อให้ -ฮุกของ Plugin สามารถกำหนดขอบเขตเมตริก ผลข้างเคียง หรือสถานะไปยังงานที่กำหนดเวลาไว้เฉพาะได้ +ฮุก Plugin สามารถจำกัด scope ของ metrics, side effects หรือ state ไปยังงานที่ตั้งเวลาไว้เฉพาะได้ -สำหรับการรันที่มาจากช่องทาง `ctx.messageProvider` คือพื้นผิวผู้ให้บริการ เช่น -`discord` หรือ `telegram` ขณะที่ `ctx.channelId` คือ identifier เป้าหมายของการสนทนา -เมื่อ OpenClaw สามารถอนุมานได้จากคีย์เซสชันหรือเมตาดาต้าการส่งมอบ +สำหรับการรันที่มีต้นทางจาก channel, `ctx.messageProvider` คือพื้นผิว provider เช่น +`discord` หรือ `telegram` ขณะที่ `ctx.channelId` คือ identifier เป้าหมายของบทสนทนา +เมื่อ OpenClaw สามารถ derive ได้จาก session key หรือเมตาดาต้าการส่งมอบ -`agent_end` เป็นฮุกสังเกตการณ์และรันแบบ fire-and-forget หลังจบเทิร์น -ตัวรันฮุกใช้ timeout 30 วินาทีเพื่อให้ Plugin หรือ endpoint embedding -ที่ค้างอยู่ไม่ทำให้ promise ของฮุกค้างตลอดไป timeout จะถูกบันทึก log และ -OpenClaw ทำต่อ; มันไม่ยกเลิกงานเครือข่ายที่ Plugin เป็นเจ้าของ เว้นแต่ +`agent_end` เป็นฮุกสังเกตและรันแบบ fire-and-forget หลังจบเทิร์น +ตัวรันฮุกใช้ timeout 30 วินาที เพื่อไม่ให้ Plugin หรือ endpoint สำหรับ embedding ที่ค้างอยู่ +ปล่อยให้ promise ของฮุก pending ตลอดไป timeout จะถูกบันทึกใน log และ +OpenClaw จะดำเนินการต่อ โดยจะไม่ยกเลิกงาน network ที่ Plugin เป็นเจ้าของ เว้นแต่ Plugin จะใช้ abort signal ของตัวเองด้วย -ใช้ `model_call_started` และ `model_call_ended` สำหรับ telemetry ของการเรียกผู้ให้บริการ -ที่ไม่ควรได้รับพรอมป์ดิบ ประวัติ คำตอบ headers เนื้อหา request -หรือ request ID ของผู้ให้บริการ ฮุกเหล่านี้รวมเมตาดาต้าที่เสถียร เช่น -`runId`, `callId`, `provider`, `model`, `api`/`transport` แบบไม่บังคับ, -`durationMs`/`outcome` ขั้นสุดท้าย และ `upstreamRequestIdHash` เมื่อ OpenClaw สามารถอนุมาน -แฮช request-id ของผู้ให้บริการแบบมีขอบเขตได้ +ใช้ `model_call_started` และ `model_call_ended` สำหรับ telemetry การเรียก provider +ที่ไม่ควรได้รับ prompt ดิบ history response headers request bodies หรือ request ID ของ provider +ฮุกเหล่านี้รวมเมตาดาต้าที่เสถียร เช่น `runId`, `callId`, `provider`, `model`, +`api`/`transport` ที่เป็นตัวเลือก, `durationMs`/`outcome` ขั้นสุดท้าย และ +`upstreamRequestIdHash` เมื่อ OpenClaw สามารถ derive แฮช request-id ของ provider +แบบจำกัดได้ -`before_agent_finalize` รันเฉพาะเมื่อ harness กำลังจะยอมรับ -คำตอบสุดท้ายตามธรรมชาติของ assistant มันไม่ใช่เส้นทางยกเลิก `/stop` และไม่ -รันเมื่อผู้ใช้ยกเลิกเทิร์น ส่งคืน `{ action: "revise", reason }` เพื่อขอให้ -harness เรียกโมเดลเพิ่มอีกหนึ่งรอบก่อน finalize, `{ action: -"finalize", reason? }` เพื่อบังคับ finalize หรือละผลลัพธ์เพื่อทำต่อ -ฮุก `Stop` แบบเนทีฟของ Codex จะถูก relay เข้าสู่ฮุกนี้เป็นการตัดสินใจ +`before_agent_finalize` รันเฉพาะเมื่อ harness กำลังจะยอมรับคำตอบสุดท้ายของ assistant +ตามธรรมชาติ ไม่ใช่เส้นทางการยกเลิก `/stop` และไม่รันเมื่อผู้ใช้ abort เทิร์น +return `{ action: "revise", reason }` เพื่อขอให้ harness รันโมเดลอีกหนึ่งรอบก่อน finalize, +`{ action: "finalize", reason? }` เพื่อบังคับ finalize หรือเว้นผลลัพธ์ไว้เพื่อดำเนินการต่อ +ฮุก `Stop` แบบ native ของ Codex จะถูก relay เข้าสู่ฮุกนี้เป็นการตัดสินใจ `before_agent_finalize` ของ OpenClaw -Plugin ที่ไม่ได้มาพร้อมระบบซึ่งต้องใช้ `llm_input`, `llm_output`, +เมื่อ return `action: "revise"` Plugin สามารถใส่เมตาดาต้า `retry` เพื่อทำให้ +การรันโมเดลเพิ่มเติมมีขอบเขตและ replay ได้อย่างปลอดภัย: + +```typescript +type BeforeAgentFinalizeRetry = { + instruction: string; + idempotencyKey?: string; + maxAttempts?: number; +}; +``` + +`instruction` จะถูกต่อท้าย reason การ revise ที่ส่งไปยัง harness +`idempotencyKey` ให้โฮสต์นับ retry สำหรับคำขอ Plugin เดียวกันข้ามการตัดสินใจ finalize +ที่เทียบเท่ากันได้ และ `maxAttempts` จำกัดจำนวนรอบเพิ่มเติมที่โฮสต์จะอนุญาต +ก่อนดำเนินการต่อด้วยคำตอบสุดท้ายตามธรรมชาติ + +Plugin ที่ไม่ได้ bundled ซึ่งต้องใช้ `llm_input`, `llm_output`, `before_agent_finalize` หรือ `agent_end` ต้องตั้งค่า: ```json @@ -284,115 +295,110 @@ Plugin ที่ไม่ได้มาพร้อมระบบซึ่ง } ``` -ฮุกที่ mutate พรอมป์และการฉีดสำหรับเทิร์นถัดไปแบบ durable สามารถปิดใช้งานต่อ Plugin -ได้ด้วย `plugins.entries..hooks.allowPromptInjection=false` +ฮุกที่ mutate prompt และการ inject เทิร์นถัดไปแบบ durable สามารถปิดใช้งานต่อ Plugin ได้ +ด้วย `plugins.entries..hooks.allowPromptInjection=false` -### ส่วนขยายเซสชันและการฉีดเทิร์นถัดไป +### ส่วนขยายเซสชันและการ inject เทิร์นถัดไป -Plugin workflow สามารถ persist สถานะเซสชันขนาดเล็กที่เข้ากันได้กับ JSON ด้วย +Plugin สำหรับเวิร์กโฟลว์สามารถคงสถานะเซสชันขนาดเล็กที่เข้ากันได้กับ JSON ด้วย `api.registerSessionExtension(...)` และอัปเดตผ่านเมธอด -`sessions.pluginPatch` ของ Gateway แถวเซสชัน project สถานะส่วนขยายที่ลงทะเบียนไว้ -ผ่าน `pluginExtensions` ทำให้ Control UI และไคลเอนต์อื่นเรนเดอร์ -สถานะที่ Plugin เป็นเจ้าของได้โดยไม่ต้องรู้ internals ของ Plugin +`sessions.pluginPatch` ของ Gateway ได้ แถวเซสชันจะแสดงสถานะส่วนขยายที่ลงทะเบียนไว้ +ผ่าน `pluginExtensions` ทำให้ UI ควบคุมและไคลเอนต์อื่นๆ เรนเดอร์ +สถานะที่ Plugin เป็นเจ้าของได้โดยไม่ต้องรู้รายละเอียดภายในของ Plugin ใช้ `api.enqueueNextTurnInjection(...)` เมื่อ Plugin ต้องการบริบทที่คงทนเพื่อ -ส่งต่อไปถึงรอบโมเดลถัดไปเพียงครั้งเดียวพอดี OpenClaw จะระบายการแทรกที่เข้าคิวไว้ก่อน -prompt hooks, ทิ้งการแทรกที่หมดอายุ และทำการลบรายการซ้ำตาม `idempotencyKey` -ต่อ Plugin นี่คือ seam ที่เหมาะสำหรับการกลับมาทำงานต่อหลังการอนุมัติ, สรุปนโยบาย, -เดลตาจากตัวติดตามเบื้องหลัง และการดำเนินคำสั่งต่อเนื่องที่ควรมองเห็นได้ต่อ -โมเดลในรอบถัดไป แต่ไม่ควรกลายเป็นข้อความ system prompt แบบถาวร +ไปถึงเทิร์นโมเดลถัดไปแบบครั้งเดียวพอดี OpenClaw จะระบายอินเจกชันที่อยู่ในคิวก่อน +ฮุกพรอมป์ ทิ้งอินเจกชันที่หมดอายุ และลบรายการซ้ำตาม `idempotencyKey` +ต่อ Plugin นี่คือจุดเชื่อมต่อที่เหมาะสมสำหรับการกลับมาทำงานต่อหลังการอนุมัติ สรุปนโยบาย +เดลตาจากตัวมอนิเตอร์เบื้องหลัง และการดำเนินคำสั่งต่อเนื่องที่ควรปรากฏต่อ +โมเดลในเทิร์นถัดไป แต่ไม่ควรกลายเป็นข้อความพรอมป์ระบบถาวร -ความหมายของการล้างข้อมูลเป็นส่วนหนึ่งของสัญญา callback สำหรับการล้างข้อมูลส่วนขยายเซสชันและ -การล้างข้อมูลวงจรชีวิต runtime จะได้รับ `reset`, `delete`, `disable` หรือ -`restart` โฮสต์จะลบสถานะส่วนขยายเซสชันถาวรของ Plugin เจ้าของ -และการแทรกสำหรับรอบถัดไปที่ค้างอยู่เมื่อเป็น reset/delete/disable; restart จะคง -สถานะเซสชันที่คงทนไว้ ขณะที่ callback การล้างข้อมูลเปิดให้ Plugin ปล่อยงาน scheduler, -บริบทการรัน และทรัพยากรนอกแบนด์อื่น ๆ สำหรับ generation runtime เดิม +ความหมายเชิงการล้างข้อมูลเป็นส่วนหนึ่งของสัญญา คอลแบ็กการล้างข้อมูลส่วนขยายเซสชันและ +การล้างข้อมูลวงจรชีวิตรันไทม์จะได้รับ `reset`, `delete`, `disable` หรือ +`restart` โฮสต์จะลบสถานะส่วนขยายเซสชันถาวรของ Plugin ที่เป็นเจ้าของ +และอินเจกชันเทิร์นถัดไปที่ค้างอยู่สำหรับ reset/delete/disable ส่วน restart จะคง +สถานะเซสชันที่คงทนไว้ ขณะที่คอลแบ็กการล้างข้อมูลเปิดทางให้ Plugin ปล่อยงานตัวจัดตารางเวลา +บริบทรัน และทรัพยากรนอกแบนด์อื่นๆ สำหรับรุ่นรันไทม์เดิม ## ฮุกข้อความ -ใช้ฮุกข้อความสำหรับการกำหนดเส้นทางและนโยบายการส่งในระดับช่องทาง: +ใช้ฮุกข้อความสำหรับการกำหนดเส้นทางและนโยบายการส่งมอบระดับช่องทาง: -- `message_received`: สังเกตเนื้อหาขาเข้า ผู้ส่ง `threadId`, `messageId`, - `senderId`, ความสัมพันธ์กับการรัน/เซสชันที่เป็นตัวเลือก และ metadata -- `message_sending`: เขียน `content` ใหม่ หรือคืนค่า `{ cancel: true }` -- `message_sent`: สังเกตผลสำเร็จหรือความล้มเหลวสุดท้าย +- `message_received`: สังเกตเนื้อหาขาเข้า ผู้ส่ง, `threadId`, `messageId`, + `senderId`, ความสัมพันธ์กับรัน/เซสชันแบบไม่บังคับ และเมทาดาทา +- `message_sending`: เขียน `content` ใหม่หรือคืนค่า `{ cancel: true }` +- `message_sent`: สังเกตความสำเร็จหรือความล้มเหลวสุดท้าย -สำหรับการตอบกลับ TTS แบบเสียงเท่านั้น `content` อาจมี transcript คำพูดที่ซ่อนอยู่ -แม้เมื่อ payload ของช่องทางไม่มีข้อความ/คำบรรยายภาพที่มองเห็นได้ การเขียน -`content` นั้นใหม่จะอัปเดตเฉพาะ transcript ที่ฮุกมองเห็นเท่านั้น; จะไม่ถูกเรนเดอร์เป็น +สำหรับการตอบกลับ TTS ที่มีเฉพาะเสียง `content` อาจมีบันทึกถ้อยคำที่พูดแบบซ่อนอยู่ +แม้เมื่อเพย์โหลดของช่องทางไม่มีข้อความ/คำบรรยายที่มองเห็นได้ การเขียน +`content` นั้นใหม่จะอัปเดตเฉพาะบันทึกถ้อยคำที่ฮุกมองเห็นเท่านั้น และจะไม่ถูกเรนเดอร์เป็น คำบรรยายสื่อ -บริบทฮุกข้อความเปิดเผยฟิลด์ความสัมพันธ์ที่เสถียรเมื่อมี: +บริบทของฮุกข้อความจะแสดงฟิลด์ความสัมพันธ์ที่เสถียรเมื่อมีให้ใช้: `ctx.sessionKey`, `ctx.runId`, `ctx.messageId`, `ctx.senderId`, `ctx.trace`, -`ctx.traceId`, `ctx.spanId`, `ctx.parentSpanId` และ `ctx.callDepth` ควรใช้ -ฟิลด์ชั้นหนึ่งเหล่านี้ก่อนอ่าน metadata แบบเดิม +`ctx.traceId`, `ctx.spanId`, `ctx.parentSpanId` และ `ctx.callDepth` ให้ใช้ +ฟิลด์ระดับเฟิร์สต์คลาสเหล่านี้ก่อนอ่านเมทาดาทาแบบเดิม -ควรใช้ฟิลด์ `threadId` และ `replyToId` ที่มีชนิดกำกับก่อนใช้ -metadata เฉพาะช่องทาง +ให้ใช้ฟิลด์ `threadId` และ `replyToId` ที่มีชนิดข้อมูลก่อนใช้เมทาดาทาเฉพาะช่องทาง กฎการตัดสินใจ: -- `message_sending` พร้อม `cancel: true` ถือเป็นจุดสิ้นสุด -- `message_sending` พร้อม `cancel: false` ถือว่าไม่มีการตัดสินใจ -- `content` ที่ถูกเขียนใหม่จะส่งต่อไปยังฮุกที่มีลำดับความสำคัญต่ำกว่า เว้นแต่ฮุกภายหลัง - จะยกเลิกการส่ง +- `message_sending` พร้อม `cancel: true` เป็นการตัดสินใจสุดท้าย +- `message_sending` พร้อม `cancel: false` จะถือว่าไม่มีการตัดสินใจ +- `content` ที่เขียนใหม่จะส่งต่อไปยังฮุกที่มีลำดับความสำคัญต่ำกว่าต่อไป เว้นแต่ฮุกภายหลัง + จะยกเลิกการส่งมอบ ## ฮุกการติดตั้ง -`before_install` จะรันหลังการสแกนในตัวสำหรับการติดตั้ง Skills และ Plugin -คืนค่าผลการตรวจพบเพิ่มเติม หรือ `{ block: true, blockReason }` เพื่อหยุด +`before_install` จะทำงานหลังการสแกนในตัวสำหรับการติดตั้ง Skills และ Plugin +คืนค่าผลการค้นพบเพิ่มเติมหรือ `{ block: true, blockReason }` เพื่อหยุด การติดตั้ง -`block: true` ถือเป็นจุดสิ้นสุด `block: false` ถือว่าไม่มีการตัดสินใจ +`block: true` เป็นการตัดสินใจสุดท้าย `block: false` จะถือว่าไม่มีการตัดสินใจ ## วงจรชีวิต Gateway -ใช้ `gateway_start` สำหรับบริการของ Plugin ที่ต้องการสถานะที่ Gateway เป็นเจ้าของ บริบท -เปิดเผย `ctx.config`, `ctx.workspaceDir` และ `ctx.getCron?.()` สำหรับ -การตรวจสอบและอัปเดต cron ใช้ `gateway_stop` เพื่อล้างข้อมูล -ทรัพยากรที่รันเป็นเวลานาน +ใช้ `gateway_start` สำหรับบริการของ Plugin ที่ต้องการสถานะที่ Gateway เป็นเจ้าของ +บริบทจะแสดง `ctx.config`, `ctx.workspaceDir` และ `ctx.getCron?.()` สำหรับ +การตรวจสอบและอัปเดต cron ใช้ `gateway_stop` เพื่อล้างทรัพยากรที่ทำงานระยะยาว -อย่าพึ่งพาฮุกภายใน `gateway:startup` สำหรับบริการ runtime -ที่ Plugin เป็นเจ้าของ +อย่าพึ่งพาฮุกภายใน `gateway:startup` สำหรับบริการรันไทม์ที่ Plugin เป็นเจ้าของ -`cron_changed` จะทำงานสำหรับเหตุการณ์วงจรชีวิต cron ที่ gateway เป็นเจ้าของ พร้อม -payload เหตุการณ์ที่มีชนิดกำกับ ครอบคลุมเหตุผล `added`, `updated`, `removed`, `started`, `finished` -และ `scheduled` เหตุการณ์จะพก snapshot ของ `PluginHookGatewayCronJob` +`cron_changed` จะทำงานสำหรับเหตุการณ์วงจรชีวิต cron ที่ Gateway เป็นเจ้าของ โดยมี +เพย์โหลดเหตุการณ์แบบมีชนิดที่ครอบคลุมเหตุผล `added`, `updated`, `removed`, `started`, `finished`, +และ `scheduled` เหตุการณ์จะนำสแนปช็อต `PluginHookGatewayCronJob` (รวมถึง `state.nextRunAtMs`, `state.lastRunStatus` และ `state.lastError` เมื่อมี) พร้อม `PluginHookGatewayCronDeliveryStatus` -ของ `not-requested` | `delivered` | `not-delivered` | `unknown` เหตุการณ์ที่ถูกลบ -ยังคงพก snapshot ของงานที่ถูกลบ เพื่อให้ scheduler ภายนอกสามารถ -กระทบยอดสถานะได้ ใช้ `ctx.getCron?.()` และ `ctx.config` จากบริบท -runtime เมื่อซิงก์ scheduler ปลุกระบบภายนอก และให้ OpenClaw เป็น -แหล่งข้อมูลจริงสำหรับการตรวจสอบกำหนดเวลาและการดำเนินงาน +เป็น `not-requested` | `delivered` | `not-delivered` | `unknown` เหตุการณ์ที่ถูกลบ +ยังคงมีสแนปช็อตงานที่ถูกลบเพื่อให้ตัวจัดตารางเวลาภายนอกสามารถกระทบยอดสถานะได้ +ใช้ `ctx.getCron?.()` และ `ctx.config` จากบริบทรันไทม์เมื่อซิงค์ตัวจัดตารางเวลาปลุกภายนอก +และให้ OpenClaw เป็นแหล่งข้อมูลจริงสำหรับการตรวจสอบเวลาถึงกำหนดและการดำเนินการ ## การเลิกใช้งานที่กำลังจะมาถึง -พื้นผิวบางส่วนที่อยู่ใกล้กับฮุกถูกเลิกใช้แล้วแต่ยังรองรับอยู่ ให้ย้าย -ก่อนรีลีสหลักครั้งถัดไป: +พื้นผิวบางส่วนที่อยู่ใกล้กับฮุกถูกเลิกใช้แล้วแต่ยังรองรับอยู่ ให้ย้ายก่อน +รีลีสเมเจอร์ถัดไป: -- **envelope ช่องทางแบบข้อความล้วน** ใน handler ของ `inbound_claim` และ `message_received` - ให้อ่าน `BodyForAgent` และบล็อกบริบทผู้ใช้แบบมีโครงสร้าง - แทนการแยกวิเคราะห์ข้อความ envelope แบบแบน ดู - [envelope ช่องทางแบบข้อความล้วน → BodyForAgent](/th/plugins/sdk-migration#active-deprecations) +- **เอนเวโลปช่องทางแบบข้อความธรรมดา** ในตัวจัดการ `inbound_claim` และ `message_received` + อ่าน `BodyForAgent` และบล็อกบริบทผู้ใช้แบบมีโครงสร้าง + แทนการแยกวิเคราะห์ข้อความเอนเวโลปแบบแบน ดู + [เอนเวโลปช่องทางแบบข้อความธรรมดา → BodyForAgent](/th/plugins/sdk-migration#active-deprecations) - **`before_agent_start`** ยังคงอยู่เพื่อความเข้ากันได้ Plugin ใหม่ควรใช้ - `before_model_resolve` และ `before_prompt_build` แทน phase - แบบรวม -- **`onResolution` ใน `before_tool_call`** ตอนนี้ใช้ union ที่มีชนิดกำกับ - `PluginApprovalResolution` (`allow-once` / `allow-always` / `deny` / - `timeout` / `cancelled`) แทน `string` แบบอิสระ + `before_model_resolve` และ `before_prompt_build` แทนเฟสแบบรวม +- **`onResolution` ใน `before_tool_call`** ตอนนี้ใช้ยูเนียน + `PluginApprovalResolution` แบบมีชนิด (`allow-once` / `allow-always` / `deny` / + `timeout` / `cancelled`) แทน `string` แบบรูปแบบอิสระ -สำหรับรายการทั้งหมด — การลงทะเบียนความสามารถหน่วยความจำ, profile การคิดของ provider, -provider การยืนยันตัวตนภายนอก, ชนิดการค้นพบ provider, accessor ของ runtime งาน, +สำหรับรายการทั้งหมด — การลงทะเบียนความสามารถหน่วยความจำ โปรไฟล์การคิดของผู้ให้บริการ +ผู้ให้บริการตรวจสอบสิทธิ์ภายนอก ชนิดการค้นพบผู้ให้บริการ ตัวเข้าถึงรันไทม์งาน และการเปลี่ยนชื่อ `command-auth` → `command-status` — ดู [การย้าย Plugin SDK → การเลิกใช้งานที่ยังมีผล](/th/plugins/sdk-migration#active-deprecations) ## ที่เกี่ยวข้อง -- [การย้าย Plugin SDK](/th/plugins/sdk-migration) — การเลิกใช้งานที่ยังมีผลและไทม์ไลน์การลบออก +- [การย้าย Plugin SDK](/th/plugins/sdk-migration) — การเลิกใช้งานที่ยังมีผลและกำหนดเวลาการนำออก - [การสร้าง Plugin](/th/plugins/building-plugins) - [ภาพรวม Plugin SDK](/th/plugins/sdk-overview) -- [จุดเข้าใช้งานของ Plugin](/th/plugins/sdk-entrypoints) +- [จุดเข้าใช้งาน Plugin](/th/plugins/sdk-entrypoints) - [ฮุกภายใน](/th/automation/hooks) -- [ส่วนภายในของสถาปัตยกรรม Plugin](/th/plugins/architecture-internals) +- [รายละเอียดภายในสถาปัตยกรรม Plugin](/th/plugins/architecture-internals) diff --git a/docs/th/plugins/sdk-overview.md b/docs/th/plugins/sdk-overview.md index 84c36460a..242df4b8f 100644 --- a/docs/th/plugins/sdk-overview.md +++ b/docs/th/plugins/sdk-overview.md @@ -1,21 +1,21 @@ --- read_when: - - คุณต้องทราบว่าควรนำเข้าจากเส้นทางย่อยใดของ SDK + - คุณต้องทราบว่าจะนำเข้าจากพาธย่อยใดของ SDK - คุณต้องการเอกสารอ้างอิงสำหรับเมธอดการลงทะเบียนทั้งหมดบน OpenClawPluginApi - - คุณกำลังค้นหารายการส่งออกเฉพาะของ SDK + - คุณกำลังค้นหาการส่งออกของ SDK ที่เฉพาะเจาะจง sidebarTitle: Plugin SDK overview -summary: แผนที่การนำเข้า, เอกสารอ้างอิงส่วนติดต่อโปรแกรมประยุกต์สำหรับการลงทะเบียน และสถาปัตยกรรมชุดพัฒนาซอฟต์แวร์ -title: ภาพรวมของ Plugin SDK +summary: แผนผังการนำเข้า เอกสารอ้างอิง API สำหรับการลงทะเบียน และสถาปัตยกรรม SDK +title: ภาพรวม Plugin SDK x-i18n: - generated_at: "2026-05-02T10:26:00Z" + generated_at: "2026-05-04T18:24:44Z" model: gpt-5.5 provider: openai - source_hash: be5fa531e603fb6d87f84e3193ebd61be1431b57b8f284871ae15f34ca93fc69 + source_hash: 8187e7d4cfb9d6fb19bbdebfbaea0bb4d98fa5cea4742d0f82a765ae5bc60127 source_path: plugins/sdk-overview.md workflow: 16 --- -Plugin SDK คือสัญญาแบบมีชนิดข้อมูลระหว่าง Plugin กับแกนหลัก หน้านี้คือ +Plugin SDK คือสัญญาแบบมีชนิดข้อมูลระหว่าง Plugin กับแกนหลัก หน้านี้เป็น ข้อมูลอ้างอิงสำหรับ **สิ่งที่ต้อง import** และ **สิ่งที่คุณสามารถลงทะเบียนได้** @@ -27,78 +27,80 @@ Plugin SDK คือสัญญาแบบมีชนิดข้อมูล -กำลังมองหาคู่มือวิธีทำอยู่หรือไม่ เริ่มที่ [การสร้าง Plugin](/th/plugins/building-plugins), ใช้ [Plugin ช่องทาง](/th/plugins/sdk-channel-plugins) สำหรับ Plugin ช่องทาง, [Plugin ผู้ให้บริการ](/th/plugins/sdk-provider-plugins) สำหรับ Plugin ผู้ให้บริการ และ [ฮุก Plugin](/th/plugins/hooks) สำหรับ Plugin ฮุกเครื่องมือหรือวงจรชีวิต +กำลังมองหาคู่มือวิธีทำอยู่หรือไม่ เริ่มจาก [การสร้าง Plugin](/th/plugins/building-plugins), ใช้ [Plugin ช่องทาง](/th/plugins/sdk-channel-plugins) สำหรับ Plugin ช่องทาง, [Plugin ผู้ให้บริการ](/th/plugins/sdk-provider-plugins) สำหรับ Plugin ผู้ให้บริการ และ [Hook ของ Plugin](/th/plugins/hooks) สำหรับ Plugin hook เครื่องมือหรือวงจรชีวิต ## รูปแบบการ import -ให้ import จากซับพาธที่เฉพาะเจาะจงเสมอ: +ให้ import จาก subpath ที่เฉพาะเจาะจงเสมอ: ```typescript import { definePluginEntry } from "openclaw/plugin-sdk/plugin-entry"; import { defineChannelPluginEntry } from "openclaw/plugin-sdk/channel-core"; ``` -แต่ละซับพาธเป็นโมดูลขนาดเล็กที่แยกตัวเองครบถ้วน วิธีนี้ช่วยให้การเริ่มต้นทำงานเร็ว -และป้องกันปัญหาการพึ่งพาแบบวนรอบ สำหรับตัวช่วย entry/build ที่เฉพาะกับช่องทาง -ควรใช้ `openclaw/plugin-sdk/channel-core`; เก็บ `openclaw/plugin-sdk/core` ไว้สำหรับ -พื้นผิวรวมที่กว้างกว่าและตัวช่วยที่ใช้ร่วมกัน เช่น +แต่ละ subpath เป็นโมดูลขนาดเล็กที่ครบถ้วนในตัวเอง สิ่งนี้ช่วยให้การเริ่มต้นทำงานเร็ว +และป้องกันปัญหา dependency แบบวนกลับ สำหรับตัวช่วย entry/build เฉพาะช่องทาง +ให้เลือกใช้ `openclaw/plugin-sdk/channel-core`; เก็บ `openclaw/plugin-sdk/core` ไว้สำหรับ +พื้นผิวครอบคลุมที่กว้างกว่าและตัวช่วยร่วม เช่น `buildChannelConfigSchema` -สำหรับคอนฟิกช่องทาง ให้เผยแพร่ JSON Schema ที่ช่องทางเป็นเจ้าของผ่าน -`openclaw.plugin.json#channelConfigs` ซับพาธ `plugin-sdk/channel-config-schema` -มีไว้สำหรับ primitive ของสคีมาที่ใช้ร่วมกันและตัวสร้างทั่วไป Plugin ที่บันเดิลมากับ -OpenClaw ใช้ `plugin-sdk/bundled-channel-config-schema` สำหรับสคีมาช่องทางบันเดิลที่ยังคงไว้ -export เพื่อความเข้ากันได้ที่เลิกใช้แล้วคงอยู่ใน -`plugin-sdk/channel-config-schema-legacy`; ซับพาธสคีมาบันเดิลทั้งสองไม่ใช่ +สำหรับการกำหนดค่าช่องทาง ให้เผยแพร่ JSON Schema ที่ช่องทางเป็นเจ้าของผ่าน +`openclaw.plugin.json#channelConfigs` subpath `plugin-sdk/channel-config-schema` +มีไว้สำหรับ primitive ของ schema ร่วมและตัวสร้างทั่วไป Plugin ที่มาพร้อมกับ OpenClaw +ใช้ `plugin-sdk/bundled-channel-config-schema` สำหรับ schema ของช่องทางที่มาพร้อมกันซึ่งยังคงเก็บไว้ +export ความเข้ากันได้ที่เลิกแนะนำแล้วยังคงอยู่บน +`plugin-sdk/channel-config-schema-legacy`; subpath ของ schema ที่มาพร้อมกันทั้งสองแบบไม่ใช่ รูปแบบสำหรับ Plugin ใหม่ - อย่า import seam อำนวยความสะดวกที่ติดแบรนด์ผู้ให้บริการหรือช่องทาง (เช่น + อย่า import seam อำนวยความสะดวกที่มีแบรนด์ผู้ให้บริการหรือช่องทาง (เช่น `openclaw/plugin-sdk/slack`, `.../discord`, `.../signal`, `.../whatsapp`) - Plugin ที่บันเดิลมาจะประกอบซับพาธ SDK ทั่วไปไว้ภายใน barrel `api.ts` / - `runtime-api.ts` ของตนเอง; ผู้ใช้แกนหลักควรใช้ barrel ภายใน Plugin เหล่านั้น - หรือเพิ่มสัญญา SDK ทั่วไปแบบแคบเมื่อความจำเป็นนั้นเป็นแบบข้ามช่องทางจริง ๆ + Plugin ที่มาพร้อมกันประกอบ subpath SDK ทั่วไปภายใน barrel `api.ts` / + `runtime-api.ts` ของตัวเอง; ผู้ใช้แกนหลักควรใช้ barrel เฉพาะ Plugin เหล่านั้น + หรือเพิ่มสัญญา SDK ทั่วไปแบบแคบเมื่อความจำเป็นนั้นเป็นแบบ + ข้ามช่องทางจริง ๆ -seam ตัวช่วยของ Plugin บันเดิลชุดเล็กยังคงปรากฏในแผนที่ export ที่สร้างขึ้น -เมื่อมีการติดตามการใช้งานโดยเจ้าของ seam เหล่านี้มีไว้สำหรับการบำรุงรักษา -Plugin บันเดิลเท่านั้น และไม่แนะนำให้ใช้เป็นพาธ import สำหรับ Plugin บุคคลที่สามใหม่ +seam ตัวช่วยของ Plugin ที่มาพร้อมกันชุดเล็ก ๆ ยังคงปรากฏใน export map ที่สร้างขึ้น +เมื่อมีการติดตามการใช้งานโดยเจ้าของ สิ่งเหล่านี้มีไว้สำหรับการบำรุงรักษา Plugin +ที่มาพร้อมกันเท่านั้น และไม่ใช่เส้นทาง import ที่แนะนำสำหรับ Plugin บุคคลที่สามใหม่ -`openclaw/plugin-sdk/discord` และ `openclaw/plugin-sdk/telegram-account` ยังถูกเก็บไว้เป็น -facade เพื่อความเข้ากันได้ที่เลิกใช้แล้วสำหรับการใช้งานโดยเจ้าของที่ติดตามไว้ อย่า -คัดลอกพาธ import เหล่านี้ไปยัง Plugin ใหม่; ให้ใช้ตัวช่วยรันไทม์ที่ฉีดเข้ามาและ -ซับพาธ SDK ช่องทางทั่วไปแทน +`openclaw/plugin-sdk/discord` และ `openclaw/plugin-sdk/telegram-account` ยัง +คงไว้เป็น facade ความเข้ากันได้ที่เลิกแนะนำแล้วสำหรับการใช้งานโดยเจ้าของที่ติดตามไว้ อย่า +คัดลอกเส้นทาง import เหล่านั้นไปยัง Plugin ใหม่; ให้ใช้ตัวช่วย runtime ที่ฉีดเข้ามาและ +subpath SDK ช่องทางทั่วไปแทน -## ข้อมูลอ้างอิงซับพาธ +## ข้อมูลอ้างอิง subpath -Plugin SDK ถูกเปิดเผยเป็นชุดซับพาธแคบที่จัดกลุ่มตามพื้นที่ (entry ของ Plugin, -ช่องทาง, ผู้ให้บริการ, การยืนยันตัวตน, รันไทม์, ความสามารถ, หน่วยความจำ และตัวช่วย -Plugin บันเดิลที่สงวนไว้) สำหรับแค็ตตาล็อกฉบับเต็มที่จัดกลุ่มและลิงก์ไว้ โปรดดู -[ซับพาธ Plugin SDK](/th/plugins/sdk-subpaths) +Plugin SDK ถูกเปิดเผยเป็นชุดของ subpath แบบแคบที่จัดกลุ่มตามพื้นที่ (entry ของ Plugin, +ช่องทาง, ผู้ให้บริการ, auth, runtime, capability, memory และตัวช่วยของ Plugin +ที่มาพร้อมกันซึ่งสงวนไว้) สำหรับแค็ตตาล็อกทั้งหมดที่จัดกลุ่มและเชื่อมโยงไว้ โปรดดู +[subpath ของ Plugin SDK](/th/plugins/sdk-subpaths) -รายการซับพาธกว่า 200 รายการที่สร้างขึ้นอยู่ใน `scripts/lib/plugin-sdk-entrypoints.json` +รายการ subpath กว่า 200 รายการที่สร้างขึ้นอยู่ใน `scripts/lib/plugin-sdk-entrypoints.json` ## API การลงทะเบียน -คอลแบ็ก `register(api)` จะได้รับอ็อบเจกต์ `OpenClawPluginApi` พร้อมเมธอดเหล่านี้: +callback `register(api)` ได้รับออบเจ็กต์ `OpenClawPluginApi` ที่มี +เมธอดเหล่านี้: -### การลงทะเบียนความสามารถ +### การลงทะเบียน capability | เมธอด | สิ่งที่ลงทะเบียน | | ------------------------------------------------ | ------------------------------------- | | `api.registerProvider(...)` | การอนุมานข้อความ (LLM) | -| `api.registerAgentHarness(...)` | ตัวดำเนินการเอเจนต์ระดับต่ำเชิงทดลอง | -| `api.registerCliBackend(...)` | แบ็กเอนด์การอนุมาน CLI ในเครื่อง | +| `api.registerAgentHarness(...)` | ตัวเรียกใช้งานเอเจนต์ระดับต่ำแบบทดลอง | +| `api.registerCliBackend(...)` | backend การอนุมาน CLI ภายในเครื่อง | | `api.registerChannel(...)` | ช่องทางการรับส่งข้อความ | -| `api.registerSpeechProvider(...)` | การสังเคราะห์ข้อความเป็นเสียง / STT | -| `api.registerRealtimeTranscriptionProvider(...)` | การถอดความแบบเรียลไทม์ชนิดสตรีม | -| `api.registerRealtimeVoiceProvider(...)` | เซสชันเสียงเรียลไทม์แบบสองทาง | +| `api.registerSpeechProvider(...)` | การสังเคราะห์ text-to-speech / STT | +| `api.registerRealtimeTranscriptionProvider(...)` | การถอดเสียงแบบเรียลไทม์แบบสตรีม | +| `api.registerRealtimeVoiceProvider(...)` | เซสชันเสียงแบบเรียลไทม์สองทาง | | `api.registerMediaUnderstandingProvider(...)` | การวิเคราะห์รูปภาพ/เสียง/วิดีโอ | | `api.registerImageGenerationProvider(...)` | การสร้างรูปภาพ | | `api.registerMusicGenerationProvider(...)` | การสร้างเพลง | | `api.registerVideoGenerationProvider(...)` | การสร้างวิดีโอ | -| `api.registerWebFetchProvider(...)` | ผู้ให้บริการดึงข้อมูลเว็บ / scrape | +| `api.registerWebFetchProvider(...)` | ผู้ให้บริการดึงเว็บ / scrape | | `api.registerWebSearchProvider(...)` | การค้นหาเว็บ | ### เครื่องมือและคำสั่ง @@ -108,91 +110,91 @@ Plugin บันเดิลที่สงวนไว้) สำหรับ | `api.registerTool(tool, opts?)` | เครื่องมือเอเจนต์ (จำเป็นหรือ `{ optional: true }`) | | `api.registerCommand(def)` | คำสั่งกำหนดเอง (ข้าม LLM) | -คำสั่งของ Plugin สามารถตั้งค่า `agentPromptGuidance` ได้เมื่อเอเจนต์ต้องการ -คำใบ้การกำหนดเส้นทางสั้น ๆ ที่คำสั่งเป็นเจ้าของ ให้เนื้อหานั้นเกี่ยวกับตัวคำสั่งเอง; -อย่าเพิ่มนโยบายเฉพาะผู้ให้บริการหรือเฉพาะ Plugin เข้าไปในตัวสร้างพรอมป์แกนหลัก +คำสั่งของ Plugin สามารถตั้งค่า `agentPromptGuidance` เมื่อเอเจนต์ต้องการ +คำใบ้การกำหนดเส้นทางสั้น ๆ ที่คำสั่งเป็นเจ้าของ เก็บข้อความนั้นให้เกี่ยวกับตัวคำสั่งเอง; +อย่าเพิ่มนโยบายเฉพาะผู้ให้บริการหรือเฉพาะ Plugin ไปยังตัวสร้าง prompt ของแกนหลัก ### โครงสร้างพื้นฐาน | เมธอด | สิ่งที่ลงทะเบียน | | ---------------------------------------------- | --------------------------------------- | -| `api.registerHook(events, handler, opts?)` | ฮุกเหตุการณ์ | -| `api.registerHttpRoute(params)` | ปลายทาง HTTP ของ Gateway | +| `api.registerHook(events, handler, opts?)` | hook เหตุการณ์ | +| `api.registerHttpRoute(params)` | endpoint HTTP ของ Gateway | | `api.registerGatewayMethod(name, handler)` | เมธอด RPC ของ Gateway | -| `api.registerGatewayDiscoveryService(service)` | ตัวประกาศการค้นพบ Gateway ในเครื่อง | +| `api.registerGatewayDiscoveryService(service)` | ตัวประกาศการค้นพบ Gateway ภายในเครื่อง | | `api.registerCli(registrar, opts?)` | คำสั่งย่อย CLI | | `api.registerService(service)` | บริการเบื้องหลัง | -| `api.registerInteractiveHandler(registration)` | ตัวจัดการแบบโต้ตอบ | -| `api.registerAgentToolResultMiddleware(...)` | มิดเดิลแวร์ผลลัพธ์เครื่องมือของรันไทม์ | -| `api.registerMemoryPromptSupplement(builder)` | ส่วนพรอมป์เพิ่มเติมที่อยู่ใกล้หน่วยความจำ | -| `api.registerMemoryCorpusSupplement(adapter)` | คลังข้อมูลค้นหา/อ่านหน่วยความจำเพิ่มเติม | +| `api.registerInteractiveHandler(registration)` | handler แบบโต้ตอบ | +| `api.registerAgentToolResultMiddleware(...)` | middleware ผลลัพธ์เครื่องมือ runtime | +| `api.registerMemoryPromptSupplement(builder)` | ส่วน prompt เพิ่มเติมที่อยู่ใกล้ memory | +| `api.registerMemoryCorpusSupplement(adapter)` | corpus ค้นหา/อ่าน memory เพิ่มเติม | -### ฮุกโฮสต์สำหรับ Plugin เวิร์กโฟลว์ +### Host hook สำหรับ Plugin workflow -ฮุกโฮสต์คือ seam ของ SDK สำหรับ Plugin ที่ต้องมีส่วนร่วมในวงจรชีวิตของโฮสต์ -แทนที่จะเพิ่มเฉพาะผู้ให้บริการ ช่องทาง หรือเครื่องมือเท่านั้น ฮุกเหล่านี้เป็น -สัญญาทั่วไป; โหมด Plan ใช้งานได้ แต่เวิร์กโฟลว์การอนุมัติ, -เกตนโยบายพื้นที่ทำงาน, มอนิเตอร์เบื้องหลัง, วิซาร์ดตั้งค่า และ Plugin คู่หู UI -ก็ใช้งานได้เช่นกัน +Host hook คือ seam ของ SDK สำหรับ Plugin ที่ต้องเข้าร่วมในวงจรชีวิตของโฮสต์ +แทนที่จะเพิ่มเพียงผู้ให้บริการ ช่องทาง หรือเครื่องมือเท่านั้น สิ่งเหล่านี้เป็น +สัญญาทั่วไป; Plan Mode สามารถใช้ได้ แต่ workflow การอนุมัติ +gate นโยบาย workspace, ตัวตรวจสอบเบื้องหลัง, wizard ตั้งค่า และ Plugin เสริม UI +ก็ใช้ได้เช่นกัน -| เมธอด | สัญญาที่เมธอดเป็นเจ้าของ | +| เมธอด | สัญญาที่เป็นเจ้าของ | | ------------------------------------------------------------------------ | --------------------------------------------------------------------------------------------------------------------------------- | | `api.registerSessionExtension(...)` | สถานะเซสชันที่ Plugin เป็นเจ้าของและเข้ากันได้กับ JSON ซึ่งฉายผ่านเซสชัน Gateway | -| `api.enqueueNextTurnInjection(...)` | บริบทที่คงทนและเกิดครั้งเดียวพอดี ซึ่งถูกฉีดเข้าสู่เทิร์นเอเจนต์ถัดไปสำหรับหนึ่งเซสชัน | -| `api.registerTrustedToolPolicy(...)` | นโยบายเครื่องมือก่อน Plugin แบบบันเดิล/เชื่อถือได้ ซึ่งสามารถบล็อกหรือเขียนพารามิเตอร์เครื่องมือใหม่ได้ | -| `api.registerToolMetadata(...)` | เมทาดาทาการแสดงผลของแค็ตตาล็อกเครื่องมือโดยไม่เปลี่ยนการนำเครื่องมือไปใช้ | -| `api.registerCommand(...)` | คำสั่ง Plugin แบบมีขอบเขต; ผลลัพธ์คำสั่งสามารถตั้งค่า `continueAgent: true`; คำสั่งเนทีฟของ Discord รองรับ `descriptionLocalizations` | -| `api.registerControlUiDescriptor(...)` | ตัวอธิบายการมีส่วนร่วมของ UI ควบคุมสำหรับพื้นผิวเซสชัน เครื่องมือ การรัน หรือการตั้งค่า | -| `api.registerRuntimeLifecycle(...)` | คอลแบ็กทำความสะอาดสำหรับทรัพยากรรันไทม์ที่ Plugin เป็นเจ้าของบนเส้นทางรีเซ็ต/ลบ/โหลดใหม่ | -| `api.registerAgentEventSubscription(...)` | การสมัครรับเหตุการณ์ที่ผ่านการทำให้ปลอดภัยสำหรับสถานะเวิร์กโฟลว์และมอนิเตอร์ | -| `api.setRunContext(...)` / `getRunContext(...)` / `clearRunContext(...)` | สถานะชั่วคราวของ Plugin ต่อการรัน ซึ่งถูกล้างเมื่อวงจรชีวิตการรันสิ้นสุด | -| `api.registerSessionSchedulerJob(...)` | ระเบียนงานตัวจัดกำหนดการเซสชันที่ Plugin เป็นเจ้าของ พร้อมการทำความสะอาดที่กำหนดแน่นอน | +| `api.enqueueNextTurnInjection(...)` | บริบทที่คงทนแบบ exactly-once ซึ่งฉีดเข้าไปใน turn ถัดไปของเอเจนต์สำหรับหนึ่งเซสชัน | +| `api.registerTrustedToolPolicy(...)` | นโยบายเครื่องมือ pre-plugin ที่มาพร้อมกัน/เชื่อถือได้ ซึ่งสามารถบล็อกหรือเขียน params ของเครื่องมือใหม่ | +| `api.registerToolMetadata(...)` | metadata การแสดงผลแค็ตตาล็อกเครื่องมือโดยไม่เปลี่ยน implementation ของเครื่องมือ | +| `api.registerCommand(...)` | คำสั่ง Plugin แบบกำหนดขอบเขต; ผลลัพธ์คำสั่งสามารถตั้งค่า `continueAgent: true`; คำสั่ง native ของ Discord รองรับ `descriptionLocalizations` | +| `api.registerControlUiDescriptor(...)` | descriptor การมีส่วนร่วมของ Control UI สำหรับพื้นผิวเซสชัน เครื่องมือ การเรียกใช้ หรือการตั้งค่า | +| `api.registerRuntimeLifecycle(...)` | callback ทำความสะอาดสำหรับทรัพยากร runtime ที่ Plugin เป็นเจ้าของบนเส้นทาง reset/delete/reload | +| `api.registerAgentEventSubscription(...)` | การสมัครรับเหตุการณ์ที่ทำให้ปลอดภัยแล้วสำหรับสถานะ workflow และตัวตรวจสอบ | +| `api.setRunContext(...)` / `getRunContext(...)` / `clearRunContext(...)` | สถานะ scratch ของ Plugin ต่อการรัน ซึ่งถูกล้างเมื่อวงจรชีวิตการรันสิ้นสุด | +| `api.registerSessionSchedulerJob(...)` | ระเบียนงานตัวจัดกำหนดการเซสชันที่ Plugin เป็นเจ้าของ พร้อมการทำความสะอาดแบบกำหนดได้แน่นอน | -สัญญาเหล่านี้จงใจแยกอำนาจออกจากกัน: +สัญญาเหล่านี้ตั้งใจแยกอำนาจ: -- Plugin ภายนอกสามารถเป็นเจ้าของส่วนขยายเซสชัน ตัวอธิบาย UI คำสั่ง เมทาดาทาเครื่องมือ - การฉีดในเทิร์นถัดไป และฮุกปกติ -- นโยบายเครื่องมือที่เชื่อถือได้ทำงานก่อนฮุก `before_tool_call` ทั่วไป และเป็นแบบ - บันเดิลเท่านั้น เพราะมีส่วนร่วมในนโยบายความปลอดภัยของโฮสต์ -- การเป็นเจ้าของคำสั่งที่สงวนไว้เป็นแบบบันเดิลเท่านั้น Plugin ภายนอกควรใช้ - ชื่อคำสั่งหรือนามแฝงของตนเอง -- `allowPromptInjection=false` ปิดใช้งานฮุกที่เปลี่ยนแปลงพรอมป์ รวมถึง +- Plugin ภายนอกสามารถเป็นเจ้าของส่วนขยายเซสชัน, descriptor UI, คำสั่ง, metadata เครื่องมือ, + การฉีด turn ถัดไป และ hook ปกติ +- นโยบายเครื่องมือที่เชื่อถือได้รันก่อน hook `before_tool_call` ทั่วไป และเป็นแบบ + ที่มาพร้อมกันเท่านั้น เพราะมีส่วนร่วมในนโยบายความปลอดภัยของโฮสต์ +- ความเป็นเจ้าของคำสั่งที่สงวนไว้เป็นแบบที่มาพร้อมกันเท่านั้น Plugin ภายนอกควรใช้ + ชื่อคำสั่งหรือ alias ของตัวเอง +- `allowPromptInjection=false` ปิดใช้งาน hook ที่แก้ไข prompt รวมถึง `agent_turn_prepare`, `before_prompt_build`, `heartbeat_prompt_contribution`, - ฟิลด์พรอมป์จาก `before_agent_start` แบบเดิม และ + ช่อง prompt จาก `before_agent_start` แบบเดิม และ `enqueueNextTurnInjection` ตัวอย่างผู้ใช้ที่ไม่ใช่ Plan: -| รูปแบบ Plugin | ฮุกที่ใช้ | +| รูปแบบ Plugin | Hook ที่ใช้ | | ---------------------------- | -------------------------------------------------------------------------------------------------------------------------------------- | -| เวิร์กโฟลว์การอนุมัติ | ส่วนขยายเซสชัน, การดำเนินคำสั่งต่อ, การฉีดในเทิร์นถัดไป, ตัวอธิบาย UI | -| เกตนโยบายงบประมาณ/พื้นที่ทำงาน | นโยบายเครื่องมือที่เชื่อถือได้, เมทาดาทาเครื่องมือ, การฉายเซสชัน | -| มอนิเตอร์วงจรชีวิตเบื้องหลัง | การทำความสะอาดวงจรชีวิตรันไทม์, การสมัครรับเหตุการณ์เอเจนต์, การเป็นเจ้าของ/ทำความสะอาดตัวจัดกำหนดการเซสชัน, การมีส่วนร่วมพรอมป์ Heartbeat, ตัวอธิบาย UI | -| วิซาร์ดตั้งค่าหรือเริ่มใช้งาน | ส่วนขยายเซสชัน, คำสั่งแบบมีขอบเขต, ตัวอธิบาย UI ควบคุม | +| workflow การอนุมัติ | ส่วนขยายเซสชัน, การต่อเนื่องของคำสั่ง, การฉีด turn ถัดไป, descriptor UI | +| gate นโยบายงบประมาณ/workspace | นโยบายเครื่องมือที่เชื่อถือได้, metadata เครื่องมือ, การฉายเซสชัน | +| ตัวตรวจสอบวงจรชีวิตเบื้องหลัง | การทำความสะอาดวงจรชีวิต runtime, การสมัครรับเหตุการณ์เอเจนต์, ความเป็นเจ้าของ/การทำความสะอาดตัวจัดกำหนดการเซสชัน, การมีส่วนร่วมกับ prompt Heartbeat, descriptor UI | +| wizard ตั้งค่าหรือ onboarding | ส่วนขยายเซสชัน, คำสั่งแบบกำหนดขอบเขต, descriptor Control UI | - เนมสเปซผู้ดูแลแกนหลักที่สงวนไว้ (`config.*`, `exec.approvals.*`, `wizard.*`, + namespace ผู้ดูแลแกนหลักที่สงวนไว้ (`config.*`, `exec.approvals.*`, `wizard.*`, `update.*`) จะคงเป็น `operator.admin` เสมอ แม้ว่า Plugin จะพยายามกำหนด - ขอบเขตเมธอด Gateway ที่แคบกว่า ควรใช้คำนำหน้าเฉพาะ Plugin สำหรับ + ขอบเขตเมธอด gateway ที่แคบกว่า ให้เลือกใช้ prefix เฉพาะ Plugin สำหรับ เมธอดที่ Plugin เป็นเจ้าของ - - Plugin ที่บันเดิลมาสามารถใช้ `api.registerAgentToolResultMiddleware(...)` เมื่อ - ต้องเขียนผลลัพธ์เครื่องมือใหม่หลังการเรียกใช้และก่อนที่รันไทม์จะ - ป้อนผลลัพธ์นั้นกลับเข้าโมเดล นี่คือ seam ที่เชื่อถือได้และเป็นกลางต่อรันไทม์ - สำหรับตัวลดเอาต์พุตแบบ async เช่น tokenjuice + + Plugin ที่มาพร้อมกันสามารถใช้ `api.registerAgentToolResultMiddleware(...)` เมื่อ + จำเป็นต้องเขียนผลลัพธ์เครื่องมือใหม่หลังการดำเนินการและก่อนที่ runtime + จะป้อนผลลัพธ์นั้นกลับเข้าไปในโมเดล นี่คือ seam ที่เป็นกลางต่อ runtime และเชื่อถือได้ + สำหรับตัวลด output แบบ async เช่น tokenjuice -Plugin ที่บันเดิลมาต้องประกาศ `contracts.agentToolResultMiddleware` สำหรับแต่ละ -รันไทม์เป้าหมาย เช่น `["pi", "codex"]` Plugin ภายนอก -ไม่สามารถลงทะเบียนมิดเดิลแวร์นี้ได้; ให้ใช้ฮุก Plugin ของ OpenClaw ตามปกติสำหรับงาน -ที่ไม่ต้องการจังหวะผลลัพธ์เครื่องมือก่อนเข้าโมเดล เส้นทางการลงทะเบียน factory -ส่วนขยายแบบฝังเดิมที่ใช้ได้เฉพาะ Pi ถูกลบออกแล้ว +Plugin ที่มาพร้อมกันต้องประกาศ `contracts.agentToolResultMiddleware` สำหรับแต่ละ +runtime เป้าหมาย เช่น `["pi", "codex"]` Plugin ภายนอก +ไม่สามารถลงทะเบียน middleware นี้ได้; ให้ใช้ hook Plugin ของ OpenClaw ตามปกติสำหรับงาน +ที่ไม่ต้องการจังหวะผลลัพธ์เครื่องมือก่อนเข้าโมเดล เส้นทางการลงทะเบียน factory ของ extension +แบบฝังเฉพาะ Pi เดิมถูกนำออกแล้ว ### การลงทะเบียนการค้นพบ Gateway -`api.registerGatewayDiscoveryService(...)` ช่วยให้ Plugin ประกาศ Gateway ที่ใช้งานอยู่บนการขนส่งสำหรับการค้นพบภายในเครื่อง เช่น mDNS/Bonjour ได้ OpenClaw เรียก service ระหว่างการเริ่มต้น Gateway เมื่อเปิดใช้งานการค้นพบภายในเครื่อง ส่งพอร์ต Gateway ปัจจุบันและข้อมูลคำใบ้ TXT ที่ไม่ใช่ความลับ และเรียกตัวจัดการ `stop` ที่ส่งคืนมาในระหว่างการปิด Gateway +`api.registerGatewayDiscoveryService(...)` ช่วยให้ Plugin โฆษณา Gateway ที่ใช้งานอยู่บนทรานสปอร์ตการค้นหาในเครื่อง เช่น mDNS/Bonjour ได้ OpenClaw จะเรียกใช้บริการนี้ระหว่างการเริ่มต้น Gateway เมื่อเปิดใช้การค้นหาในเครื่อง ส่งพอร์ต Gateway ปัจจุบันและข้อมูลคำใบ้ TXT ที่ไม่ใช่ความลับให้ และเรียกตัวจัดการ `stop` ที่ส่งกลับมาระหว่างการปิด Gateway ```typescript api.registerGatewayDiscoveryService({ @@ -208,15 +210,14 @@ api.registerGatewayDiscoveryService({ }); ``` -Plugin สำหรับการค้นพบ Gateway ต้องไม่ถือว่าค่า TXT ที่ประกาศเป็นความลับหรือการยืนยันตัวตน การค้นพบเป็นเพียงคำใบ้สำหรับการกำหนดเส้นทาง ส่วนความน่าเชื่อถือยังเป็นหน้าที่ของการยืนยันตัวตนของ Gateway และ TLS pinning +Plugin สำหรับการค้นหา Gateway ต้องไม่ถือว่าค่า TXT ที่โฆษณาเป็นความลับหรือการยืนยันตัวตน การค้นหาเป็นคำใบ้สำหรับการกำหนดเส้นทางเท่านั้น ส่วนความเชื่อถือยังเป็นหน้าที่ของการยืนยันตัวตนของ Gateway และการตรึง TLS -### เมตาดาต้าการลงทะเบียน CLI +### เมตาดาทาการลงทะเบียน CLI -`api.registerCli(registrar, opts?)` รับเมตาดาต้าระดับบนสุดสองชนิด: +`api.registerCli(registrar, opts?)` รับเมตาดาทาระดับบนสุดสองชนิด: -- `commands`: รากคำสั่งแบบชัดเจนที่ registrar เป็นเจ้าของ -- `descriptors`: ตัวอธิบายคำสั่งในช่วง parse ที่ใช้สำหรับความช่วยเหลือของ CLI ราก, - การกำหนดเส้นทาง และการลงทะเบียน CLI ของ Plugin แบบ lazy +- `commands`: รากคำสั่งแบบชัดเจนที่เป็นของ registrar +- `descriptors`: descriptor คำสั่งขณะ parse ที่ใช้สำหรับความช่วยเหลือของ CLI ราก การกำหนดเส้นทาง และการลงทะเบียน CLI ของ Plugin แบบ lazy หากคุณต้องการให้คำสั่งของ Plugin ยังคงโหลดแบบ lazy ในเส้นทาง CLI รากตามปกติ ให้ระบุ `descriptors` ที่ครอบคลุมรากคำสั่งระดับบนสุดทุกตัวที่ registrar นั้นเปิดเผย @@ -238,93 +239,84 @@ api.registerCli( ); ``` -ใช้ `commands` เพียงอย่างเดียวเฉพาะเมื่อคุณไม่ต้องการการลงทะเบียน CLI รากแบบ lazy เส้นทางความเข้ากันได้แบบ eager นั้นยังคงรองรับอยู่ แต่จะไม่ติดตั้ง placeholder ที่มี descriptor รองรับสำหรับการโหลดแบบ lazy ในช่วง parse +ใช้ `commands` อย่างเดียวเฉพาะเมื่อคุณไม่ต้องการการลงทะเบียน CLI รากแบบ lazy เส้นทางความเข้ากันได้แบบ eager นั้นยังรองรับอยู่ แต่จะไม่ติดตั้ง placeholder ที่มี descriptor รองรับสำหรับการโหลดแบบ lazy ขณะ parse ### การลงทะเบียนแบ็กเอนด์ CLI -`api.registerCliBackend(...)` ช่วยให้ Plugin เป็นเจ้าของ config เริ่มต้นสำหรับแบ็กเอนด์ AI CLI ภายในเครื่อง เช่น `codex-cli` +`api.registerCliBackend(...)` ช่วยให้ Plugin เป็นเจ้าของ config เริ่มต้นสำหรับแบ็กเอนด์ AI CLI ในเครื่อง เช่น `codex-cli` -- `id` ของแบ็กเอนด์จะกลายเป็นคำนำหน้าผู้ให้บริการใน model ref เช่น `codex-cli/gpt-5` -- `config` ของแบ็กเอนด์ใช้รูปแบบเดียวกับ `agents.defaults.cliBackends.` -- config ของผู้ใช้ยังคงมีสิทธิ์เหนือกว่า OpenClaw จะผสาน `agents.defaults.cliBackends.` ทับค่าเริ่มต้นของ - Plugin ก่อนเรียกใช้ CLI -- ใช้ `normalizeConfig` เมื่อแบ็กเอนด์ต้องเขียนใหม่เพื่อความเข้ากันได้หลังการผสาน - (เช่น การปรับรูปแบบ flag เก่าให้เป็นมาตรฐาน) +- `id` ของแบ็กเอนด์จะกลายเป็นคำนำหน้า provider ในการอ้างอิงโมเดล เช่น `codex-cli/gpt-5` +- `config` ของแบ็กเอนด์ใช้รูปทรงเดียวกับ `agents.defaults.cliBackends.` +- config ของผู้ใช้ยังมีสิทธิ์เหนือกว่า OpenClaw จะ merge `agents.defaults.cliBackends.` ทับค่าเริ่มต้นของ Plugin ก่อนเรียกใช้ CLI +- ใช้ `normalizeConfig` เมื่อแบ็กเอนด์ต้องเขียนซ้ำเพื่อความเข้ากันได้หลัง merge แล้ว เช่น การทำให้รูปทรง flag เก่าเป็นรูปแบบปกติ +- ใช้ `resolveExecutionArgs` สำหรับการเขียน argv ใหม่ตามคำขอที่เป็นของ dialect ของ CLI เช่น การแมประดับ thinking ของ OpenClaw ไปเป็น flag effort แบบ native -### สล็อตแบบผูกขาด +### สล็อตเฉพาะ | เมธอด | สิ่งที่ลงทะเบียน | | ------------------------------------------ | --------------------------------------------------------------------------------------------------------------------------------------------------------- | -| `api.registerContextEngine(id, factory)` | context engine (ใช้งานได้ทีละหนึ่งตัว) callback `assemble()` จะได้รับ `availableTools` และ `citationsMode` เพื่อให้ engine ปรับแต่งส่วนเพิ่มของ prompt ได้ | +| `api.registerContextEngine(id, factory)` | Context engine (ใช้งานได้ครั้งละหนึ่งรายการ) callback `assemble()` จะได้รับ `availableTools` และ `citationsMode` เพื่อให้ engine ปรับแต่งส่วนเพิ่มของ prompt ได้ | | `api.registerMemoryCapability(capability)` | ความสามารถ memory แบบรวมศูนย์ | | `api.registerMemoryPromptSection(builder)` | ตัวสร้างส่วน prompt ของ memory | -| `api.registerMemoryFlushPlan(resolver)` | resolver ของแผน flush memory | -| `api.registerMemoryRuntime(runtime)` | adapter ของ runtime memory | +| `api.registerMemoryFlushPlan(resolver)` | resolver แผน flush ของ memory | +| `api.registerMemoryRuntime(runtime)` | adapter runtime ของ memory | -### adapter สำหรับ memory embedding +### Adapter embedding ของ memory | เมธอด | สิ่งที่ลงทะเบียน | | ---------------------------------------------- | ---------------------------------------------- | -| `api.registerMemoryEmbeddingProvider(adapter)` | adapter สำหรับ memory embedding ของ Plugin ที่ใช้งานอยู่ | +| `api.registerMemoryEmbeddingProvider(adapter)` | adapter embedding ของ memory สำหรับ Plugin ที่ใช้งานอยู่ | -- `registerMemoryCapability` เป็น API สำหรับ Plugin memory แบบผูกขาดที่แนะนำ -- `registerMemoryCapability` อาจเปิดเผย `publicArtifacts.listArtifacts(...)` - ด้วย เพื่อให้ Plugin คู่ขนานใช้ artifact ของ memory ที่ export ผ่าน - `openclaw/plugin-sdk/memory-host-core` แทนการเข้าถึง layout ส่วนตัวของ - Plugin memory ตัวใดตัวหนึ่ง -- `registerMemoryPromptSection`, `registerMemoryFlushPlan` และ - `registerMemoryRuntime` เป็น API สำหรับ Plugin memory แบบผูกขาดที่เข้ากันได้กับระบบเดิม -- `MemoryFlushPlan.model` สามารถตรึงรอบการ flush ไปยัง reference `provider/model` - ที่แน่นอน เช่น `ollama/qwen3:8b` โดยไม่สืบทอด fallback chain ที่ใช้งานอยู่ -- `registerMemoryEmbeddingProvider` ช่วยให้ Plugin memory ที่ใช้งานอยู่ลงทะเบียน id ของ - embedding adapter ได้หนึ่งรายการหรือมากกว่า (เช่น `openai`, `gemini` หรือ id แบบกำหนดเอง - ที่ Plugin กำหนด) -- config ของผู้ใช้ เช่น `agents.defaults.memorySearch.provider` และ - `agents.defaults.memorySearch.fallback` จะ resolve กับ id ของ adapter ที่ลงทะเบียนเหล่านั้น +- `registerMemoryCapability` คือ API Plugin memory แบบเฉพาะที่แนะนำ +- `registerMemoryCapability` อาจเปิดเผย `publicArtifacts.listArtifacts(...)` ด้วย เพื่อให้ Plugin คู่ข้างเคียงใช้ artifact memory ที่ export แล้วผ่าน `openclaw/plugin-sdk/memory-host-core` แทนการเข้าถึง layout ส่วนตัวของ Plugin memory เฉพาะตัว +- `registerMemoryPromptSection`, `registerMemoryFlushPlan` และ `registerMemoryRuntime` คือ API Plugin memory แบบเฉพาะที่รองรับความเข้ากันได้กับแบบเดิม +- `MemoryFlushPlan.model` สามารถตรึงรอบ flush ไปยังการอ้างอิง `provider/model` ที่แน่นอนได้ เช่น `ollama/qwen3:8b` โดยไม่สืบทอด fallback chain ที่ใช้งานอยู่ +- `registerMemoryEmbeddingProvider` ช่วยให้ Plugin memory ที่ใช้งานอยู่ลงทะเบียน id ของ adapter embedding ได้หนึ่งรายการหรือมากกว่า เช่น `openai`, `gemini` หรือ id แบบกำหนดเองที่ Plugin กำหนด +- config ของผู้ใช้ เช่น `agents.defaults.memorySearch.provider` และ `agents.defaults.memorySearch.fallback` จะ resolve เทียบกับ id adapter ที่ลงทะเบียนเหล่านั้น -### เหตุการณ์และวงจรชีวิต +### เหตุการณ์และ lifecycle | เมธอด | สิ่งที่ทำ | | -------------------------------------------- | ----------------------------- | -| `api.on(hookName, handler, opts?)` | lifecycle hook แบบ typed | -| `api.onConversationBindingResolved(handler)` | callback สำหรับ conversation binding | +| `api.on(hookName, handler, opts?)` | hook lifecycle แบบ typed | +| `api.onConversationBindingResolved(handler)` | callback การผูก conversation | -ดู [Plugin hooks](/th/plugins/hooks) สำหรับตัวอย่าง ชื่อ hook ทั่วไป และ semantics ของ guard +ดู [hook ของ Plugin](/th/plugins/hooks) สำหรับตัวอย่าง ชื่อ hook ที่พบบ่อย และ semantics ของ guard -### semantics การตัดสินใจของ Hook +### Semantics การตัดสินใจของ hook -- `before_tool_call`: การส่งคืน `{ block: true }` เป็นผลลัพธ์สุดท้าย เมื่อ handler ใดตั้งค่าแล้ว handler ที่มีลำดับความสำคัญต่ำกว่าจะถูกข้าม -- `before_tool_call`: การส่งคืน `{ block: false }` จะถือว่าไม่มีการตัดสินใจ (เหมือนกับการละ `block`) ไม่ใช่การ override -- `before_install`: การส่งคืน `{ block: true }` เป็นผลลัพธ์สุดท้าย เมื่อ handler ใดตั้งค่าแล้ว handler ที่มีลำดับความสำคัญต่ำกว่าจะถูกข้าม -- `before_install`: การส่งคืน `{ block: false }` จะถือว่าไม่มีการตัดสินใจ (เหมือนกับการละ `block`) ไม่ใช่การ override -- `reply_dispatch`: การส่งคืน `{ handled: true, ... }` เป็นผลลัพธ์สุดท้าย เมื่อ handler ใดอ้างสิทธิ์การ dispatch แล้ว handler ที่มีลำดับความสำคัญต่ำกว่าและเส้นทางการ dispatch ไปยังโมเดลเริ่มต้นจะถูกข้าม -- `message_sending`: การส่งคืน `{ cancel: true }` เป็นผลลัพธ์สุดท้าย เมื่อ handler ใดตั้งค่าแล้ว handler ที่มีลำดับความสำคัญต่ำกว่าจะถูกข้าม -- `message_sending`: การส่งคืน `{ cancel: false }` จะถือว่าไม่มีการตัดสินใจ (เหมือนกับการละ `cancel`) ไม่ใช่การ override -- `message_received`: ใช้ฟิลด์ typed `threadId` เมื่อคุณต้องการการกำหนดเส้นทาง thread/topic ขาเข้า เก็บ `metadata` ไว้สำหรับส่วนเสริมเฉพาะ channel +- `before_tool_call`: การส่งกลับ `{ block: true }` ถือเป็น terminal เมื่อ handler ใดตั้งค่านี้แล้ว handler ที่ priority ต่ำกว่าจะถูกข้าม +- `before_tool_call`: การส่งกลับ `{ block: false }` จะถูกถือว่าไม่มีการตัดสินใจ (เหมือนกับละเว้น `block`) ไม่ใช่การ override +- `before_install`: การส่งกลับ `{ block: true }` ถือเป็น terminal เมื่อ handler ใดตั้งค่านี้แล้ว handler ที่ priority ต่ำกว่าจะถูกข้าม +- `before_install`: การส่งกลับ `{ block: false }` จะถูกถือว่าไม่มีการตัดสินใจ (เหมือนกับละเว้น `block`) ไม่ใช่การ override +- `reply_dispatch`: การส่งกลับ `{ handled: true, ... }` ถือเป็น terminal เมื่อ handler ใด claim dispatch แล้ว handler ที่ priority ต่ำกว่าและเส้นทาง dispatch โมเดลเริ่มต้นจะถูกข้าม +- `message_sending`: การส่งกลับ `{ cancel: true }` ถือเป็น terminal เมื่อ handler ใดตั้งค่านี้แล้ว handler ที่ priority ต่ำกว่าจะถูกข้าม +- `message_sending`: การส่งกลับ `{ cancel: false }` จะถูกถือว่าไม่มีการตัดสินใจ (เหมือนกับละเว้น `cancel`) ไม่ใช่การ override +- `message_received`: ใช้ฟิลด์ typed `threadId` เมื่อคุณต้องการการกำหนดเส้นทาง thread/topic ขาเข้า เก็บ `metadata` ไว้สำหรับส่วนเพิ่มเติมเฉพาะ channel - `message_sending`: ใช้ฟิลด์การกำหนดเส้นทาง typed `replyToId` / `threadId` ก่อน fallback ไปยัง `metadata` เฉพาะ channel -- `gateway_start`: ใช้ `ctx.config`, `ctx.workspaceDir` และ `ctx.getCron?.()` สำหรับสถานะเริ่มต้นที่ Gateway เป็นเจ้าของ แทนการพึ่งพา hook ภายใน `gateway:startup` -- `cron_changed`: สังเกตการเปลี่ยนแปลงวงจรชีวิต Cron ที่ Gateway เป็นเจ้าของ ใช้ `event.job?.state?.nextRunAtMs` และ `ctx.getCron?.()` เมื่อ sync ตัวตั้งปลุกภายนอก และคงให้ OpenClaw เป็นแหล่งข้อมูลจริงสำหรับการตรวจสอบงานที่ครบกำหนดและการดำเนินการ +- `gateway_start`: ใช้ `ctx.config`, `ctx.workspaceDir` และ `ctx.getCron?.()` สำหรับสถานะ startup ที่ Gateway เป็นเจ้าของ แทนการพึ่งพา hook ภายใน `gateway:startup` +- `cron_changed`: สังเกตการเปลี่ยนแปลง lifecycle ของ Cron ที่ Gateway เป็นเจ้าของ ใช้ `event.job?.state?.nextRunAtMs` และ `ctx.getCron?.()` เมื่อซิงค์ตัวจัดตาราง wake ภายนอก และคงให้ OpenClaw เป็นแหล่งข้อมูลจริงสำหรับการตรวจสอบงานถึงกำหนดและการดำเนินการ -### ฟิลด์ของอ็อบเจกต์ API +### ฟิลด์ของออบเจ็กต์ API -| ฟิลด์ | ประเภท | คำอธิบาย | +| ฟิลด์ | ชนิด | คำอธิบาย | | ------------------------ | ------------------------- | ------------------------------------------------------------------------------------------- | | `api.id` | `string` | id ของ Plugin | | `api.name` | `string` | ชื่อที่แสดง | | `api.version` | `string?` | เวอร์ชันของ Plugin (ไม่บังคับ) | -| `api.description` | `string?` | คำอธิบายของ Plugin (ไม่บังคับ) | -| `api.source` | `string` | path ของแหล่งที่มา Plugin | +| `api.description` | `string?` | คำอธิบาย Plugin (ไม่บังคับ) | +| `api.source` | `string` | เส้นทาง source ของ Plugin | | `api.rootDir` | `string?` | ไดเรกทอรีรากของ Plugin (ไม่บังคับ) | -| `api.config` | `OpenClawConfig` | snapshot ของ config ปัจจุบัน (snapshot runtime ในหน่วยความจำที่ใช้งานอยู่เมื่อมี) | +| `api.config` | `OpenClawConfig` | snapshot config ปัจจุบัน (snapshot runtime ในหน่วยความจำที่ใช้งานอยู่เมื่อมีให้ใช้) | | `api.pluginConfig` | `Record` | config เฉพาะ Plugin จาก `plugins.entries..config` | | `api.runtime` | `PluginRuntime` | [ตัวช่วย runtime](/th/plugins/sdk-runtime) | -| `api.logger` | `PluginLogger` | logger ตาม scope (`debug`, `info`, `warn`, `error`) | -| `api.registrationMode` | `PluginRegistrationMode` | โหมดการโหลดปัจจุบัน; `"setup-runtime"` คือช่วง startup/setup แบบเบาก่อน full-entry | -| `api.resolvePath(input)` | `(string) => string` | resolve path ที่สัมพันธ์กับราก Plugin | +| `api.logger` | `PluginLogger` | logger แบบ scoped (`debug`, `info`, `warn`, `error`) | +| `api.registrationMode` | `PluginRegistrationMode` | โหมดการโหลดปัจจุบัน; `"setup-runtime"` คือหน้าต่าง startup/setup แบบ lightweight ก่อน full-entry | +| `api.resolvePath(input)` | `(string) => string` | resolve เส้นทางแบบสัมพันธ์กับรากของ Plugin | -## ข้อตกลงของโมดูลภายใน +## Convention ของโมดูลภายใน -ภายใน Plugin ของคุณ ให้ใช้ไฟล์ barrel ภายในเครื่องสำหรับการ import ภายใน: +ภายใน Plugin ของคุณ ให้ใช้ไฟล์ barrel ในเครื่องสำหรับ import ภายใน: ``` my-plugin/ @@ -335,48 +327,34 @@ my-plugin/ ``` - อย่า import Plugin ของคุณเองผ่าน `openclaw/plugin-sdk/` + ห้าม import Plugin ของคุณเองผ่าน `openclaw/plugin-sdk/` จากโค้ด production ให้กำหนดเส้นทาง import ภายในผ่าน `./api.ts` หรือ - `./runtime-api.ts` path ของ SDK เป็นสัญญาภายนอกเท่านั้น + `./runtime-api.ts` เส้นทาง SDK เป็นสัญญาภายนอกเท่านั้น -พื้นผิวสาธารณะของ Plugin ที่ bundled และโหลดผ่าน facade (`api.ts`, `runtime-api.ts`, -`index.ts`, `setup-entry.ts` และไฟล์ entry สาธารณะลักษณะเดียวกัน) จะเลือกใช้ -snapshot config runtime ที่ใช้งานอยู่เมื่อ OpenClaw กำลังทำงานอยู่ หากยังไม่มี -snapshot runtime จะ fallback ไปยังไฟล์ config ที่ resolve ได้บนดิสก์ -facade ของ Plugin ที่ bundled แบบ packaged ควรถูกโหลดผ่าน loader facade ของ Plugin -ของ OpenClaw; การ import โดยตรงจาก `dist/extensions/...` จะข้ามการตรวจ manifest -และ runtime sidecar ที่การติดตั้งแบบ packaged ใช้สำหรับโค้ดที่ Plugin เป็นเจ้าของ +พื้นผิวสาธารณะของ Plugin ที่ bundled และโหลดผ่าน facade (`api.ts`, `runtime-api.ts`, `index.ts`, `setup-entry.ts` และไฟล์ entry สาธารณะที่คล้ายกัน) จะเลือกใช้ snapshot config runtime ที่ใช้งานอยู่เมื่อ OpenClaw กำลังรันอยู่ หากยังไม่มี snapshot runtime จะ fallback ไปยังไฟล์ config ที่ resolve แล้วบนดิสก์ facade ของ Plugin bundled ที่ package แล้วควรถูกโหลดผ่านตัวโหลด facade ของ Plugin ใน OpenClaw; การ import โดยตรงจาก `dist/extensions/...` จะข้าม manifest และการตรวจสอบ sidecar ของ runtime ที่การติดตั้งแบบ packaged ใช้สำหรับโค้ดที่ Plugin เป็นเจ้าของ -Plugin ผู้ให้บริการสามารถเปิดเผย contract barrel เฉพาะ Plugin แบบแคบได้ เมื่อ -helper ตั้งใจให้เฉพาะผู้ให้บริการจริง ๆ และยังไม่เหมาะอยู่ใน subpath SDK ทั่วไป -ตัวอย่างที่ bundled: +Plugin provider สามารถเปิดเผย barrel สัญญาแบบแคบในเครื่องของ Plugin ได้ เมื่อ helper นั้นตั้งใจให้เฉพาะกับ provider และยังไม่ควรอยู่ใน subpath SDK ทั่วไป ตัวอย่างแบบ bundled: -- **Anthropic**: seam สาธารณะ `api.ts` / `contract-api.ts` สำหรับ helper ของ Claude - beta-header และ stream `service_tier` -- **`@openclaw/openai-provider`**: `api.ts` export provider builder, - helper สำหรับโมเดลเริ่มต้น และ realtime provider builder -- **`@openclaw/openrouter-provider`**: `api.ts` export provider builder - รวมถึง helper onboarding/config +- **Anthropic**: seam `api.ts` / `contract-api.ts` สาธารณะสำหรับ helper สตรีม beta-header และ `service_tier` ของ Claude +- **`@openclaw/openai-provider`**: `api.ts` export ตัวสร้าง provider, helper โมเดลเริ่มต้น และตัวสร้าง provider realtime +- **`@openclaw/openrouter-provider`**: `api.ts` export ตัวสร้าง provider พร้อม helper onboarding/config - โค้ด production ของ Extension ควรหลีกเลี่ยงการ import - `openclaw/plugin-sdk/` ด้วย หาก helper ถูกใช้ร่วมกันอย่างแท้จริง ให้ยกระดับไปยัง subpath SDK ที่เป็นกลาง - เช่น `openclaw/plugin-sdk/speech`, `.../provider-model-shared` หรือพื้นผิวอื่นที่มุ่งตาม capability - แทนการผูก Plugin สองตัวเข้าด้วยกัน + โค้ด production ของ Extension ควรหลีกเลี่ยง import `openclaw/plugin-sdk/` ด้วย หาก helper นั้นแชร์กันจริง ให้ยกระดับไปยัง subpath SDK ที่เป็นกลาง เช่น `openclaw/plugin-sdk/speech`, `.../provider-model-shared` หรือพื้นผิวอื่นที่เน้น capability แทนการผูก Plugin สองตัวเข้าด้วยกัน ## ที่เกี่ยวข้อง - ตัวเลือกของ `definePluginEntry` และ `defineChannelPluginEntry` + ตัวเลือก `definePluginEntry` และ `defineChannelPluginEntry` - ข้อมูลอ้างอิง namespace `api.runtime` ฉบับเต็ม + ข้อมูลอ้างอิงเนมสเปซ `api.runtime` ฉบับเต็ม - - การจัดแพ็กเกจ, manifest, และ schema การกำหนดค่า + + การจัดแพ็กเกจ, manifest และสคีมาการกำหนดค่า ยูทิลิตีทดสอบและกฎ lint @@ -384,7 +362,7 @@ helper ตั้งใจให้เฉพาะผู้ให้บริก การย้ายจากพื้นผิวที่เลิกใช้แล้ว - + สถาปัตยกรรมเชิงลึกและโมเดลความสามารถ diff --git a/docs/th/security/network-proxy.md b/docs/th/security/network-proxy.md index d6a999e1a..7e46b6faa 100644 --- a/docs/th/security/network-proxy.md +++ b/docs/th/security/network-proxy.md @@ -1,40 +1,40 @@ --- read_when: - - คุณต้องการการป้องกันเชิงลึกจากการโจมตีแบบ SSRF และการผูก DNS ใหม่ - - การกำหนดค่าพร็อกซีแบบส่งต่อภายนอกสำหรับทราฟฟิกขณะรันไทม์ของ OpenClaw -summary: วิธีกำหนดเส้นทางทราฟฟิก HTTP และ WebSocket ของรันไทม์ OpenClaw ผ่านพร็อกซีกรองที่จัดการโดยผู้ปฏิบัติการ + - คุณต้องการการป้องกันแบบหลายชั้นจากการโจมตี SSRF และการโจมตีด้วยการผูก DNS ใหม่ + - การกำหนดค่าพร็อกซีส่งต่อภายนอกสำหรับทราฟฟิกขณะรันไทม์ของ OpenClaw +summary: วิธีกำหนดเส้นทางการรับส่งข้อมูล HTTP และ WebSocket ของรันไทม์ OpenClaw ผ่านพร็อกซีกรองที่จัดการโดยผู้ปฏิบัติการ title: พร็อกซีเครือข่าย x-i18n: - generated_at: "2026-05-04T07:07:03Z" + generated_at: "2026-05-04T18:24:44Z" model: gpt-5.5 provider: openai - source_hash: fc7140c5ced0e7454a6f85d1ea8f3256bbd28cc0cb42eeafe8e5e6439b90e3f0 + source_hash: eedbf3bac14800c34c7ca2e3b6879dac360a88d51b5b7449ddf41a4dd471648b source_path: security/network-proxy.md workflow: 16 --- # พร็อกซีเครือข่าย -OpenClaw สามารถกำหนดเส้นทางทราฟฟิก HTTP และ WebSocket ขณะรันไทม์ผ่านพร็อกซีส่งต่อที่ผู้ปฏิบัติงานจัดการได้ นี่เป็นการป้องกันเชิงลึกแบบเลือกใช้ สำหรับการปรับใช้ที่ต้องการควบคุมทราฟฟิกขาออกจากศูนย์กลาง เพิ่มการป้องกัน SSRF ให้แข็งแรงขึ้น และตรวจสอบเครือข่ายได้ดียิ่งขึ้น +OpenClaw สามารถกำหนดเส้นทางทราฟฟิก HTTP และ WebSocket ระหว่างรันไทม์ผ่านพร็อกซีส่งต่อที่ผู้ปฏิบัติการจัดการได้ นี่เป็นการป้องกันเชิงลึกแบบไม่บังคับสำหรับการปรับใช้ที่ต้องการควบคุมทราฟฟิกขาออกจากศูนย์กลาง เพิ่มการป้องกัน SSRF ให้แข็งแรงขึ้น และตรวจสอบเครือข่ายได้ดียิ่งขึ้น -OpenClaw ไม่ได้จัดส่ง ดาวน์โหลด เริ่มต้น กำหนดค่า หรือรับรองพร็อกซี คุณเป็นผู้รันเทคโนโลยีพร็อกซีที่เหมาะกับสภาพแวดล้อมของคุณ และ OpenClaw จะกำหนดเส้นทางไคลเอนต์ HTTP และ WebSocket ภายในโปรเซสตามปกติผ่านพร็อกซีนั้น +OpenClaw ไม่ได้จัดส่ง ดาวน์โหลด เริ่มต้น กำหนดค่า หรือรับรองพร็อกซี คุณรันเทคโนโลยีพร็อกซีที่เหมาะกับสภาพแวดล้อมของคุณ และ OpenClaw จะกำหนดเส้นทางไคลเอนต์ HTTP และ WebSocket แบบปกติที่อยู่ภายในโพรเซสผ่านพร็อกซีนั้น ## ทำไมต้องใช้พร็อกซี? -พร็อกซีให้จุดควบคุมเครือข่ายจุดเดียวแก่ผู้ปฏิบัติงานสำหรับทราฟฟิก HTTP และ WebSocket ขาออก ซึ่งมีประโยชน์ได้แม้อยู่นอกเหนือจากการเสริมความแข็งแรงเพื่อป้องกัน SSRF: +พร็อกซีให้จุดควบคุมเครือข่ายหนึ่งจุดแก่ผู้ปฏิบัติการสำหรับทราฟฟิก HTTP และ WebSocket ขาออก สิ่งนี้มีประโยชน์ได้แม้นอกเหนือจากการเสริมความแข็งแกร่งด้าน SSRF: -- นโยบายส่วนกลาง: ดูแลนโยบายขาออกเพียงชุดเดียว แทนที่จะพึ่งให้ทุกจุดเรียก HTTP ของแอปพลิเคชันกำหนดกฎเครือข่ายให้ถูกต้องเอง -- การตรวจสอบ ณ เวลาเชื่อมต่อ: ประเมินปลายทางหลังการแก้ชื่อ DNS และทันทีก่อนที่พร็อกซีจะเปิดการเชื่อมต่อต้นทาง +- นโยบายส่วนกลาง: ดูแลนโยบายขาออกเพียงชุดเดียว แทนที่จะต้องพึ่งพาให้ทุกจุดเรียก HTTP ของแอปพลิเคชันตั้งกฎเครือข่ายให้ถูกต้อง +- การตรวจสอบขณะเชื่อมต่อ: ประเมินปลายทางหลังจากการแปลง DNS และทันทีก่อนที่พร็อกซีจะเปิดการเชื่อมต่ออัปสตรีม - การป้องกัน DNS rebinding: ลดช่องว่างระหว่างการตรวจสอบ DNS ระดับแอปพลิเคชันกับการเชื่อมต่อขาออกจริง -- ครอบคลุม JavaScript กว้างขึ้น: กำหนดเส้นทางไคลเอนต์ทั่วไปอย่าง `fetch`, `node:http`, `node:https`, WebSocket, axios, got, node-fetch และไคลเอนต์ลักษณะใกล้เคียงผ่านเส้นทางเดียวกัน -- การตรวจสอบย้อนหลัง: บันทึกปลายทางที่อนุญาตและปฏิเสธไว้ที่ขอบเขตทราฟฟิกขาออก -- การควบคุมเชิงปฏิบัติการ: บังคับใช้กฎปลายทาง การแบ่งส่วนเครือข่าย การจำกัดอัตรา หรือ allowlist ขาออกได้โดยไม่ต้องสร้าง OpenClaw ใหม่ +- ครอบคลุม JavaScript กว้างขึ้น: กำหนดเส้นทางไคลเอนต์ทั่วไปอย่าง `fetch`, `node:http`, `node:https`, WebSocket, axios, got, node-fetch และไคลเอนต์ที่คล้ายกันผ่านเส้นทางเดียวกัน +- ความสามารถในการตรวจสอบ: บันทึกปลายทางที่อนุญาตและปฏิเสธที่ขอบเขตขาออก +- การควบคุมเชิงปฏิบัติการ: บังคับใช้กฎปลายทาง การแบ่งส่วนเครือข่าย ขีดจำกัดอัตรา หรือรายการอนุญาตขาออกโดยไม่ต้องสร้าง OpenClaw ใหม่ -การกำหนดเส้นทางพร็อกซีเป็นกรอบป้องกันระดับโปรเซสสำหรับ HTTP และ WebSocket ขาออกตามปกติ ช่วยให้ผู้ปฏิบัติงานมีเส้นทางแบบ fail-closed สำหรับกำหนดเส้นทางไคลเอนต์ HTTP ของ JavaScript ที่รองรับผ่านพร็อกซีกรองข้อมูลของตนเอง แต่ไม่ใช่ sandbox เครือข่ายระดับ OS และไม่ได้ทำให้ OpenClaw รับรองนโยบายปลายทางของพร็อกซี +การกำหนดเส้นทางผ่านพร็อกซีเป็นแนวป้องกันระดับโพรเซสสำหรับขาออก HTTP และ WebSocket แบบปกติ โดยให้เส้นทางแบบปิดเมื่อผิดพลาดแก่ผู้ปฏิบัติการสำหรับการกำหนดเส้นทางไคลเอนต์ HTTP ของ JavaScript ที่รองรับผ่านพร็อกซีกรองของตนเอง แต่ไม่ใช่แซนด์บ็อกซ์เครือข่ายระดับระบบปฏิบัติการ และไม่ได้ทำให้ OpenClaw รับรองนโยบายปลายทางของพร็อกซี ## OpenClaw กำหนดเส้นทางทราฟฟิกอย่างไร -เมื่อ `proxy.enabled=true` และมีการกำหนดค่า URL พร็อกซี โปรเซสรันไทม์ที่ได้รับการปกป้อง เช่น `openclaw gateway run`, `openclaw node run` และ `openclaw agent --local` จะกำหนดเส้นทาง HTTP และ WebSocket ขาออกตามปกติผ่านพร็อกซีที่กำหนดค่าไว้: +เมื่อกำหนด `proxy.enabled=true` และตั้งค่า URL ของพร็อกซีไว้ โพรเซสรันไทม์ที่ได้รับการป้องกัน เช่น `openclaw gateway run`, `openclaw node run` และ `openclaw agent --local` จะกำหนดเส้นทางขาออก HTTP และ WebSocket แบบปกติผ่านพร็อกซีที่กำหนดค่าไว้: ```text OpenClaw process @@ -43,27 +43,27 @@ OpenClaw process WebSocket clients -> operator-managed filtering proxy -> public internet ``` -สัญญาสาธารณะคือพฤติกรรมการกำหนดเส้นทาง ไม่ใช่ hook ภายในของ Node ที่ใช้ในการนำไปใช้งาน ไคลเอนต์ WebSocket ใน control plane ของ OpenClaw Gateway ใช้เส้นทางตรงแบบแคบสำหรับทราฟฟิก RPC ของ Gateway ผ่าน local loopback เมื่อ URL ของ Gateway ใช้ `localhost` หรือ IP loopback แบบ literal เช่น `127.0.0.1` หรือ `[::1]` เส้นทาง control plane นั้นต้องสามารถเข้าถึง Gateway บน loopback ได้แม้พร็อกซีของผู้ปฏิบัติงานจะบล็อกปลายทาง loopback ก็ตาม คำขอ HTTP และ WebSocket ของรันไทม์ตามปกติยังคงใช้พร็อกซีที่กำหนดค่าไว้ +สัญญาสาธารณะคือพฤติกรรมการกำหนดเส้นทาง ไม่ใช่ฮุกภายในของ Node ที่ใช้ในการติดตั้งใช้งาน ไคลเอนต์ WebSocket ของ control plane สำหรับ OpenClaw Gateway ใช้เส้นทางตรงแบบแคบสำหรับทราฟฟิก RPC ของ Gateway แบบ local loopback เมื่อ URL ของ Gateway ใช้ `localhost` หรือ IP loopback แบบตัวอักษร เช่น `127.0.0.1` หรือ `[::1]` เส้นทาง control plane นั้นต้องเข้าถึง Gateway แบบ loopback ได้ แม้พร็อกซีของผู้ปฏิบัติการจะบล็อกปลายทาง loopback คำขอ HTTP และ WebSocket ระหว่างรันไทม์แบบปกติยังคงใช้พร็อกซีที่กำหนดค่าไว้ -ภายใน OpenClaw ใช้ hook การกำหนดเส้นทางระดับโปรเซสสองแบบสำหรับฟีเจอร์นี้: +ภายใน OpenClaw ใช้ฮุกกำหนดเส้นทางระดับโพรเซสสองตัวสำหรับฟีเจอร์นี้: -- การกำหนดเส้นทางด้วย dispatcher ของ Undici ครอบคลุม `fetch`, ไคลเอนต์ที่มี undici รองรับ และ transport ที่มี dispatcher ของ undici เป็นของตนเอง -- การกำหนดเส้นทางด้วย `global-agent` ครอบคลุมผู้เรียก Node core `node:http` และ `node:https` รวมถึงไลบรารีจำนวนมากที่ต่อยอดบน `http.request`, `https.request`, `http.get` และ `https.get` โหมดพร็อกซีที่จัดการจะบังคับใช้ global agent นั้น เพื่อไม่ให้ agent ของ Node HTTP ที่ระบุไว้โดยตรงข้ามพร็อกซีของผู้ปฏิบัติงานโดยไม่ตั้งใจ +- การกำหนดเส้นทาง dispatcher ของ Undici ครอบคลุม `fetch`, ไคลเอนต์ที่มี undici รองรับ และ transport ที่จัดเตรียม dispatcher ของ undici เอง +- การกำหนดเส้นทาง `global-agent` ครอบคลุมผู้เรียก Node core อย่าง `node:http` และ `node:https` รวมถึงไลบรารีจำนวนมากที่วางซ้อนบน `http.request`, `https.request`, `http.get` และ `https.get` โหมดพร็อกซีที่จัดการจะบังคับใช้ global agent นั้น เพื่อไม่ให้เอเจนต์ HTTP ของ Node ที่ระบุชัดเจนข้ามพร็อกซีของผู้ปฏิบัติการโดยไม่ตั้งใจ -Plugin บางตัวมี transport แบบกำหนดเองที่ต้องเดินสายพร็อกซีอย่างชัดเจน แม้จะมีการกำหนดเส้นทางระดับโปรเซสอยู่แล้วก็ตาม ตัวอย่างเช่น transport ของ Bot API ใน Telegram ใช้ HTTP/1 undici dispatcher ของตัวเอง จึงเคารพ env พร็อกซีของโปรเซส รวมถึง fallback `OPENCLAW_PROXY_URL` ที่จัดการในเส้นทาง transport เฉพาะเจ้าของนั้น +Plugin บางตัวเป็นเจ้าของ transport แบบกำหนดเองที่ต้องเดินสายพร็อกซีอย่างชัดเจน แม้จะมีการกำหนดเส้นทางระดับโพรเซสอยู่แล้ว ตัวอย่างเช่น transport ของ Telegram Bot API ใช้ dispatcher HTTP/1 ของ undici ของตัวเอง ดังนั้นจึงเคารพ env ของพร็อกซีโพรเซสพร้อม fallback `OPENCLAW_PROXY_URL` ที่จัดการแล้วในเส้นทาง transport เฉพาะเจ้าของนั้น -URL ของพร็อกซีเองต้องใช้ `http://` ปลายทาง HTTPS ยังคงรองรับผ่านพร็อกซีด้วย HTTP `CONNECT`; นี่หมายความเพียงว่า OpenClaw คาดหวัง listener ของพร็อกซีส่งต่อ HTTP แบบธรรมดา เช่น `http://127.0.0.1:3128` +URL ของพร็อกซีเองต้องใช้ `http://` ปลายทาง HTTPS ยังคงรองรับผ่านพร็อกซีด้วย HTTP `CONNECT`; นี่หมายความเพียงว่า OpenClaw คาดหวัง listener ของพร็อกซีส่งต่อแบบ HTTP ธรรมดา เช่น `http://127.0.0.1:3128` -ขณะที่พร็อกซีทำงานอยู่ OpenClaw จะล้าง `no_proxy`, `NO_PROXY` และ `GLOBAL_AGENT_NO_PROXY` รายการข้ามเหล่านี้อิงตามปลายทาง ดังนั้นหากปล่อย `localhost` หรือ `127.0.0.1` ไว้ในนั้น จะทำให้เป้าหมาย SSRF ความเสี่ยงสูงข้ามพร็อกซีกรองข้อมูลได้ +ขณะที่พร็อกซีทำงานอยู่ OpenClaw จะล้าง `no_proxy`, `NO_PROXY` และ `GLOBAL_AGENT_NO_PROXY` รายการข้ามเหล่านั้นอิงตามปลายทาง ดังนั้นหากปล่อย `localhost` หรือ `127.0.0.1` ไว้ในนั้น จะทำให้เป้าหมาย SSRF ที่มีความเสี่ยงสูงข้ามพร็อกซีกรองได้ -เมื่อปิดการทำงาน OpenClaw จะกู้คืนสภาพแวดล้อมพร็อกซีก่อนหน้าและรีเซ็ตสถานะการกำหนดเส้นทางของโปรเซสที่แคชไว้ +เมื่อปิดระบบ OpenClaw จะกู้คืนสภาพแวดล้อมพร็อกซีก่อนหน้าและรีเซ็ตสถานะการกำหนดเส้นทางโพรเซสที่แคชไว้ -## คำศัพท์เกี่ยวกับพร็อกซีที่เกี่ยวข้อง +## คำที่เกี่ยวข้องกับพร็อกซี -- `proxy.enabled` / `proxy.proxyUrl`: การกำหนดเส้นทางพร็อกซีส่งต่อขาออกสำหรับทราฟฟิกขาออกของรันไทม์ OpenClaw หน้านี้อธิบายฟีเจอร์นั้น -- `gateway.auth.mode: "trusted-proxy"`: การยืนยันตัวตนขาเข้าผ่าน reverse proxy ที่รับรู้ตัวตนสำหรับการเข้าถึง Gateway ดู [การยืนยันตัวตนผ่านพร็อกซีที่เชื่อถือได้](/th/gateway/trusted-proxy-auth) -- `openclaw proxy`: พร็อกซีดีบักในเครื่องและตัวตรวจสอบการจับข้อมูลสำหรับการพัฒนาและการสนับสนุน ดู [openclaw proxy](/th/cli/proxy) -- การตั้งค่าพร็อกซีเฉพาะช่องทางหรือ provider: override เฉพาะเจ้าของสำหรับ transport รายใดรายหนึ่ง ควรใช้พร็อกซีเครือข่ายที่จัดการเมื่อเป้าหมายคือการควบคุมทราฟฟิกขาออกจากศูนย์กลางทั่วทั้งรันไทม์ +- `proxy.enabled` / `proxy.proxyUrl`: การกำหนดเส้นทางผ่านพร็อกซีส่งต่อขาออกสำหรับทราฟฟิกขาออกระหว่างรันไทม์ของ OpenClaw หน้านี้บันทึกฟีเจอร์นั้น +- `gateway.auth.mode: "trusted-proxy"`: การยืนยันตัวตนผ่าน reverse proxy ฝั่งขาเข้าที่รับรู้อัตลักษณ์สำหรับการเข้าถึง Gateway ดู [การยืนยันตัวตนผ่านพร็อกซีที่เชื่อถือได้](/th/gateway/trusted-proxy-auth) +- `openclaw proxy`: พร็อกซีดีบักเฉพาะเครื่องและตัวตรวจสอบการจับข้อมูลสำหรับการพัฒนาและการสนับสนุน ดู [openclaw proxy](/th/cli/proxy) +- การตั้งค่าพร็อกซีเฉพาะช่องทางหรือผู้ให้บริการ: การ override เฉพาะเจ้าของสำหรับ transport เฉพาะตัว ควรใช้พร็อกซีเครือข่ายที่จัดการเมื่อเป้าหมายคือการควบคุมทราฟฟิกขาออกจากศูนย์กลางทั่วทั้งรันไทม์ ## การกำหนดค่า @@ -73,7 +73,7 @@ proxy: proxyUrl: http://127.0.0.1:3128 ``` -คุณยังสามารถระบุ URL ผ่านสภาพแวดล้อมได้ โดยยังคงตั้ง `proxy.enabled=true` ไว้ใน config: +คุณยังสามารถระบุ URL ผ่านสภาพแวดล้อมได้ โดยยังคงตั้ง `proxy.enabled=true` ไว้ในการกำหนดค่า: ```bash OPENCLAW_PROXY_URL=http://127.0.0.1:3128 openclaw gateway run @@ -81,9 +81,9 @@ OPENCLAW_PROXY_URL=http://127.0.0.1:3128 openclaw gateway run `proxy.proxyUrl` มีลำดับความสำคัญเหนือ `OPENCLAW_PROXY_URL` -หาก `enabled=true` แต่ไม่มี URL พร็อกซีที่ถูกต้องกำหนดไว้ คำสั่งที่ได้รับการปกป้องจะเริ่มต้นล้มเหลวแทนที่จะ fallback ไปใช้การเข้าถึงเครือข่ายโดยตรง +หาก `enabled=true` แต่ไม่ได้กำหนดค่า URL ของพร็อกซีที่ถูกต้อง คำสั่งที่ได้รับการป้องกันจะล้มเหลวระหว่างเริ่มต้น แทนที่จะย้อนกลับไปใช้การเข้าถึงเครือข่ายโดยตรง -สำหรับบริการ gateway ที่จัดการซึ่งเริ่มด้วย `openclaw gateway start` ควรเก็บ URL ไว้ใน config: +สำหรับบริการ Gateway ที่จัดการซึ่งเริ่มด้วย `openclaw gateway start` แนะนำให้เก็บ URL ไว้ในการกำหนดค่า: ```bash openclaw config set proxy.enabled true @@ -92,51 +92,51 @@ openclaw gateway install --force openclaw gateway start ``` -fallback ผ่านสภาพแวดล้อมเหมาะที่สุดสำหรับการรันแบบ foreground หากคุณใช้กับบริการที่ติดตั้งแล้ว ให้ใส่ `OPENCLAW_PROXY_URL` ในสภาพแวดล้อมถาวรของบริการ เช่น `$OPENCLAW_STATE_DIR/.env` หรือ `~/.openclaw/.env` แล้วติดตั้งบริการใหม่ เพื่อให้ launchd, systemd หรือ Scheduled Tasks เริ่ม gateway พร้อมค่านั้น +fallback ผ่านสภาพแวดล้อมเหมาะที่สุดสำหรับการรันแบบ foreground หากคุณใช้กับบริการที่ติดตั้งแล้ว ให้ใส่ `OPENCLAW_PROXY_URL` ในสภาพแวดล้อมถาวรของบริการ เช่น `$OPENCLAW_STATE_DIR/.env` หรือ `~/.openclaw/.env` จากนั้นติดตั้งบริการใหม่เพื่อให้ launchd, systemd หรือ Scheduled Tasks เริ่ม Gateway ด้วยค่านั้น -สำหรับคำสั่ง `openclaw --container ...` OpenClaw จะส่งต่อ `OPENCLAW_PROXY_URL` เข้าไปยัง CLI ลูกที่มีเป้าหมายเป็นคอนเทนเนอร์เมื่อมีการตั้งค่า URL ต้องเข้าถึงได้จากภายในคอนเทนเนอร์; `127.0.0.1` หมายถึงตัวคอนเทนเนอร์เอง ไม่ใช่โฮสต์ OpenClaw จะปฏิเสธ URL พร็อกซีแบบ loopback สำหรับคำสั่งที่มีเป้าหมายเป็นคอนเทนเนอร์ เว้นแต่คุณจะ override การตรวจสอบความปลอดภัยนั้นอย่างชัดเจน +สำหรับคำสั่ง `openclaw --container ...` OpenClaw จะส่งต่อ `OPENCLAW_PROXY_URL` เข้าไปยัง CLI ลูกที่กำหนดเป้าหมายไปยังคอนเทนเนอร์เมื่อมีการตั้งค่าไว้ URL ต้องเข้าถึงได้จากภายในคอนเทนเนอร์; `127.0.0.1` หมายถึงตัวคอนเทนเนอร์เอง ไม่ใช่โฮสต์ OpenClaw จะปฏิเสธ URL พร็อกซีแบบ loopback สำหรับคำสั่งที่กำหนดเป้าหมายไปยังคอนเทนเนอร์ เว้นแต่คุณจะ override การตรวจสอบความปลอดภัยนั้นอย่างชัดเจน ## ข้อกำหนดของพร็อกซี -นโยบายพร็อกซีคือขอบเขตความปลอดภัย OpenClaw ไม่สามารถตรวจสอบได้ว่าพร็อกซีบล็อกเป้าหมายที่ถูกต้องหรือไม่ +นโยบายพร็อกซีคือขอบเขตความปลอดภัย OpenClaw ไม่สามารถตรวจสอบว่าพร็อกซีบล็อกเป้าหมายที่ถูกต้องได้ กำหนดค่าพร็อกซีให้: -- bind เฉพาะกับ loopback หรืออินเทอร์เฟซส่วนตัวที่เชื่อถือได้ -- จำกัดการเข้าถึงเพื่อให้มีเพียงโปรเซส OpenClaw, โฮสต์, คอนเทนเนอร์ หรือบัญชีบริการเท่านั้นที่ใช้งานได้ -- แก้ชื่อปลายทางเองและบล็อก IP ปลายทางหลังการแก้ชื่อ DNS -- ใช้นโยบาย ณ เวลาเชื่อมต่อสำหรับทั้งคำขอ HTTP แบบธรรมดาและ tunnel HTTPS `CONNECT` -- ปฏิเสธการข้ามตามปลายทางสำหรับช่วง loopback, private, link-local, metadata, multicast, reserved หรือ documentation -- หลีกเลี่ยง allowlist ชื่อโฮสต์ เว้นแต่คุณจะเชื่อถือเส้นทางการแก้ชื่อ DNS อย่างเต็มที่ -- บันทึกปลายทาง การตัดสินใจ สถานะ และเหตุผล โดยไม่บันทึกเนื้อหาคำขอ header การอนุญาต cookie หรือความลับอื่นๆ -- เก็บนโยบายพร็อกซีไว้ในระบบควบคุมเวอร์ชันและรีวิวการเปลี่ยนแปลงเหมือนการกำหนดค่าที่อ่อนไหวด้านความปลอดภัย +- ผูกกับ loopback หรืออินเทอร์เฟซส่วนตัวที่เชื่อถือได้เท่านั้น +- จำกัดการเข้าถึงเพื่อให้เฉพาะโพรเซส โฮสต์ คอนเทนเนอร์ หรือบัญชีบริการของ OpenClaw เท่านั้นที่ใช้งานได้ +- แปลงปลายทางด้วยตัวเองและบล็อก IP ปลายทางหลังจากการแปลง DNS +- ใช้นโยบายขณะเชื่อมต่อสำหรับทั้งคำขอ HTTP แบบธรรมดาและอุโมงค์ HTTPS `CONNECT` +- ปฏิเสธการข้ามที่อิงตามปลายทางสำหรับ loopback, private, link-local, metadata, multicast, reserved หรือช่วงเอกสาร +- หลีกเลี่ยงรายการอนุญาตชื่อโฮสต์ เว้นแต่คุณจะเชื่อถือเส้นทางการแปลง DNS อย่างเต็มที่ +- บันทึกปลายทาง การตัดสินใจ สถานะ และเหตุผล โดยไม่บันทึกเนื้อหาคำขอ ส่วนหัว authorization คุกกี้ หรือความลับอื่นๆ +- เก็บนโยบายพร็อกซีไว้ภายใต้ระบบควบคุมเวอร์ชันและทบทวนการเปลี่ยนแปลงเหมือนการกำหนดค่าที่อ่อนไหวด้านความปลอดภัย ## ปลายทางที่แนะนำให้บล็อก -ใช้ denylist นี้เป็นจุดเริ่มต้นสำหรับพร็อกซีส่งต่อ ไฟร์วอลล์ หรือนโยบายทราฟฟิกขาออกใดๆ +ใช้ denylist นี้เป็นจุดเริ่มต้นสำหรับพร็อกซีส่งต่อ ไฟร์วอลล์ หรือนโยบายขาออกใดๆ -ตรรกะตัวจัดประเภทระดับแอปพลิเคชันของ OpenClaw อยู่ใน `src/infra/net/ssrf.ts` และ `src/shared/net/ip.ts` hook ที่เกี่ยวข้องสำหรับ parity คือ `BLOCKED_HOSTNAMES`, `BLOCKED_IPV4_SPECIAL_USE_RANGES`, `BLOCKED_IPV6_SPECIAL_USE_RANGES`, `RFC2544_BENCHMARK_PREFIX` และการจัดการ sentinel IPv4 แบบฝังสำหรับ NAT64, 6to4, Teredo, ISATAP และรูปแบบ IPv4-mapped ไฟล์เหล่านั้นเป็นข้อมูลอ้างอิงที่มีประโยชน์เมื่อดูแลนโยบายพร็อกซีภายนอก แต่ OpenClaw ไม่ได้ส่งออกหรือบังคับใช้กฎเหล่านั้นในพร็อกซีของคุณโดยอัตโนมัติ +ตรรกะ classifier ระดับแอปพลิเคชันของ OpenClaw อยู่ใน `src/infra/net/ssrf.ts` และ `src/shared/net/ip.ts` ฮุก parity ที่เกี่ยวข้องคือ `BLOCKED_HOSTNAMES`, `BLOCKED_IPV4_SPECIAL_USE_RANGES`, `BLOCKED_IPV6_SPECIAL_USE_RANGES`, `RFC2544_BENCHMARK_PREFIX` และการจัดการ sentinel ของ IPv4 ที่ฝังอยู่สำหรับ NAT64, 6to4, Teredo, ISATAP และรูปแบบ IPv4-mapped ไฟล์เหล่านั้นเป็นข้อมูลอ้างอิงที่มีประโยชน์เมื่อดูแลนโยบายพร็อกซีภายนอก แต่ OpenClaw ไม่ได้ส่งออกหรือบังคับใช้กฎเหล่านั้นในพร็อกซีของคุณโดยอัตโนมัติ | ช่วงหรือโฮสต์ | เหตุผลที่ควรบล็อก | | ------------------------------------------------------------------------------------ | ---------------------------------------------------- | | `127.0.0.0/8`, `localhost`, `localhost.localdomain` | IPv4 loopback | | `::1/128` | IPv6 loopback | -| `0.0.0.0/8`, `::/128` | ที่อยู่แบบไม่ระบุและที่อยู่ this-network | +| `0.0.0.0/8`, `::/128` | ที่อยู่แบบไม่ระบุและที่อยู่เครือข่ายนี้ | | `10.0.0.0/8`, `172.16.0.0/12`, `192.168.0.0/16` | เครือข่ายส่วนตัว RFC1918 | -| `169.254.0.0/16`, `fe80::/10` | ที่อยู่ link-local และเส้นทาง metadata ของคลาวด์ที่พบบ่อย | +| `169.254.0.0/16`, `fe80::/10` | ที่อยู่ link-local และเส้นทาง metadata คลาวด์ทั่วไป | | `169.254.169.254`, `metadata.google.internal` | บริการ metadata ของคลาวด์ | -| `100.64.0.0/10` | พื้นที่ที่อยู่ร่วมกันของ carrier-grade NAT | +| `100.64.0.0/10` | พื้นที่ที่อยู่ร่วมของ NAT ระดับผู้ให้บริการ | | `198.18.0.0/15`, `2001:2::/48` | ช่วงสำหรับ benchmarking | -| `192.0.0.0/24`, `192.0.2.0/24`, `198.51.100.0/24`, `203.0.113.0/24`, `2001:db8::/32` | ช่วง special-use และ documentation | +| `192.0.0.0/24`, `192.0.2.0/24`, `198.51.100.0/24`, `203.0.113.0/24`, `2001:db8::/32` | ช่วง special-use และเอกสาร | | `224.0.0.0/4`, `ff00::/8` | Multicast | | `240.0.0.0/4` | IPv4 ที่สงวนไว้ | -| `fc00::/7`, `fec0::/10` | ช่วง local/private ของ IPv6 | -| `100::/64`, `2001:20::/28` | ช่วง discard และ ORCHIDv2 ของ IPv6 | -| `64:ff9b::/96`, `64:ff9b:1::/48` | prefix NAT64 ที่มี IPv4 ฝังอยู่ | +| `fc00::/7`, `fec0::/10` | ช่วง IPv6 local/private | +| `100::/64`, `2001:20::/28` | ช่วง IPv6 discard และ ORCHIDv2 | +| `64:ff9b::/96`, `64:ff9b:1::/48` | พรีฟิกซ์ NAT64 ที่มี IPv4 ฝังอยู่ | | `2002::/16`, `2001::/32` | 6to4 และ Teredo ที่มี IPv4 ฝังอยู่ | -| `::/96`, `::ffff:0:0/96` | IPv6 แบบ IPv4-compatible และ IPv4-mapped | +| `::/96`, `::ffff:0:0/96` | IPv6 ที่เข้ากันได้กับ IPv4 และ IPv6 แบบ IPv4-mapped | -หากผู้ให้บริการคลาวด์หรือแพลตฟอร์มเครือข่ายของคุณมีเอกสารระบุโฮสต์ metadata หรือช่วงที่สงวนไว้เพิ่มเติม ให้เพิ่มรายการเหล่านั้นด้วย +หากผู้ให้บริการคลาวด์หรือแพลตฟอร์มเครือข่ายของคุณมีเอกสารเกี่ยวกับโฮสต์ metadata หรือช่วงที่สงวนไว้เพิ่มเติม ให้เพิ่มรายการเหล่านั้นด้วย ## การตรวจสอบความถูกต้อง @@ -146,9 +146,9 @@ fallback ผ่านสภาพแวดล้อมเหมาะที่ openclaw proxy validate --proxy-url http://127.0.0.1:3128 ``` -โดยค่าเริ่มต้น เมื่อไม่ได้ระบุปลายทางแบบกำหนดเอง คำสั่งจะตรวจสอบว่า `https://example.com/` สำเร็จ และเริ่ม canary แบบ loopback ชั่วคราวที่พร็อกซีต้องไม่เข้าถึง การตรวจสอบที่คาดว่าถูกปฏิเสธโดยค่าเริ่มต้นจะผ่านเมื่อพร็อกซีส่งคืนการปฏิเสธแบบ non-2xx หรือบล็อก canary ด้วยความล้มเหลวของ transport; จะล้มเหลวหากการตอบกลับที่สำเร็จไปถึง canary หากไม่มีพร็อกซีที่เปิดใช้และกำหนดค่าไว้ การตรวจสอบจะรายงานปัญหา config; ใช้ `--proxy-url` สำหรับ preflight แบบครั้งเดียวก่อนเปลี่ยน config ใช้ `--allowed-url` และ `--denied-url` เพื่อทดสอบความคาดหวังเฉพาะการปรับใช้ ปลายทางที่ถูกปฏิเสธแบบกำหนดเองเป็นแบบ fail-closed: การตอบกลับ HTTP ใดๆ หมายความว่าปลายทางนั้นเข้าถึงได้ผ่านพร็อกซี และข้อผิดพลาด transport ใดๆ จะถูกรายงานว่าไม่สามารถสรุปได้ เพราะ OpenClaw ไม่สามารถพิสูจน์ได้ว่าพร็อกซีบล็อก origin ที่เข้าถึงได้ เมื่อการตรวจสอบล้มเหลว คำสั่งจะออกด้วยรหัส 1 +โดยค่าเริ่มต้น เมื่อไม่ได้ระบุปลายทางแบบกำหนดเอง คำสั่งจะตรวจสอบว่า `https://example.com/` สำเร็จ และเริ่ม canary แบบ loopback ชั่วคราวที่พร็อกซีต้องเข้าถึงไม่ได้ การตรวจสอบการปฏิเสธเริ่มต้นจะผ่านเมื่อพร็อกซีส่งคืนการตอบกลับปฏิเสธที่ไม่ใช่ 2xx หรือบล็อก canary ด้วยความล้มเหลวของ transport; จะล้มเหลวหากมีการตอบกลับสำเร็จไปถึง canary หากไม่มีพร็อกซีที่เปิดใช้งานและกำหนดค่าไว้ การตรวจสอบจะรายงานปัญหาการกำหนดค่า; ใช้ `--proxy-url` สำหรับ preflight แบบครั้งเดียวก่อนเปลี่ยนการกำหนดค่า ใช้ `--allowed-url` และ `--denied-url` เพื่อทดสอบความคาดหวังเฉพาะการปรับใช้ เพิ่ม `--apns-reachable` เพื่อยืนยันด้วยว่าการส่ง APNs HTTP/2 โดยตรงสามารถเปิดอุโมงค์ CONNECT ผ่านพร็อกซีและรับการตอบกลับ APNs sandbox ได้; โพรบใช้โทเค็นผู้ให้บริการที่ตั้งใจให้ไม่ถูกต้อง ดังนั้นจึงคาดหวัง `403 InvalidProviderToken` และนับว่าเข้าถึงได้ ปลายทางแบบกำหนดเองที่ถูกปฏิเสธเป็นแบบปิดเมื่อผิดพลาด: การตอบกลับ HTTP ใดๆ หมายความว่าปลายทางเข้าถึงได้ผ่านพร็อกซี และข้อผิดพลาด transport ใดๆ จะถูกรายงานว่าไม่สามารถสรุปผลได้ เพราะ OpenClaw ไม่สามารถพิสูจน์ได้ว่าพร็อกซีบล็อก origin ที่เข้าถึงได้ เมื่อการตรวจสอบล้มเหลว คำสั่งจะออกด้วยรหัส 1 -ใช้ `--json` สำหรับการทำ automation เอาต์พุต JSON มีผลลัพธ์รวม แหล่งที่มาของ config พร็อกซีที่มีผล ข้อผิดพลาด config ใดๆ และการตรวจสอบแต่ละปลายทาง credential ใน URL พร็อกซีจะถูกปิดบังทั้งในเอาต์พุตข้อความและ JSON: +ใช้ `--json` สำหรับระบบอัตโนมัติ เอาต์พุต JSON ประกอบด้วยผลลัพธ์โดยรวม แหล่งที่มาของการกำหนดค่าพร็อกซีที่มีผล ข้อผิดพลาดการกำหนดค่าใดๆ และการตรวจสอบแต่ละปลายทาง ข้อมูลรับรองของ URL พร็อกซีจะถูกปกปิดในเอาต์พุตข้อความและ JSON: ```json { @@ -165,12 +165,18 @@ openclaw proxy validate --proxy-url http://127.0.0.1:3128 "url": "https://example.com/", "ok": true, "status": 200 + }, + { + "kind": "apns", + "url": "https://api.sandbox.push.apple.com", + "ok": true, + "status": 403 } ] } ``` -คุณสามารถตรวจสอบด้วยตนเองด้วย `curl` ได้เช่นกัน: +คุณยังสามารถตรวจสอบด้วยตนเองด้วย `curl` ได้ด้วย: ```bash curl -x http://127.0.0.1:3128 https://example.com/ @@ -178,7 +184,7 @@ curl -x http://127.0.0.1:3128 http://127.0.0.1/ curl -x http://127.0.0.1:3128 http://169.254.169.254/ ``` -คำขอสาธารณะควรสำเร็จ ส่วนคำขอ loopback และ metadata ควรถูกพร็อกซีบล็อก สำหรับ `openclaw proxy validate` นั้น canary loopback ในตัวสามารถแยกแยะการปฏิเสธจากพร็อกซีออกจากต้นทางที่เข้าถึงได้ การตรวจสอบ `--denied-url` แบบกำหนดเองไม่มี canary ดังกล่าว ดังนั้นให้ถือว่าทั้งการตอบกลับ HTTP และความล้มเหลวด้านการส่งข้อมูลที่กำกวมเป็นความล้มเหลวของการตรวจสอบ เว้นแต่ว่าพร็อกซีของคุณเปิดเผยสัญญาณการปฏิเสธเฉพาะการปรับใช้ที่คุณสามารถตรวจสอบแยกต่างหากได้ +คำขอสาธารณะควรสำเร็จ คำขอลูปแบ็กและคำขอเมทาดาทาควรถูกพร็อกซีบล็อก สำหรับ `openclaw proxy validate` คานารีลูปแบ็กในตัวสามารถแยกการปฏิเสธจากพร็อกซีออกจากต้นทางที่เข้าถึงได้ การตรวจสอบ `--denied-url` แบบกำหนดเองไม่มีคานารีนั้น ดังนั้นให้ถือว่าทั้งการตอบกลับ HTTP และความล้มเหลวของการขนส่งที่กำกวมเป็นความล้มเหลวในการตรวจสอบ เว้นแต่ว่าพร็อกซีของคุณจะเปิดเผยสัญญาณการปฏิเสธเฉพาะการปรับใช้ที่คุณสามารถตรวจสอบแยกต่างหากได้ จากนั้นเปิดใช้การกำหนดเส้นทางพร็อกซีของ OpenClaw: @@ -188,7 +194,7 @@ openclaw config set proxy.proxyUrl http://127.0.0.1:3128 openclaw gateway run ``` -หรือกำหนด: +หรือตั้งค่า: ```yaml proxy: @@ -196,13 +202,13 @@ proxy: proxyUrl: http://127.0.0.1:3128 ``` -## ขีดจำกัด +## ข้อจำกัด -- พร็อกซีช่วยเพิ่มความครอบคลุมสำหรับไคลเอ็นต์ HTTP และ WebSocket ของ JavaScript ที่อยู่ภายในกระบวนการ แต่ไม่ใช่แซนด์บ็อกซ์เครือข่ายระดับ OS -- ซ็อกเก็ต `net`, `tls`, และ `http2` แบบดิบ, native addons, และกระบวนการลูก อาจเลี่ยงการกำหนดเส้นทางพร็อกซีระดับ Node ได้ เว้นแต่ว่าจะสืบทอดและเคารพตัวแปรสภาพแวดล้อมของพร็อกซี -- IRC เป็นช่องทาง TCP/TLS แบบดิบที่อยู่นอกการกำหนดเส้นทางผ่านพร็อกซีส่งต่อที่ผู้ปฏิบัติการจัดการ ในการปรับใช้ที่กำหนดให้อีเกรสทั้งหมดต้องผ่านพร็อกซีส่งต่อนั้น ให้ตั้งค่า `channels.irc.enabled=false` เว้นแต่ว่าอีเกรส IRC โดยตรงจะได้รับอนุมัติอย่างชัดเจน -- พร็อกซีดีบักภายในเครื่องเป็นเครื่องมือวินิจฉัย และการส่งต่ออัปสตรีมโดยตรงสำหรับคำขอพร็อกซีและ CONNECT tunnels จะถูกปิดใช้งานตามค่าเริ่มต้นขณะที่โหมดพร็อกซีที่จัดการอยู่ทำงานอยู่ ให้เปิดใช้การส่งต่อโดยตรงเฉพาะสำหรับการวินิจฉัยภายในเครื่องที่ได้รับอนุมัติเท่านั้น -- WebUI ภายในเครื่องของผู้ใช้และเซิร์ฟเวอร์โมเดลภายในเครื่องควรถูกเพิ่มลงในรายการอนุญาตในนโยบายพร็อกซีของผู้ปฏิบัติการเมื่อจำเป็น OpenClaw ไม่ได้เปิดเผยการเลี่ยงเครือข่ายภายในเครื่องแบบทั่วไปสำหรับสิ่งเหล่านี้ -- การเลี่ยงพร็อกซีของ control plane ของ Gateway ถูกจำกัดไว้ที่ `localhost` และ URL ที่เป็น IP loopback ตามตัวอักษรโดยตั้งใจ ใช้ `ws://127.0.0.1:18789`, `ws://[::1]:18789`, หรือ `ws://localhost:18789` สำหรับการเชื่อมต่อ control plane ของ Gateway ภายในเครื่องโดยตรง ชื่อโฮสต์อื่นจะถูกกำหนดเส้นทางเหมือนทราฟฟิกที่อิงตามชื่อโฮสต์ทั่วไป +- พร็อกซีช่วยเพิ่มความครอบคลุมสำหรับไคลเอนต์ HTTP และ WebSocket ของ JavaScript ภายในกระบวนการ แต่ไม่ใช่แซนด์บ็อกซ์เครือข่ายระดับ OS +- ซ็อกเก็ต `net`, `tls` และ `http2` แบบดิบ, native addons และกระบวนการลูกอาจเลี่ยงการกำหนดเส้นทางพร็อกซีระดับ Node ได้ เว้นแต่ว่าจะสืบทอดและเคารพตัวแปรสภาพแวดล้อมของพร็อกซี +- IRC เป็นช่องทาง TCP/TLS แบบดิบที่อยู่นอกการกำหนดเส้นทางพร็อกซีส่งต่อที่ผู้ปฏิบัติงานจัดการ ในการปรับใช้ที่กำหนดให้ทราฟฟิกขาออกทั้งหมดผ่านพร็อกซีส่งต่อนั้น ให้ตั้งค่า `channels.irc.enabled=false` เว้นแต่ว่าการออกไปยัง IRC โดยตรงได้รับการอนุมัติอย่างชัดเจน +- พร็อกซีดีบักภายในเครื่องเป็นเครื่องมือวินิจฉัย และการส่งต่อโดยตรงไปยังอัปสตรีมสำหรับคำขอพร็อกซีและอุโมงค์ CONNECT จะถูกปิดใช้งานโดยค่าเริ่มต้นขณะที่โหมดพร็อกซีที่มีการจัดการทำงานอยู่ เปิดใช้การส่งต่อโดยตรงเฉพาะสำหรับการวินิจฉัยภายในเครื่องที่ได้รับอนุมัติแล้วเท่านั้น +- WebUI ภายในเครื่องของผู้ใช้และเซิร์ฟเวอร์โมเดลภายในเครื่องควรถูกเพิ่มในรายการอนุญาตในนโยบายพร็อกซีของผู้ปฏิบัติงานเมื่อจำเป็น OpenClaw ไม่ได้เปิดเผยการเลี่ยงเครือข่ายภายในเครื่องแบบทั่วไปสำหรับสิ่งเหล่านั้น +- การเลี่ยงพร็อกซีของ control plane ของ Gateway ถูกจำกัดไว้ที่ `localhost` และ URL ที่เป็น IP ลูปแบ็กตามตัวอักษรโดยเจตนา ใช้ `ws://127.0.0.1:18789`, `ws://[::1]:18789` หรือ `ws://localhost:18789` สำหรับการเชื่อมต่อ control plane ของ Gateway โดยตรงภายในเครื่อง ชื่อโฮสต์อื่นจะถูกกำหนดเส้นทางเหมือนทราฟฟิกตามชื่อโฮสต์ทั่วไป - OpenClaw ไม่ตรวจสอบ ทดสอบ หรือรับรองนโยบายพร็อกซีของคุณ -- ให้ถือว่าการเปลี่ยนแปลงนโยบายพร็อกซีเป็นการเปลี่ยนแปลงการปฏิบัติงานที่มีความอ่อนไหวด้านความปลอดภัย +- ให้ถือว่าการเปลี่ยนแปลงนโยบายพร็อกซีเป็นการเปลี่ยนแปลงการปฏิบัติงานที่อ่อนไหวด้านความปลอดภัย diff --git a/docs/th/tools/thinking.md b/docs/th/tools/thinking.md index 7a3bd6d8d..0898a429d 100644 --- a/docs/th/tools/thinking.md +++ b/docs/th/tools/thinking.md @@ -1,20 +1,20 @@ --- read_when: - การปรับการแยกวิเคราะห์หรือค่าเริ่มต้นของคำสั่ง thinking, fast-mode หรือ verbose -summary: ไวยากรณ์ของไดเรกทีฟสำหรับ /think, /fast, /verbose, /trace และการมองเห็นการให้เหตุผล +summary: ไวยากรณ์คำสั่งกำกับสำหรับ /think, /fast, /verbose, /trace และการมองเห็นการให้เหตุผล title: ระดับการคิด x-i18n: - generated_at: "2026-05-04T02:27:32Z" + generated_at: "2026-05-04T18:24:48Z" model: gpt-5.5 provider: openai - source_hash: 6fa1b0a2b5f7b93a706488c3ad39dfe08c08eed0bdd30880eb4c07d730ee4d4f + source_hash: fcd1cd76ca5d0b08656e0629df656ad8aa037201d8de68093b3e46eb0708f811 source_path: tools/thinking.md workflow: 16 --- -## สิ่งที่ทำ +## หน้าที่ของมัน -- คำสั่งแบบอินไลน์ในเนื้อหาขาเข้าใด ๆ: `/t `, `/think:`, หรือ `/thinking ` +- คำสั่งแบบอินไลน์ในเนื้อหาขาเข้าใดๆ: `/t `, `/think:`, หรือ `/thinking `. - ระดับ (นามแฝง): `off | minimal | low | medium | high | xhigh | adaptive | max` - minimal → “think” - low → “think hard” @@ -22,122 +22,123 @@ x-i18n: - high → “ultrathink” (งบประมาณสูงสุด) - xhigh → “ultrathink+” (โมเดล GPT-5.2+ และ Codex รวมถึง effort ของ Anthropic Claude Opus 4.7) - adaptive → การคิดแบบปรับตัวที่ผู้ให้บริการจัดการ (รองรับสำหรับ Claude 4.6 บน Anthropic/Bedrock, Anthropic Claude Opus 4.7 และการคิดแบบไดนามิกของ Google Gemini) - - max → การใช้เหตุผลสูงสุดของผู้ให้บริการ (Anthropic Claude Opus 4.7; Ollama จับคู่ค่านี้กับ effort `think` เนทีฟระดับสูงสุด) - - `x-high`, `x_high`, `extra-high`, `extra high` และ `extra_high` จะจับคู่เป็น `xhigh` - - `highest` จะจับคู่เป็น `high` -- หมายเหตุสำหรับผู้ให้บริการ: - - เมนูและตัวเลือกการคิดขับเคลื่อนโดยโปรไฟล์ผู้ให้บริการ Plugin ของผู้ให้บริการประกาศชุดระดับที่แน่นอนสำหรับโมเดลที่เลือก รวมถึงป้ายกำกับอย่าง `on` แบบไบนารี - - `adaptive`, `xhigh` และ `max` จะแสดงเฉพาะสำหรับโปรไฟล์ผู้ให้บริการ/โมเดลที่รองรับเท่านั้น คำสั่งที่พิมพ์สำหรับระดับที่ไม่รองรับจะถูกปฏิเสธพร้อมตัวเลือกที่ใช้ได้ของโมเดลนั้น - - ระดับที่ไม่รองรับซึ่งจัดเก็บไว้เดิมจะถูกจับคู่ใหม่ตามลำดับชั้นโปรไฟล์ผู้ให้บริการ `adaptive` จะถอยกลับเป็น `medium` บนโมเดลที่ไม่รองรับการปรับตัว ขณะที่ `xhigh` และ `max` จะถอยกลับเป็นระดับที่รองรับสูงสุดซึ่งไม่ใช่ off สำหรับโมเดลที่เลือก - - โมเดล Anthropic Claude 4.6 มีค่าเริ่มต้นเป็น `adaptive` เมื่อไม่ได้ตั้งค่าระดับการคิดอย่างชัดเจน - - Anthropic Claude Opus 4.7 ไม่ได้มีค่าเริ่มต้นเป็นการคิดแบบปรับตัว ค่าเริ่มต้น effort ของ API ยังคงเป็นของผู้ให้บริการ เว้นแต่คุณจะตั้งค่าระดับการคิดอย่างชัดเจน - - Anthropic Claude Opus 4.7 จับคู่ `/think xhigh` เป็นการคิดแบบปรับตัวพร้อม `output_config.effort: "xhigh"` เพราะ `/think` เป็นคำสั่งการคิด และ `xhigh` เป็นการตั้งค่า effort ของ Opus 4.7 - - Anthropic Claude Opus 4.7 ยังเปิดเผย `/think max` ด้วย โดยจับคู่กับเส้นทาง effort สูงสุดที่ผู้ให้บริการเป็นเจ้าของเดียวกัน - - โมเดล DeepSeek V4 เปิดเผย `/think xhigh|max`; ทั้งสองจับคู่กับ DeepSeek `reasoning_effort: "max"` ขณะที่ระดับที่ต่ำกว่าและไม่ใช่ off จะจับคู่เป็น `high` + - max → การให้เหตุผลสูงสุดของผู้ให้บริการ (Anthropic Claude Opus 4.7; Ollama จับคู่ค่านี้กับ effort `think` แบบเนทีฟสูงสุดของตน) + - `x-high`, `x_high`, `extra-high`, `extra high` และ `extra_high` จับคู่กับ `xhigh`. + - `highest` จับคู่กับ `high`. +- หมายเหตุผู้ให้บริการ: + - เมนูและตัวเลือกการคิดขับเคลื่อนโดยโปรไฟล์ผู้ให้บริการ Plugin ของผู้ให้บริการประกาศชุดระดับที่แน่นอนสำหรับโมเดลที่เลือก รวมถึงป้ายกำกับอย่างไบนารี `on`. + - `adaptive`, `xhigh` และ `max` จะแสดงเฉพาะสำหรับโปรไฟล์ผู้ให้บริการ/โมเดลที่รองรับเท่านั้น คำสั่งแบบพิมพ์สำหรับระดับที่ไม่รองรับจะถูกปฏิเสธพร้อมตัวเลือกที่ถูกต้องของโมเดลนั้น + - ระดับที่ไม่รองรับซึ่งจัดเก็บไว้เดิมจะถูกจับคู่ใหม่ตามลำดับชั้นของโปรไฟล์ผู้ให้บริการ `adaptive` จะย้อนกลับไปเป็น `medium` บนโมเดลที่ไม่รองรับการปรับตัว ขณะที่ `xhigh` และ `max` จะย้อนกลับไปเป็นระดับที่รองรับสูงสุดซึ่งไม่ใช่ off สำหรับโมเดลที่เลือก + - โมเดล Anthropic Claude 4.6 ใช้ค่าเริ่มต้นเป็น `adaptive` เมื่อไม่ได้ตั้งค่าระดับการคิดไว้อย่างชัดเจน + - Anthropic Claude Opus 4.7 ไม่ได้ใช้ค่าเริ่มต้นเป็นการคิดแบบปรับตัว ค่าเริ่มต้น effort ของ API ยังคงเป็นของผู้ให้บริการ เว้นแต่คุณจะตั้งค่าระดับการคิดไว้อย่างชัดเจน + - Anthropic Claude Opus 4.7 จับคู่ `/think xhigh` กับการคิดแบบปรับตัวพร้อม `output_config.effort: "xhigh"` เพราะ `/think` เป็นคำสั่งการคิด และ `xhigh` เป็นการตั้งค่า effort ของ Opus 4.7 + - Anthropic Claude Opus 4.7 ยังเปิดเผย `/think max`; ค่านี้จับคู่กับเส้นทาง effort สูงสุดเดียวกันที่ผู้ให้บริการเป็นเจ้าของ + - โมเดล DeepSeek V4 เปิดเผย `/think xhigh|max`; ทั้งสองจับคู่กับ `reasoning_effort: "max"` ของ DeepSeek ขณะที่ระดับที่ต่ำกว่าซึ่งไม่ใช่ off จับคู่กับ `high` - โมเดล Ollama ที่รองรับการคิดเปิดเผย `/think low|medium|high|max`; `max` จับคู่กับ `think: "high"` แบบเนทีฟ เพราะ API เนทีฟของ Ollama รับสตริง effort `low`, `medium` และ `high` - - โมเดล OpenAI GPT จับคู่ `/think` ผ่านการรองรับ effort ของ Responses API เฉพาะโมเดล `/think off` จะส่ง `reasoning.effort: "none"` เฉพาะเมื่อโมเดลเป้าหมายรองรับเท่านั้น มิฉะนั้น OpenClaw จะละเว้นเพย์โหลดการใช้เหตุผลที่ปิดใช้งาน แทนที่จะส่งค่าที่ไม่รองรับ - - รายการแค็ตตาล็อกที่เข้ากันได้กับ OpenAI แบบกำหนดเองสามารถเลือกรองรับ `/think xhigh` ได้โดยตั้งค่า `models.providers..models[].compat.supportedReasoningEfforts` ให้รวม `"xhigh"` ซึ่งใช้เมทาดาทา compat เดียวกันที่จับคู่เพย์โหลด effort การใช้เหตุผลของ OpenAI ขาออก ดังนั้นเมนู การตรวจสอบเซสชัน agent CLI และ `llm-task` จึงสอดคล้องกับพฤติกรรมการขนส่ง - - refs ของ OpenRouter Hunter Alpha ที่กำหนดค่าไว้แต่ล้าสมัยจะข้ามการฉีด reasoning ของพร็อกซี เพราะเส้นทางที่เลิกใช้แล้วนั้นอาจคืนข้อความคำตอบสุดท้ายผ่านฟิลด์ reasoning ได้ - - Google Gemini จับคู่ `/think adaptive` กับการคิดแบบไดนามิกที่ผู้ให้บริการของ Gemini เป็นเจ้าของ คำขอ Gemini 3 จะละเว้น `thinkingLevel` แบบคงที่ ขณะที่คำขอ Gemini 2.5 ส่ง `thinkingBudget: -1`; ระดับคงที่ยังคงจับคู่กับ `thinkingLevel` หรือ budget ของ Gemini ที่ใกล้ที่สุดสำหรับตระกูลโมเดลนั้น - - MiniMax (`minimax/*`) บนเส้นทางสตรีมมิงที่เข้ากันได้กับ Anthropic มีค่าเริ่มต้นเป็น `thinking: { type: "disabled" }` เว้นแต่คุณจะตั้งค่าการคิดอย่างชัดเจนในพารามิเตอร์โมเดลหรือพารามิเตอร์คำขอ ซึ่งช่วยหลีกเลี่ยงเดลตา `reasoning_content` ที่รั่วจากรูปแบบสตรีม Anthropic ที่ไม่ใช่เนทีฟของ MiniMax - - Z.AI (`zai/*`) รองรับเฉพาะการคิดแบบไบนารี (`on`/`off`) ระดับใด ๆ ที่ไม่ใช่ `off` จะถือเป็น `on` (จับคู่เป็น `low`) - - Moonshot (`moonshot/*`) จับคู่ `/think off` เป็น `thinking: { type: "disabled" }` และระดับใด ๆ ที่ไม่ใช่ `off` เป็น `thinking: { type: "enabled" }` เมื่อเปิดใช้การคิด Moonshot รับเฉพาะ `tool_choice` `auto|none`; OpenClaw ทำให้ค่าที่เข้ากันไม่ได้เป็น `auto` + - โมเดล OpenAI GPT จับคู่ `/think` ผ่านการรองรับ effort เฉพาะโมเดลของ Responses API `/think off` ส่ง `reasoning.effort: "none"` เฉพาะเมื่อโมเดลเป้าหมายรองรับเท่านั้น มิฉะนั้น OpenClaw จะละเว้น payload การให้เหตุผลที่ปิดใช้งาน แทนที่จะส่งค่าที่ไม่รองรับ + - รายการแค็ตตาล็อกที่เข้ากันได้กับ OpenAI แบบกำหนดเองสามารถเลือกใช้ `/think xhigh` ได้โดยตั้งค่า `models.providers..models[].compat.supportedReasoningEfforts` ให้รวม `"xhigh"` ค่านี้ใช้เมทาดาทา compat เดียวกันที่จับคู่ payload effort การให้เหตุผลขาออกของ OpenAI ดังนั้นเมนู การตรวจสอบเซสชัน agent CLI และ `llm-task` จึงสอดคล้องกับพฤติกรรมการขนส่ง + - refs ของ OpenRouter Hunter Alpha ที่กำหนดค่าไว้แต่ล้าสมัยจะข้ามการฉีดการให้เหตุผลของพร็อกซี เพราะเส้นทางที่เลิกใช้แล้วนั้นอาจส่งคืนข้อความคำตอบสุดท้ายผ่านฟิลด์การให้เหตุผล + - Google Gemini จับคู่ `/think adaptive` กับการคิดแบบไดนามิกที่ผู้ให้บริการเป็นเจ้าของของ Gemini คำขอ Gemini 3 จะละเว้น `thinkingLevel` แบบคงที่ ขณะที่คำขอ Gemini 2.5 ส่ง `thinkingBudget: -1`; ระดับคงที่ยังคงจับคู่กับ `thinkingLevel` หรืองบประมาณของ Gemini ที่ใกล้ที่สุดสำหรับตระกูลโมเดลนั้น + - MiniMax (`minimax/*`) บนเส้นทางสตรีมมิงที่เข้ากันได้กับ Anthropic ใช้ค่าเริ่มต้นเป็น `thinking: { type: "disabled" }` เว้นแต่คุณจะตั้งค่าการคิดไว้อย่างชัดเจนในพารามิเตอร์โมเดลหรือพารามิเตอร์คำขอ วิธีนี้หลีกเลี่ยงเดลตา `reasoning_content` ที่รั่วจากรูปแบบสตรีม Anthropic ที่ไม่ใช่เนทีฟของ MiniMax + - Z.AI (`zai/*`) รองรับเฉพาะการคิดแบบไบนารี (`on`/`off`) ระดับใดๆ ที่ไม่ใช่ `off` จะถือเป็น `on` (จับคู่กับ `low`) + - Moonshot (`moonshot/*`) จับคู่ `/think off` กับ `thinking: { type: "disabled" }` และระดับใดๆ ที่ไม่ใช่ `off` กับ `thinking: { type: "enabled" }` เมื่อเปิดใช้งานการคิด Moonshot จะรับเฉพาะ `tool_choice` `auto|none`; OpenClaw ทำให้ค่าที่ไม่เข้ากันเป็น `auto` -## ลำดับการแก้ไขค่า +## ลำดับการแก้ค่า -1. คำสั่งแบบอินไลน์ในข้อความ (ใช้กับข้อความนั้นเท่านั้น) -2. การแทนที่ของเซสชัน (ตั้งค่าโดยส่งข้อความที่มีเฉพาะคำสั่ง) +1. คำสั่งแบบอินไลน์บนข้อความ (ใช้กับข้อความนั้นเท่านั้น) +2. การแทนที่ของเซสชัน (ตั้งค่าโดยส่งข้อความที่มีแต่คำสั่ง) 3. ค่าเริ่มต้นราย agent (`agents.list[].thinkingDefault` ใน config) 4. ค่าเริ่มต้นส่วนกลาง (`agents.defaults.thinkingDefault` ใน config) -5. ค่าถอยกลับ: ค่าเริ่มต้นที่ผู้ให้บริการประกาศเมื่อมี มิฉะนั้นโมเดลที่รองรับการใช้เหตุผลจะแก้ค่าเป็น `medium` หรือระดับที่รองรับและไม่ใช่ `off` ที่ใกล้ที่สุดสำหรับโมเดลนั้น และโมเดลที่ไม่ใช้เหตุผลจะคงเป็น `off` +5. ค่าถอยกลับ: ค่าเริ่มต้นที่ผู้ให้บริการประกาศเมื่อมี; มิฉะนั้นโมเดลที่รองรับการให้เหตุผลจะแก้ค่าเป็น `medium` หรือระดับที่รองรับใกล้ที่สุดซึ่งไม่ใช่ `off` สำหรับโมเดลนั้น และโมเดลที่ไม่รองรับการให้เหตุผลจะคงเป็น `off` ## การตั้งค่าเริ่มต้นของเซสชัน -- ส่งข้อความที่เป็นคำสั่ง **เท่านั้น** (อนุญาตช่องว่างได้) เช่น `/think:medium` หรือ `/t high` -- ค่านั้นจะติดอยู่กับเซสชันปัจจุบัน (โดยค่าเริ่มต้นแยกตามผู้ส่ง); ล้างด้วย `/think:off` หรือการรีเซ็ตเมื่อเซสชันว่างนาน -- จะมีการส่งคำตอบยืนยัน (`Thinking level set to high.` / `Thinking disabled.`) หากระดับไม่ถูกต้อง (เช่น `/thinking big`) คำสั่งจะถูกปฏิเสธพร้อมคำแนะนำ และสถานะเซสชันจะไม่เปลี่ยนแปลง +- ส่งข้อความที่เป็นคำสั่ง **เท่านั้น** (อนุญาตช่องว่าง), เช่น `/think:medium` หรือ `/t high`. +- ค่านี้จะคงอยู่สำหรับเซสชันปัจจุบัน (ค่าเริ่มต้นแยกตามผู้ส่ง); ล้างด้วย `/think:off` หรือการรีเซ็ตเมื่อเซสชันว่าง +- จะส่งข้อความยืนยัน (`Thinking level set to high.` / `Thinking disabled.`) หากระดับไม่ถูกต้อง (เช่น `/thinking big`) คำสั่งจะถูกปฏิเสธพร้อมคำใบ้ และสถานะเซสชันจะไม่เปลี่ยนแปลง - ส่ง `/think` (หรือ `/think:`) โดยไม่มีอาร์กิวเมนต์เพื่อดูระดับการคิดปัจจุบัน -## การใช้งานตาม agent +## การใช้โดย agent -- **Pi แบบฝังตัว**: ระดับที่แก้ไขแล้วจะถูกส่งต่อไปยังรันไทม์ agent Pi ในโปรเซส +- **Pi แบบฝังตัว**: ระดับที่แก้ค่าแล้วจะถูกส่งไปยัง runtime ของ Pi agent ในกระบวนการ +- **แบ็กเอนด์ Claude CLI**: ระดับที่ไม่ใช่ off จะถูกส่งไปยัง Claude Code เป็น `--effort` เมื่อใช้ `claude-cli`; ดู [แบ็กเอนด์ CLI](/th/gateway/cli-backends) ## โหมดเร็ว (/fast) -- ระดับ: `on|off` -- ข้อความที่มีเฉพาะคำสั่งจะสลับการแทนที่โหมดเร็วของเซสชัน และตอบกลับ `Fast mode enabled.` / `Fast mode disabled.` -- ส่ง `/fast` (หรือ `/fast status`) โดยไม่มีโหมดเพื่อดูสถานะโหมดเร็วที่มีผลอยู่ในปัจจุบัน +- ระดับ: `on|off`. +- ข้อความที่มีแต่คำสั่งจะสลับการแทนที่โหมดเร็วของเซสชันและตอบกลับ `Fast mode enabled.` / `Fast mode disabled.`. +- ส่ง `/fast` (หรือ `/fast status`) โดยไม่มีโหมดเพื่อดูสถานะโหมดเร็วที่มีผลในปัจจุบัน - OpenClaw แก้ค่าโหมดเร็วตามลำดับนี้: - 1. `/fast on|off` แบบอินไลน์/มีเฉพาะคำสั่ง + 1. อินไลน์/เฉพาะคำสั่ง `/fast on|off` 2. การแทนที่ของเซสชัน 3. ค่าเริ่มต้นราย agent (`agents.list[].fastModeDefault`) 4. config รายโมเดล: `agents.defaults.models["/"].params.fastMode` 5. ค่าถอยกลับ: `off` -- สำหรับ `openai/*` โหมดเร็วจับคู่กับการประมวลผลลำดับความสำคัญของ OpenAI โดยส่ง `service_tier=priority` ในคำขอ Responses ที่รองรับ -- สำหรับ `openai-codex/*` โหมดเร็วส่งแฟล็ก `service_tier=priority` เดียวกันใน Codex Responses OpenClaw คงสวิตช์ `/fast` ร่วมกันหนึ่งตัวสำหรับเส้นทาง auth ทั้งสอง -- สำหรับคำขอ `anthropic/*` สาธารณะโดยตรง รวมถึงทราฟฟิกที่ยืนยันตัวตนด้วย OAuth ซึ่งส่งไปยัง `api.anthropic.com` โหมดเร็วจับคู่กับ service tier ของ Anthropic: `/fast on` ตั้งค่า `service_tier=auto`, `/fast off` ตั้งค่า `service_tier=standard_only` -- สำหรับ `minimax/*` บนเส้นทางที่เข้ากันได้กับ Anthropic, `/fast on` (หรือ `params.fastMode: true`) จะเขียน `MiniMax-M2.7` ใหม่เป็น `MiniMax-M2.7-highspeed` -- พารามิเตอร์โมเดล Anthropic `serviceTier` / `service_tier` ที่ระบุชัดเจนจะแทนที่ค่าเริ่มต้นของโหมดเร็วเมื่อทั้งสองถูกตั้งค่า OpenClaw ยังคงข้ามการฉีด service-tier ของ Anthropic สำหรับ URL ฐานของพร็อกซีที่ไม่ใช่ Anthropic -- `/status` แสดง `Fast` เฉพาะเมื่อเปิดใช้โหมดเร็ว +- สำหรับ `openai/*` โหมดเร็วจับคู่กับการประมวลผลลำดับความสำคัญของ OpenAI โดยส่ง `service_tier=priority` บนคำขอ Responses ที่รองรับ +- สำหรับ `openai-codex/*` โหมดเร็วส่งแฟล็ก `service_tier=priority` เดียวกันบน Codex Responses OpenClaw ใช้ตัวสลับ `/fast` ร่วมกันตัวเดียวสำหรับทั้งสองเส้นทางการยืนยันตัวตน +- สำหรับคำขอ `anthropic/*` สาธารณะโดยตรง รวมถึงทราฟฟิกที่ยืนยันตัวตนด้วย OAuth ซึ่งส่งไปยัง `api.anthropic.com` โหมดเร็วจับคู่กับระดับบริการของ Anthropic: `/fast on` ตั้งค่า `service_tier=auto`, `/fast off` ตั้งค่า `service_tier=standard_only` +- สำหรับ `minimax/*` บนเส้นทางที่เข้ากันได้กับ Anthropic, `/fast on` (หรือ `params.fastMode: true`) เขียน `MiniMax-M2.7` ใหม่เป็น `MiniMax-M2.7-highspeed` +- พารามิเตอร์โมเดล Anthropic `serviceTier` / `service_tier` ที่ตั้งไว้อย่างชัดเจนจะแทนที่ค่าเริ่มต้นของโหมดเร็วเมื่อทั้งสองถูกตั้งค่า OpenClaw ยังคงข้ามการฉีดระดับบริการของ Anthropic สำหรับ URL ฐานพร็อกซีที่ไม่ใช่ Anthropic +- `/status` แสดง `Fast` เฉพาะเมื่อเปิดใช้งานโหมดเร็ว -## คำสั่ง verbose (/verbose หรือ /v) +## คำสั่งแบบละเอียด (/verbose หรือ /v) -- ระดับ: `on` (น้อยที่สุด) | `full` | `off` (ค่าเริ่มต้น) -- ข้อความที่มีเฉพาะคำสั่งจะสลับ verbose ของเซสชัน และตอบกลับ `Verbose logging enabled.` / `Verbose logging disabled.`; ระดับที่ไม่ถูกต้องจะคืนคำแนะนำโดยไม่เปลี่ยนสถานะ -- `/verbose off` จัดเก็บการแทนที่เซสชันแบบชัดเจน; ล้างผ่าน UI เซสชันโดยเลือก `inherit` -- คำสั่งแบบอินไลน์มีผลเฉพาะข้อความนั้น มิฉะนั้นจะใช้ค่าเริ่มต้นของเซสชัน/ส่วนกลาง +- ระดับ: `on` (น้อยที่สุด) | `full` | `off` (ค่าเริ่มต้น). +- ข้อความที่มีแต่คำสั่งจะสลับ verbose ของเซสชันและตอบกลับ `Verbose logging enabled.` / `Verbose logging disabled.`; ระดับที่ไม่ถูกต้องจะคืนคำใบ้โดยไม่เปลี่ยนสถานะ +- `/verbose off` เก็บการแทนที่เซสชันอย่างชัดเจน; ล้างผ่าน UI เซสชันโดยเลือก `inherit` +- คำสั่งแบบอินไลน์มีผลเฉพาะข้อความนั้น; มิฉะนั้นจะใช้ค่าเริ่มต้นของเซสชัน/ส่วนกลาง - ส่ง `/verbose` (หรือ `/verbose:`) โดยไม่มีอาร์กิวเมนต์เพื่อดูระดับ verbose ปัจจุบัน -- เมื่อ verbose เปิดอยู่ agent ที่ปล่อยผลลัพธ์เครื่องมือแบบมีโครงสร้าง (Pi และ agent JSON อื่น ๆ) จะส่งการเรียกเครื่องมือแต่ละครั้งกลับเป็นข้อความเฉพาะเมทาดาทาของตัวเอง โดยนำหน้าด้วย ` : ` เมื่อมี สรุปเครื่องมือเหล่านี้จะถูกส่งทันทีที่เครื่องมือแต่ละตัวเริ่มทำงาน (บับเบิลแยกกัน) ไม่ใช่เดลตาสตรีมมิง -- สรุปความล้มเหลวของเครื่องมือยังคงมองเห็นได้ในโหมดปกติ แต่ suffix รายละเอียดข้อผิดพลาดดิบจะถูกซ่อนไว้ เว้นแต่ verbose เป็น `on` หรือ `full` -- เมื่อ verbose เป็น `full` เอาต์พุตเครื่องมือจะถูกส่งต่อหลังเสร็จสิ้นด้วย (บับเบิลแยกกัน ตัดให้เหลือความยาวที่ปลอดภัย) หากคุณสลับ `/verbose on|full|off` ขณะที่การรันกำลังดำเนินอยู่ บับเบิลเครื่องมือถัดไปจะใช้การตั้งค่าใหม่ -- `agents.defaults.toolProgressDetail` ควบคุมรูปแบบของสรุปเครื่องมือ `/verbose` และบรรทัดเครื่องมือแบบร่างความคืบหน้า ใช้ `"explain"` (ค่าเริ่มต้น) สำหรับป้ายกำกับสั้น ๆ ที่มนุษย์อ่านได้ เช่น `🛠️ Exec: checking JS syntax`; ใช้ `"raw"` เมื่อคุณต้องการให้แนบคำสั่ง/รายละเอียดดิบสำหรับการดีบักด้วย `agents.list[].toolProgressDetail` ราย agent จะแทนที่ค่าเริ่มต้น +- เมื่อเปิด verbose, agents ที่ปล่อยผลลัพธ์เครื่องมือแบบมีโครงสร้าง (Pi, agent JSON อื่นๆ) จะส่งการเรียกเครื่องมือแต่ละครั้งกลับเป็นข้อความเฉพาะเมทาดาทาของตัวเอง โดยมีคำนำหน้า ` : ` เมื่อมี สรุปเครื่องมือเหล่านี้จะถูกส่งทันทีที่แต่ละเครื่องมือเริ่มทำงาน (บับเบิลแยก) ไม่ใช่เป็นเดลตาสตรีมมิง +- สรุปความล้มเหลวของเครื่องมือยังคงมองเห็นได้ในโหมดปกติ แต่ส่วนต่อท้ายรายละเอียดข้อผิดพลาดดิบจะถูกซ่อน เว้นแต่ verbose เป็น `on` หรือ `full` +- เมื่อ verbose เป็น `full` เอาต์พุตเครื่องมือจะถูกส่งต่อหลังเสร็จสิ้นด้วย (บับเบิลแยก ตัดทอนให้มีความยาวที่ปลอดภัย) หากคุณสลับ `/verbose on|full|off` ระหว่างที่รันอยู่ บับเบิลเครื่องมือถัดไปจะใช้การตั้งค่าใหม่ +- `agents.defaults.toolProgressDetail` ควบคุมรูปแบบของสรุปเครื่องมือ `/verbose` และบรรทัดเครื่องมือแบบร่างความคืบหน้า ใช้ `"explain"` (ค่าเริ่มต้น) สำหรับป้ายกำกับมนุษย์แบบกระชับ เช่น `🛠️ Exec: checking JS syntax`; ใช้ `"raw"` เมื่อคุณต้องการให้แนบคำสั่ง/รายละเอียดดิบสำหรับการดีบักด้วย `agents.list[].toolProgressDetail` ราย agent จะแทนที่ค่าเริ่มต้น - `explain`: `🛠️ Exec: check JS syntax for /tmp/app.js` - `raw`: `🛠️ Exec: check JS syntax for /tmp/app.js, node --check /tmp/app.js` -## คำสั่ง trace ของ Plugin (/trace) +## คำสั่งติดตาม Plugin (/trace) -- ระดับ: `on` | `off` (ค่าเริ่มต้น) -- ข้อความที่มีเฉพาะคำสั่งจะสลับเอาต์พุต trace ของ Plugin ในเซสชัน และตอบกลับ `Plugin trace enabled.` / `Plugin trace disabled.` -- คำสั่งแบบอินไลน์มีผลเฉพาะข้อความนั้น มิฉะนั้นจะใช้ค่าเริ่มต้นของเซสชัน/ส่วนกลาง -- ส่ง `/trace` (หรือ `/trace:`) โดยไม่มีอาร์กิวเมนต์เพื่อดูระดับ trace ปัจจุบัน -- `/trace` แคบกว่า `/verbose`: โดยเปิดเผยเฉพาะบรรทัด trace/debug ที่ Plugin เป็นเจ้าของ เช่น สรุป debug ของ Active Memory -- บรรทัด trace อาจปรากฏใน `/status` และเป็นข้อความวินิจฉัยติดตามผลหลังคำตอบผู้ช่วยตามปกติ +- ระดับ: `on` | `off` (ค่าเริ่มต้น). +- ข้อความที่มีแต่คำสั่งจะสลับเอาต์พุตติดตาม Plugin ของเซสชันและตอบกลับ `Plugin trace enabled.` / `Plugin trace disabled.`. +- คำสั่งแบบอินไลน์มีผลเฉพาะข้อความนั้น; มิฉะนั้นจะใช้ค่าเริ่มต้นของเซสชัน/ส่วนกลาง +- ส่ง `/trace` (หรือ `/trace:`) โดยไม่มีอาร์กิวเมนต์เพื่อดูระดับการติดตามปัจจุบัน +- `/trace` แคบกว่า `/verbose`: แสดงเฉพาะบรรทัดติดตาม/ดีบักที่ Plugin เป็นเจ้าของ เช่น สรุปดีบักของ Active Memory +- บรรทัดติดตามสามารถปรากฏใน `/status` และเป็นข้อความวินิจฉัยติดตามหลังการตอบกลับปกติของผู้ช่วย -## การมองเห็นการใช้เหตุผล (/reasoning) +## การมองเห็นการให้เหตุผล (/reasoning) -- ระดับ: `on|off|stream` -- ข้อความที่มีเฉพาะคำสั่งจะสลับว่าจะให้แสดงบล็อกการคิดในคำตอบหรือไม่ -- เมื่อเปิดใช้งาน การใช้เหตุผลจะถูกส่งเป็น **ข้อความแยกต่างหาก** ที่นำหน้าด้วย `Reasoning:` -- `stream` (เฉพาะ Telegram): สตรีมการใช้เหตุผลลงในบับเบิลร่างของ Telegram ระหว่างสร้างคำตอบ จากนั้นส่งคำตอบสุดท้ายโดยไม่มีการใช้เหตุผล -- นามแฝง: `/reason` -- ส่ง `/reasoning` (หรือ `/reasoning:`) โดยไม่มีอาร์กิวเมนต์เพื่อดูระดับการใช้เหตุผลปัจจุบัน -- ลำดับการแก้ไขค่า: คำสั่งแบบอินไลน์ จากนั้นการแทนที่ของเซสชัน จากนั้นค่าเริ่มต้นราย agent (`agents.list[].reasoningDefault`) จากนั้นค่าถอยกลับ (`off`) +- ระดับ: `on|off|stream`. +- ข้อความที่มีแต่คำสั่งจะสลับว่าจะให้แสดงบล็อกการคิดในคำตอบหรือไม่ +- เมื่อเปิดใช้งาน การให้เหตุผลจะถูกส่งเป็น **ข้อความแยก** ที่ขึ้นต้นด้วย `Reasoning:`. +- `stream` (เฉพาะ Telegram): สตรีมการให้เหตุผลเข้าไปในบับเบิลร่างของ Telegram ขณะที่กำลังสร้างคำตอบ จากนั้นส่งคำตอบสุดท้ายโดยไม่มีการให้เหตุผล +- นามแฝง: `/reason`. +- ส่ง `/reasoning` (หรือ `/reasoning:`) โดยไม่มีอาร์กิวเมนต์เพื่อดูระดับการให้เหตุผลปัจจุบัน +- ลำดับการแก้ค่า: คำสั่งแบบอินไลน์ จากนั้นการแทนที่ของเซสชัน จากนั้นค่าเริ่มต้นราย agent (`agents.list[].reasoningDefault`) จากนั้นค่าถอยกลับ (`off`) -แท็กการใช้เหตุผลของโมเดลในเครื่องที่ผิดรูปแบบจะถูกจัดการอย่างระมัดระวัง บล็อก `...` ที่ปิดแล้วจะยังคงถูกซ่อนในคำตอบปกติ และการใช้เหตุผลที่ไม่ได้ปิดหลังข้อความที่มองเห็นแล้วก็จะถูกซ่อนเช่นกัน หากคำตอบถูกครอบทั้งหมดในแท็กเปิดเดียวที่ไม่ได้ปิด และมิฉะนั้นจะส่งเป็นข้อความว่าง OpenClaw จะลบแท็กเปิดที่ผิดรูปแบบออกและส่งข้อความที่เหลือ +แท็กการให้เหตุผลของโมเดลภายในที่มีรูปแบบผิดพลาดจะถูกจัดการอย่างระมัดระวัง บล็อก `...` ที่ปิดแล้วจะยังถูกซ่อนในคำตอบปกติ และการให้เหตุผลที่ไม่ปิดหลังข้อความที่มองเห็นแล้วก็จะถูกซ่อนเช่นกัน หากคำตอบถูกห่อทั้งหมดด้วยแท็กเปิดที่ไม่ปิดเพียงแท็กเดียว และมิฉะนั้นจะส่งเป็นข้อความว่าง OpenClaw จะลบแท็กเปิดที่ผิดรูปแบบนั้นและส่งข้อความที่เหลือ ## ที่เกี่ยวข้อง -- เอกสารโหมดยกระดับอยู่ใน [โหมดยกระดับ](/th/tools/elevated) +- เอกสารโหมดยกระดับอยู่ใน [โหมดยกระดับ](/th/tools/elevated). -## Heartbeat +## Heartbeats -- เนื้อหา probe ของ Heartbeat คือ prompt Heartbeat ที่กำหนดค่าไว้ (ค่าเริ่มต้น: `Read HEARTBEAT.md if it exists (workspace context). Follow it strictly. Do not infer or repeat old tasks from prior chats. If nothing needs attention, reply HEARTBEAT_OK.`) คำสั่งแบบอินไลน์ในข้อความ Heartbeat จะมีผลตามปกติ (แต่หลีกเลี่ยงการเปลี่ยนค่าเริ่มต้นของเซสชันจาก Heartbeat) -- การส่ง Heartbeat มีค่าเริ่มต้นเป็นเฉพาะเพย์โหลดสุดท้าย หากต้องการส่งข้อความ `Reasoning:` แยกต่างหากด้วย (เมื่อมี) ให้ตั้งค่า `agents.defaults.heartbeat.includeReasoning: true` หรือ `agents.list[].heartbeat.includeReasoning: true` ราย agent +- เนื้อหาโพรบ Heartbeat คือพรอมป์ heartbeat ที่กำหนดค่าไว้ (ค่าเริ่มต้น: `Read HEARTBEAT.md if it exists (workspace context). Follow it strictly. Do not infer or repeat old tasks from prior chats. If nothing needs attention, reply HEARTBEAT_OK.`) คำสั่งแบบอินไลน์ในข้อความ heartbeat จะถูกใช้ตามปกติ (แต่ควรหลีกเลี่ยงการเปลี่ยนค่าเริ่มต้นของเซสชันจาก heartbeats) +- การส่ง Heartbeat ใช้ค่าเริ่มต้นเป็น payload สุดท้ายเท่านั้น หากต้องการส่งข้อความ `Reasoning:` แยกต่างหากด้วย (เมื่อมี) ให้ตั้งค่า `agents.defaults.heartbeat.includeReasoning: true` หรือราย agent `agents.list[].heartbeat.includeReasoning: true` -## UI แชตบนเว็บ +## UI แชทเว็บ -- ตัวเลือกระดับการคิดของแชตบนเว็บจะสะท้อนระดับที่จัดเก็บของเซสชันจาก session store/config ขาเข้าเมื่อหน้าโหลด -- การเลือกอีกระดับจะเขียนการแทนที่เซสชันทันทีผ่าน `sessions.patch`; ไม่ต้องรอการส่งครั้งถัดไป และไม่ใช่การแทนที่ `thinkingOnce` แบบใช้ครั้งเดียว -- ตัวเลือกแรกจะเป็น `Default ()` เสมอ โดยค่าเริ่มต้นที่แก้ไขแล้วมาจากโปรไฟล์การคิดของผู้ให้บริการของโมเดลเซสชันที่ใช้งานอยู่ รวมกับตรรกะค่าถอยกลับเดียวกันกับที่ `/status` และ `session_status` ใช้ -- ตัวเลือกใช้ `thinkingLevels` ที่คืนโดยแถวเซสชัน/defaults ของ Gateway โดยคง `thinkingOptions` ไว้เป็นรายการป้ายกำกับแบบเดิม UI เบราว์เซอร์ไม่ได้เก็บรายการ regex ผู้ให้บริการของตัวเอง; Plugin เป็นเจ้าของชุดระดับเฉพาะโมเดล -- `/think:` ยังคงใช้งานได้และอัปเดตระดับเซสชันที่จัดเก็บเดียวกัน ดังนั้นคำสั่งแชตและตัวเลือกจึงซิงก์กัน +- ตัวเลือกการคิดในแชทเว็บสะท้อนระดับที่จัดเก็บของเซสชันจาก session store/config ขาเข้าเมื่อโหลดหน้า +- การเลือกระดับอื่นจะเขียนการแทนที่ของเซสชันทันทีผ่าน `sessions.patch`; ไม่รอการส่งครั้งถัดไป และไม่ใช่การแทนที่แบบครั้งเดียว `thinkingOnce` +- ตัวเลือกแรกคือ `Default ()` เสมอ โดยค่าเริ่มต้นที่แก้ค่าแล้วมาจากโปรไฟล์การคิดของผู้ให้บริการสำหรับโมเดลเซสชันที่ใช้งานอยู่ รวมกับตรรกะค่าถอยกลับเดียวกันที่ `/status` และ `session_status` ใช้ +- ตัวเลือกใช้ `thinkingLevels` ที่ส่งคืนโดยแถวเซสชัน/ค่าเริ่มต้นของ gateway โดยคง `thinkingOptions` ไว้เป็นรายการป้ายกำกับ legacy UI เบราว์เซอร์ไม่ได้เก็บรายการ regex ของผู้ให้บริการเอง; plugins เป็นเจ้าของชุดระดับเฉพาะโมเดล +- `/think:` ยังใช้งานได้และอัปเดตระดับเซสชันที่จัดเก็บเดียวกัน ดังนั้นคำสั่งแชทและตัวเลือกจึงซิงค์กัน ## โปรไฟล์ผู้ให้บริการ -- Plugin ผู้ให้บริการสามารถเปิดเผย `resolveThinkingProfile(ctx)` เพื่อกำหนดระดับที่โมเดลรองรับและค่าเริ่มต้นได้ -- Plugin ผู้ให้บริการที่พร็อกซีโมเดล Claude ควรใช้ `resolveClaudeThinkingProfile(modelId)` จาก `openclaw/plugin-sdk/provider-model-shared` ซ้ำ เพื่อให้แคตตาล็อก Anthropic โดยตรงและแคตตาล็อกพร็อกซีสอดคล้องกัน -- แต่ละระดับของโปรไฟล์มี `id` มาตรฐานที่จัดเก็บไว้ (`off`, `minimal`, `low`, `medium`, `high`, `xhigh`, `adaptive`, หรือ `max`) และอาจมี `label` สำหรับแสดงผล ผู้ให้บริการแบบไบนารีใช้ `{ id: "low", label: "on" }` -- Plugin เครื่องมือที่ต้องตรวจสอบการกำหนดระดับการคิดทับอย่างชัดเจนควรใช้ `api.runtime.agent.resolveThinkingPolicy({ provider, model })` ร่วมกับ `api.runtime.agent.normalizeThinkingLevel(...)`; ไม่ควรเก็บรายการระดับของผู้ให้บริการ/โมเดลไว้เอง -- Plugin เครื่องมือที่เข้าถึงเมตาดาต้าโมเดลแบบกำหนดเองที่กำหนดค่าไว้ได้ สามารถส่ง `catalog` เข้าไปใน `resolveThinkingPolicy` เพื่อให้การเลือกใช้ `compat.supportedReasoningEfforts` สะท้อนอยู่ในการตรวจสอบฝั่ง Plugin -- ฮุกแบบเดิมที่เผยแพร่แล้ว (`supportsXHighThinking`, `isBinaryThinking`, และ `resolveDefaultThinkingLevel`) ยังคงอยู่ในฐานะอะแดปเตอร์ความเข้ากันได้ แต่ชุดระดับแบบกำหนดเองใหม่ควรใช้ `resolveThinkingProfile` -- แถว/ค่าเริ่มต้นของ Gateway เปิดเผย `thinkingLevels`, `thinkingOptions`, และ `thinkingDefault` เพื่อให้ไคลเอนต์ ACP/แชตแสดงผลรหัสโปรไฟล์และป้ายกำกับเดียวกับที่การตรวจสอบขณะรันไทม์ใช้ +- Plugin ของผู้ให้บริการสามารถเปิดเผย `resolveThinkingProfile(ctx)` เพื่อกำหนดระดับที่โมเดลรองรับและค่าเริ่มต้น +- Plugin ของผู้ให้บริการที่พร็อกซีโมเดล Claude ควรใช้ `resolveClaudeThinkingProfile(modelId)` จาก `openclaw/plugin-sdk/provider-model-shared` ซ้ำ เพื่อให้แค็ตตาล็อก Anthropic โดยตรงและแค็ตตาล็อกพร็อกซีสอดคล้องกัน +- แต่ละระดับของโปรไฟล์มี `id` แบบบัญญัติที่จัดเก็บไว้ (`off`, `minimal`, `low`, `medium`, `high`, `xhigh`, `adaptive` หรือ `max`) และอาจมี `label` สำหรับแสดงผล ผู้ให้บริการแบบไบนารีใช้ `{ id: "low", label: "on" }` +- Plugin เครื่องมือที่ต้องตรวจสอบการแทนที่การคิดอย่างชัดเจนควรใช้ `api.runtime.agent.resolveThinkingPolicy({ provider, model })` พร้อมกับ `api.runtime.agent.normalizeThinkingLevel(...)`; ไม่ควรเก็บรายการระดับของผู้ให้บริการ/โมเดลไว้เอง +- Plugin เครื่องมือที่เข้าถึงเมตาดาต้าโมเดลแบบกำหนดเองที่ตั้งค่าไว้สามารถส่ง `catalog` เข้าไปใน `resolveThinkingPolicy` เพื่อให้การเลือกใช้ `compat.supportedReasoningEfforts` สะท้อนในการตรวจสอบฝั่ง Plugin +- hook แบบเดิมที่เผยแพร่แล้ว (`supportsXHighThinking`, `isBinaryThinking` และ `resolveDefaultThinkingLevel`) ยังคงเป็นอะแดปเตอร์ความเข้ากันได้ แต่ชุดระดับแบบกำหนดเองใหม่ควรใช้ `resolveThinkingProfile` +- แถว/ค่าเริ่มต้นของ Gateway เปิดเผย `thinkingLevels`, `thinkingOptions` และ `thinkingDefault` เพื่อให้ไคลเอนต์ ACP/chat แสดง id และ label ของโปรไฟล์เดียวกับที่การตรวจสอบรันไทม์ใช้