@nebulacomponents/citable 1.13.1 → 1.15.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (359) hide show
  1. package/CHANGELOG.md +312 -0
  2. package/README.md +44 -6
  3. package/dist/universal/.agents/skills/citable/SKILL.md +22 -8
  4. package/dist/universal/.agents/skills/citable/VERSION +1 -1
  5. package/dist/universal/.agents/skills/citable/agents/citable-auditor.md +64 -0
  6. package/dist/universal/.agents/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  7. package/dist/universal/.agents/skills/citable/commands/README.md +4 -1
  8. package/dist/universal/.agents/skills/citable/commands/action-findings.md +9 -1
  9. package/dist/universal/.agents/skills/citable/commands/observe-and-act.md +62 -8
  10. package/dist/universal/.agents/skills/citable/commands/plan-audit.md +35 -0
  11. package/dist/universal/.agents/skills/citable/commands/reporting.md +57 -0
  12. package/dist/universal/.agents/skills/citable/manifest.json +29 -16
  13. package/dist/universal/.agents/skills/citable/schemas/action-plan.schema.json +13 -0
  14. package/dist/universal/.agents/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  15. package/dist/universal/.agents/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  16. package/dist/universal/.agents/skills/citable/schemas/common.defs.json +12 -1
  17. package/dist/universal/.agents/skills/citable/schemas/corroboration-import.schema.json +48 -0
  18. package/dist/universal/.agents/skills/citable/schemas/entity-graph.schema.json +75 -0
  19. package/dist/universal/.agents/skills/citable/schemas/entity.schema.json +13 -0
  20. package/dist/universal/.agents/skills/citable/schemas/observation.schema.json +1 -1
  21. package/dist/universal/.agents/skills/citable/schemas/page.schema.json +3 -0
  22. package/dist/universal/.agents/skills/citable/schemas/regional-network-import.schema.json +55 -0
  23. package/dist/universal/.agents/skills/citable/schemas/schedule.schema.json +1 -1
  24. package/dist/universal/.agents/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  25. package/dist/universal/.agents/skills/citable/scripts/README.md +3 -1
  26. package/dist/universal/.claude/agents/citable/citable-auditor.md +64 -0
  27. package/dist/universal/.claude/agents/citable/citable-semantic-reviewer.md +66 -0
  28. package/dist/universal/.claude/agents/citable/manifest.json +12 -0
  29. package/dist/universal/.claude/skills/citable/SKILL.md +22 -8
  30. package/dist/universal/.claude/skills/citable/VERSION +1 -1
  31. package/dist/universal/.claude/skills/citable/agents/citable-auditor.md +64 -0
  32. package/dist/universal/.claude/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  33. package/dist/universal/.claude/skills/citable/commands/README.md +4 -1
  34. package/dist/universal/.claude/skills/citable/commands/action-findings.md +9 -1
  35. package/dist/universal/.claude/skills/citable/commands/observe-and-act.md +62 -8
  36. package/dist/universal/.claude/skills/citable/commands/plan-audit.md +35 -0
  37. package/dist/universal/.claude/skills/citable/commands/reporting.md +57 -0
  38. package/dist/universal/.claude/skills/citable/manifest.json +34 -16
  39. package/dist/universal/.claude/skills/citable/schemas/action-plan.schema.json +13 -0
  40. package/dist/universal/.claude/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  41. package/dist/universal/.claude/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  42. package/dist/universal/.claude/skills/citable/schemas/common.defs.json +12 -1
  43. package/dist/universal/.claude/skills/citable/schemas/corroboration-import.schema.json +48 -0
  44. package/dist/universal/.claude/skills/citable/schemas/entity-graph.schema.json +75 -0
  45. package/dist/universal/.claude/skills/citable/schemas/entity.schema.json +13 -0
  46. package/dist/universal/.claude/skills/citable/schemas/observation.schema.json +1 -1
  47. package/dist/universal/.claude/skills/citable/schemas/page.schema.json +3 -0
  48. package/dist/universal/.claude/skills/citable/schemas/regional-network-import.schema.json +55 -0
  49. package/dist/universal/.claude/skills/citable/schemas/schedule.schema.json +1 -1
  50. package/dist/universal/.claude/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  51. package/dist/universal/.claude/skills/citable/scripts/README.md +3 -1
  52. package/dist/universal/.cursor/skills/citable/SKILL.md +22 -8
  53. package/dist/universal/.cursor/skills/citable/VERSION +1 -1
  54. package/dist/universal/.cursor/skills/citable/agents/citable-auditor.md +64 -0
  55. package/dist/universal/.cursor/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  56. package/dist/universal/.cursor/skills/citable/commands/README.md +4 -1
  57. package/dist/universal/.cursor/skills/citable/commands/action-findings.md +9 -1
  58. package/dist/universal/.cursor/skills/citable/commands/observe-and-act.md +62 -8
  59. package/dist/universal/.cursor/skills/citable/commands/plan-audit.md +35 -0
  60. package/dist/universal/.cursor/skills/citable/commands/reporting.md +57 -0
  61. package/dist/universal/.cursor/skills/citable/manifest.json +29 -16
  62. package/dist/universal/.cursor/skills/citable/schemas/action-plan.schema.json +13 -0
  63. package/dist/universal/.cursor/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  64. package/dist/universal/.cursor/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  65. package/dist/universal/.cursor/skills/citable/schemas/common.defs.json +12 -1
  66. package/dist/universal/.cursor/skills/citable/schemas/corroboration-import.schema.json +48 -0
  67. package/dist/universal/.cursor/skills/citable/schemas/entity-graph.schema.json +75 -0
  68. package/dist/universal/.cursor/skills/citable/schemas/entity.schema.json +13 -0
  69. package/dist/universal/.cursor/skills/citable/schemas/observation.schema.json +1 -1
  70. package/dist/universal/.cursor/skills/citable/schemas/page.schema.json +3 -0
  71. package/dist/universal/.cursor/skills/citable/schemas/regional-network-import.schema.json +55 -0
  72. package/dist/universal/.cursor/skills/citable/schemas/schedule.schema.json +1 -1
  73. package/dist/universal/.cursor/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  74. package/dist/universal/.cursor/skills/citable/scripts/README.md +3 -1
  75. package/dist/universal/.gemini/skills/citable/SKILL.md +22 -8
  76. package/dist/universal/.gemini/skills/citable/VERSION +1 -1
  77. package/dist/universal/.gemini/skills/citable/agents/citable-auditor.md +64 -0
  78. package/dist/universal/.gemini/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  79. package/dist/universal/.gemini/skills/citable/commands/README.md +4 -1
  80. package/dist/universal/.gemini/skills/citable/commands/action-findings.md +9 -1
  81. package/dist/universal/.gemini/skills/citable/commands/observe-and-act.md +62 -8
  82. package/dist/universal/.gemini/skills/citable/commands/plan-audit.md +35 -0
  83. package/dist/universal/.gemini/skills/citable/commands/reporting.md +57 -0
  84. package/dist/universal/.gemini/skills/citable/manifest.json +29 -16
  85. package/dist/universal/.gemini/skills/citable/schemas/action-plan.schema.json +13 -0
  86. package/dist/universal/.gemini/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  87. package/dist/universal/.gemini/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  88. package/dist/universal/.gemini/skills/citable/schemas/common.defs.json +12 -1
  89. package/dist/universal/.gemini/skills/citable/schemas/corroboration-import.schema.json +48 -0
  90. package/dist/universal/.gemini/skills/citable/schemas/entity-graph.schema.json +75 -0
  91. package/dist/universal/.gemini/skills/citable/schemas/entity.schema.json +13 -0
  92. package/dist/universal/.gemini/skills/citable/schemas/observation.schema.json +1 -1
  93. package/dist/universal/.gemini/skills/citable/schemas/page.schema.json +3 -0
  94. package/dist/universal/.gemini/skills/citable/schemas/regional-network-import.schema.json +55 -0
  95. package/dist/universal/.gemini/skills/citable/schemas/schedule.schema.json +1 -1
  96. package/dist/universal/.gemini/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  97. package/dist/universal/.gemini/skills/citable/scripts/README.md +3 -1
  98. package/dist/universal/.github/skills/citable/SKILL.md +22 -8
  99. package/dist/universal/.github/skills/citable/VERSION +1 -1
  100. package/dist/universal/.github/skills/citable/agents/citable-auditor.md +64 -0
  101. package/dist/universal/.github/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  102. package/dist/universal/.github/skills/citable/commands/README.md +4 -1
  103. package/dist/universal/.github/skills/citable/commands/action-findings.md +9 -1
  104. package/dist/universal/.github/skills/citable/commands/observe-and-act.md +62 -8
  105. package/dist/universal/.github/skills/citable/commands/plan-audit.md +35 -0
  106. package/dist/universal/.github/skills/citable/commands/reporting.md +57 -0
  107. package/dist/universal/.github/skills/citable/manifest.json +29 -16
  108. package/dist/universal/.github/skills/citable/schemas/action-plan.schema.json +13 -0
  109. package/dist/universal/.github/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  110. package/dist/universal/.github/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  111. package/dist/universal/.github/skills/citable/schemas/common.defs.json +12 -1
  112. package/dist/universal/.github/skills/citable/schemas/corroboration-import.schema.json +48 -0
  113. package/dist/universal/.github/skills/citable/schemas/entity-graph.schema.json +75 -0
  114. package/dist/universal/.github/skills/citable/schemas/entity.schema.json +13 -0
  115. package/dist/universal/.github/skills/citable/schemas/observation.schema.json +1 -1
  116. package/dist/universal/.github/skills/citable/schemas/page.schema.json +3 -0
  117. package/dist/universal/.github/skills/citable/schemas/regional-network-import.schema.json +55 -0
  118. package/dist/universal/.github/skills/citable/schemas/schedule.schema.json +1 -1
  119. package/dist/universal/.github/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  120. package/dist/universal/.github/skills/citable/scripts/README.md +3 -1
  121. package/dist/universal/.kiro/skills/citable/SKILL.md +22 -8
  122. package/dist/universal/.kiro/skills/citable/VERSION +1 -1
  123. package/dist/universal/.kiro/skills/citable/agents/citable-auditor.md +64 -0
  124. package/dist/universal/.kiro/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  125. package/dist/universal/.kiro/skills/citable/commands/README.md +4 -1
  126. package/dist/universal/.kiro/skills/citable/commands/action-findings.md +9 -1
  127. package/dist/universal/.kiro/skills/citable/commands/observe-and-act.md +62 -8
  128. package/dist/universal/.kiro/skills/citable/commands/plan-audit.md +35 -0
  129. package/dist/universal/.kiro/skills/citable/commands/reporting.md +57 -0
  130. package/dist/universal/.kiro/skills/citable/manifest.json +29 -16
  131. package/dist/universal/.kiro/skills/citable/schemas/action-plan.schema.json +13 -0
  132. package/dist/universal/.kiro/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  133. package/dist/universal/.kiro/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  134. package/dist/universal/.kiro/skills/citable/schemas/common.defs.json +12 -1
  135. package/dist/universal/.kiro/skills/citable/schemas/corroboration-import.schema.json +48 -0
  136. package/dist/universal/.kiro/skills/citable/schemas/entity-graph.schema.json +75 -0
  137. package/dist/universal/.kiro/skills/citable/schemas/entity.schema.json +13 -0
  138. package/dist/universal/.kiro/skills/citable/schemas/observation.schema.json +1 -1
  139. package/dist/universal/.kiro/skills/citable/schemas/page.schema.json +3 -0
  140. package/dist/universal/.kiro/skills/citable/schemas/regional-network-import.schema.json +55 -0
  141. package/dist/universal/.kiro/skills/citable/schemas/schedule.schema.json +1 -1
  142. package/dist/universal/.kiro/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  143. package/dist/universal/.kiro/skills/citable/scripts/README.md +3 -1
  144. package/dist/universal/.opencode/skills/citable/SKILL.md +22 -8
  145. package/dist/universal/.opencode/skills/citable/VERSION +1 -1
  146. package/dist/universal/.opencode/skills/citable/agents/citable-auditor.md +64 -0
  147. package/dist/universal/.opencode/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  148. package/dist/universal/.opencode/skills/citable/commands/README.md +4 -1
  149. package/dist/universal/.opencode/skills/citable/commands/action-findings.md +9 -1
  150. package/dist/universal/.opencode/skills/citable/commands/observe-and-act.md +62 -8
  151. package/dist/universal/.opencode/skills/citable/commands/plan-audit.md +35 -0
  152. package/dist/universal/.opencode/skills/citable/commands/reporting.md +57 -0
  153. package/dist/universal/.opencode/skills/citable/manifest.json +29 -16
  154. package/dist/universal/.opencode/skills/citable/schemas/action-plan.schema.json +13 -0
  155. package/dist/universal/.opencode/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  156. package/dist/universal/.opencode/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  157. package/dist/universal/.opencode/skills/citable/schemas/common.defs.json +12 -1
  158. package/dist/universal/.opencode/skills/citable/schemas/corroboration-import.schema.json +48 -0
  159. package/dist/universal/.opencode/skills/citable/schemas/entity-graph.schema.json +75 -0
  160. package/dist/universal/.opencode/skills/citable/schemas/entity.schema.json +13 -0
  161. package/dist/universal/.opencode/skills/citable/schemas/observation.schema.json +1 -1
  162. package/dist/universal/.opencode/skills/citable/schemas/page.schema.json +3 -0
  163. package/dist/universal/.opencode/skills/citable/schemas/regional-network-import.schema.json +55 -0
  164. package/dist/universal/.opencode/skills/citable/schemas/schedule.schema.json +1 -1
  165. package/dist/universal/.opencode/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  166. package/dist/universal/.opencode/skills/citable/scripts/README.md +3 -1
  167. package/dist/universal/.pi/agent/skills/citable/SKILL.md +22 -8
  168. package/dist/universal/.pi/agent/skills/citable/VERSION +1 -1
  169. package/dist/universal/.pi/agent/skills/citable/agents/citable-auditor.md +64 -0
  170. package/dist/universal/.pi/agent/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  171. package/dist/universal/.pi/agent/skills/citable/commands/README.md +4 -1
  172. package/dist/universal/.pi/agent/skills/citable/commands/action-findings.md +9 -1
  173. package/dist/universal/.pi/agent/skills/citable/commands/observe-and-act.md +62 -8
  174. package/dist/universal/.pi/agent/skills/citable/commands/plan-audit.md +35 -0
  175. package/dist/universal/.pi/agent/skills/citable/commands/reporting.md +57 -0
  176. package/dist/universal/.pi/agent/skills/citable/manifest.json +29 -16
  177. package/dist/universal/.pi/agent/skills/citable/schemas/action-plan.schema.json +13 -0
  178. package/dist/universal/.pi/agent/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  179. package/dist/universal/.pi/agent/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  180. package/dist/universal/.pi/agent/skills/citable/schemas/common.defs.json +12 -1
  181. package/dist/universal/.pi/agent/skills/citable/schemas/corroboration-import.schema.json +48 -0
  182. package/dist/universal/.pi/agent/skills/citable/schemas/entity-graph.schema.json +75 -0
  183. package/dist/universal/.pi/agent/skills/citable/schemas/entity.schema.json +13 -0
  184. package/dist/universal/.pi/agent/skills/citable/schemas/observation.schema.json +1 -1
  185. package/dist/universal/.pi/agent/skills/citable/schemas/page.schema.json +3 -0
  186. package/dist/universal/.pi/agent/skills/citable/schemas/regional-network-import.schema.json +55 -0
  187. package/dist/universal/.pi/agent/skills/citable/schemas/schedule.schema.json +1 -1
  188. package/dist/universal/.pi/agent/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  189. package/dist/universal/.pi/agent/skills/citable/scripts/README.md +3 -1
  190. package/dist/universal/.qoder/skills/citable/SKILL.md +22 -8
  191. package/dist/universal/.qoder/skills/citable/VERSION +1 -1
  192. package/dist/universal/.qoder/skills/citable/agents/citable-auditor.md +64 -0
  193. package/dist/universal/.qoder/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  194. package/dist/universal/.qoder/skills/citable/commands/README.md +4 -1
  195. package/dist/universal/.qoder/skills/citable/commands/action-findings.md +9 -1
  196. package/dist/universal/.qoder/skills/citable/commands/observe-and-act.md +62 -8
  197. package/dist/universal/.qoder/skills/citable/commands/plan-audit.md +35 -0
  198. package/dist/universal/.qoder/skills/citable/commands/reporting.md +57 -0
  199. package/dist/universal/.qoder/skills/citable/manifest.json +29 -16
  200. package/dist/universal/.qoder/skills/citable/schemas/action-plan.schema.json +13 -0
  201. package/dist/universal/.qoder/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  202. package/dist/universal/.qoder/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  203. package/dist/universal/.qoder/skills/citable/schemas/common.defs.json +12 -1
  204. package/dist/universal/.qoder/skills/citable/schemas/corroboration-import.schema.json +48 -0
  205. package/dist/universal/.qoder/skills/citable/schemas/entity-graph.schema.json +75 -0
  206. package/dist/universal/.qoder/skills/citable/schemas/entity.schema.json +13 -0
  207. package/dist/universal/.qoder/skills/citable/schemas/observation.schema.json +1 -1
  208. package/dist/universal/.qoder/skills/citable/schemas/page.schema.json +3 -0
  209. package/dist/universal/.qoder/skills/citable/schemas/regional-network-import.schema.json +55 -0
  210. package/dist/universal/.qoder/skills/citable/schemas/schedule.schema.json +1 -1
  211. package/dist/universal/.qoder/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  212. package/dist/universal/.qoder/skills/citable/scripts/README.md +3 -1
  213. package/dist/universal/.rovodev/skills/citable/SKILL.md +22 -8
  214. package/dist/universal/.rovodev/skills/citable/VERSION +1 -1
  215. package/dist/universal/.rovodev/skills/citable/agents/citable-auditor.md +64 -0
  216. package/dist/universal/.rovodev/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  217. package/dist/universal/.rovodev/skills/citable/commands/README.md +4 -1
  218. package/dist/universal/.rovodev/skills/citable/commands/action-findings.md +9 -1
  219. package/dist/universal/.rovodev/skills/citable/commands/observe-and-act.md +62 -8
  220. package/dist/universal/.rovodev/skills/citable/commands/plan-audit.md +35 -0
  221. package/dist/universal/.rovodev/skills/citable/commands/reporting.md +57 -0
  222. package/dist/universal/.rovodev/skills/citable/manifest.json +29 -16
  223. package/dist/universal/.rovodev/skills/citable/schemas/action-plan.schema.json +13 -0
  224. package/dist/universal/.rovodev/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  225. package/dist/universal/.rovodev/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  226. package/dist/universal/.rovodev/skills/citable/schemas/common.defs.json +12 -1
  227. package/dist/universal/.rovodev/skills/citable/schemas/corroboration-import.schema.json +48 -0
  228. package/dist/universal/.rovodev/skills/citable/schemas/entity-graph.schema.json +75 -0
  229. package/dist/universal/.rovodev/skills/citable/schemas/entity.schema.json +13 -0
  230. package/dist/universal/.rovodev/skills/citable/schemas/observation.schema.json +1 -1
  231. package/dist/universal/.rovodev/skills/citable/schemas/page.schema.json +3 -0
  232. package/dist/universal/.rovodev/skills/citable/schemas/regional-network-import.schema.json +55 -0
  233. package/dist/universal/.rovodev/skills/citable/schemas/schedule.schema.json +1 -1
  234. package/dist/universal/.rovodev/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  235. package/dist/universal/.rovodev/skills/citable/scripts/README.md +3 -1
  236. package/dist/universal/.trae/skills/citable/SKILL.md +22 -8
  237. package/dist/universal/.trae/skills/citable/VERSION +1 -1
  238. package/dist/universal/.trae/skills/citable/agents/citable-auditor.md +64 -0
  239. package/dist/universal/.trae/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  240. package/dist/universal/.trae/skills/citable/commands/README.md +4 -1
  241. package/dist/universal/.trae/skills/citable/commands/action-findings.md +9 -1
  242. package/dist/universal/.trae/skills/citable/commands/observe-and-act.md +62 -8
  243. package/dist/universal/.trae/skills/citable/commands/plan-audit.md +35 -0
  244. package/dist/universal/.trae/skills/citable/commands/reporting.md +57 -0
  245. package/dist/universal/.trae/skills/citable/manifest.json +29 -16
  246. package/dist/universal/.trae/skills/citable/schemas/action-plan.schema.json +13 -0
  247. package/dist/universal/.trae/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  248. package/dist/universal/.trae/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  249. package/dist/universal/.trae/skills/citable/schemas/common.defs.json +12 -1
  250. package/dist/universal/.trae/skills/citable/schemas/corroboration-import.schema.json +48 -0
  251. package/dist/universal/.trae/skills/citable/schemas/entity-graph.schema.json +75 -0
  252. package/dist/universal/.trae/skills/citable/schemas/entity.schema.json +13 -0
  253. package/dist/universal/.trae/skills/citable/schemas/observation.schema.json +1 -1
  254. package/dist/universal/.trae/skills/citable/schemas/page.schema.json +3 -0
  255. package/dist/universal/.trae/skills/citable/schemas/regional-network-import.schema.json +55 -0
  256. package/dist/universal/.trae/skills/citable/schemas/schedule.schema.json +1 -1
  257. package/dist/universal/.trae/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  258. package/dist/universal/.trae/skills/citable/scripts/README.md +3 -1
  259. package/dist/universal/.trae-cn/skills/citable/SKILL.md +22 -8
  260. package/dist/universal/.trae-cn/skills/citable/VERSION +1 -1
  261. package/dist/universal/.trae-cn/skills/citable/agents/citable-auditor.md +64 -0
  262. package/dist/universal/.trae-cn/skills/citable/agents/citable-semantic-reviewer.md +66 -0
  263. package/dist/universal/.trae-cn/skills/citable/commands/README.md +4 -1
  264. package/dist/universal/.trae-cn/skills/citable/commands/action-findings.md +9 -1
  265. package/dist/universal/.trae-cn/skills/citable/commands/observe-and-act.md +62 -8
  266. package/dist/universal/.trae-cn/skills/citable/commands/plan-audit.md +35 -0
  267. package/dist/universal/.trae-cn/skills/citable/commands/reporting.md +57 -0
  268. package/dist/universal/.trae-cn/skills/citable/manifest.json +29 -16
  269. package/dist/universal/.trae-cn/skills/citable/schemas/action-plan.schema.json +13 -0
  270. package/dist/universal/.trae-cn/skills/citable/schemas/browser-evidence-plan.schema.json +14 -0
  271. package/dist/universal/.trae-cn/skills/citable/schemas/canonical-index-import.schema.json +30 -0
  272. package/dist/universal/.trae-cn/skills/citable/schemas/common.defs.json +12 -1
  273. package/dist/universal/.trae-cn/skills/citable/schemas/corroboration-import.schema.json +48 -0
  274. package/dist/universal/.trae-cn/skills/citable/schemas/entity-graph.schema.json +75 -0
  275. package/dist/universal/.trae-cn/skills/citable/schemas/entity.schema.json +13 -0
  276. package/dist/universal/.trae-cn/skills/citable/schemas/observation.schema.json +1 -1
  277. package/dist/universal/.trae-cn/skills/citable/schemas/page.schema.json +3 -0
  278. package/dist/universal/.trae-cn/skills/citable/schemas/regional-network-import.schema.json +55 -0
  279. package/dist/universal/.trae-cn/skills/citable/schemas/schedule.schema.json +1 -1
  280. package/dist/universal/.trae-cn/skills/citable/schemas/source-identity-chain.schema.json +83 -0
  281. package/dist/universal/.trae-cn/skills/citable/scripts/README.md +3 -1
  282. package/dist/universal/manifest.json +306 -195
  283. package/package.json +1 -1
  284. package/schemas/action-plan.schema.json +13 -0
  285. package/schemas/browser-evidence-plan.schema.json +14 -0
  286. package/schemas/canonical-index-import.schema.json +30 -0
  287. package/schemas/common.defs.json +12 -1
  288. package/schemas/corroboration-import.schema.json +48 -0
  289. package/schemas/entity-graph.schema.json +75 -0
  290. package/schemas/entity.schema.json +13 -0
  291. package/schemas/observation.schema.json +1 -1
  292. package/schemas/page.schema.json +3 -0
  293. package/schemas/regional-network-import.schema.json +55 -0
  294. package/schemas/schedule.schema.json +1 -1
  295. package/schemas/source-identity-chain.schema.json +83 -0
  296. package/scripts/build-dist.js +36 -3
  297. package/skill/SKILL.md +22 -8
  298. package/skill/agents/citable-auditor.md +64 -0
  299. package/skill/agents/citable-semantic-reviewer.md +66 -0
  300. package/skill/commands/README.md +4 -1
  301. package/skill/commands/action-findings.md +9 -1
  302. package/skill/commands/observe-and-act.md +62 -8
  303. package/skill/commands/plan-audit.md +35 -0
  304. package/skill/commands/reporting.md +57 -0
  305. package/src/cli/index.js +115 -15
  306. package/src/commands/actionPlan.js +12 -1
  307. package/src/commands/audit.js +4 -0
  308. package/src/commands/connect.js +29 -0
  309. package/src/commands/context.js +15 -0
  310. package/src/commands/delivery.js +86 -2
  311. package/src/commands/demo.js +36 -0
  312. package/src/commands/fixtures/demo/.citable/claims.yaml +27 -0
  313. package/src/commands/fixtures/demo/.citable/competitors.yaml +3 -0
  314. package/src/commands/fixtures/demo/.citable/config.yaml +18 -0
  315. package/src/commands/fixtures/demo/.citable/crawlers.yaml +30 -0
  316. package/src/commands/fixtures/demo/.citable/entities.yaml +28 -0
  317. package/src/commands/fixtures/demo/.citable/evidence.yaml +19 -0
  318. package/src/commands/fixtures/demo/.citable/experiments.yaml +3 -0
  319. package/src/commands/fixtures/demo/.citable/pages.yaml +54 -0
  320. package/src/commands/fixtures/demo/.citable/prompts.yaml +11 -0
  321. package/src/commands/fixtures/demo/.citable/queries.yaml +10 -0
  322. package/src/commands/fixtures/demo/site/index.html +12 -0
  323. package/src/commands/fixtures/demo/site/learn/execution-governance/index.html +14 -0
  324. package/src/commands/fixtures/demo/site/pricing/index.html +10 -0
  325. package/src/commands/fixtures/demo/site/products/gatekeeper/index.html +15 -0
  326. package/src/commands/fixtures/demo/site/robots.txt +7 -0
  327. package/src/commands/fixtures/demo/site/sitemap.xml +7 -0
  328. package/src/commands/init.js +5 -2
  329. package/src/commands/monitor.js +35 -0
  330. package/src/commands/observe.js +315 -15
  331. package/src/commands/planAudit.js +151 -0
  332. package/src/commands/reportDashboard.js +21 -0
  333. package/src/commands/reportShareOfVoice.js +60 -0
  334. package/src/commands/schemaCmd.js +5 -1
  335. package/src/commands/substantiate.js +22 -10
  336. package/src/connectors/http.js +6 -3
  337. package/src/connectors/index.js +3 -1
  338. package/src/connectors/webflow.js +224 -0
  339. package/src/connectors/wordpress.js +226 -0
  340. package/src/crawler/fetch.js +34 -6
  341. package/src/detectors/geoReco.js +101 -0
  342. package/src/extractor/page.js +17 -0
  343. package/src/installer/index.js +282 -28
  344. package/src/installer/providers.js +11 -0
  345. package/src/monitoring/alertDelivery.js +98 -0
  346. package/src/observations/browserJourney.js +15 -7
  347. package/src/observations/claimDiff.js +83 -0
  348. package/src/observations/common.js +25 -0
  349. package/src/observations/entityGraph.js +89 -0
  350. package/src/observations/renderParity.js +49 -0
  351. package/src/observations/sourceIdentity.js +62 -0
  352. package/src/observations/stance.js +261 -0
  353. package/src/registries/seed.js +95 -0
  354. package/src/registries/seeds/saas-pricing/claims.yaml +18 -0
  355. package/src/registries/seeds/saas-pricing/entities.yaml +20 -0
  356. package/src/registries/seeds/saas-pricing/seed.json +6 -0
  357. package/src/reporting/dashboard.js +254 -0
  358. package/src/reporting/shareOfVoice.js +362 -0
  359. package/src/shared/checklist.js +19 -0
