xonecode 0.3.0 → 0.5.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 (406) hide show
  1. package/README.md +49 -7
  2. package/THIRD_PARTY_NOTICES.md +128 -0
  3. package/apps/web/dist/assets/KaTeX_AMS-Regular-BQhdFMY1.woff2 +0 -0
  4. package/apps/web/dist/assets/KaTeX_AMS-Regular-DMm9YOAa.woff +0 -0
  5. package/apps/web/dist/assets/KaTeX_AMS-Regular-DRggAlZN.ttf +0 -0
  6. package/apps/web/dist/assets/KaTeX_Caligraphic-Bold-ATXxdsX0.ttf +0 -0
  7. package/apps/web/dist/assets/KaTeX_Caligraphic-Bold-BEiXGLvX.woff +0 -0
  8. package/apps/web/dist/assets/KaTeX_Caligraphic-Bold-Dq_IR9rO.woff2 +0 -0
  9. package/apps/web/dist/assets/KaTeX_Caligraphic-Regular-CTRA-rTL.woff +0 -0
  10. package/apps/web/dist/assets/KaTeX_Caligraphic-Regular-Di6jR-x-.woff2 +0 -0
  11. package/apps/web/dist/assets/KaTeX_Caligraphic-Regular-wX97UBjC.ttf +0 -0
  12. package/apps/web/dist/assets/KaTeX_Fraktur-Bold-BdnERNNW.ttf +0 -0
  13. package/apps/web/dist/assets/KaTeX_Fraktur-Bold-BsDP51OF.woff +0 -0
  14. package/apps/web/dist/assets/KaTeX_Fraktur-Bold-CL6g_b3V.woff2 +0 -0
  15. package/apps/web/dist/assets/KaTeX_Fraktur-Regular-CB_wures.ttf +0 -0
  16. package/apps/web/dist/assets/KaTeX_Fraktur-Regular-CTYiF6lA.woff2 +0 -0
  17. package/apps/web/dist/assets/KaTeX_Fraktur-Regular-Dxdc4cR9.woff +0 -0
  18. package/apps/web/dist/assets/KaTeX_Main-Bold-Cx986IdX.woff2 +0 -0
  19. package/apps/web/dist/assets/KaTeX_Main-Bold-Jm3AIy58.woff +0 -0
  20. package/apps/web/dist/assets/KaTeX_Main-Bold-waoOVXN0.ttf +0 -0
  21. package/apps/web/dist/assets/KaTeX_Main-BoldItalic-DxDJ3AOS.woff2 +0 -0
  22. package/apps/web/dist/assets/KaTeX_Main-BoldItalic-DzxPMmG6.ttf +0 -0
  23. package/apps/web/dist/assets/KaTeX_Main-BoldItalic-SpSLRI95.woff +0 -0
  24. package/apps/web/dist/assets/KaTeX_Main-Italic-3WenGoN9.ttf +0 -0
  25. package/apps/web/dist/assets/KaTeX_Main-Italic-BMLOBm91.woff +0 -0
  26. package/apps/web/dist/assets/KaTeX_Main-Italic-NWA7e6Wa.woff2 +0 -0
  27. package/apps/web/dist/assets/KaTeX_Main-Regular-B22Nviop.woff2 +0 -0
  28. package/apps/web/dist/assets/KaTeX_Main-Regular-Dr94JaBh.woff +0 -0
  29. package/apps/web/dist/assets/KaTeX_Main-Regular-ypZvNtVU.ttf +0 -0
  30. package/apps/web/dist/assets/KaTeX_Math-BoldItalic-B3XSjfu4.ttf +0 -0
  31. package/apps/web/dist/assets/KaTeX_Math-BoldItalic-CZnvNsCZ.woff2 +0 -0
  32. package/apps/web/dist/assets/KaTeX_Math-BoldItalic-iY-2wyZ7.woff +0 -0
  33. package/apps/web/dist/assets/KaTeX_Math-Italic-DA0__PXp.woff +0 -0
  34. package/apps/web/dist/assets/KaTeX_Math-Italic-flOr_0UB.ttf +0 -0
  35. package/apps/web/dist/assets/KaTeX_Math-Italic-t53AETM-.woff2 +0 -0
  36. package/apps/web/dist/assets/KaTeX_SansSerif-Bold-CFMepnvq.ttf +0 -0
  37. package/apps/web/dist/assets/KaTeX_SansSerif-Bold-D1sUS0GD.woff2 +0 -0
  38. package/apps/web/dist/assets/KaTeX_SansSerif-Bold-DbIhKOiC.woff +0 -0
  39. package/apps/web/dist/assets/KaTeX_SansSerif-Italic-C3H0VqGB.woff2 +0 -0
  40. package/apps/web/dist/assets/KaTeX_SansSerif-Italic-DN2j7dab.woff +0 -0
  41. package/apps/web/dist/assets/KaTeX_SansSerif-Italic-YYjJ1zSn.ttf +0 -0
  42. package/apps/web/dist/assets/KaTeX_SansSerif-Regular-BNo7hRIc.ttf +0 -0
  43. package/apps/web/dist/assets/KaTeX_SansSerif-Regular-CS6fqUqJ.woff +0 -0
  44. package/apps/web/dist/assets/KaTeX_SansSerif-Regular-DDBCnlJ7.woff2 +0 -0
  45. package/apps/web/dist/assets/KaTeX_Script-Regular-C5JkGWo-.ttf +0 -0
  46. package/apps/web/dist/assets/KaTeX_Script-Regular-D3wIWfF6.woff2 +0 -0
  47. package/apps/web/dist/assets/KaTeX_Script-Regular-D5yQViql.woff +0 -0
  48. package/apps/web/dist/assets/KaTeX_Size1-Regular-C195tn64.woff +0 -0
  49. package/apps/web/dist/assets/KaTeX_Size1-Regular-Dbsnue_I.ttf +0 -0
  50. package/apps/web/dist/assets/KaTeX_Size1-Regular-mCD8mA8B.woff2 +0 -0
  51. package/apps/web/dist/assets/KaTeX_Size2-Regular-B7gKUWhC.ttf +0 -0
  52. package/apps/web/dist/assets/KaTeX_Size2-Regular-Dy4dx90m.woff2 +0 -0
  53. package/apps/web/dist/assets/KaTeX_Size2-Regular-oD1tc_U0.woff +0 -0
  54. package/apps/web/dist/assets/KaTeX_Size3-Regular-CTq5MqoE.woff +0 -0
  55. package/apps/web/dist/assets/KaTeX_Size3-Regular-DgpXs0kz.ttf +0 -0
  56. package/apps/web/dist/assets/KaTeX_Size4-Regular-BF-4gkZK.woff +0 -0
  57. package/apps/web/dist/assets/KaTeX_Size4-Regular-DWFBv043.ttf +0 -0
  58. package/apps/web/dist/assets/KaTeX_Size4-Regular-Dl5lxZxV.woff2 +0 -0
  59. package/apps/web/dist/assets/KaTeX_Typewriter-Regular-C0xS9mPB.woff +0 -0
  60. package/apps/web/dist/assets/KaTeX_Typewriter-Regular-CO6r4hn1.woff2 +0 -0
  61. package/apps/web/dist/assets/KaTeX_Typewriter-Regular-D3Ib7_Hf.ttf +0 -0
  62. package/apps/web/dist/assets/c-BIGW1oBm.js +1 -0
  63. package/apps/web/dist/assets/cpp-DddhVWhK.js +1 -0
  64. package/apps/web/dist/assets/csharp-DSvCPggb.js +1 -0
  65. package/apps/web/dist/assets/css-CLj8gQPS.js +1 -0
  66. package/apps/web/dist/assets/go-C27-OAKa.js +1 -0
  67. package/apps/web/dist/assets/html-CfGypltT.js +1 -0
  68. package/apps/web/dist/assets/index-BB3SamhR.css +1 -0
  69. package/apps/web/dist/assets/index-CFYAoHdw.js +477 -0
  70. package/apps/web/dist/assets/ini-BEwlwnbL.js +1 -0
  71. package/apps/web/dist/assets/inter-cyrillic-ext-wght-normal-BOeWTOD4.woff2 +0 -0
  72. package/apps/web/dist/assets/inter-cyrillic-wght-normal-DqGufNeO.woff2 +0 -0
  73. package/apps/web/dist/assets/inter-greek-ext-wght-normal-DlzME5K_.woff2 +0 -0
  74. package/apps/web/dist/assets/inter-greek-wght-normal-CkhJZR-_.woff2 +0 -0
  75. package/apps/web/dist/assets/inter-latin-ext-wght-normal-DO1Apj_S.woff2 +0 -0
  76. package/apps/web/dist/assets/inter-latin-wght-normal-Dx4kXJAl.woff2 +0 -0
  77. package/apps/web/dist/assets/inter-vietnamese-wght-normal-CBcvBZtf.woff2 +0 -0
  78. package/apps/web/dist/assets/java-CylS5w8V.js +1 -0
  79. package/apps/web/dist/assets/jetbrains-mono-cyrillic-wght-normal-D73BlboJ.woff2 +0 -0
  80. package/apps/web/dist/assets/jetbrains-mono-greek-wght-normal-Bw9x6K1M.woff2 +0 -0
  81. package/apps/web/dist/assets/jetbrains-mono-latin-ext-wght-normal-DBQx-q_a.woff2 +0 -0
  82. package/apps/web/dist/assets/jetbrains-mono-latin-wght-normal-B9CIFXIH.woff2 +0 -0
  83. package/apps/web/dist/assets/jetbrains-mono-vietnamese-wght-normal-Bt-aOZkq.woff2 +0 -0
  84. package/apps/web/dist/assets/kotlin-BdnUsdx6.js +1 -0
  85. package/apps/web/dist/assets/less-B1dDrJ26.js +1 -0
  86. package/apps/web/dist/assets/lua-BaeVxFsk.js +1 -0
  87. package/apps/web/dist/assets/markdown-Cvjx9yec.js +1 -0
  88. package/apps/web/dist/assets/mdx-Cmh6b_Ma.js +1 -0
  89. package/apps/web/dist/assets/php-D_2--9WK.js +1 -0
  90. package/apps/web/dist/assets/python-B6aJPvgy.js +1 -0
  91. package/apps/web/dist/assets/ruby-DSHSDbk1.js +1 -0
  92. package/apps/web/dist/assets/rust-B1yitclQ.js +1 -0
  93. package/apps/web/dist/assets/scss-D5BDwBP9.js +1 -0
  94. package/apps/web/dist/assets/sql-CRqJ_cUM.js +1 -0
  95. package/apps/web/dist/assets/swift-C2oV4EkX.js +1 -0
  96. package/apps/web/dist/assets/toml-vGWfd6FD.js +1 -0
  97. package/apps/web/dist/assets/xml-sdJ4AIDG.js +1 -0
  98. package/apps/web/dist/assets/yaml-Buea-lGh.js +1 -0
  99. package/apps/web/dist/iconos/xonecode.png +0 -0
  100. package/apps/web/dist/index.html +20 -0
  101. package/dist/agent/agentesEnDisco.js +539 -0
  102. package/dist/agent/agentesEnDisco.js.map +1 -0
  103. package/dist/agent/arbolDeProyecto.js +245 -0
  104. package/dist/agent/arbolDeProyecto.js.map +1 -0
  105. package/dist/agent/artefactosEnDisco.js +139 -0
  106. package/dist/agent/artefactosEnDisco.js.map +1 -0
  107. package/dist/agent/aumentador.js +175 -0
  108. package/dist/agent/aumentador.js.map +1 -0
  109. package/dist/agent/authEnDisco.js +76 -1
  110. package/dist/agent/authEnDisco.js.map +1 -1
  111. package/dist/agent/busquedaRegex.js +92 -0
  112. package/dist/agent/busquedaRegex.js.map +1 -0
  113. package/dist/agent/catalogoModelos.js +345 -0
  114. package/dist/agent/catalogoModelos.js.map +1 -0
  115. package/dist/agent/checkpointer.js +127 -0
  116. package/dist/agent/checkpointer.js.map +1 -0
  117. package/dist/agent/cloudstudioClient.js +194 -0
  118. package/dist/agent/cloudstudioClient.js.map +1 -0
  119. package/dist/agent/cloudstudioMcp.js +722 -0
  120. package/dist/agent/cloudstudioMcp.js.map +1 -0
  121. package/dist/agent/configEnDisco.js +309 -11
  122. package/dist/agent/configEnDisco.js.map +1 -1
  123. package/dist/agent/consumoExterno.js +99 -0
  124. package/dist/agent/consumoExterno.js.map +1 -0
  125. package/dist/agent/descarga.js +149 -0
  126. package/dist/agent/descarga.js.map +1 -0
  127. package/dist/agent/diagnosticoDeTools.js +51 -0
  128. package/dist/agent/diagnosticoDeTools.js.map +1 -0
  129. package/dist/agent/dispositivosEnMaquina.js +596 -0
  130. package/dist/agent/dispositivosEnMaquina.js.map +1 -0
  131. package/dist/agent/escrituraDeCodex.js +134 -0
  132. package/dist/agent/escrituraDeCodex.js.map +1 -0
  133. package/dist/agent/escrituraDeOpencode.js +80 -0
  134. package/dist/agent/escrituraDeOpencode.js.map +1 -0
  135. package/dist/agent/escrituraExterna.js +742 -0
  136. package/dist/agent/escrituraExterna.js.map +1 -0
  137. package/dist/agent/gemini.js +81 -0
  138. package/dist/agent/gemini.js.map +1 -0
  139. package/dist/agent/git.js +83 -0
  140. package/dist/agent/git.js.map +1 -0
  141. package/dist/agent/gitSync.js +441 -0
  142. package/dist/agent/gitSync.js.map +1 -0
  143. package/dist/agent/hotswap.js +448 -0
  144. package/dist/agent/hotswap.js.map +1 -0
  145. package/dist/agent/instalacionEnMaquina.js +252 -0
  146. package/dist/agent/instalacionEnMaquina.js.map +1 -0
  147. package/dist/agent/instantanea.js +7 -10
  148. package/dist/agent/instantanea.js.map +1 -1
  149. package/dist/agent/interrupts.js +11 -2
  150. package/dist/agent/interrupts.js.map +1 -1
  151. package/dist/agent/juezDeTarea.js +345 -0
  152. package/dist/agent/juezDeTarea.js.map +1 -0
  153. package/dist/agent/lanzamientoEnMaquina.js +377 -0
  154. package/dist/agent/lanzamientoEnMaquina.js.map +1 -0
  155. package/dist/agent/manifiesto.js +59 -0
  156. package/dist/agent/manifiesto.js.map +1 -0
  157. package/dist/agent/memoriaDeProyecto.js +60 -0
  158. package/dist/agent/memoriaDeProyecto.js.map +1 -0
  159. package/dist/agent/modelos.js +105 -17
  160. package/dist/agent/modelos.js.map +1 -1
  161. package/dist/agent/modelosDeMotor.js +204 -0
  162. package/dist/agent/modelosDeMotor.js.map +1 -0
  163. package/dist/agent/paqueteDelProyecto.js +181 -0
  164. package/dist/agent/paqueteDelProyecto.js.map +1 -0
  165. package/dist/agent/perfiles.js +92 -31
  166. package/dist/agent/perfiles.js.map +1 -1
  167. package/dist/agent/persona.js +40 -0
  168. package/dist/agent/persona.js.map +1 -0
  169. package/dist/agent/procesosEnMaquina.js +204 -0
  170. package/dist/agent/procesosEnMaquina.js.map +1 -0
  171. package/dist/agent/proyecto.js +311 -13
  172. package/dist/agent/proyecto.js.map +1 -1
  173. package/dist/agent/puente.js +63 -6
  174. package/dist/agent/puente.js.map +1 -1
  175. package/dist/agent/resumenDeContexto.js +30 -0
  176. package/dist/agent/resumenDeContexto.js.map +1 -0
  177. package/dist/agent/resumenDeTool.js +64 -18
  178. package/dist/agent/resumenDeTool.js.map +1 -1
  179. package/dist/agent/sesionGit.js +481 -0
  180. package/dist/agent/sesionGit.js.map +1 -0
  181. package/dist/agent/settingsEnDisco.js +189 -0
  182. package/dist/agent/settingsEnDisco.js.map +1 -0
  183. package/dist/agent/subagenteCodex.js +368 -0
  184. package/dist/agent/subagenteCodex.js.map +1 -0
  185. package/dist/agent/subagenteExterno.js +423 -0
  186. package/dist/agent/subagenteExterno.js.map +1 -0
  187. package/dist/agent/subagenteOpencode.js +389 -0
  188. package/dist/agent/subagenteOpencode.js.map +1 -0
  189. package/dist/agent/subida.js +202 -0
  190. package/dist/agent/subida.js.map +1 -0
  191. package/dist/agent/tareasEnDisco.js +466 -0
  192. package/dist/agent/tareasEnDisco.js.map +1 -0
  193. package/dist/agent/turnoReal.js +663 -50
  194. package/dist/agent/turnoReal.js.map +1 -1
  195. package/dist/agent/versionEnDisco.js +48 -0
  196. package/dist/agent/versionEnDisco.js.map +1 -0
  197. package/dist/agent/xoneAgent.js +290 -49
  198. package/dist/agent/xoneAgent.js.map +1 -1
  199. package/dist/agent/zip.js +52 -0
  200. package/dist/agent/zip.js.map +1 -0
  201. package/dist/cli/acuseDeModelo.js +30 -0
  202. package/dist/cli/acuseDeModelo.js.map +1 -0
  203. package/dist/cli/aprobar.js +55 -2
  204. package/dist/cli/aprobar.js.map +1 -1
  205. package/dist/cli/config.js +9 -13
  206. package/dist/cli/config.js.map +1 -1
  207. package/dist/cli/consola.js +750 -19
  208. package/dist/cli/consola.js.map +1 -1
  209. package/dist/cli/main.js +740 -81
  210. package/dist/cli/main.js.map +1 -1
  211. package/dist/cli/markdown.js +188 -2
  212. package/dist/cli/markdown.js.map +1 -1
  213. package/dist/cli/run.js +32 -4
  214. package/dist/cli/run.js.map +1 -1
  215. package/dist/cli/stdio.js +46 -19
  216. package/dist/cli/stdio.js.map +1 -1
  217. package/dist/cli/tema.js +96 -8
  218. package/dist/cli/tema.js.map +1 -1
  219. package/dist/cli/tokens.js +29 -0
  220. package/dist/cli/tokens.js.map +1 -0
  221. package/dist/cli/tui/app.js +171 -0
  222. package/dist/cli/tui/app.js.map +1 -0
  223. package/dist/cli/tui/aprobarTui.js +80 -0
  224. package/dist/cli/tui/aprobarTui.js.map +1 -0
  225. package/dist/cli/tui/barra.js +37 -0
  226. package/dist/cli/tui/barra.js.map +1 -0
  227. package/dist/cli/tui/correrTui.js +478 -0
  228. package/dist/cli/tui/correrTui.js.map +1 -0
  229. package/dist/cli/tui/entrada.js +166 -0
  230. package/dist/cli/tui/entrada.js.map +1 -0
  231. package/dist/cli/tui/filas.js +24 -0
  232. package/dist/cli/tui/filas.js.map +1 -0
  233. package/dist/cli/tui/logo.js +49 -0
  234. package/dist/cli/tui/logo.js.map +1 -0
  235. package/dist/cli/tui/pielTui.js +14 -0
  236. package/dist/cli/tui/pielTui.js.map +1 -0
  237. package/dist/cli/tui/raton.js +126 -0
  238. package/dist/cli/tui/raton.js.map +1 -0
  239. package/dist/cli/tui/sidebar.js +86 -0
  240. package/dist/cli/tui/sidebar.js.map +1 -0
  241. package/dist/cli/tui/store.js +143 -0
  242. package/dist/cli/tui/store.js.map +1 -0
  243. package/dist/cli/tui/tarjeta.js +19 -0
  244. package/dist/cli/tui/tarjeta.js.map +1 -0
  245. package/dist/cli/tui/temaInk.js +114 -0
  246. package/dist/cli/tui/temaInk.js.map +1 -0
  247. package/dist/cli/tui/transcript.js +254 -0
  248. package/dist/cli/tui/transcript.js.map +1 -0
  249. package/dist/cli/wizardInicial.js +240 -0
  250. package/dist/cli/wizardInicial.js.map +1 -0
  251. package/dist/core/actos.js +113 -0
  252. package/dist/core/actos.js.map +1 -0
  253. package/dist/core/adjuntos.js +97 -0
  254. package/dist/core/adjuntos.js.map +1 -0
  255. package/dist/core/agentes.js +227 -0
  256. package/dist/core/agentes.js.map +1 -0
  257. package/dist/core/artefactos.js +149 -0
  258. package/dist/core/artefactos.js.map +1 -0
  259. package/dist/core/cloudstudio.js +7 -0
  260. package/dist/core/cloudstudio.js.map +1 -0
  261. package/dist/core/config.js +212 -5
  262. package/dist/core/config.js.map +1 -1
  263. package/dist/core/contextos.js +53 -1
  264. package/dist/core/contextos.js.map +1 -1
  265. package/dist/core/descargas.js +106 -0
  266. package/dist/core/descargas.js.map +1 -0
  267. package/dist/core/descriptoresDeApp.js +279 -0
  268. package/dist/core/descriptoresDeApp.js.map +1 -0
  269. package/dist/core/dispositivos.js +466 -0
  270. package/dist/core/dispositivos.js.map +1 -0
  271. package/dist/core/entrega.js +141 -0
  272. package/dist/core/entrega.js.map +1 -0
  273. package/dist/core/entrelazar.js +90 -0
  274. package/dist/core/entrelazar.js.map +1 -0
  275. package/dist/core/esqueleto.js +10 -0
  276. package/dist/core/esqueleto.js.map +1 -1
  277. package/dist/core/modelos.js +235 -3
  278. package/dist/core/modelos.js.map +1 -1
  279. package/dist/core/notify.js +27 -9
  280. package/dist/core/notify.js.map +1 -1
  281. package/dist/core/planDeSubida.js +127 -0
  282. package/dist/core/planDeSubida.js.map +1 -0
  283. package/dist/core/ports.js +189 -1
  284. package/dist/core/ports.js.map +1 -1
  285. package/dist/core/puedeLanzarse.js +239 -0
  286. package/dist/core/puedeLanzarse.js.map +1 -0
  287. package/dist/core/rutaVirtual.js +42 -0
  288. package/dist/core/rutaVirtual.js.map +1 -0
  289. package/dist/core/settings.js +246 -0
  290. package/dist/core/settings.js.map +1 -0
  291. package/dist/core/tareas.js +230 -0
  292. package/dist/core/tareas.js.map +1 -0
  293. package/dist/core/textos.js +36 -0
  294. package/dist/core/textos.js.map +1 -0
  295. package/dist/core/turno.js +56 -8
  296. package/dist/core/turno.js.map +1 -1
  297. package/dist/core/version.js +31 -0
  298. package/dist/core/version.js.map +1 -0
  299. package/dist/vendor/tokenTracking.js +22 -1
  300. package/dist/vendor/tokenTracking.js.map +1 -1
  301. package/dist/web/servidor/arranque.js +3964 -0
  302. package/dist/web/servidor/arranque.js.map +1 -0
  303. package/dist/web/servidor/consolaDeTarea.js +161 -0
  304. package/dist/web/servidor/consolaDeTarea.js.map +1 -0
  305. package/dist/web/servidor/consolaWeb.js +389 -0
  306. package/dist/web/servidor/consolaWeb.js.map +1 -0
  307. package/dist/web/servidor/corredorDeTareas.js +1119 -0
  308. package/dist/web/servidor/corredorDeTareas.js.map +1 -0
  309. package/dist/web/servidor/pielWeb.js +269 -0
  310. package/dist/web/servidor/pielWeb.js.map +1 -0
  311. package/dist/web/servidor/servidor.js +257 -0
  312. package/dist/web/servidor/servidor.js.map +1 -0
  313. package/dist/web/servidor/sesiones.js +440 -0
  314. package/dist/web/servidor/sesiones.js.map +1 -0
  315. package/dist/web/servidor/transporte.js +169 -0
  316. package/dist/web/servidor/transporte.js.map +1 -0
  317. package/dist/web/servidor/vestibulo.js +1276 -0
  318. package/dist/web/servidor/vestibulo.js.map +1 -0
  319. package/package.json +30 -8
  320. package/skills/archify/LICENSE +22 -0
  321. package/skills/archify/SKILL.md +109 -0
  322. package/skills/archify/THIRD_PARTY_NOTICES.md +56 -0
  323. package/skills/archify/assets/template.html +14787 -0
  324. package/skills/archify/bin/archify.mjs +1990 -0
  325. package/skills/archify/bin/open-artifact.mjs +86 -0
  326. package/skills/archify/bin/preview.mjs +648 -0
  327. package/skills/archify/bin/visual-check.mjs +829 -0
  328. package/skills/archify/brand-marks/README.md +31 -0
  329. package/skills/archify/brand-marks/catalog.json +131 -0
  330. package/skills/archify/delta/architecture-delta.mjs +1214 -0
  331. package/skills/archify/examples/agent-run.lifecycle.json +71 -0
  332. package/skills/archify/examples/agent-tool-call.workflow.json +94 -0
  333. package/skills/archify/examples/async-job-roundtrip.sequence.json +61 -0
  334. package/skills/archify/examples/brand-aware-delivery.architecture.json +47 -0
  335. package/skills/archify/examples/cache-miss-request.sequence.json +81 -0
  336. package/skills/archify/examples/checkout-platform.base.architecture.json +31 -0
  337. package/skills/archify/examples/checkout-platform.head.architecture.json +31 -0
  338. package/skills/archify/examples/dataflow-product-analytics.html +14898 -0
  339. package/skills/archify/examples/deployment-release.lifecycle.json +49 -0
  340. package/skills/archify/examples/event-stream.dataflow.json +57 -0
  341. package/skills/archify/examples/incident-response.workflow.json +64 -0
  342. package/skills/archify/examples/lifecycle-agent-run.html +14847 -0
  343. package/skills/archify/examples/product-analytics.dataflow.json +76 -0
  344. package/skills/archify/examples/production-deployment.architecture.json +71 -0
  345. package/skills/archify/examples/release-delivery.workflow.json +62 -0
  346. package/skills/archify/examples/sequence-cache-miss-request.html +14913 -0
  347. package/skills/archify/examples/web-app-rendered.html +14862 -0
  348. package/skills/archify/examples/web-app.architecture.json +46 -0
  349. package/skills/archify/examples/workflow-agent-tool-call-rendered.html +14904 -0
  350. package/skills/archify/migrations/workflow-v2.mjs +279 -0
  351. package/skills/archify/package.json +17 -0
  352. package/skills/archify/recipes/scenarios.mjs +391 -0
  353. package/skills/archify/references/authoring-contract.md +198 -0
  354. package/skills/archify/references/brand-marks.md +69 -0
  355. package/skills/archify/references/delivery-contract.md +116 -0
  356. package/skills/archify/references/viewer-runtime.md +45 -0
  357. package/skills/archify/renderers/architecture/grid.mjs +62 -0
  358. package/skills/archify/renderers/architecture/render-architecture.mjs +1078 -0
  359. package/skills/archify/renderers/dataflow/README.md +104 -0
  360. package/skills/archify/renderers/dataflow/render-dataflow.mjs +483 -0
  361. package/skills/archify/renderers/lifecycle/README.md +115 -0
  362. package/skills/archify/renderers/lifecycle/render-lifecycle.mjs +561 -0
  363. package/skills/archify/renderers/sequence/README.md +114 -0
  364. package/skills/archify/renderers/sequence/render-sequence.mjs +453 -0
  365. package/skills/archify/renderers/shared/brand-marks.mjs +563 -0
  366. package/skills/archify/renderers/shared/cli.mjs +218 -0
  367. package/skills/archify/renderers/shared/desktop-readability.mjs +26 -0
  368. package/skills/archify/renderers/shared/diagnostics.mjs +127 -0
  369. package/skills/archify/renderers/shared/engineering-profiles.mjs +157 -0
  370. package/skills/archify/renderers/shared/generated-brand-marks.mjs +2003 -0
  371. package/skills/archify/renderers/shared/generated-validators.mjs +13 -0
  372. package/skills/archify/renderers/shared/geometry.mjs +1423 -0
  373. package/skills/archify/renderers/shared/i18n.mjs +594 -0
  374. package/skills/archify/renderers/shared/layout-report.mjs +40 -0
  375. package/skills/archify/renderers/shared/legend.mjs +217 -0
  376. package/skills/archify/renderers/shared/output-path.mjs +321 -0
  377. package/skills/archify/renderers/shared/repository-evidence.mjs +235 -0
  378. package/skills/archify/renderers/shared/text-fit.mjs +49 -0
  379. package/skills/archify/renderers/shared/utils.mjs +232 -0
  380. package/skills/archify/renderers/shared/validator.mjs +86 -0
  381. package/skills/archify/renderers/workflow/README.md +223 -0
  382. package/skills/archify/renderers/workflow/render-workflow.mjs +35 -0
  383. package/skills/archify/renderers/workflow/workflow-compiler.mjs +4400 -0
  384. package/skills/archify/renderers/workflow/workflow-migration-geometry.mjs +144 -0
  385. package/skills/archify/schemas/README.md +211 -0
  386. package/skills/archify/schemas/architecture.schema.json +176 -0
  387. package/skills/archify/schemas/common.schema.json +115 -0
  388. package/skills/archify/schemas/dataflow.schema.json +243 -0
  389. package/skills/archify/schemas/lifecycle.schema.json +266 -0
  390. package/skills/archify/schemas/sequence.schema.json +223 -0
  391. package/skills/archify/schemas/workflow.schema.json +428 -0
  392. package/skills/archify/scripts/check-render-output.mjs +835 -0
  393. package/skills/archify/scripts/check-update.mjs +1667 -0
  394. package/skills/archify/scripts/render-examples.mjs +26 -0
  395. package/skills/archify/scripts/update-contract.mjs +182 -0
  396. package/skills/archify/skill-release.json +10 -0
  397. package/skills/artifacts-builder/SKILL.md +120 -0
  398. package/skills/artifacts-builder/reference/diagramas.md +123 -0
  399. package/skills/artifacts-builder/reference/estilo.md +123 -0
  400. package/skills/artifacts-builder/reference/exportar-pdf.md +56 -0
  401. package/skills/artifacts-builder/reference/graficas.md +22 -0
  402. package/skills/artifacts-builder/scripts/bundle_artifact.py +109 -0
  403. package/skills/artifacts-builder/scripts/validate_artifact.py +345 -0
  404. package/skills/xone-hotswap/SKILL.md +185 -0
  405. package/skills/xone-hotswap/references/comandos.md +706 -0
  406. package/skills/xone-hotswap/references/conexion-y-despliegue.md +226 -0
