Skip to content

feat(agent-chat): reply_to param, installer isolation, pg-env precedence (#548, #569, #403) - #572

Merged
NOVA-Openclaw merged 15 commits into
mainfrom
feature/issue-548-reply-to-param
Aug 11, 2026
Merged

feat(agent-chat): reply_to param, installer isolation, pg-env precedence (#548, #569, #403)#572
NOVA-Openclaw merged 15 commits into
mainfrom
feature/issue-548-reply-to-param

Conversation

@NOVA-Openclaw

Copy link
Copy Markdown
Owner

Summary

Closes nova-mind#548, closes nova-mind#569, closes nova-mind#403.

Testing

  • 3 QA desk reviews + 2 targeted re-reviews, all PASS (reports/se633-step6-qa-review.md, with 5 addenda).
  • 23 automated test cases + BATS 28/28 + Python 84+25, all green.
  • 5 staging rounds on nova-staging, culminating in TC-001 + DoD-8 PASS — a real round-trip (received → routed → responded) verified end-to-end (reports/se633-step6-round5-tc001-dod8.md).
  • Step-8 QA validation PASS, live-verified.
  • Documentation audit completed (reports/se633-step9-doc-audit.md).

Deployment note

The production agent_chat database already runs the 5-arg migration (applied during the #569 incident on 2026-08-10; ownership corrected the same day). The deploy step for this PR is extension/installer alignment only — not a schema change.

Coder added 15 commits August 10, 2026 13:19
…y_to param (#548)

- Add database/agent-chat/migrations/001-send-agent-message-reply-to.sql
  that drops all historical overloads and recreates send_agent_message
  with p_ttl (4th) and p_reply_to (5th) positional parameters.
- Sync database/agent-chat/schema.sql to the live-plus-fix state:
  * add expires_at column and partial index,
  * update send_agent_message to 5 args including session_user check and
    self-message guard,
  * update enforce_agent_chat_function_use to live DML lockdown logic.
- Mark cognition/focus/agent_chat/schema.sql as deprecated post-#320 and
  keep its send_agent_message/enforce definitions consistent with the
  canonical schema.
#548)

- insertOutboundMessage now passes replyTo as p_reply_to in the single
  send_agent_message() SECURITY DEFINER call (named-argument form).
- Removes the separate UPDATE agent_chat SET reply_to statement that was
  rejected by the DML lockdown trigger.
- Distinctly logs foreign-key violations (SQLSTATE 23503) from the old
  permission-denied failure class; errors still propagate so
  markMessageFailed sets agent_chat_processed.status='failed'.
…548)

- Add _apply_agent_chat_migrations helper that runs sorted *.sql files from
  database/agent-chat/migrations/ against the dedicated agent_chat database.
- Invoke it after the agent_chat extension build in the cognition install
  section, with hard failure on migration error.
- Update the stale comment that pointed to the manual migrate.sh runbook.
- Add Node built-in test suite under cognition/focus/agent_chat/tests/.
- TC-006–TC-008: migration mechanics and overload ambiguity.
- TC-002–TC-016 + TC-020: send_agent_message behavior including reply_to,
  named args, backward compatibility, TTL, FK violations, validation guards,
  and atomicity.
- TC-018/TC-019: insertOutboundMessage issues one query and no UPDATE.
- TC-009/TC-020 amendment: processAgentChatMessage logs FK violations
  distinctly and drives markMessageFailed.
- Export insertOutboundMessage and processAgentChatMessage for testability.
- Add npm test script with constrained concurrency.
…ck (#548)

Finding 1 fix from SE633 Step 6 QA loop-back:
- channel.ts deliver() now calls markMessageFailed directly before re-throwing,
  because the real OpenClaw dispatcher swallows deliver's throw via .catch(onError).
- channel-insert.test.mjs mock now reproduces the real .then().catch(onError)
  promise-chain semantics so a regression of this class fails automatically.

Refs: nova-mind#548
Finding 2 fix from SE633 Step 6 QA loop-back:
- _apply_agent_chat_migrations now applies database/agent-chat/schema.sql
  unconditionally before the migrations loop. The schema file is idempotent,
  so re-applying it on every install run is safe, and it guarantees fresh
  installs have the tables/triggers/functions that migration 001 assumes.

Refs: nova-mind#548
…write (#548)

Finding A fix from SE633 Step 6 re-review:
- markMessageRouted's UPDATE now includes AND status NOT IN ('failed', 'responded')
  so a downstream 'routed' transition cannot clobber a terminal status already
  written by deliver's markMessageFailed call.
- Strengthened channel-insert.test.mjs to assert the FINAL status write is
  'failed', and updated the fake client to simulate the SQL guard only when the
  guard text is present (pre-fix FAIL, post-fix PASS).

Refs: nova-mind#548
…es (#548)

Finding B fix from SE633 Step 6 re-review:
- Added DROP FUNCTION IF EXISTS for 3-arg, 4-arg, and 5-arg signatures
  immediately before CREATE OR REPLACE in both canonical schema files.
- Prevents a transient function-overload window when agent-install.sh re-runs
  schema.sql against a live DB that still has the pre-#548 4-arg signature,
  matching migration 001's idempotent pattern.

Refs: nova-mind#548
…mutation

- Resolve agent_chat DB from ~/.openclaw/postgres.json agentChatDatabase,
  falling back to AGENT_CHAT_DB_NAME env var, then default agent_chat.
- Hard-refuse to target the literal 'agent_chat' DB when run as a non-nova
  unix user, preventing staging installs from mutating the shared production
  agent_chat bus.
- Preserve the chosen target as agentChatDatabase in postgres.json.

Fixes #569
Add a wrapped ALTER FUNCTION ... OWNER TO postgres after CREATE OR REPLACE
in both schema files and migration 001. This ensures the SECURITY DEFINER
function is owned by postgres regardless of which superuser applies the DDL,
so the DML lockdown trigger continues to authorize INSERTs via current_user
= 'postgres'. Wrapped in a DO block so non-superuser devtest applies skip the
owner assignment gracefully.

Refs #569
…guard

- SQL suite: verify canonical schema, deprecated schema, and migration 001 all
  contain ALTER FUNCTION ... OWNER TO postgres; also assert the temp-harness
  owner equals the applying role (the wrapped ALTER is skipped when not a
  superuser).
- BATS suite: update postgres.json assertions for agentChatDatabase,
  add refusal-guard tests that simulate a non-nova user targeting agent_chat.

Refs #569
Applies the nova-mind#398 Python fix pattern to all three TypeScript
loadPgEnv implementations:
- lib/pg-env.ts
- memory/lib/pg-env.ts
- cognition/focus/agent_chat/lib/pg-env.ts

Contract: when a section is provided and explicitly defines a field
(non-null, non-empty), that section value wins over process.env for that
field only. Omitted fields keep ENV -> flat-config -> default.

Also updates docstrings/comments to match the new precedence and ports
Python TC-30 through TC-43 coverage to the TS test suites, including a
regression test for the staging failure mode where PGDATABASE shadows the
agent_chat section database.

Closes #403
…ioning, #403 pg-env TS parity

- psyche/ARCHITECTURE-agent-chat.md: 5-arg send_agent_message() signature,
  session_user spoofing-proof validation, self-address guard, postgres
  ownership rationale, rewritten trigger semantics, markMessageRouted()
  terminal-status guard, expires_at column
- database/schema-reference.md: signature note + corrected agent_chat column
  count (6->7)
- memory/docs/database-config.md: corrected stale TS-vs-Python precedence
  claim (TS now has per-field section-over-ENV parity, was previously
  documented as still ENV-first); new Installer-Provisioned agent_chat
  Database Target section (agentChatDatabase, refusal guard, schema-then-
  migrations sequence)
- memory/README.md: same TS-parity correction
- memory/CHANGELOG.md, cognition/CHANGELOG.md, CHANGELOG.md (root): new
  entries for #548/#569/#403
- memory/INSTALLATION.md: Recent Changes entry
- memory/docs/database-schema-guide.md: updated agent_chat schema/example
- cognition/docs/installation.md, cognition/README.md: corrected stale
  'schema applied separately, not by this installer' claims (installer now
  applies schema+migrations automatically)
- scripts/agent-chat-migration/README.md: clarified historical-runbook status
  vs. the new migrations-directory mechanism; clarified agentChatDatabase vs.
  nested agent_chat section are distinct, non-superseding concepts
- skills/agent-ecosystem/SKILL.md: p_reply_to usage example
- reports/se633-step9-doc-audit.md: full audit report

Refs #548, #569, #403
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant