5.4 KiB
Command Registration And Execution Paths
Status: authoritative local registration and routing contract for
beta 1.0.x.
Three Execution Paths
Every accepted message resolves to exactly one named execution path:
| Execution path | Input | Runtime | Reply behavior |
|---|---|---|---|
local-command |
Registered /command |
Kernel command or reviewed plugin | Synchronous local reply, except explicitly asynchronous Steam |
deepseek |
Ordinary @JWeBot message |
Direct DeepSeek client | Fast ACK, background generation, ACK-gated final reply |
openclaw |
@JWeBot #task |
OpenClaw cloud runner | Fast ACK, durable cloud outbox, ACK-gated final reply |
The compatibility route values remain local, chat, and cloud in stored
events. API responses and telemetry also include the explicit
execution_path, so operators and plugin authors do not need to infer the
actual provider from a legacy storage label.
Unknown slash commands remain on local-command and fail with a local command
error. They never fall through to DeepSeek or OpenClaw.
Fast Local Ingress
The local command path is:
- XDamage reports a relevant message-region change, or a two-second idle reconciliation capture detects a missed final drawing.
- OpenCV segments incoming bubbles without running OCR over the whole screen.
- The OCR engine reuses exact visual-fingerprint matches from a bounded LRU.
- Only new or changed sender/body crops use RapidOCR.
- Both recognition-only and detection fallback paths are prewarmed at startup.
- A command event is written to an atomic, fsynced spool file.
- The in-process responder is signalled immediately after durable replacement.
- Edge durably records and executes the local command.
- The guarded GUI sender revalidates the selected group and sends the reply.
The queue directory remains the recovery source of truth. The wake signal is only a latency optimization; a separate responder process or a missed signal still discovers work through the bounded one-second fallback scan.
Exact image bytes, crop dimensions, and sender pixels participate in the OCR
cache key. Identical repeated messages remain separate visible occurrences
because each bubble position still produces its own IncomingMessage.
Changed pixels force fresh OCR. The cache is bounded and periodically
revalidated.
For the local plugins introduced during the 0.6.x line, including bilingual commands, person identity limitations and atomic single-player game settlement, see local plugin rules.
Bundled Plugin Registration
Bundled command metadata has one source:
packages/jwebot-official-extensions/
src/jwebot_official_extensions/descriptors.py
Each LocalExtensionDescriptor declares:
extension_id;author;- user-visible
description; - user-visible
help_entries; - owned internal
command_kinds.
Aliases are resolved from the same inventory. Run:
./tools/sync-local-extensions.py
The generator writes matching:
plugin.toml;- SDK adapter source;
- package README;
- package registration test;
- in-process compatibility adapter.
--check is part of the repository gate and rejects generated drift.
Friend Plugin Registration
Create a command plugin with explicit user-facing metadata:
./tools/create-plugin.py weather-command /weather \
--author FriendName \
--description "查询指定城市天气" \
--help-entry "/weather 城市"
The command must also be registered in the plugin entrypoint:
def plugin(context):
context.commands.register("/weather", handle)
Startup fails if registered commands differ from signed manifest commands. The catalog freezes after startup, so command ownership cannot change during request processing.
Automatic Help
/功能列表, /帮助, and /help are Kernel commands. Their visible output is
generated from:
- Kernel command descriptors;
- each bundled plugin's
description; - each bundled plugin's
help_entries; - the fixed DeepSeek and OpenClaw path descriptions.
There is no separate hand-maintained help list. Adding or changing a bundled plugin command without updating its descriptor changes generated files and fails the sync gate.
Signed Host health responses include description and help metadata. Edge compares them with the startup inventory together with author, commands, and service profiles before activating the Host.
Manifest Metadata
Command manifests must declare:
description = "查询指定城市天气"
help = ["/weather 城市"]
description and help must be declared together. Help entries are bounded,
single-line command usage strings beginning with /. Bundled plugins require
both fields.
User-visible help text is metadata only. It grants no capability and cannot change routing ownership.
Official Operational Plugins
Operational slash commands are implemented through official reviewed plugin descriptors unless they are strictly Kernel-only. The current official operational commands are:
/状态and/status: server, Edge, OCR, and queue status./version: installed JWeBot package versions plus the latest changelog date and summary./debug: recent privacy-safe telemetry p50/p95/max summary.
These commands delegate to Kernel-owned service profiles through generated adapters. They do not give plugin code direct access to raw SQLite, systemd, journal, GUI, shell, or secrets.