feat: REPL development tool + naming drift fixes + HITL gateways
Some checks failed
Deploy (Gitea) / deploy (push) Failing after 3s

REPL tool:
- ~/.opencode/bin/repl — connects to running daemon, evaluates Lisp forms,
  returns results. Usage: repl '(+ 1 2)' or via stdin.
- Server-side handler in programming-repl skill registers for :repl-eval
  sensor, bypasses LLM pipeline, writes result back through reply-stream.
- Core provides pre-reason-handler registry (register-pre-reason-handler)
  for skills to register custom sensors without modifying core code.

HITL gateway integration:
- hitl-handle-message: TUI, Telegram, and Signal gateways intercept
  approval/deny commands before they reach the LLM.
- hitl-create/hitl-approve/hitl-deny: in-memory HITL store with correlation
  tokens for gateway-agnostic approval.
- loop-gate-perceive detects HITL commands and blocks LLM processing.

Naming drift fixes (the complete batch):
- register-actuator vs actuator-register — fixed to register-actuator
- process-signal vs loop-process — alias added
- perceive-gate/reason-gate/act-gate vs loop-gate-* — aliases added
- initialize-actuators vs actuator-initialize — fixed to actuator-initialize
- initialize-all-skills vs skill-initialize-all — fixed to skill-initialize-all
- inject-stimulus alias added for backward compatibility
- All original gateway-manager inject-stimulus → stimulus-inject + HITL check
This commit is contained in:
2026-05-03 13:46:32 -04:00
parent a77580c449
commit e0a47575e9
16 changed files with 209 additions and 49 deletions

View File

@@ -61,6 +61,30 @@ A global interrupt flag that can be set by any signal. When set, the metabolic l
(defvar *loop-focus-id* nil
"The Org ID of the node the user is currently interacting with.")
#+end_src
** Pre-Reason Handler Registry
Skills register handlers for custom sensors here. When a signal arrives
with a registered sensor, the handler is called in the perceive gate,
before the signal reaches the LLM. The handler receives the full signal
and returns T if the signal was consumed (don't continue to reason)
or nil if processing should proceed normally.
;; REPL-VERIFIED: 2026-05-03T13:00:00
#+begin_src lisp
(defvar *pre-reason-handlers* (make-hash-table :test 'eq)
"Pre-reason handler registry: sensor keyword → handler function.")
(defun register-pre-reason-handler (sensor fn)
"Registers FN to handle signals with SENSOR in the perceive gate.
FN receives (signal) and returns T if consumed, nil to continue."
(setf (gethash sensor *pre-reason-handlers*) fn))
;; Alias for backward compatibility
(defun inject-stimulus (raw-message &key stream (depth 0))
"Alias for stimulus-inject."
(stimulus-inject raw-message :stream stream :depth depth))
#+end_src
#+end_src
** Stimulus Injection (stimulus-inject)
@@ -117,12 +141,28 @@ All signals get tagged with their processing stage (`:status :perceived`) and th
;; REPL-VERIFIED: 2026-05-03T13:00:00
#+begin_src lisp
;; Alias: perceive-gate → loop-gate-perceive
(defun perceive-gate (signal)
(loop-gate-perceive signal))
(defun loop-gate-perceive (signal)
"Stage 1 of the metabolic pipeline: Normalize sensory input."
(let* ((payload (getf signal :payload))
(type (getf signal :type))
(meta (getf signal :meta))
(sensor (getf payload :sensor)))
(type (getf signal :type))
(meta (getf signal :meta))
(sensor (getf payload :sensor)))
;; HITL: intercept approval/denial commands before LLM processing
(when (and (eq sensor :user-input)
(stringp (getf payload :text)))
(let ((text (getf payload :text)))
(when (ignore-errors (hitl-handle-message text (getf meta :source)))
(log-message "GATE [Perceive]: HITL command processed — ~a" text)
(return-from loop-gate-perceive signal))))
;; Pre-reason handlers: dispatch custom sensors to registered skill handlers
(let ((handler (gethash sensor *pre-reason-handlers*)))
(when handler
(when (funcall handler signal)
(return-from loop-gate-perceive signal))))
(log-message "GATE [Perceive]: ~a (~a) [Source: ~s]"
type (or sensor "no-sensor") (getf meta :source))