Rule Engine ↔ SCSAI Synchronization Architecture and Operations Manual

Rule Engine ↔ SCSAI Synchronization Architecture and Operations Manual

Last Updated: 2026-07-23

Applicable Code: server/core/SCSAI-rule-sync.js, server/core/rule-engine.js, server/core/capability-runtime.js, server/scripts/sync-rules-bidirectional.js, server.js (drift self-check)


1. Authoritative Source and Data Flow

  • Authoritative Storage: SCSAI's BossAgent_Rule (2000+ entries, fields with prefix bossagent_*).
  • Local Copy: The sciot_rules_v2 table in server/data/rule_engine.db (the database actually read by the runtime engine).
  • Direction:
  • SCSAI → Local: Read-only pull, using item_number (= local rule.id) for idempotent upsert.
  • Local → SCSAI: Writeback (push), via SCSAIRuleSync.syncRuleToSCSAI, writes to BossAgent_Rule (no longer the deprecated BOS_RULE: Method).

⚠️ Historical pitfall (fixed, recorded to prevent regression)

  • The old SCSAIRuleSync wrote rules into BOS_RULE: Method (a dead path no one reads). Now rewritten to write to BossAgent_Rule.
  • The old version didn't pass SCSAIClient when creating the engine → the saveRule writeback was entirely skipped. Now capability-runtime.js passes this.SCSAIClient when creating the UnifiedRuleEngine.

2. Field Mapping (SCSAI BossAgent_Rule ↔ Local sciot_rules_v2)

Local ColumnSCSAI AttributeDescription
iditem_numberupsert key, consistent across both ends
namename
descriptiondescription
scopebossagent_scopevalidate/repair/optimize/compare/generate/identify
item_type_namebossagent_item_typeApplicable object class, * indicates universal
severitybossagent_severityinfo/warn/error
prioritybossagent_priorityinteger
condition_scriptbossagent_condition_scriptTEXT, nullable
action_typebossagent_action_typesuggest/auto_fix/...
action_configbossagent_action_configJSON string
action_scriptbossagent_generated_amlTEXT, nullable
is_activebossagent_is_active0/1
is_builtinbossagent_is_builtin0/1
sourcebossagent_sourcegenerated/builtin/inspect/biz/manual/SCSAI
versionbossagent_versioninteger
tagsbossagent_tagsCSV or JSON string
categorybossagent_category
SCSAI_idid (@_id)GUID of the SCSAI item, written back as proof

Key normalization: _SCSAIVal()

Empty properties returned by SCSAI sendAML are not null, but objects {is_null:"1"}; reference properties may be {keyed_name:...}. Using value || null as a fallback directly in code doesn't work (objects are truthy), which passes the object into better-sqlite3 → binding fails with 'Too few parameter values' → entire batch is skipped (this was the real culprit behind the long-term 0 records in previous PULL).

_SCSAIVal(v) is responsible for normalization:

  • Original null/undefined → null
  • String/Number/Boolean → String
  • Object: contains is_null → null; contains #text/keyed_name/value → take its value; others → JSON.stringify into TEXT column

3. Synchronization Script

server/scripts/sync-rules-bidirectional.js:

node server/scripts/sync-rules-bidirectional.js            # 默认:pull(SCSAI → 本地)
node server/scripts/sync-rules-bidirectional.js --push    # 本地 → SCSAI(仅 is_builtin=0)
node server/scripts/sync-rules-bidirectional.js --both    # 先 pull 再 push
node server/scripts/sync-rules-bidirectional.js --dry     # 只读漂移检查,不写任一端
  • PULL:SCSAIRuleSync.syncRulesFromSCSAI(SCSAIClient, engine),按 item_number upsert。maxRecords 5000。
  • PUSH:遍历本地 is_builtin = 0 行,逐条 syncRuleToSCSAI。id 为 NULL 的行会被跳过(无合法 id 无法映射,非 bug)。
  • 漂移自检:server.js 启动后约 15s 报告本地与 SCSAI 的 item_number 差异(只读 Warn,不写任一端)。

4. 规则生命周期(CRUD 是否回写)

| 操作位置 | 是否回写 SCSAI | 现状 |

|---|---|---|

| Server-side BossAgent_Rule add/edit/delete | Project only reads via get, never writes | Server changes → require manual pull locally to take effect |

| Local management interface saveRule | Yes, writes to BossAgent_Rule | Takes effect immediately when engine is created with SCSAIClient passed |

| Local management interface deleteRule | Yes (via SCSAIRuleSync) | Same as above |

| sync-rules-SCSAI-to-local.js | Read-only pull | Idempotent overwrite, will overwrite local modifications not uploaded to SCSAI |

Note: Pull uses item_number for idempotent overwrite. If local manual modifications exist but the corresponding item is missing on the SCSAI side, rerunning pull will not delete locally redundant rules, but will overwrite rules with the same name—local exclusive modifications risk being overwritten; it is recommended to push first.


5. Operational Key Points

  1. First/Periodic Alignment: Run --both for a bidirectional sync to converge.
  2. Confirm Sync Rate: Check the count of entries in sciot_rules_v2 where SCSAI_id is not null; normally this should be close to the total number of local non-garbage rules.
  3. Orphaned Rules: Local rules with id IS NULL cannot be pushed; assign them semantic IDs first (e.g., biz-repair-xxx-001).
  4. Drift Alert: Search for [RuleDrift] in startup logs; a WARN indicates divergence between the two ends, requiring --both to fix.
  5. Data Quality: action_config/tags must be valid JSON or CSV; action_config for inspect-type rules allows key:value text (the engine has special parsing).
  6. rule_engine.db is a runtime artifact and is excluded by .gitignore; it can be rebuilt from SCSAI at any time using --both.

6. Known Legacy Issues

  • Local source=builtin rules (e.g., BUILTIN-, built-in biz-) are not written back to SCSAI (by design, SCSAI is the authoritative source; built-in rules should align with SCSAI).
  • No automatic/scheduled sync; currently relies on startup drift self-check + manual --both. For persistent sync, add cron/scheduled tasks to call this script.
  • Local copies of BossAgent_Prompt / BossAgent_Template / BossAgent_BizPrompt are still pulled read-only by template-sync-service.js; modifications via the management interface are not yet written back to SCSAI (a separate to-do).
← 返回案例列表

Try 左帮右臂 Industrial Agent — your digital workforce

Available as a WeChat mini program, web app (ylxt.chat) and desktop client. Start from whichever fits your workflow.

🌐 Web App 💻 Desktop Download 📞 Call 189-8606-6876
WeChat mini program QR
Scan for the WeChat mini program
Share:
🤖 Try Now →
🤖
🎁