@@ -0,0 +1,362 @@
1
+ import fs from 'node:fs';
2
+ import path from 'node:path';
3
+ import { readJson } from '../shared/io.js';
4
+
5
+ const NO_GUARANTEE = 'This report calculates citation presence and share strictly from recorded observation runs and declared competitor domains. It does not estimate visibility, predict search rankings, or guarantee citation outcomes in live consumer experiences.';
6
+
7
+ export function extractDomain(urlStr) {
8
+ if (!urlStr) return null;
9
+ try {
10
+ const parsed = new URL(urlStr.includes('://') ? urlStr : `https://${urlStr}`);
11
+ return parsed.hostname.toLowerCase();
12
+ } catch {
13
+ return null;
14
+ }
15
+ }
16
+
17
+ export function matchesDomain(hostname, targetDomain) {
18
+ if (!hostname || !targetDomain) return false;
19
+ const h = hostname.toLowerCase();
20
+ const t = extractDomain(targetDomain) || targetDomain.toLowerCase();
21
+ return h === t || h.endsWith(`.${t}`);
22
+ }
23
+
24
+ export function loadCitationRuns(root, { since, last } = {}) {
25
+ const runsDir = path.join(root, '.citable', 'runs');
26
+ const included = [];
27
+ const skipped = [];
28
+ if (!fs.existsSync(runsDir)) return { included, skipped };
29
+
30
+ let runIds = fs.readdirSync(runsDir).sort();
31
+ if (since) runIds = runIds.filter((id) => id >= since);
32
+
33
+ for (const runId of runIds) {
34
+ const dir = path.join(runsDir, runId);
35
+ const obsDir = path.join(dir, 'observations');
36
+ if (!fs.existsSync(obsDir)) continue;
37
+
38
+ try {
39
+ const obsFiles = fs.readdirSync(obsDir).filter((f) => f.endsWith('.json')).sort();
40
+ const citations = [];
41
+ const reviews = [];
42
+
43
+ for (const f of obsFiles) {
44
+ const item = readJson(path.join(obsDir, f));
45
+ if (item.kind === 'citation') citations.push(item);
46
+ if (item.kind === 'citation_review') reviews.push(item);
47
+ }
48
+
49
+ if (citations.length > 0 || reviews.length > 0) {
50
+ const manifest = fs.existsSync(path.join(dir, 'manifest.json'))
51
+ ? readJson(path.join(dir, 'manifest.json'))
52
+ : null;
53
+ included.push({ run_id: runId, manifest, citations, reviews });
54
+ }
55
+ } catch (err) {
56
+ skipped.push({ run_id: runId, reason: err.message });
57
+ }
58
+ }
59
+
60
+ const windowed = Number.isInteger(last) && last > 0 ? included.slice(-last) : included;
61
+ const truncated = windowed.length < included.length && windowed.length > 0;
62
+ return {
63
+ included: windowed,
64
+ skipped: truncated ? skipped.filter((item) => item.run_id >= windowed[0].run_id) : skipped,
65
+ };
66
+ }
67
+
68
+ export function calculateShareOfVoice(includedRuns, competitors = [], firstPartyDomains = new Set()) {
69
+ const promptsMap = new Map();
70
+ let totalObservations = 0;
71
+ let totalCitationsCount = 0;
72
+
73
+ for (const run of includedRuns) {
74
+ for (const item of run.citations) {
75
+ totalObservations++;
76
+ const promptId = item.data?.prompt_id || 'unspecified_prompt';
77
+ const promptText = item.data?.prompt_text || promptId;
78
+ const promptRecord = promptsMap.get(promptId) || {
79
+ prompt_id: promptId,
80
+ prompt_text: promptText,
81
+ total_runs: 0,
82
+ total_citations: 0,
83
+ first_party_presence_runs: 0,
84
+ first_party_citations: 0,
85
+ competitors: {},
86
+ other_citations: 0,
87
+ };
88
+
89
+ promptRecord.total_runs++;
90
+ if (item.data?.property_cited) {
91
+ promptRecord.first_party_presence_runs++;
92
+ }
93
+
94
+ const reviews = item.data?.citations || [];
95
+ const competitorPresentInRun = new Set();
96
+
97
+ for (const review of reviews) {
98
+ promptRecord.total_citations++;
99
+ totalCitationsCount++;
100
+ const url = review.canonical_url || review.url || '';
101
+ const host = extractDomain(url);
102
+
103
+ const isFirstParty = review.first_party === true || (host && [...firstPartyDomains].some((d) => matchesDomain(host, d)));
104
+ if (isFirstParty) {
105
+ promptRecord.first_party_citations++;
106
+ continue;
107
+ }
108
+
109
+ let matchedCompetitor = null;
110
+ for (const comp of competitors) {
111
+ const compDomains = comp.domains || [];
112
+ if (host && compDomains.some((d) => matchesDomain(host, d))) {
113
+ matchedCompetitor = comp;
114
+ break;
115
+ }
116
+ }
117
+
118
+ if (matchedCompetitor) {
119
+ const compId = matchedCompetitor.competitor_id;
120
+ promptRecord.competitors[compId] ||= { citations: 0, presence_runs: 0 };
121
+ promptRecord.competitors[compId].citations++;
122
+ competitorPresentInRun.add(compId);
123
+ } else {
124
+ promptRecord.other_citations++;
125
+ }
126
+ }
127
+
128
+ for (const compId of competitorPresentInRun) {
129
+ promptRecord.competitors[compId].presence_runs++;
130
+ }
131
+
132
+ promptsMap.set(promptId, promptRecord);
133
+ }
134
+ }
135
+
136
+ // Calculate aggregates
137
+ const aggregateCompetitors = {};
138
+ for (const comp of competitors) {
139
+ aggregateCompetitors[comp.competitor_id] = {
140
+ name: comp.name,
141
+ domains: comp.domains || [],
142
+ citations: 0,
143
+ presence_runs: 0,
144
+ };
145
+ }
146
+
147
+ let aggregateFirstPartyCitations = 0;
148
+ let aggregateFirstPartyPresenceRuns = 0;
149
+ let aggregateOtherCitations = 0;
150
+
151
+ for (const prompt of promptsMap.values()) {
152
+ aggregateFirstPartyCitations += prompt.first_party_citations;
153
+ aggregateFirstPartyPresenceRuns += prompt.first_party_presence_runs;
154
+ aggregateOtherCitations += prompt.other_citations;
155
+
156
+ for (const [compId, stats] of Object.entries(prompt.competitors)) {
157
+ if (aggregateCompetitors[compId]) {
158
+ aggregateCompetitors[compId].citations += stats.citations;
159
+ aggregateCompetitors[compId].presence_runs += stats.presence_runs;
160
+ }
161
+ }
162
+ }
163
+
164
+ return {
165
+ total_runs_evaluated: totalObservations,
166
+ total_citations_recorded: totalCitationsCount,
167
+ prompts: [...promptsMap.values()],
168
+ aggregate: {
169
+ first_party: {
170
+ citations: aggregateFirstPartyCitations,
171
+ presence_runs: aggregateFirstPartyPresenceRuns,
172
+ citation_share: totalCitationsCount > 0 ? aggregateFirstPartyCitations / totalCitationsCount : null,
173
+ presence_rate: totalObservations > 0 ? aggregateFirstPartyPresenceRuns / totalObservations : null,
174
+ },
175
+ competitors: Object.entries(aggregateCompetitors).map(([compId, data]) => ({
176
+ competitor_id: compId,
177
+ name: data.name,
178
+ domains: data.domains,
179
+ citations: data.citations,
180
+ presence_runs: data.presence_runs,
181
+ citation_share: totalCitationsCount > 0 ? data.citations / totalCitationsCount : null,
182
+ presence_rate: totalObservations > 0 ? data.presence_runs / totalObservations : null,
183
+ })),
184
+ other: {
185
+ citations: aggregateOtherCitations,
186
+ citation_share: totalCitationsCount > 0 ? aggregateOtherCitations / totalCitationsCount : null,
187
+ },
188
+ },
189
+ };
190
+ }
191
+
192
+ function formatPercent(val) {
193
+ return val == null ? 'not evidenced' : `${(val * 100).toFixed(1)}%`;
194
+ }
195
+
196
+ export function renderShareOfVoiceMarkdown(data, skipped = []) {
197
+ const lines = [];
198
+ lines.push('# Citable share-of-voice report');
199
+ lines.push('');
200
+ lines.push(`- Observation runs evaluated: ${data.total_runs_evaluated}`);
201
+ lines.push(`- Total citations recorded: ${data.total_citations_recorded}`);
202
+ lines.push(`- Prompts evaluated: ${data.prompts.length}`);
203
+ lines.push(`- Runs skipped: ${skipped.length}`);
204
+ lines.push('');
205
+ lines.push(`> ${NO_GUARANTEE}`);
206
+ lines.push('');
207
+
208
+ if (data.total_runs_evaluated === 0) {
209
+ lines.push('## Insufficient history');
210
+ lines.push('');
211
+ lines.push('No citation observations were found in `.citable/runs/`. Run `citable observe citations` to record provider citation evidence.');
212
+ lines.push('');
213
+ return lines.join('\n');
214
+ }
215
+
216
+ lines.push('## Aggregate citation share');
217
+ lines.push('');
218
+ lines.push('| Entity | Status | Citations | Citation share | Presence rate |');
219
+ lines.push('| --- | --- | --- | --- | --- |');
220
+
221
+ lines.push(`| **First-party** | Primary | ${data.aggregate.first_party.citations} | ${formatPercent(data.aggregate.first_party.citation_share)} | ${formatPercent(data.aggregate.first_party.presence_rate)} |`);
222
+
223
+ for (const comp of data.aggregate.competitors) {
224
+ lines.push(`| ${comp.name} (\`${comp.competitor_id}\`) | Registered competitor | ${comp.citations} | ${formatPercent(comp.citation_share)} | ${formatPercent(comp.presence_rate)} |`);
225
+ }
226
+
227
+ lines.push(`| Third-party sources (unregistered) | Uncontested | ${data.aggregate.other.citations} | ${formatPercent(data.aggregate.other.citation_share)} | — |`);
228
+ lines.push('');
229
+
230
+ lines.push('## Prompt breakdown');
231
+ lines.push('');
232
+ for (const prompt of data.prompts) {
233
+ lines.push(`### \`${prompt.prompt_id}\`: "${prompt.prompt_text}"`);
234
+ lines.push('');
235
+ lines.push(`- Total runs: ${prompt.total_runs}`);
236
+ lines.push(`- Total citations: ${prompt.total_citations}`);
237
+ lines.push('');
238
+ lines.push('| Entity | Citations | Share | Prompt presence |');
239
+ lines.push('| --- | --- | --- | --- |');
240
+ const fpShare = prompt.total_citations > 0 ? prompt.first_party_citations / prompt.total_citations : null;
241
+ const fpPres = prompt.total_runs > 0 ? prompt.first_party_presence_runs / prompt.total_runs : null;
242
+ lines.push(`| First-party | ${prompt.first_party_citations} | ${formatPercent(fpShare)} | ${formatPercent(fpPres)} |`);
243
+
244
+ for (const comp of data.aggregate.competitors) {
245
+ const stats = prompt.competitors[comp.competitor_id] || { citations: 0, presence_runs: 0 };
246
+ const compShare = prompt.total_citations > 0 ? stats.citations / prompt.total_citations : null;
247
+ const compPres = prompt.total_runs > 0 ? stats.presence_runs / prompt.total_runs : null;
248
+ lines.push(`| ${comp.name} | ${stats.citations} | ${formatPercent(compShare)} | ${formatPercent(compPres)} |`);
249
+ }
250
+ const otherShare = prompt.total_citations > 0 ? prompt.other_citations / prompt.total_citations : null;
251
+ lines.push(`| Other | ${prompt.other_citations} | ${formatPercent(otherShare)} | — |`);
252
+ lines.push('');
253
+ }
254
+
255
+ if (skipped.length) {
256
+ lines.push('## Skipped runs');
257
+ lines.push('');
258
+ for (const item of skipped) lines.push(`- \`${item.run_id}\`: ${item.reason}`);
259
+ lines.push('');
260
+ }
261
+
262
+ return lines.join('\n');
263
+ }
264
+
265
+ function escapeHtml(val) {
266
+ return String(val ?? '')
267
+ .replace(/&/g, '&amp;')
268
+ .replace(/</g, '&lt;')
269
+ .replace(/>/g, '&gt;')
270
+ .replace(/"/g, '&quot;')
271
+ .replace(/'/g, '&#39;');
272
+ }
273
+
274
+ export function renderShareOfVoiceHtml(data, skipped = []) {
275
+ const html = [];
276
+ html.push('<!doctype html>');
277
+ html.push('<html lang="en">');
278
+ html.push('<head>');
279
+ html.push('<meta charset="utf-8" />');
280
+ html.push('<meta name="viewport" content="width=device-width, initial-scale=1" />');
281
+ html.push('<title>Citable share-of-voice report</title>');
282
+ html.push('<style>');
283
+ html.push('body { font: 16px/1.5 system-ui, sans-serif; margin: 2rem auto; max-width: 60rem; padding: 0 1rem; color: #1c1c1c; }');
284
+ html.push('table { border-collapse: collapse; width: 100%; font-size: 0.875rem; margin: 1rem 0 2rem; }');
285
+ html.push('th, td { border: 1px solid #d4d4d4; padding: 0.375rem 0.5rem; text-align: left; }');
286
+ html.push('th { background: #f3f3f3; }');
287
+ html.push('code { font-size: 0.8125rem; }');
288
+ html.push('blockquote { border-left: 4px solid #999; margin: 0 0 1.5rem; padding: 0.25rem 1rem; color: #333; }');
289
+ html.push('.bar-container { display: flex; height: 24px; border-radius: 4px; overflow: hidden; margin: 1rem 0; border: 1px solid #ccc; }');
290
+ html.push('.bar-fp { background: #2f6f4f; color: #fff; text-align: center; font-size: 0.75rem; line-height: 24px; }');
291
+ html.push('.bar-comp { background: #e09f3e; color: #fff; text-align: center; font-size: 0.75rem; line-height: 24px; }');
292
+ html.push('.bar-other { background: #999; color: #fff; text-align: center; font-size: 0.75rem; line-height: 24px; }');
293
+ html.push('.insufficient { background: #fbf1d8; border: 1px solid #e2c98a; padding: 0.75rem 1rem; }');
294
+ html.push('</style>');
295
+ html.push('</head>');
296
+ html.push('<body>');
297
+ html.push('<h1>Citable share-of-voice report</h1>');
298
+ html.push('<ul>');
299
+ html.push(`<li>Observation runs evaluated: ${data.total_runs_evaluated}</li>`);
300
+ html.push(`<li>Total citations recorded: ${data.total_citations_recorded}</li>`);
301
+ html.push(`<li>Prompts evaluated: ${data.prompts.length}</li>`);
302
+ html.push(`<li>Runs skipped: ${skipped.length}</li>`);
303
+ html.push('</ul>');
304
+ html.push(`<blockquote>${escapeHtml(NO_GUARANTEE)}</blockquote>`);
305
+
306
+ if (data.total_runs_evaluated === 0) {
307
+ html.push('<section class="insufficient"><h2>Insufficient history</h2><p>No citation observations found in <code>.citable/runs/</code>.</p></section>');
308
+ html.push('</body></html>');
309
+ return html.join('\n');
310
+ }
311
+
312
+ html.push('<h2>Aggregate citation distribution</h2>');
313
+ const fpPct = data.aggregate.first_party.citation_share ? (data.aggregate.first_party.citation_share * 100).toFixed(1) : 0;
314
+ const otherPct = data.aggregate.other.citation_share ? (data.aggregate.other.citation_share * 100).toFixed(1) : 0;
315
+
316
+ html.push('<div class="bar-container">');
317
+ if (fpPct > 0) html.push(`<div class="bar-fp" style="width: ${fpPct}%;">First-party (${fpPct}%)</div>`);
318
+ for (const comp of data.aggregate.competitors) {
319
+ const cPct = comp.citation_share ? (comp.citation_share * 100).toFixed(1) : 0;
320
+ if (cPct > 0) html.push(`<div class="bar-comp" style="width: ${cPct}%;">${escapeHtml(comp.name)} (${cPct}%)</div>`);
321
+ }
322
+ if (otherPct > 0) html.push(`<div class="bar-other" style="width: ${otherPct}%;">Other (${otherPct}%)</div>`);
323
+ html.push('</div>');
324
+
325
+ html.push('<table>');
326
+ html.push('<thead><tr><th>Entity</th><th>Type</th><th>Citations</th><th>Citation share</th><th>Presence rate</th></tr></thead>');
327
+ html.push('<tbody>');
328
+ html.push(`<tr><td><strong>First-party</strong></td><td>Primary</td><td>${data.aggregate.first_party.citations}</td><td>${formatPercent(data.aggregate.first_party.citation_share)}</td><td>${formatPercent(data.aggregate.first_party.presence_rate)}</td></tr>`);
329
+ for (const comp of data.aggregate.competitors) {
330
+ html.push(`<tr><td>${escapeHtml(comp.name)} (<code>${escapeHtml(comp.competitor_id)}</code>)</td><td>Competitor</td><td>${comp.citations}</td><td>${formatPercent(comp.citation_share)}</td><td>${formatPercent(comp.presence_rate)}</td></tr>`);
331
+ }
332
+ html.push(`<tr><td>Other third-party</td><td>Unregistered</td><td>${data.aggregate.other.citations}</td><td>${formatPercent(data.aggregate.other.citation_share)}</td><td>—</td></tr>`);
333
+ html.push('</tbody></table>');
334
+
335
+ html.push('<h2>Prompt breakdown</h2>');
336
+ for (const prompt of data.prompts) {
337
+ html.push(`<h3><code>${escapeHtml(prompt.prompt_id)}</code>: &ldquo;${escapeHtml(prompt.prompt_text)}&rdquo;</h3>`);
338
+ html.push(`<ul><li>Runs: ${prompt.total_runs}</li><li>Citations: ${prompt.total_citations}</li></ul>`);
339
+ html.push('<table><thead><tr><th>Entity</th><th>Citations</th><th>Share</th><th>Presence rate</th></tr></thead><tbody>');
340
+ const fpShare = prompt.total_citations > 0 ? prompt.first_party_citations / prompt.total_citations : null;
341
+ const fpPres = prompt.total_runs > 0 ? prompt.first_party_presence_runs / prompt.total_runs : null;
342
+ html.push(`<tr><td>First-party</td><td>${prompt.first_party_citations}</td><td>${formatPercent(fpShare)}</td><td>${formatPercent(fpPres)}</td></tr>`);
343
+ for (const comp of data.aggregate.competitors) {
344
+ const stats = prompt.competitors[comp.competitor_id] || { citations: 0, presence_runs: 0 };
345
+ const compShare = prompt.total_citations > 0 ? stats.citations / prompt.total_citations : null;
346
+ const compPres = prompt.total_runs > 0 ? stats.presence_runs / prompt.total_runs : null;
347
+ html.push(`<tr><td>${escapeHtml(comp.name)}</td><td>${stats.citations}</td><td>${formatPercent(compShare)}</td><td>${formatPercent(compPres)}</td></tr>`);
348
+ }
349
+ const otherShare = prompt.total_citations > 0 ? prompt.other_citations / prompt.total_citations : null;
350
+ html.push(`<tr><td>Other</td><td>${prompt.other_citations}</td><td>${formatPercent(otherShare)}</td><td>—</td></tr>`);
351
+ html.push('</tbody></table>');
352
+ }
353
+
354
+ if (skipped.length) {
355
+ html.push('<h2>Skipped runs</h2><ul>');
356
+ for (const item of skipped) html.push(`<li><code>${escapeHtml(item.run_id)}</code>: ${escapeHtml(item.reason)}</li>`);
357
+ html.push('</ul>');
358
+ }
359
+
360
+ html.push('</body></html>');
361
+ return html.join('\n');
362
+ }
@@ -0,0 +1,19 @@
1
+ /**
2
+ * Shared required-input checklist item builder used by substantiate, schemaCmd,
3
+ * and actionPlan so the three no longer maintain independent literal-string lists.
4
+ * Callers still serialize to array<string> via toStringArray — no consumer-facing
5
+ * shape changes.
6
+ */
7
+ export function checklistItem(id, label, note) {
8
+ return { id, label, satisfied: false, note: note ?? null };
9
+ }
10
+
11
+ /** Render one item (or an already-plain string) down to its display label. */
12
+ export function toLabel(item) {
13
+ return typeof item === 'string' ? item : item.label;
14
+ }
15
+
16
+ /** Serialize a list of items (or plain strings) to array<string>. */
17
+ export function toStringArray(items) {
18
+ return items.map(toLabel);
19
+ }