@@ -0,0 +1,26 @@
1
+ // Re-render every bundled example from its JSON IR. Installed skills keep HTML
2
+ // beside the JSON examples; the development script passes the golden directory.
3
+
4
+ import { execFileSync } from 'node:child_process';
5
+ import path from 'node:path';
6
+ import { fileURLToPath } from 'node:url';
7
+
8
+ const __dirname = path.dirname(fileURLToPath(import.meta.url));
9
+ const skillRoot = path.resolve(__dirname, '..');
10
+ const outputRoot = path.resolve(process.argv[2] || path.join(skillRoot, 'examples'));
11
+
12
+ const TARGETS = [
13
+ ['workflow', 'agent-tool-call.workflow.json', 'workflow-agent-tool-call-rendered.html'],
14
+ ['sequence', 'cache-miss-request.sequence.json', 'sequence-cache-miss-request.html'],
15
+ ['dataflow', 'product-analytics.dataflow.json', 'dataflow-product-analytics.html'],
16
+ ['lifecycle', 'agent-run.lifecycle.json', 'lifecycle-agent-run.html'],
17
+ ['architecture', 'web-app.architecture.json', 'web-app-rendered.html'],
18
+ ];
19
+
20
+ for (const [mode, input, output] of TARGETS) {
21
+ execFileSync(process.execPath, [
22
+ path.join(skillRoot, `renderers/${mode}/render-${mode}.mjs`),
23
+ path.join(skillRoot, 'examples', input),
24
+ path.join(outputRoot, output),
25
+ ], { stdio: 'inherit' });
26
+ }
@@ -0,0 +1,182 @@
1
+ export const SKILL_ID = 'archify';
2
+ export const EXPECTED_REPOSITORY = 'https://github.com/tt-a1i/archify';
3
+ export const DEFAULT_MANIFEST_URL = 'https://tt-a1i.github.io/archify/skill-updates/archify/stable.json';
4
+
5
+ const CONTROL_OR_BIDI = /[\u0000-\u001f\u007f-\u009f\u202a-\u202e\u2066-\u2069]/u;
6
+ const HEX_40 = /^[a-f0-9]{40}$/;
7
+ const HEX_64 = /^[a-f0-9]{64}$/;
8
+ const SEMVER = /^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-([0-9A-Za-z-]+(?:\.[0-9A-Za-z-]+)*))?(?:\+([0-9A-Za-z-]+(?:\.[0-9A-Za-z-]+)*))?$/;
9
+ const UTC_SECONDS = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}Z$/;
10
+
11
+ export class UpdateContractError extends Error {
12
+ constructor(message) {
13
+ super(message);
14
+ this.name = 'UpdateContractError';
15
+ }
16
+ }
17
+
18
+ function isPlainObject(value) {
19
+ return Boolean(value) && typeof value === 'object' && !Array.isArray(value);
20
+ }
21
+
22
+ function hasExactKeys(value, expected) {
23
+ return isPlainObject(value)
24
+ && Object.keys(value).sort().join('\0') === [...expected].sort().join('\0');
25
+ }
26
+
27
+ export function parseSemver(value) {
28
+ if (typeof value !== 'string' || value.length > 128) {
29
+ throw new UpdateContractError(`invalid SemVer: ${JSON.stringify(value)}`);
30
+ }
31
+ const match = SEMVER.exec(value);
32
+ if (!match) throw new UpdateContractError(`invalid SemVer: ${JSON.stringify(value)}`);
33
+ const prerelease = match[4]?.split('.') ?? null;
34
+ if (prerelease?.some((identifier) => /^\d+$/.test(identifier)
35
+ && identifier.length > 1 && identifier.startsWith('0'))) {
36
+ throw new UpdateContractError(`invalid SemVer: ${JSON.stringify(value)}`);
37
+ }
38
+ return {
39
+ core: match.slice(1, 4),
40
+ prerelease,
41
+ build: match[5]?.split('.') ?? null,
42
+ };
43
+ }
44
+
45
+ function compareNumericIdentifiers(left, right) {
46
+ if (left.length !== right.length) return left.length < right.length ? -1 : 1;
47
+ if (left === right) return 0;
48
+ return left < right ? -1 : 1;
49
+ }
50
+
51
+ function comparePrerelease(left, right) {
52
+ if (left === null && right === null) return 0;
53
+ if (left === null) return 1;
54
+ if (right === null) return -1;
55
+ const length = Math.max(left.length, right.length);
56
+ for (let index = 0; index < length; index += 1) {
57
+ if (left[index] === undefined) return -1;
58
+ if (right[index] === undefined) return 1;
59
+ if (left[index] === right[index]) continue;
60
+ const leftNumeric = /^\d+$/.test(left[index]);
61
+ const rightNumeric = /^\d+$/.test(right[index]);
62
+ if (leftNumeric && rightNumeric) return compareNumericIdentifiers(left[index], right[index]);
63
+ if (leftNumeric !== rightNumeric) return leftNumeric ? -1 : 1;
64
+ return left[index] < right[index] ? -1 : 1;
65
+ }
66
+ return 0;
67
+ }
68
+
69
+ export function compareSemver(leftValue, rightValue) {
70
+ const left = parseSemver(leftValue);
71
+ const right = parseSemver(rightValue);
72
+ for (let index = 0; index < left.core.length; index += 1) {
73
+ const comparison = compareNumericIdentifiers(left.core[index], right.core[index]);
74
+ if (comparison !== 0) return comparison;
75
+ }
76
+ return comparePrerelease(left.prerelease, right.prerelease);
77
+ }
78
+
79
+ export function releaseChannelForVersion(value) {
80
+ return parseSemver(value).prerelease ? 'development' : 'stable';
81
+ }
82
+
83
+ export function isStableCoreVersion(value) {
84
+ try {
85
+ const parsed = parseSemver(value);
86
+ return parsed.prerelease === null && parsed.build === null;
87
+ } catch {
88
+ return false;
89
+ }
90
+ }
91
+
92
+ export function validateCanonicalUtcTimestamp(value) {
93
+ if (typeof value !== 'string' || !UTC_SECONDS.test(value)) {
94
+ throw new UpdateContractError('publication time must use YYYY-MM-DDTHH:mm:ssZ');
95
+ }
96
+ const timestamp = Date.parse(value);
97
+ if (!Number.isFinite(timestamp)
98
+ || new Date(timestamp).toISOString().replace('.000Z', 'Z') !== value) {
99
+ throw new UpdateContractError('publication time is not a real UTC calendar instant');
100
+ }
101
+ return value;
102
+ }
103
+
104
+ export function validateLocalRelease(value) {
105
+ if (!hasExactKeys(value, [
106
+ 'schemaVersion', 'skillId', 'channel', 'version', 'source', 'updateManifestUrl',
107
+ ])
108
+ || value.schemaVersion !== 1
109
+ || value.skillId !== SKILL_ID
110
+ || !hasExactKeys(value.source, ['repository'])
111
+ || value.source.repository !== EXPECTED_REPOSITORY
112
+ || value.updateManifestUrl !== DEFAULT_MANIFEST_URL) {
113
+ throw new UpdateContractError('invalid local release identity');
114
+ }
115
+ const expectedChannel = releaseChannelForVersion(value.version);
116
+ if (value.channel !== expectedChannel) {
117
+ throw new UpdateContractError('local release channel does not match its version');
118
+ }
119
+ return {
120
+ schemaVersion: value.schemaVersion,
121
+ skillId: value.skillId,
122
+ channel: value.channel,
123
+ version: value.version,
124
+ source: { repository: value.source.repository },
125
+ updateManifestUrl: value.updateManifestUrl,
126
+ };
127
+ }
128
+
129
+ export function validateReleaseNotesUrl(value, version) {
130
+ if (!isStableCoreVersion(version)) {
131
+ throw new UpdateContractError('release notes require a stable core version');
132
+ }
133
+ const expected = `https://github.com/tt-a1i/archify/releases/tag/v${version}`;
134
+ if (value !== expected) {
135
+ throw new UpdateContractError('release notes URL is outside the exact trusted release path');
136
+ }
137
+ return value;
138
+ }
139
+
140
+ export function validateStableUpdateManifest(value) {
141
+ if (!hasExactKeys(value, [
142
+ 'schemaVersion', 'skillId', 'channel', 'version', 'publishedAt', 'source',
143
+ 'artifact', 'summary', 'releaseNotes', 'severity',
144
+ ])
145
+ || value.schemaVersion !== 1
146
+ || value.skillId !== SKILL_ID
147
+ || value.channel !== 'stable'
148
+ || !isStableCoreVersion(value.version)
149
+ || !hasExactKeys(value.source, ['repository', 'ref', 'treeSha'])
150
+ || value.source.repository !== EXPECTED_REPOSITORY
151
+ || value.source.ref !== `v${value.version}`
152
+ || !HEX_40.test(value.source.treeSha)
153
+ || !hasExactKeys(value.artifact, ['sha256'])
154
+ || !HEX_64.test(value.artifact.sha256)) {
155
+ throw new UpdateContractError('invalid immutable stable release identity');
156
+ }
157
+ validateCanonicalUtcTimestamp(value.publishedAt);
158
+ if (typeof value.summary !== 'string' || value.summary.length < 1 || value.summary.length > 160
159
+ || CONTROL_OR_BIDI.test(value.summary)) {
160
+ throw new UpdateContractError('invalid release summary');
161
+ }
162
+ validateReleaseNotesUrl(value.releaseNotes, value.version);
163
+ if (!['normal', 'security'].includes(value.severity)) {
164
+ throw new UpdateContractError('invalid update severity');
165
+ }
166
+ return {
167
+ schemaVersion: value.schemaVersion,
168
+ skillId: value.skillId,
169
+ channel: value.channel,
170
+ version: value.version,
171
+ publishedAt: value.publishedAt,
172
+ source: {
173
+ repository: value.source.repository,
174
+ ref: value.source.ref,
175
+ treeSha: value.source.treeSha,
176
+ },
177
+ artifact: { sha256: value.artifact.sha256 },
178
+ summary: value.summary,
179
+ releaseNotes: value.releaseNotes,
180
+ severity: value.severity,
181
+ };
182
+ }
@@ -0,0 +1,10 @@
1
+ {
2
+ "schemaVersion": 1,
3
+ "skillId": "archify",
4
+ "channel": "development",
5
+ "version": "2.17.0-dev.1",
6
+ "source": {
7
+ "repository": "https://github.com/tt-a1i/archify"
8
+ },
9
+ "updateManifestUrl": "https://tt-a1i.github.io/archify/skill-updates/archify/stable.json"
10
+ }
@@ -0,0 +1,120 @@
1
+ ---
2
+ name: artifacts-builder
3
+ description: "Build a self-contained interactive HTML artifact the user can view in the chat: dashboards, interactive charts, flow diagrams, filterable tables, printable reports. Use when a plain text answer would lose information that a visual or interactive piece would keep."
4
+ ---
5
+
6
+ # Artifacts Builder
7
+
8
+ You write ONE self-contained HTML file. No build step, no npm, no `execute` anywhere this
9
+ skill is mounted — nothing here runs a script.
10
+
11
+ ## Steps
12
+
13
+ 1. **Pick a character and paste the tokens** — `reference/estilo.md`, one table row, whole.
14
+ This is a STEP and not optional reading, and the reason is measured: while it lived under
15
+ "read when you need it" the builder **never opened it**, and every panel came out the same —
16
+ Inter, indigo accent, four different corner radii and zero CSS variables. Five tokens
17
+ (`--surface --surface-2 --ink --ink-muted --border --accent --radius`) and one row of the
18
+ character table are the whole decision; the file is 86 lines and it is the short one.
19
+ 2. **Write** the HTML with `write_file` **en `/artefactos/<nombre>.html`** — nunca en la raíz
20
+ del proyecto. Esa carpeta no es del proyecto: no pasa por la aprobación humana, no entra
21
+ en git y no sube a CloudStudio. Un HTML escrito fuera de ella acaba DENTRO de la app XOne
22
+ del usuario, que no es lo que nadie pidió. Keep it ONE file: with no `execute` tool
23
+ anywhere here, there is no bundler to run. Inline local assets (fonts, images) as `data:`
24
+ URIs directly in the file you write, instead of splitting it and planning to combine the
25
+ pieces later.
26
+ 3. **Entrega, según la tool que TENGAS:**
27
+ - **Si tienes `publish_artifact`** (el panel): `publish_artifact(path="/artifact.html",
28
+ title="…")`. Valida al publicar contra el contrato de abajo. Si lo rechaza, te dice
29
+ exactamente qué arreglar; corrige y reintenta. Para actualizar uno que ya publicaste,
30
+ pasa su `artifact_id` — el enlace del usuario no cambia.
31
+ - **Si tienes `renderizar_diagrama` en vez de `publish_artifact`** (el camino de
32
+ `documentar`): si lo que construiste es un DIAGRAMA (arquitectura, flujo, secuencia,
33
+ dataflow, lifecycle), no sigas este camino — usa la skill `archify` y llama a
34
+ `renderizar_diagrama(tipo, spec_json, ruta)`, que valida y coloca el fichero por ti.
35
+ Para cualquier OTRO artefacto (tabla, dashboard, gráfica que no es un diagrama de
36
+ archify), ya tienes `write_file`: escríbelo en `/artefactos/` — el contrato de abajo NO
37
+ aplica en este camino, es del sandbox del panel (ver su nota).
38
+ - **Si no tienes NINGUNA de las dos** (xonecode): `write_file` en
39
+ `/artefactos/<nombre>.html` y ya está. No inventes ninguna de las dos tools, y no
40
+ anuncies capacidades del panel —sandbox, enlace compartible, actualización por
41
+ `artifact_id`— que en este camino no existen. La entrega ES la escritura: la consola
42
+ anuncia el artefacto sola.
43
+ **Cuando la entrega confirme, HAS TERMINADO** — no reescribas el mismo artefacto otra vez.
44
+
45
+ ## The contract — non-negotiable — solo si tienes `publish_artifact`
46
+
47
+ El artefacto corre en un sandbox cerrado. Esto lo hace cumplir el SERVIDOR de `publish_artifact`,
48
+ no la confianza — y por eso solo es cierto en este camino, no en el de `write_file`:
49
+
50
+ - **No network.** No `fetch`, `XMLHttpRequest`, `WebSocket`, `EventSource`, `sendBeacon`,
51
+ dynamic `import()`. Bake the data into the HTML as a JS constant.
52
+ - **Libraries only from** `https://cdnjs.cloudflare.com` or `https://cdn.jsdelivr.net`
53
+ (fonts: `fonts.googleapis.com` + `fonts.gstatic.com`). Pin an exact version.
54
+ - **Images**: `data:` URIs only. An external `<img src>` leaks data through its query string.
55
+ - **No** `<base>`, no external `<iframe>`, no external `<form action>`.
56
+ - **5 MB max.**
57
+ - **`localStorage` THROWS. Wrap every access in `try/catch` — or don't use it.** The widget
58
+ renders the artifact in an iframe with `sandbox="allow-scripts allow-downloads allow-modals"`
59
+ and **no `allow-same-origin`**, so the document has an opaque origin and merely *reading*
60
+ `localStorage` raises:
61
+
62
+ ```
63
+ Failed to read the 'localStorage' property from 'Window':
64
+ The document is sandboxed and lacks the 'allow-same-origin' flag.
65
+ ```
66
+
67
+ This is measured, not theoretical, and it is the **most expensive mistake in this list**
68
+ because it fails SILENTLY. A real panel died on `'theme' in localStorage` before
69
+ `mermaid.initialize(…)` ever ran, and the page looked perfect while the diagram stayed an
70
+ empty rectangle. `matchMedia('(prefers-color-scheme: dark)')` needs no storage for the theme;
71
+ if you really want to remember something per viewer, wrap it: `try { localStorage.setItem(k,
72
+ v) } catch {}`.
73
+
74
+ ## El contrato del OTRO camino, `write_file` en `/artefactos/` (xonecode)
75
+
76
+ Este párrafo decía que sin `publish_artifact` no había sandbox: «el fichero queda tal cual en el
77
+ proyecto del cliente, sin iframe, sin lista blanca de CDN, `localStorage` no lanza ahí». **Es
78
+ falso desde que la consola los ABRE**, y era el error más caro que se podía dejar escrito: quien
79
+ lo leyera usaría `localStorage` y el diagrama moriría en silencio.
80
+
81
+ Aquí el sandbox lo impone el VISOR de la consola, no un servidor de publicación — y lo impone
82
+ igual. Medido en el navegador (2026-09-07) sobre un artefacto real, con el iframe en
83
+ `sandbox="allow-scripts"` y **sin** `allow-same-origin`:
84
+
85
+ - **`localStorage`, `sessionStorage` e `indexedDB` LANZAN `SecurityError`.** Los tres, no solo el
86
+ primero. Vale entera la advertencia de arriba, incluido por qué es el error más caro de la
87
+ lista: falla EN SILENCIO, con la página perfecta y el diagrama sin dibujar.
88
+ - **Las CDNs SÍ funcionan, con conexión.** `cdnjs.cloudflare.com` y `fonts.googleapis.com` /
89
+ `fonts.gstatic.com` contestaron 200 desde dentro del iframe. No hay lista blanca que cumplir
90
+ ni tope de 5 MB (el visor sirve hasta 20 MB) ni validador que rechace nada: lo que escribas es
91
+ lo que se verá. Usa esas dos CDNs igualmente.
92
+ - **Al ORIGEN de la consola no se llega.** Un `fetch` a cualquier ruta suya muere en el propio
93
+ navegador («from origin 'null' has been blocked by CORS»), así que sus tipografías
94
+ empaquetadas y sus rutas no están a tu alcance: da igual que estén ahí al lado.
95
+ - **Nada bloquea una petición a un tercero**, y justo por eso: no hagas ninguna que no
96
+ necesites. Hornea los datos dentro del HTML, como en el otro camino — un proyecto XOne puede
97
+ abrirse offline, y una petición saliente se lleva consigo lo que lleve en la URL.
98
+
99
+ ## What you can use
100
+
101
+ React 18 (UMD), Tailwind, any chart library, mermaid, via CDN `<script>` tags — no bundler,
102
+ either path. **Con `publish_artifact`**, solo pasan `cdnjs.cloudflare.com` y `cdn.jsdelivr.net`
103
+ (`https://cdn.jsdelivr.net/npm/@tailwindcss/browser@4`, NUNCA `cdn.tailwindcss.com`: no está en
104
+ la lista blanca). **Con `write_file`**, no hay lista blanca que cumplir — igual, usa esas dos
105
+ CDNs por defecto salvo que el proyecto ya traiga otra cosa.
106
+
107
+ ## Read when you need it
108
+
109
+ - `reference/graficas.md` — interactive charts
110
+ - `reference/diagramas.md` — flow diagrams with mermaid
111
+ - `reference/exportar-pdf.md` — a working PDF export button
112
+ - `reference/estilo.md` — **el sistema visual (paso 1, no opcional)**: tokens, carácter, escala
113
+
114
+ ## Rules of thumb
115
+
116
+ - Support dark and light: don't hardcode one color scheme.
117
+ - One page, one job. If it needs two unrelated screens, that's two artifacts (or two files).
118
+ - Bake enough data to be useful, not the whole dataset. Con `publish_artifact` el tope de 5 MB
119
+ lo impone el servidor; con `write_file` no hay tope impuesto, pero un fichero de datos entero
120
+ sigue siendo mala idea igual.
@@ -0,0 +1,123 @@
1
+ # Diagramas de flujo
2
+
3
+ ## Antes de escribir HTML: `archify` decide el diagrama
4
+
5
+ Si la petición es **solo** un diagrama, esquema, arquitectura, flujo, secuencia, data-flow o
6
+ ciclo de estados, **no uses esta skill**: carga únicamente **`archify`**. Es quien decide el
7
+ tipo de diagrama, qué evidencia del proyecto es relevante y cómo conservar nombres reales.
8
+
9
+ `artifacts-builder` participa únicamente cuando el usuario pide además un contenedor HTML
10
+ interactivo, dashboard, informe o tabla. En ese caso, espera a que `archify` haya decidido el
11
+ diagrama, crea su SVG y **lo incrusta inline** en el único HTML de este artefacto.
12
+
13
+ - La salida se guarda en `/artefactos/<nombre>.html`, nunca en la raíz del proyecto —de ahí
14
+ acabaría dentro de la app XOne del usuario, en git y en CloudStudio— ni en `/skills`, donde
15
+ viven solo instrucciones y recursos del harness.
16
+ - No inventes `renderizar_diagrama`, `publish_artifact` ni una ejecución de scripts si esas
17
+ herramientas no figuran en tu contexto. Con `write_file`, entrega el HTML autocontenido.
18
+ - Usa Mermaid únicamente cuando el usuario lo pida expresamente o cuando un SVG manual no aporte
19
+ claridad. Para el resto, `archify` es la fuente de decisión visual y semántica.
20
+ - Si el resultado combina análisis del proyecto y un diagrama, primero confirma los hechos con
21
+ el código; no dibujes componentes, rutas ni estados que no estén comprobados.
22
+
23
+ ## Mermaid, solo cuando procede
24
+
25
+ Mermaid desde cdnjs. Sin red: el diagrama es texto dentro de la página. **Éste es el montaje
26
+ canónico** — copia el bloque entero, no la mitad:
27
+
28
+ ```html
29
+ <script src="https://cdnjs.cloudflare.com/ajax/libs/mermaid/10.9.0/mermaid.min.js"></script>
30
+ <pre class="mermaid">
31
+ flowchart LR
32
+ Login["LoginRest (login-coll)"] --> Entry["VisitasClientes_v2 (entry-point)"]
33
+ Entry --> Q{"¿Cliente nuevo?"}
34
+ Q -->|"Sí"| Alta["Clientes.xne"]
35
+ Q -->|"No"| DB[("gestion.db")]
36
+ </pre>
37
+ <style>
38
+ .mermaid { width: 100%; overflow-x: auto; }
39
+ .mermaid svg { width: 100%; height: auto; max-width: none; }
40
+ </style>
41
+ <script>
42
+ mermaid.initialize({
43
+ startOnLoad: true,
44
+ theme: "base", // el ÚNICO que acepta themeVariables
45
+ themeVariables: {
46
+ primaryColor: "#ffffff", // relleno del nodo → --surface
47
+ primaryTextColor: "#151a21", // texto del nodo → --ink
48
+ primaryBorderColor: "#d7dee6", // borde → --rule
49
+ lineColor: "#4e5a68", // flechas → --ink-soft
50
+ secondaryColor: "#eef2f6", // fondo de subgrafos → --surface-2
51
+ tertiaryColor: "#d9edf4", // lo acentuado → --accent-soft
52
+ fontFamily: "'IBM Plex Serif', Georgia, serif",
53
+ fontSize: "15px",
54
+ },
55
+ flowchart: { curve: "basis", nodeSpacing: 40, rankSpacing: 55, padding: 12 },
56
+ });
57
+ </script>
58
+ ```
59
+
60
+ ## Por qué ese bloque y no el de por omisión
61
+
62
+ Los defectos de mermaid pintan **nodos amarillo pastel con borde marrón, en escuadra y
63
+ apelotonados**: el diagrama parece de otro producto que el panel que lo rodea. Comprobado en un
64
+ navegador con 10.9.0, con el bloque de arriba el relleno del nodo sale `#ffffff`, el borde
65
+ `#d7dee6` y las flechas `#4e5a68` — o sea **los mismos tokens que el panel** (`estilo.md`).
66
+
67
+ - **`theme: "base"`**: con `default`, `dark` o `neutral`, `themeVariables` **se ignora**.
68
+ - **`curve: "basis"`**: aristas curvas en vez de en escuadra. El cambio de una línea que más
69
+ aire da.
70
+ - **`nodeSpacing`/`rankSpacing`**: los defectos (15/50) aprietan; 40/55 respira.
71
+ - **Los colores van A MANO, no como `var(--x)`**: mermaid los escribe dentro del SVG y no
72
+ resuelve variables CSS. Con tema oscuro, pásale el juego oscuro cuando
73
+ `matchMedia('(prefers-color-scheme: dark)').matches`.
74
+ - **Las dos líneas del `<style>`**: `overflow-x` en el BLOQUE (la página no debe scrollear en
75
+ horizontal) y `max-width: none` en el SVG, porque mermaid le escribe su tamaño natural y sin
76
+ eso se queda pequeño y centrado en un panel ancho.
77
+
78
+ ## LO PRIMERO: toda etiqueta con `(` va ENTRE COMILLAS
79
+
80
+ Un paréntesis sin comillas es un error de SINTAXIS y **se lleva el diagrama entero**: la página
81
+ carga perfecta y en su sitio sale «Syntax error in text». Medido con `mermaid.parse`, y **en
82
+ 10.9.0 y en 11.15.0 igual** — no es cosa de la versión:
83
+
84
+ | lo que escribes | |
85
+ |---|---|
86
+ | `A[Mapeos (mapcol)]` | **ROMPE** |
87
+ | `A["Mapeos (mapcol)"]` | ✓ |
88
+ | `subgraph Vistas (contents)` | **ROMPE** |
89
+ | `subgraph S1 [Vistas (contents)]` | **ROMPE** — los corchetes NO salvan |
90
+ | `subgraph "Vistas (contents)"` | ✓ |
91
+ | `A[(Tabla (usuarios))]` | **ROMPE** · `DB[("Tabla (usuarios)")]` ✓ |
92
+
93
+ Y lo que **NO** rompe, comprobado igual: almohadillas (`A[Salida ##EXIT##]`), puntos
94
+ (`A[LoginColl.xne]`), acentos, `:`, `@` y texto en las flechas — las almohadillas se han acusado
95
+ en falso DOS veces. En un proyecto XOne los nombres traen paréntesis solos (`(mapcol)`,
96
+ `(contents)`, `(entry-point)`), así que la regla práctica es **comillas siempre**.
97
+
98
+ ## Si el diagrama va en una PESTAÑA, `startOnLoad: true` lo deja en blanco
99
+
100
+ **Fallo real, medido**: dentro de un contenedor oculto mermaid produce un SVG de **0×0** y no
101
+ vuelve a dibujar al mostrarlo (visible al cargar da 563×427). El usuario ve un hueco y la
102
+ consola no dice nada. Con pestañas, acordeones o `<details>` cerrados: **`startOnLoad: false`, y
103
+ dibujar DESPUÉS de mostrar**.
104
+
105
+ ```js
106
+ const dibujados = new WeakSet();
107
+ async function mostrarPestana(panel) {
108
+ panel.style.display = 'block'; // primero VISIBLE
109
+ for (const nodo of panel.querySelectorAll('.mermaid')) {
110
+ if (dibujados.has(nodo)) continue; // una sola vez por nodo
111
+ dibujados.add(nodo);
112
+ await mermaid.run({ nodes: [nodo] }); // y AHORA se dibuja
113
+ }
114
+ }
115
+ ```
116
+
117
+ De `0×0` a `278×105`. Tres detalles: **el orden no es negociable** (`display: block` ANTES de
118
+ `mermaid.run`; al revés vuelve a dar 0×0) · **`run({ nodes: [...] })` y no `run()` a secas**
119
+ (sin `nodes` reprocesa la página entera) · **una sola vez por nodo** (mermaid sustituye el
120
+ `<pre>` por el SVG, así que un segundo pase no tiene texto que parsear).
121
+
122
+ Diagnóstico rápido: «Syntax error in text» → un paréntesis sin comillas. Hueco en blanco SIN
123
+ error → el contenedor oculto. Nunca las almohadillas.
@@ -0,0 +1,123 @@
1
+ # El estilo es un SISTEMA: pega los tokens, elige un carácter
2
+
3
+ Este fichero era una lista de consejos y se incumplía entera. Medido en un panel real
4
+ (2026-09-01): decía «evita Inter» y salió `Inter`; decía «evita los morados» y salieron índigo
5
+ `#6366f1` + púrpura + rosa; decía «una escala» y salieron cuatro radios sueltos; y cero
6
+ variables CSS. **Un consejo no es un sistema**: lo que sigue se pega y se acabó.
7
+
8
+ ## Los tokens, y el tema en TRES bloques
9
+
10
+ **El de por omisión**, elegido por el usuario el 2026-09-01: fondo casi blanco frío, tinta negra
11
+ azulada, acento azul petróleo y el **cuerpo en SERIF**, que es lo que le quita la cara de
12
+ plantilla. Pega el bloque tal cual y no uses ningún color más.
13
+
14
+ ```html
15
+ <link rel="stylesheet" href="https://fonts.googleapis.com/css2?family=Archivo:wght@500;600;700&family=IBM+Plex+Serif:ital,wght@0,400;0,600;1,400&family=IBM+Plex+Mono:wght@400;500&display=swap">
16
+ <style>
17
+ :root {
18
+ --ground:#f6f8fa; --surface:#ffffff; --surface-2:#eef2f6; /* página / tarjeta / elevado */
19
+ --ink:#151a21; --ink-soft:#4e5a68; --rule:#d7dee6; /* texto / apoyo / separador */
20
+ --accent:#0e6c88; --accent-soft:#d9edf4; /* SOLO lo que actúa o mide */
21
+ --alerta:#8d3b2d; --alerta-soft:#f5e3df; /* lo retirado, lo que falla */
22
+ --display:'Archivo','Helvetica Neue',Arial,sans-serif;
23
+ --body:'IBM Plex Serif',Georgia,serif;
24
+ --mono:'IBM Plex Mono','SF Mono',Menlo,monospace;
25
+ --radius:6px;
26
+ }
27
+ @media (prefers-color-scheme: dark) { :root:not([data-theme="light"]) {
28
+ --ground:#11151a; --surface:#171c23; --surface-2:#1e242c;
29
+ --ink:#e5e9ef; --ink-soft:#9aa7b6; --rule:#2c343e;
30
+ --accent:#58b6d2; --accent-soft:#16323d; --alerta:#d98a7b; --alerta-soft:#35211d;
31
+ } }
32
+ :root[data-theme="dark"] { /* las MISMAS seis líneas de arriba, repetidas */ }
33
+ body { background:var(--ground); color:var(--ink); font-family:var(--body);
34
+ font-size:17px; line-height:1.65; margin:0; }
35
+ </style>
36
+ ```
37
+
38
+ **Los tres bloques son tres ESTADOS y hacen falta los tres**: el visor puede no decir nada (gana
39
+ `prefers-color-scheme`), decir `data-theme="dark"` o decir `data-theme="light"` — y sin el
40
+ `:not([data-theme="light"])` un visor en claro dentro de un sistema oscuro sale oscuro. **Ningún
41
+ color puede tener su única definición dentro de un `@media`.**
42
+
43
+ Con Tailwind se usan tal cual: `bg-[var(--surface)]`, `text-[var(--ink-soft)]`,
44
+ `border-[var(--rule)]`, `rounded-[var(--radius)]`, `font-[var(--display)]`. Y el diagrama se
45
+ pinta con estos MISMOS tokens: `reference/diagramas.md`, sección del tema.
46
+
47
+ ## El cuerpo en SERIF, los titulares en sans, los identificadores en mono
48
+
49
+ `IBM Plex Serif` a **17px / 1.65** para leer, `Archivo` para titulares y `IBM Plex Mono` para lo
50
+ que es un identificador (`app.xml`, `MAP_BT_MENU`, nombres de coll). Esa mezcla es lo contrario
51
+ del defecto —todo en Inter a 14px— y es la mitad del carácter.
52
+
53
+ Otros caracteres, si el contenido pide otra cosa. **Se toma la fila ENTERA:**
54
+
55
+ | carácter | display / cuerpo / mono | acento | radio |
56
+ |---|---|---|---|
57
+ | **documento** (el de arriba) | Archivo / IBM Plex Serif / IBM Plex Mono | `#0e6c88` petróleo | `6px` |
58
+ | **instrumento** | IBM Plex Sans / IBM Plex Sans / IBM Plex Mono | `#0f766e` teal | `4px` |
59
+ | **cuadro de mando** | Space Grotesk / Public Sans / IBM Plex Mono | `#1d4ed8` tinta | `10px` |
60
+ | **xonecode** (solo si el artefacto habla de la CONSOLA) | IBM Plex Sans / IBM Plex Sans / IBM Plex Mono | `#00a3e0` cian de marca | `6px` |
61
+
62
+ **Ninguna es Inter y ningún acento es índigo ni púrpura**, que es la otra mitad.
63
+
64
+ La fila **xonecode** es la excepción con dueño, y tiene su regla: el cian `#00a3e0` es el color
65
+ de marca MEDIDO (`apps/web/estilos/marca.css`, junto al azul `#083b56` de las superficies de
66
+ marca), y se usa **solo cuando el artefacto es sobre xonecode o sobre el harness** — un diagrama
67
+ de sus capas, un panel de su lazo de turno. Para el mockup de una pantalla XOne o para un
68
+ informe del proyecto del cliente, NO: ahí el tema es el de por omisión, y la app tiene su propio
69
+ CSS. Dos cosas que no son negociables en esa fila:
70
+
71
+ - **El cian es ACENTO y jamás sostiene texto.** Es la misma regla que la consola aplica sobre sí
72
+ misma: el relleno del botón primario es casi negro y el cian se reserva para la pestaña
73
+ elegida, el filo de la tarjeta viva, el punto de estado y la fila seleccionada. Un titular
74
+ cian sobre blanco no tiene contraste y es exactamente el aspecto que esta fila intenta evitar.
75
+ - **La tipografía de la consola —Inter— no está en el menú**, y por dos motivos a la vez: la
76
+ regla de arriba de este mismo fichero, y que sus fuentes empaquetadas **no se pueden cargar**
77
+ desde el artefacto (el iframe tiene origen opaco y no llega al origen de la consola; medido).
78
+ Se usa IBM Plex Sans, que es un instrumento y viene de Google Fonts como el resto.
79
+
80
+ ## El ancho: la PÁGINA no lleva `max-width`
81
+
82
+ **El artifact se pinta en un panel, no en una ventana de navegador**, y su ancho lo decide quien
83
+ mira — puede ser 1.700 px. Un `max-w-7xl mx-auto` en el contenedor exterior (que es lo que sale
84
+ por defecto) son **1.280 px centrados**: en ese panel deja **460 px de margen muerto** a los
85
+ lados, con el diagrama encogido en medio. Medido sobre un panel real, 2026-09-01.
86
+
87
+ - **Nada de `max-w-*` ni `mx-auto` en el envoltorio de la página.** Se respira con `padding`
88
+ (`p-6 md:p-8`), no estrechando.
89
+ - **La MEDIDA se limita solo en la PROSA**, que es donde de verdad importa: `max-w-prose` en los
90
+ párrafos largos. Una tabla, un diagrama o una rejilla de tarjetas quieren todo el ancho.
91
+ - **Y el SVG de un diagrama tiene que poder CRECER**: mermaid le pone un `max-width` propio que
92
+ lo deja a su tamaño natural. Ver `reference/diagramas.md`.
93
+ - **Y tiene que sobrevivir al panel ESTRECHO, que es el otro lado de lo mismo.** En la consola de
94
+ xonecode el artefacto se pinta en la columna central, con la barra lateral (280 px) y la lista
95
+ de artefactos (260 px) a los lados: en un portátil eso deja el iframe por debajo de 700 px. No
96
+ es motivo para estrechar la página —sigue sin `max-width`—, sino para que la rejilla ceda:
97
+ columnas que se apilan, tablas con su propio scroll horizontal, y ninguna medida fija en px
98
+ para el contenedor.
99
+
100
+ ## Tres reglas duras
101
+
102
+ 1. **UN radio por panel**, el de la fila que hayas elegido. La excepción única es `rounded-full`
103
+ para pastillas y avatares. Cuatro radios en una página es la firma de que nadie decidió.
104
+ 2. **El acento SOLO para lo que actúa o mide**: el botón que se pulsa, la barra que crece, el
105
+ nodo activo. Si el título, los iconos y las etiquetas van del color de acento, no destaca
106
+ nada — y ése es el aspecto de plantilla que se intenta evitar.
107
+ 3. **El fondo se PINTA, siempre y explícito** (`background: var(--ground)` en `body`). El visor
108
+ pinta su propio fondo detrás, así que un `body` transparente hereda el tema del anfitrión y
109
+ el texto puede acabar ilegible.
110
+
111
+ **Y no pongas un INTERRUPTOR de tema.** Los tres bloques de arriba ya cubren los tres estados,
112
+ así que no hace falta — y recordar la elección pide `localStorage`, que **LANZA** en el sandbox
113
+ del visor y se lleva el bloque `<script>` entero: la página se ve perfecta y el diagrama no
114
+ llega a dibujarse. Con `publish_artifact` lo rechaza además el validador. En la consola de
115
+ xonecode no hay validador que lo pare, así que el único que lo evita eres tú — y ahí está medido
116
+ (2026-09-07) que **los tres** almacenes lanzan `SecurityError`: `localStorage`, `sessionStorage`
117
+ e `indexedDB`. Ver `SKILL.md`, «El contrato del OTRO camino».
118
+
119
+ ## Y lo de siempre
120
+
121
+ Una jerarquía de TRES tamaños y sostenerla · alineación a la izquierda salvo motivo (centrarlo
122
+ todo es la marca de fábrica) · espaciado 4/8/16/24 y nada entre medias · densidad al servicio
123
+ del dato: una tabla de 40 filas legible vale más que 6 tarjetas enormes con tres cifras.
@@ -0,0 +1,56 @@
1
+ # Exportar a PDF
2
+
3
+ **La vía sencilla y fiable: `window.print()` con CSS de impresión.** No necesita librería, y el
4
+ widget de NappAI pinta el artifact en un iframe con `allow-modals`, que es lo que permite abrir
5
+ el diálogo de impresión desde dentro.
6
+
7
+ ```html
8
+ <button class="no-imprimir" onclick="window.print()">Exportar a PDF</button>
9
+ <style>
10
+ @media print {
11
+ .no-imprimir { display: none; }
12
+ body { background: #fff; color: #000; }
13
+ .pagina { break-inside: avoid; }
14
+ }
15
+ @page { margin: 15mm; }
16
+ </style>
17
+ ```
18
+
19
+ El usuario elige «Guardar como PDF» en el diálogo del navegador.
20
+
21
+ ## Si el artifact tiene varias vistas, exporta SOLO la que se está viendo
22
+
23
+ Un panel con pestañas no debe imprimir las pestañas ocultas: salen paginas en blanco o, peor,
24
+ contenido que el usuario no estaba mirando. Marca lo imprimible y esconde el resto:
25
+
26
+ ```html
27
+ <section class="vista" data-vista="resumen">…</section>
28
+ <section class="vista" data-vista="detalle" hidden>…</section>
29
+
30
+ <style>
31
+ @media print {
32
+ /* Solo la vista visible llega al PDF. */
33
+ .vista[hidden] { display: none !important; }
34
+ nav, .filtros, .no-imprimir { display: none; }
35
+ }
36
+ </style>
37
+ ```
38
+
39
+ Si una vista **no** tiene sentido en papel —un mapa interactivo, un formulario— dilo en la
40
+ interfaz en vez de imprimirla mal: deshabilita el botón para esa vista, o añade un
41
+ `@media print` que la sustituya por una nota corta.
42
+
43
+ ## Antes de dar el botón por bueno
44
+
45
+ - **Las gráficas se imprimen desde el canvas ya pintado.** Si la librería redibuja al cambiar el
46
+ tamaño, escucha `beforeprint` y fuerza un `resize`/`update`; si no, el PDF sale con la gráfica
47
+ del tamaño anterior.
48
+ - **Los colores de fondo se pierden.** El navegador no imprime fondos por omisión. Para una
49
+ tabla con filas alternas o un badge de color, usa `print-color-adjust: exact` en ese elemento.
50
+ - **Nada de `position: fixed`** en lo que deba salir: se repite o desaparece.
51
+
52
+ ## Si generas el fichero desde JavaScript
53
+
54
+ jsPDF o html2pdf desde cdnjs. Ten en cuenta que la descarga dentro del iframe depende de
55
+ `allow-downloads`, que el widget sí pone. Aun así `window.print()` falla en menos sitios y no
56
+ gasta presupuesto del tope de 5 MB en una librería.
@@ -0,0 +1,22 @@
1
+ # Gráficas interactivas
2
+
3
+ Chart.js desde cdnjs, versión fijada. Los datos van horneados: no hay red.
4
+
5
+ ```html
6
+ <script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/4.4.0/chart.umd.min.js"></script>
7
+ <canvas id="ventas"></canvas>
8
+ <script>
9
+ const DATOS = [/* horneado en tiempo de generación */];
10
+ new Chart(document.getElementById('ventas'), {
11
+ type: 'bar',
12
+ data: { labels: DATOS.map(d => d.mes), datasets: [{ data: DATOS.map(d => d.total) }] },
13
+ options: { responsive: true, plugins: { legend: { display: false } } }
14
+ });
15
+ </script>
16
+ ```
17
+
18
+ **Interactividad sin red:** filtra el array en memoria y llama a `chart.update()`. Todo el
19
+ dataset ya está en la página.
20
+
21
+ **Tema:** lee `window.matchMedia('(prefers-color-scheme: dark)')` y pásale los colores a
22
+ `options.scales` y `options.plugins.legend.labels.color`.