agents-city 0.3.0-beta.21

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 (440) hide show
  1. package/.claude-plugin/marketplace.json +16 -0
  2. package/LICENSE +202 -0
  3. package/NOTICE +5 -0
  4. package/README.es.md +2021 -0
  5. package/README.md +1999 -0
  6. package/benchmarks/committee/README.md +39 -0
  7. package/benchmarks/committee/metrics.py +51 -0
  8. package/benchmarks/committee/run.py +64 -0
  9. package/benchmarks/committee/traces/01-single.json +8 -0
  10. package/benchmarks/committee/traces/02-mesh.json +16 -0
  11. package/benchmarks/committee/traces/03-chair.json +15 -0
  12. package/benchmarks/latency/README.md +35 -0
  13. package/benchmarks/latency/fake-claude-cli.mjs +119 -0
  14. package/benchmarks/latency/fake-native-server.mjs +340 -0
  15. package/benchmarks/latency/fake-tui.py +91 -0
  16. package/benchmarks/latency/live.py +380 -0
  17. package/benchmarks/stress/README.md +20 -0
  18. package/benchmarks/stress/run.py +487 -0
  19. package/bin/agents +4 -0
  20. package/bin/agents-city.js +116 -0
  21. package/bin/benchmark +17 -0
  22. package/bin/bus +6 -0
  23. package/bin/cities +3 -0
  24. package/bin/city +86 -0
  25. package/bin/committee +6 -0
  26. package/bin/demo +200 -0
  27. package/bin/exit +5 -0
  28. package/bin/hall +73 -0
  29. package/bin/hall.html +426 -0
  30. package/bin/logs +3 -0
  31. package/bin/report.py +14 -0
  32. package/bin/reset +3 -0
  33. package/bin/road +3 -0
  34. package/bin/seat +10 -0
  35. package/bin/serve.py +1428 -0
  36. package/bin/setup.py +753 -0
  37. package/bin/skills +3 -0
  38. package/bin/test +131 -0
  39. package/bin/test-adapter.py +183 -0
  40. package/bin/test-admision.py +99 -0
  41. package/bin/test-avatar.py +58 -0
  42. package/bin/test-benchmark.py +40 -0
  43. package/bin/test-broker.py +334 -0
  44. package/bin/test-cage.py +206 -0
  45. package/bin/test-card.py +402 -0
  46. package/bin/test-channel.py +379 -0
  47. package/bin/test-cities.py +453 -0
  48. package/bin/test-claude-runtime.py +252 -0
  49. package/bin/test-committee.py +340 -0
  50. package/bin/test-contracts.py +544 -0
  51. package/bin/test-crecimiento.py +164 -0
  52. package/bin/test-demo.py +308 -0
  53. package/bin/test-doctor.py +106 -0
  54. package/bin/test-domains.py +151 -0
  55. package/bin/test-evidencia.py +50 -0
  56. package/bin/test-exit.py +128 -0
  57. package/bin/test-hall-protocol.py +93 -0
  58. package/bin/test-launch.py +169 -0
  59. package/bin/test-live-feed.py +508 -0
  60. package/bin/test-pairing.py +99 -0
  61. package/bin/test-parcels.py +283 -0
  62. package/bin/test-runtime-failures.py +252 -0
  63. package/bin/test-runtime-ui.py +488 -0
  64. package/bin/test-runtime.py +268 -0
  65. package/bin/test-rutas.py +80 -0
  66. package/bin/test-seat.py +1386 -0
  67. package/bin/test-security.py +150 -0
  68. package/bin/test-serve.py +1057 -0
  69. package/bin/test-stress.py +64 -0
  70. package/bin/test-widgets.py +143 -0
  71. package/bin/test-workspace.py +188 -0
  72. package/bin/testlib.py +95 -0
  73. package/bin/tokens.py +14 -0
  74. package/bus/scripts/deploy.sh +60 -0
  75. package/bus/scripts/mint-token.sh +68 -0
  76. package/bus/scripts/setup-dev.sh +79 -0
  77. package/bus/scripts/test-channel.ts +8 -0
  78. package/bus/scripts/test-hub.ts +266 -0
  79. package/bus/scripts/test-local.sh +40 -0
  80. package/bus/scripts/test-queue.ts +132 -0
  81. package/bus/worker/package-lock.json +1971 -0
  82. package/bus/worker/package.json +17 -0
  83. package/bus/worker/src/index.ts +485 -0
  84. package/bus/worker/tsconfig.json +13 -0
  85. package/bus/worker/wrangler.toml +32 -0
  86. package/city/oven/README.md +59 -0
  87. package/city/oven/collect.py +43 -0
  88. package/city/oven/oven.html +4 -0
  89. package/city/scripts/history.py +120 -0
  90. package/city/scripts/seed.py +442 -0
  91. package/city/web/assets/modelos/License.txt +28 -0
  92. package/city/web/assets/modelos/PROCEDENCIA.txt +3 -0
  93. package/city/web/assets/modelos/building-a.glb +0 -0
  94. package/city/web/assets/modelos/building-b.glb +0 -0
  95. package/city/web/assets/modelos/building-c.glb +0 -0
  96. package/city/web/assets/modelos/building-d.glb +0 -0
  97. package/city/web/assets/modelos/building-e.glb +0 -0
  98. package/city/web/assets/modelos/building-f.glb +0 -0
  99. package/city/web/assets/modelos/building-g.glb +0 -0
  100. package/city/web/assets/modelos/building-h.glb +0 -0
  101. package/city/web/assets/sprites/building-a.png +0 -0
  102. package/city/web/assets/sprites/building-b.png +0 -0
  103. package/city/web/assets/sprites/building-c.png +0 -0
  104. package/city/web/assets/sprites/building-d.png +0 -0
  105. package/city/web/assets/sprites/building-e.png +0 -0
  106. package/city/web/assets/sprites/building-f.png +0 -0
  107. package/city/web/assets/sprites/building-g.png +0 -0
  108. package/city/web/assets/sprites/building-h.png +0 -0
  109. package/city/web/assets/sprites/building-i.png +0 -0
  110. package/city/web/assets/sprites/building-j.png +0 -0
  111. package/city/web/assets/sprites/building-k.png +0 -0
  112. package/city/web/assets/sprites/building-l.png +0 -0
  113. package/city/web/assets/sprites/building-m.png +0 -0
  114. package/city/web/assets/sprites/building-n.png +0 -0
  115. package/city/web/assets/sprites/building-skyscraper-a.png +0 -0
  116. package/city/web/assets/sprites/building-skyscraper-b.png +0 -0
  117. package/city/web/assets/sprites/building-skyscraper-c.png +0 -0
  118. package/city/web/assets/sprites/building-skyscraper-d.png +0 -0
  119. package/city/web/assets/sprites/building-skyscraper-e.png +0 -0
  120. package/city/web/assets/sprites/catalogo.json +47 -0
  121. package/city/web/assets/sprites/detail-awning-wide.png +0 -0
  122. package/city/web/assets/sprites/detail-awning.png +0 -0
  123. package/city/web/assets/sprites/detail-overhang-wide.png +0 -0
  124. package/city/web/assets/sprites/detail-overhang.png +0 -0
  125. package/city/web/assets/sprites/detail-parasol-a.png +0 -0
  126. package/city/web/assets/sprites/detail-parasol-b.png +0 -0
  127. package/city/web/assets/sprites/low-detail-building-a.png +0 -0
  128. package/city/web/assets/sprites/low-detail-building-b.png +0 -0
  129. package/city/web/assets/sprites/low-detail-building-c.png +0 -0
  130. package/city/web/assets/sprites/low-detail-building-d.png +0 -0
  131. package/city/web/assets/sprites/low-detail-building-e.png +0 -0
  132. package/city/web/assets/sprites/low-detail-building-f.png +0 -0
  133. package/city/web/assets/sprites/low-detail-building-g.png +0 -0
  134. package/city/web/assets/sprites/low-detail-building-h.png +0 -0
  135. package/city/web/assets/sprites/low-detail-building-i.png +0 -0
  136. package/city/web/assets/sprites/low-detail-building-j.png +0 -0
  137. package/city/web/assets/sprites/low-detail-building-k.png +0 -0
  138. package/city/web/assets/sprites/low-detail-building-l.png +0 -0
  139. package/city/web/assets/sprites/low-detail-building-m.png +0 -0
  140. package/city/web/assets/sprites/low-detail-building-n.png +0 -0
  141. package/city/web/assets/sprites/low-detail-building-wide-a.png +0 -0
  142. package/city/web/assets/sprites/low-detail-building-wide-b.png +0 -0
  143. package/city/web/assets/sprites/medidas.json +248 -0
  144. package/city/web/dist/city.js +939 -0
  145. package/city/web/dist/index.html +294 -0
  146. package/city/web/dist/modelos/License.txt +28 -0
  147. package/city/web/dist/modelos/PROCEDENCIA.txt +3 -0
  148. package/city/web/dist/modelos/building-a.glb +0 -0
  149. package/city/web/dist/modelos/building-b.glb +0 -0
  150. package/city/web/dist/modelos/building-c.glb +0 -0
  151. package/city/web/dist/modelos/building-d.glb +0 -0
  152. package/city/web/dist/modelos/building-e.glb +0 -0
  153. package/city/web/dist/modelos/building-f.glb +0 -0
  154. package/city/web/dist/modelos/building-g.glb +0 -0
  155. package/city/web/dist/modelos/building-h.glb +0 -0
  156. package/city/web/dist/sprites/building-a.png +0 -0
  157. package/city/web/dist/sprites/building-b.png +0 -0
  158. package/city/web/dist/sprites/building-c.png +0 -0
  159. package/city/web/dist/sprites/building-d.png +0 -0
  160. package/city/web/dist/sprites/building-e.png +0 -0
  161. package/city/web/dist/sprites/building-f.png +0 -0
  162. package/city/web/dist/sprites/building-g.png +0 -0
  163. package/city/web/dist/sprites/building-h.png +0 -0
  164. package/city/web/dist/sprites/building-i.png +0 -0
  165. package/city/web/dist/sprites/building-j.png +0 -0
  166. package/city/web/dist/sprites/building-k.png +0 -0
  167. package/city/web/dist/sprites/building-l.png +0 -0
  168. package/city/web/dist/sprites/building-m.png +0 -0
  169. package/city/web/dist/sprites/building-n.png +0 -0
  170. package/city/web/dist/sprites/building-skyscraper-a.png +0 -0
  171. package/city/web/dist/sprites/building-skyscraper-b.png +0 -0
  172. package/city/web/dist/sprites/building-skyscraper-c.png +0 -0
  173. package/city/web/dist/sprites/building-skyscraper-d.png +0 -0
  174. package/city/web/dist/sprites/building-skyscraper-e.png +0 -0
  175. package/city/web/dist/sprites/catalogo.json +47 -0
  176. package/city/web/dist/sprites/detail-awning-wide.png +0 -0
  177. package/city/web/dist/sprites/detail-awning.png +0 -0
  178. package/city/web/dist/sprites/detail-overhang-wide.png +0 -0
  179. package/city/web/dist/sprites/detail-overhang.png +0 -0
  180. package/city/web/dist/sprites/detail-parasol-a.png +0 -0
  181. package/city/web/dist/sprites/detail-parasol-b.png +0 -0
  182. package/city/web/dist/sprites/low-detail-building-a.png +0 -0
  183. package/city/web/dist/sprites/low-detail-building-b.png +0 -0
  184. package/city/web/dist/sprites/low-detail-building-c.png +0 -0
  185. package/city/web/dist/sprites/low-detail-building-d.png +0 -0
  186. package/city/web/dist/sprites/low-detail-building-e.png +0 -0
  187. package/city/web/dist/sprites/low-detail-building-f.png +0 -0
  188. package/city/web/dist/sprites/low-detail-building-g.png +0 -0
  189. package/city/web/dist/sprites/low-detail-building-h.png +0 -0
  190. package/city/web/dist/sprites/low-detail-building-i.png +0 -0
  191. package/city/web/dist/sprites/low-detail-building-j.png +0 -0
  192. package/city/web/dist/sprites/low-detail-building-k.png +0 -0
  193. package/city/web/dist/sprites/low-detail-building-l.png +0 -0
  194. package/city/web/dist/sprites/low-detail-building-m.png +0 -0
  195. package/city/web/dist/sprites/low-detail-building-n.png +0 -0
  196. package/city/web/dist/sprites/low-detail-building-wide-a.png +0 -0
  197. package/city/web/dist/sprites/low-detail-building-wide-b.png +0 -0
  198. package/city/web/dist/sprites/medidas.json +248 -0
  199. package/city/web/dist-hall/hall.js +264 -0
  200. package/city/web/index.html +294 -0
  201. package/city/web/package.json +18 -0
  202. package/city/web/sella.py +21 -0
  203. package/city/web/src/activity-actors.ts +47 -0
  204. package/city/web/src/activity.ts +172 -0
  205. package/city/web/src/ayuntamiento.ts +580 -0
  206. package/city/web/src/draw.ts +640 -0
  207. package/city/web/src/game-speech.ts +79 -0
  208. package/city/web/src/hall.ts +1867 -0
  209. package/city/web/src/main.ts +2225 -0
  210. package/city/web/src/oven.ts +124 -0
  211. package/city/web/src/people.ts +244 -0
  212. package/city/web/src/presencia.ts +193 -0
  213. package/city/web/src/puertas.ts +180 -0
  214. package/city/web/src/repo-roles.ts +59 -0
  215. package/city/worker/package.json +16 -0
  216. package/city/worker/schema.sql +117 -0
  217. package/city/worker/src/index.ts +702 -0
  218. package/city/worker/src/square.ts +218 -0
  219. package/city/worker/wrangler.toml +58 -0
  220. package/demo/ada.md +50 -0
  221. package/demo/bruno.md +62 -0
  222. package/demo/camila.md +56 -0
  223. package/demo/city/ada.md +40 -0
  224. package/demo/city/city.yml +8 -0
  225. package/demo/city/parcels.yml +15 -0
  226. package/demo/city/roads.json +4 -0
  227. package/demo/city/units.yml +10 -0
  228. package/demo/clinica/city.yml +8 -0
  229. package/demo/clinica/parcels.yml +15 -0
  230. package/demo/clinica/roads.json +4 -0
  231. package/demo/clinica/units.yml +9 -0
  232. package/demo/clinica/vera.md +46 -0
  233. package/demo/dante.md +54 -0
  234. package/demo/despacho/city.yml +8 -0
  235. package/demo/despacho/marta.md +46 -0
  236. package/demo/despacho/parcels.yml +15 -0
  237. package/demo/despacho/roads.json +4 -0
  238. package/demo/despacho/units.yml +9 -0
  239. package/demo/elsa.md +50 -0
  240. package/demo/farid.md +52 -0
  241. package/demo/greta.md +50 -0
  242. package/demo/hugo.md +49 -0
  243. package/demo/iris.md +49 -0
  244. package/demo/jonas.md +51 -0
  245. package/demo/kira.md +51 -0
  246. package/demo/luca.md +49 -0
  247. package/demo/parcels.yml +92 -0
  248. package/demo/seed.py +20 -0
  249. package/demo/show.py +161 -0
  250. package/demo/stories.py +824 -0
  251. package/demo/units.yml +33 -0
  252. package/docs/agents-first.md +99 -0
  253. package/docs/glossary.md +55 -0
  254. package/docs/map-live-layers.md +73 -0
  255. package/docs/security.md +231 -0
  256. package/docs/self-host.md +151 -0
  257. package/docs/testing.md +205 -0
  258. package/package.json +73 -0
  259. package/plugin/.claude-plugin/plugin.json +62 -0
  260. package/plugin/.mcp.json +15 -0
  261. package/plugin/channel/activity-cli.ts +16 -0
  262. package/plugin/channel/adapter-prompts.ts +113 -0
  263. package/plugin/channel/adapter.js +4292 -0
  264. package/plugin/channel/adapter.ts +133 -0
  265. package/plugin/channel/bus.js +20188 -0
  266. package/plugin/channel/bus.ts +131 -0
  267. package/plugin/channel/city-config.ts +125 -0
  268. package/plugin/channel/claude-channel.ts +58 -0
  269. package/plugin/channel/cli-args.ts +75 -0
  270. package/plugin/channel/client.js +4200 -0
  271. package/plugin/channel/client.ts +38 -0
  272. package/plugin/channel/committee/activity.ts +256 -0
  273. package/plugin/channel/committee/collection.ts +154 -0
  274. package/plugin/channel/committee/decision.ts +175 -0
  275. package/plugin/channel/committee/floor.ts +135 -0
  276. package/plugin/channel/committee/guards.ts +30 -0
  277. package/plugin/channel/committee/history.ts +38 -0
  278. package/plugin/channel/committee/render.ts +102 -0
  279. package/plugin/channel/committee/service.ts +72 -0
  280. package/plugin/channel/committee/storage.ts +92 -0
  281. package/plugin/channel/committee/types.ts +163 -0
  282. package/plugin/channel/committee/view.ts +63 -0
  283. package/plugin/channel/committee-cli.ts +109 -0
  284. package/plugin/channel/delivery-metrics.ts +61 -0
  285. package/plugin/channel/delivery-queue.ts +118 -0
  286. package/plugin/channel/hub/activity-controller.ts +72 -0
  287. package/plugin/channel/hub/activity-feed.ts +169 -0
  288. package/plugin/channel/hub/committee-controller.ts +60 -0
  289. package/plugin/channel/hub/connections.ts +48 -0
  290. package/plugin/channel/hub/diagnostics.ts +67 -0
  291. package/plugin/channel/hub/envelope-validity.ts +109 -0
  292. package/plugin/channel/hub/envelopes.ts +66 -0
  293. package/plugin/channel/hub/lifecycle.ts +91 -0
  294. package/plugin/channel/hub/local-roads.ts +89 -0
  295. package/plugin/channel/hub/remote-roads.ts +165 -0
  296. package/plugin/channel/hub/road-controller.ts +99 -0
  297. package/plugin/channel/hub-client.ts +149 -0
  298. package/plugin/channel/local-hub.js +5995 -0
  299. package/plugin/channel/local-hub.ts +349 -0
  300. package/plugin/channel/map-reporter.ts +48 -0
  301. package/plugin/channel/package-lock.json +1731 -0
  302. package/plugin/channel/package.json +19 -0
  303. package/plugin/channel/protocol.ts +98 -0
  304. package/plugin/channel/road-cli.ts +18 -0
  305. package/plugin/channel/run.sh +15 -0
  306. package/plugin/channel/runtime/claude.ts +458 -0
  307. package/plugin/channel/runtime/codex-config.ts +77 -0
  308. package/plugin/channel/runtime/codex.ts +669 -0
  309. package/plugin/channel/runtime/command.ts +62 -0
  310. package/plugin/channel/runtime/factory.ts +15 -0
  311. package/plugin/channel/runtime/json-rpc.ts +154 -0
  312. package/plugin/channel/runtime/kimi.ts +277 -0
  313. package/plugin/channel/runtime/opencode.ts +248 -0
  314. package/plugin/channel/runtime/process.ts +84 -0
  315. package/plugin/channel/runtime/types.ts +45 -0
  316. package/plugin/channel/runtime-files.ts +73 -0
  317. package/plugin/channel/runtime-gateway.js +6396 -0
  318. package/plugin/channel/runtime-gateway.ts +358 -0
  319. package/plugin/channel/runtime-metrics.ts +52 -0
  320. package/plugin/channel/runtime-subscription.ts +180 -0
  321. package/plugin/channel/terminal-delivery.ts +131 -0
  322. package/plugin/channel/untrusted.ts +60 -0
  323. package/plugin/commands/committee.md +31 -0
  324. package/plugin/commands/exit.md +32 -0
  325. package/plugin/commands/goals.md +20 -0
  326. package/plugin/commands/join.md +18 -0
  327. package/plugin/commands/notice.md +20 -0
  328. package/plugin/commands/propose.md +19 -0
  329. package/plugin/commands/round.md +17 -0
  330. package/plugin/commands/session.md +22 -0
  331. package/plugin/commands/settings.md +25 -0
  332. package/plugin/commands/setup.md +21 -0
  333. package/plugin/commands/team.md +23 -0
  334. package/plugin/domains/custom.md +27 -0
  335. package/plugin/domains/finance.md +31 -0
  336. package/plugin/domains/healthcare.md +34 -0
  337. package/plugin/domains/legal.md +31 -0
  338. package/plugin/domains/marketing.md +33 -0
  339. package/plugin/domains/operations.md +31 -0
  340. package/plugin/domains/research.md +32 -0
  341. package/plugin/domains/sales.md +30 -0
  342. package/plugin/domains/software.md +37 -0
  343. package/plugin/hooks/activity.sh +6 -0
  344. package/plugin/hooks/digging.sh +68 -0
  345. package/plugin/hooks/growth.sh +42 -0
  346. package/plugin/hooks/hooks.json +106 -0
  347. package/plugin/hooks/notice-on-pr.sh +35 -0
  348. package/plugin/hooks/notice-on-stop.sh +80 -0
  349. package/plugin/hooks/notice-pending.sh +58 -0
  350. package/plugin/hooks/solo-en-ciudad.sh +23 -0
  351. package/plugin/hooks/tokens.sh +47 -0
  352. package/plugin/roles/examples/account-executive.md +25 -0
  353. package/plugin/roles/examples/ai-manager.md +34 -0
  354. package/plugin/roles/examples/associate.md +24 -0
  355. package/plugin/roles/examples/brand-lead.md +20 -0
  356. package/plugin/roles/examples/cfo.md +20 -0
  357. package/plugin/roles/examples/city-lead.md +25 -0
  358. package/plugin/roles/examples/clinical-director.md +26 -0
  359. package/plugin/roles/examples/clinical-ops.md +25 -0
  360. package/plugin/roles/examples/clinician.md +25 -0
  361. package/plugin/roles/examples/compliance.md +27 -0
  362. package/plugin/roles/examples/content.md +24 -0
  363. package/plugin/roles/examples/controller.md +27 -0
  364. package/plugin/roles/examples/cpto.md +41 -0
  365. package/plugin/roles/examples/customer-success.md +25 -0
  366. package/plugin/roles/examples/data-engineer.md +37 -0
  367. package/plugin/roles/examples/data.md +60 -0
  368. package/plugin/roles/examples/dev.md +37 -0
  369. package/plugin/roles/examples/devops.md +39 -0
  370. package/plugin/roles/examples/enablement.md +24 -0
  371. package/plugin/roles/examples/ethics.md +24 -0
  372. package/plugin/roles/examples/fin-analytics.md +27 -0
  373. package/plugin/roles/examples/health-compliance.md +25 -0
  374. package/plugin/roles/examples/health-data.md +26 -0
  375. package/plugin/roles/examples/knowledge.md +25 -0
  376. package/plugin/roles/examples/lifecycle.md +26 -0
  377. package/plugin/roles/examples/llm-engineer.md +34 -0
  378. package/plugin/roles/examples/managing-partner.md +20 -0
  379. package/plugin/roles/examples/methods.md +23 -0
  380. package/plugin/roles/examples/operations-lead.md +23 -0
  381. package/plugin/roles/examples/ops.md +24 -0
  382. package/plugin/roles/examples/patient-safety.md +26 -0
  383. package/plugin/roles/examples/performance.md +27 -0
  384. package/plugin/roles/examples/po.md +36 -0
  385. package/plugin/roles/examples/process-owner.md +23 -0
  386. package/plugin/roles/examples/product-design.md +39 -0
  387. package/plugin/roles/examples/program-manager.md +24 -0
  388. package/plugin/roles/examples/quality.md +25 -0
  389. package/plugin/roles/examples/research-director.md +24 -0
  390. package/plugin/roles/examples/research-ops.md +25 -0
  391. package/plugin/roles/examples/researcher.md +25 -0
  392. package/plugin/roles/examples/revenue-lead.md +25 -0
  393. package/plugin/roles/examples/revops.md +26 -0
  394. package/plugin/roles/examples/seo.md +27 -0
  395. package/plugin/roles/examples/specialist.md +24 -0
  396. package/plugin/scripts/admision.py +165 -0
  397. package/plugin/scripts/apaga.py +232 -0
  398. package/plugin/scripts/avatar.py +211 -0
  399. package/plugin/scripts/broker.py +531 -0
  400. package/plugin/scripts/cage.py +252 -0
  401. package/plugin/scripts/capabilities.py +197 -0
  402. package/plugin/scripts/card.py +312 -0
  403. package/plugin/scripts/cities.py +520 -0
  404. package/plugin/scripts/city-env.sh +90 -0
  405. package/plugin/scripts/city-runtime.sh +87 -0
  406. package/plugin/scripts/city-session.sh +526 -0
  407. package/plugin/scripts/city_env.py +67 -0
  408. package/plugin/scripts/crecimiento.py +140 -0
  409. package/plugin/scripts/deliberations.py +48 -0
  410. package/plugin/scripts/doctor.py +172 -0
  411. package/plugin/scripts/domains.py +201 -0
  412. package/plugin/scripts/evidencia.py +64 -0
  413. package/plugin/scripts/find-repos.sh +111 -0
  414. package/plugin/scripts/gh.py +159 -0
  415. package/plugin/scripts/hall_protocol.py +147 -0
  416. package/plugin/scripts/hook_activity.py +139 -0
  417. package/plugin/scripts/launch.py +94 -0
  418. package/plugin/scripts/logs.py +98 -0
  419. package/plugin/scripts/pairing.py +185 -0
  420. package/plugin/scripts/parcels.py +132 -0
  421. package/plugin/scripts/read-card.py +51 -0
  422. package/plugin/scripts/report.py +201 -0
  423. package/plugin/scripts/reset.py +180 -0
  424. package/plugin/scripts/roads.py +230 -0
  425. package/plugin/scripts/roles.py +274 -0
  426. package/plugin/scripts/runtime_log.py +69 -0
  427. package/plugin/scripts/runtime_processes.py +132 -0
  428. package/plugin/scripts/rutas.py +83 -0
  429. package/plugin/scripts/seat.py +1349 -0
  430. package/plugin/scripts/tokens.py +194 -0
  431. package/plugin/scripts/trust-repos.py +59 -0
  432. package/plugin/scripts/ui.py +280 -0
  433. package/plugin/scripts/units.py +80 -0
  434. package/plugin/scripts/workspace.py +364 -0
  435. package/plugin/skills/city/SKILL.md +191 -0
  436. package/templates/blank.md +39 -0
  437. package/templates/finance.md +44 -0
  438. package/templates/legal.md +45 -0
  439. package/templates/marketing.md +48 -0
  440. package/templates/product.md +45 -0
@@ -0,0 +1,180 @@
1
+ /**
2
+ * The city gates: one per road, at the entrance, past the square.
3
+ *
4
+ * A road is an allowlist entry — reachability, not a channel — and this is its
5
+ * honest drawing: not a highway to somewhere, but a gate with a name over it.
6
+ * Everything beyond the gate is another city this map will never draw; the
7
+ * other cities exist here exactly as much as they exist to the seat, as an
8
+ * address you may send to. A letter for one of them flies out through its gate
9
+ * and fades at the edge, because that is all this city ever sees of it.
10
+ *
11
+ * The gates come from the Hall's config message. The standalone team map never
12
+ * receives one and draws no gates: a map must not invent connections.
13
+ */
14
+ import { Container, Graphics, Text, TextStyle } from 'pixi.js';
15
+ import { TH, tono } from './draw';
16
+ import type { RoadInfo } from './activity';
17
+
18
+ const PIEDRA = 0xb9a67c;
19
+
20
+ export interface Ancla {
21
+ x: number;
22
+ y: number;
23
+ }
24
+
25
+ export class Puertas {
26
+ /** The arches, in world coordinates, under the people layer. */
27
+ readonly capa = new Container();
28
+ /** The name plates, in the banner layer, zoom-stable like every label. */
29
+ readonly carteles = new Container();
30
+
31
+ private readonly sitios = new Map<string, Ancla>();
32
+
33
+ constructor(
34
+ private readonly origen: Ancla,
35
+ private readonly anima: (f: (dt: number) => boolean) => void,
36
+ private readonly alTocar?: (road: RoadInfo) => void,
37
+ ) {}
38
+
39
+ /** Draw the gates the Hall says exist. Called again when the roads change:
40
+ * it redraws from scratch — there are never more than a handful. */
41
+ configura(roads: RoadInfo[]): void {
42
+ this.capa.removeChildren().forEach((child) => child.destroy({ children: true }));
43
+ this.carteles.removeChildren().forEach((child) => child.destroy({ children: true }));
44
+ this.sitios.clear();
45
+
46
+ roads.forEach((road, i) => {
47
+ // Gates line up along the near edge, to the right of the square, each a
48
+ // step further out: the first road is the nearest gate.
49
+ const pos = { x: this.origen.x + 340 + i * 150, y: this.origen.y - 40 - i * 26 };
50
+ this.sitios.set(this.clave(road.address), pos);
51
+ this.sitios.set(this.clave(road.name), pos);
52
+
53
+ const g = new Container();
54
+ g.position.set(pos.x, pos.y);
55
+ // A gate is a question waiting to be clicked: where does this one go?
56
+ g.eventMode = 'static';
57
+ g.cursor = 'pointer';
58
+ g.on('pointertap', () => this.alTocar?.(road));
59
+
60
+ // The stub of road the gate stands on: it starts here and leaves the map.
61
+ const camino = new Graphics()
62
+ .poly([-46, 16, 96, -14, 96, 2, -46, 32])
63
+ .fill({ color: 0x1b2532, alpha: 0.9 });
64
+ camino.moveTo(-38, 22).lineTo(88, -4).stroke({ color: 0xc8b48a, width: 0.9, alpha: 0.3 });
65
+ g.addChild(camino);
66
+
67
+ // Two pillars flanking the road, a lintel across: the arch of the mock-up.
68
+ for (const [px, py] of [
69
+ [-12, 6],
70
+ [16, 22],
71
+ ] as const) {
72
+ g.addChild(
73
+ new Graphics()
74
+ .ellipse(px, py + 3, 6, 2.6)
75
+ .fill({ color: 0x000000, alpha: 0.3 })
76
+ .poly([px, py, px - 5, py - 2.5, px - 5, py - 34, px, py - 31.5])
77
+ .fill({ color: tono(PIEDRA, -0.28) })
78
+ .poly([px, py, px + 5, py - 2.5, px + 5, py - 34, px, py - 31.5])
79
+ .fill({ color: tono(PIEDRA, -0.5) })
80
+ .poly([px, py - 36.5, px + 5, py - 34, px, py - 31.5, px - 5, py - 34])
81
+ .fill({ color: tono(PIEDRA, 0.24) }),
82
+ );
83
+ }
84
+ g.addChild(
85
+ new Graphics()
86
+ .moveTo(-12, -30)
87
+ .lineTo(16, -14)
88
+ .stroke({ color: tono(PIEDRA, 0.25), width: 3.5, alpha: 0.95 }),
89
+ );
90
+ this.capa.addChild(g);
91
+
92
+ // The plate: the address is the point of the gate. `owner/city` is how the
93
+ // roads file names the far end, and how the seat addresses it.
94
+ const cartel = new Container();
95
+ const nombre = new Text({
96
+ text: road.name,
97
+ style: new TextStyle({
98
+ fontFamily: 'Chakra Petch, sans-serif',
99
+ fontSize: 10,
100
+ fontWeight: '700',
101
+ letterSpacing: 0.8,
102
+ fill: 0x131a24,
103
+ }),
104
+ });
105
+ const dir = new Text({
106
+ text: road.address,
107
+ style: new TextStyle({
108
+ fontFamily: 'IBM Plex Mono, monospace',
109
+ fontSize: 8.5,
110
+ fill: 0x8d99a8,
111
+ }),
112
+ });
113
+ const ancho = Math.max(nombre.width, dir.width) + 14;
114
+ cartel.addChild(
115
+ new Graphics()
116
+ .roundRect(-ancho / 2, -12, ancho, 18, 3)
117
+ .fill({ color: PIEDRA, alpha: 0.94 }),
118
+ );
119
+ nombre.position.set(-nombre.width / 2, -10);
120
+ dir.position.set(-dir.width / 2, 8);
121
+ cartel.addChild(nombre, dir);
122
+ cartel.position.set(pos.x + 2, pos.y - 52);
123
+ this.carteles.addChild(cartel);
124
+ });
125
+ }
126
+
127
+ hay(): boolean {
128
+ return this.sitios.size > 0;
129
+ }
130
+
131
+ /** The gate a recipient leaves through — matched by address or name, and the
132
+ * first gate when the address is external but unknown: a letter that must
133
+ * leave the city leaves by A gate, not by teleport. */
134
+ puerta(destino: string): Ancla | null {
135
+ if (!this.sitios.size) return null;
136
+ const clave = this.clave(destino);
137
+ const exacta = this.sitios.get(clave);
138
+ if (exacta) return exacta;
139
+ for (const [k, v] of this.sitios) {
140
+ if (clave.includes(k) || k.includes(clave)) return v;
141
+ }
142
+ return this.sitios.values().next().value ?? null;
143
+ }
144
+
145
+ /** A letter crossing the arch, outward or inward, fading at the map's edge. */
146
+ vuela(puerta: Ancla, color: number, sale: boolean): void {
147
+ const carta = new Graphics()
148
+ .rect(-4, -3, 8, 6)
149
+ .fill({ color: 0xf2ecdd })
150
+ .rect(-4, -3, 8, 2)
151
+ .fill({ color });
152
+ const g = new Container();
153
+ g.addChild(new Graphics().circle(0, 0, 5).fill({ color, alpha: 0.16 }), carta);
154
+ this.capa.parent?.addChild(g);
155
+ const dentro = { x: puerta.x - 4, y: puerta.y - 18 };
156
+ const fuera = { x: puerta.x + 120, y: puerta.y - 44 };
157
+ const p0 = sale ? dentro : fuera;
158
+ const p1 = sale ? fuera : dentro;
159
+ let t = 0;
160
+ this.anima((dt) => {
161
+ t += 0.03 * dt;
162
+ const s = Math.min(1, t);
163
+ g.x = p0.x + (p1.x - p0.x) * s;
164
+ g.y = p0.y + (p1.y - p0.y) * s - Math.sin(s * Math.PI) * 10;
165
+ // Outward it fades leaving; inward it arrives already faint and firms up.
166
+ g.alpha = sale ? (s > 0.6 ? (1 - s) / 0.4 : 1) : s < 0.4 ? s / 0.4 : 1;
167
+ carta.rotation = Math.sin(t * 6) * 0.25;
168
+ if (t >= 1) {
169
+ g.parent?.removeChild(g);
170
+ g.destroy({ children: true });
171
+ return false;
172
+ }
173
+ return true;
174
+ });
175
+ }
176
+
177
+ private clave(valor: string): string {
178
+ return valor.trim().toLowerCase();
179
+ }
180
+ }
@@ -0,0 +1,59 @@
1
+ /** Pure rendering/data helpers for one operating role per repo support agent. */
2
+ export interface RepoRoleOption {
3
+ id: string;
4
+ name: string;
5
+ summary: string;
6
+ trade: string;
7
+ domains: string[];
8
+ }
9
+
10
+ export type RepoRoleAssignments = Record<string, string>;
11
+
12
+ export function selectedRepoRoles(
13
+ repos: Iterable<string>,
14
+ assignments: RepoRoleAssignments,
15
+ ): RepoRoleAssignments {
16
+ return Object.fromEntries([...repos].sort().map((repo) => [repo, assignments[repo] || 'blank']));
17
+ }
18
+
19
+ export function renderRepoRoleEditor(
20
+ repos: Iterable<string>,
21
+ assignments: RepoRoleAssignments,
22
+ roles: RepoRoleOption[],
23
+ escape: (value: unknown) => string,
24
+ ): string {
25
+ const selected = [...repos].sort();
26
+ if (!selected.length) {
27
+ return '<p class="prosa">No repo agents in this city.</p>';
28
+ }
29
+ return `<div class="agenteRoles">${selected
30
+ .map((repo) => {
31
+ const current = assignments[repo] || 'blank';
32
+ const choices = roles.some((role) => role.id === current)
33
+ ? roles
34
+ : [
35
+ {
36
+ id: current,
37
+ name: `${current} (city-defined)`,
38
+ summary: 'Role defined in this city rather than the built-in catalogue.',
39
+ trade: current,
40
+ domains: [],
41
+ },
42
+ ...roles,
43
+ ];
44
+ return `<div class="agenteRol">
45
+ <div><code>${escape(repo)}</code><span>support agent · member</span></div>
46
+ <select data-repo-role="${escape(repo)}" aria-label="Operating role for ${escape(repo)}">
47
+ ${choices
48
+ .map((role) => {
49
+ const family = role.domains.filter((domain) => domain !== 'custom').join(', ');
50
+ const suffix = family ? ` · ${family}` : '';
51
+ return `<option value="${escape(role.id)}"${role.id === current ? ' selected' : ''}
52
+ title="${escape(role.summary)}">${escape(role.name)}${escape(suffix)}</option>`;
53
+ })
54
+ .join('')}
55
+ </select>
56
+ </div>`;
57
+ })
58
+ .join('')}</div>`;
59
+ }
@@ -0,0 +1,16 @@
1
+ {
2
+ "name": "city-worker",
3
+ "private": true,
4
+ "scripts": {
5
+ "dev": "bun x wrangler@4 dev --local",
6
+ "deploy": "bun x wrangler@4 deploy",
7
+ "d1:crear": "bun x wrangler@4 d1 create city",
8
+ "d1:schema": "bun x wrangler@4 d1 execute city --remote --file schema.sql",
9
+ "d1:schema:local": "bun x wrangler@4 d1 execute city --local --file schema.sql",
10
+ "typecheck": "tsc"
11
+ },
12
+ "devDependencies": {
13
+ "@cloudflare/workers-types": "^5.20260826.1",
14
+ "typescript": "^7.0.2"
15
+ }
16
+ }
@@ -0,0 +1,117 @@
1
+ -- Agents City — the record of what has been built.
2
+ -- The Durable Object holds the now; this holds the before.
3
+
4
+ -- A parcel is one business unit inside one repo: a repo can hold several, and
5
+ -- that is what the whole model is about. Seeded from your data repo's parcels.yml.
6
+ CREATE TABLE IF NOT EXISTS parcela (
7
+ id TEXT PRIMARY KEY, -- "org/repo:apps/checkout"
8
+ repo TEXT NOT NULL,
9
+ ruta TEXT NOT NULL, -- glob relative to the repo, "" = the whole repo
10
+ unidad TEXT NOT NULL, -- one of your units, or "none"
11
+ nombre TEXT NOT NULL, -- what the house is called on the map
12
+ dueno TEXT, -- the bus user who answers for it
13
+ UNIQUE(repo, ruta)
14
+ );
15
+ CREATE INDEX IF NOT EXISTS ix_parcela_unidad ON parcela(unidad);
16
+
17
+ -- What has been built: one row per parcel, recomputed by the cron.
18
+ CREATE TABLE IF NOT EXISTS casa (
19
+ parcela_id TEXT PRIMARY KEY REFERENCES parcela(id),
20
+ pisos INTEGER NOT NULL DEFAULT 0, -- merged PRs (a floor per landing)
21
+ ladrillos INTEGER NOT NULL DEFAULT 0, -- commits with no PR
22
+ andamios INTEGER NOT NULL DEFAULT 0, -- open PRs
23
+ andamio_viejo INTEGER NOT NULL DEFAULT 0, -- open PRs older than 14 days
24
+ grieta INTEGER NOT NULL DEFAULT 0, -- 1 = CI is red
25
+ actividad30 INTEGER NOT NULL DEFAULT 0, -- commits in the last 30 days
26
+ actualizado TEXT NOT NULL
27
+ );
28
+
29
+ -- Everything that happens, so the map can be rewound and the ticker has a feed.
30
+ CREATE TABLE IF NOT EXISTS evento (
31
+ id INTEGER PRIMARY KEY AUTOINCREMENT,
32
+ ts TEXT NOT NULL,
33
+ tipo TEXT NOT NULL, -- notice | floor | scaffold | crack | light
34
+ origen TEXT, -- a bus agent, or a parcel
35
+ destino TEXT,
36
+ etiqueta TEXT, -- data | ux | security | cost | product | llm
37
+ texto TEXT,
38
+ leido INTEGER NOT NULL DEFAULT 0 -- an unopened notice is the one thing worth measuring
39
+ );
40
+ CREATE INDEX IF NOT EXISTS ix_evento_ts ON evento(ts DESC);
41
+ CREATE INDEX IF NOT EXISTS ix_evento_sin_leer ON evento(leido, ts DESC);
42
+
43
+ -- The syncer's own state: how far the last pass got.
44
+ CREATE TABLE IF NOT EXISTS meta (
45
+ clave TEXT PRIMARY KEY,
46
+ valor TEXT NOT NULL
47
+ );
48
+
49
+ -- Who is who on the site: the architect, the specialists, and their trade.
50
+ CREATE TABLE IF NOT EXISTS persona (
51
+ usuario TEXT PRIMARY KEY,
52
+ nombre TEXT NOT NULL,
53
+ rol TEXT NOT NULL,
54
+ oficio TEXT NOT NULL,
55
+ agente TEXT
56
+ );
57
+
58
+ -- The history of what was built, day by day: this is what the replay plays.
59
+ -- Rebuilt backwards from each PR's merge date, so you do not have to wait for
60
+ -- time to pass before you have a past.
61
+ CREATE TABLE IF NOT EXISTS hito (
62
+ parcela_id TEXT NOT NULL,
63
+ dia TEXT NOT NULL, -- "2026-08-25"
64
+ n INTEGER NOT NULL, -- PRs landed THAT day
65
+ PRIMARY KEY (parcela_id, dia)
66
+ );
67
+ -- Per day, not per month: a month is too coarse to watch anything grow.
68
+ CREATE INDEX IF NOT EXISTS ix_hito_dia ON hito(dia);
69
+
70
+ -- The districts of the city: your business units. Data, not code — so the map
71
+ -- redraws itself when the org changes shape, without a deploy.
72
+ CREATE TABLE IF NOT EXISTS unidad (
73
+ id TEXT PRIMARY KEY,
74
+ nombre TEXT NOT NULL,
75
+ color TEXT NOT NULL, -- hex, no #
76
+ orden INTEGER NOT NULL DEFAULT 50,
77
+ nota TEXT,
78
+ cols INTEGER NOT NULL DEFAULT 3 -- how wide its grid is on the map
79
+ );
80
+
81
+ -- Token spend, aggregated by day and person. Counts only: never content, never
82
+ -- prompts.
83
+ --
84
+ -- Stored per person because that is the only way to deduplicate reports and to
85
+ -- attribute spend to a unit. Shown as a GLOBAL total, and never as a ranking —
86
+ -- the moment there is a leaderboard, people optimise for the leaderboard. Same
87
+ -- rule as everywhere else in this map.
88
+ CREATE TABLE IF NOT EXISTS gasto (
89
+ dia TEXT NOT NULL,
90
+ usuario TEXT NOT NULL,
91
+ modelo TEXT NOT NULL DEFAULT '',
92
+ entrada INTEGER NOT NULL DEFAULT 0,
93
+ salida INTEGER NOT NULL DEFAULT 0,
94
+ cache_r INTEGER NOT NULL DEFAULT 0,
95
+ cache_w INTEGER NOT NULL DEFAULT 0,
96
+ PRIMARY KEY (dia, usuario, modelo)
97
+ );
98
+ CREATE INDEX IF NOT EXISTS ix_gasto_dia ON gasto(dia DESC);
99
+
100
+ -- Goals: one per person, with the command that measures them.
101
+ --
102
+ -- The one thing that does not change whatever kind of city this is, so it lives
103
+ -- in the database and not only in a card nobody opens. Seeded from the cards,
104
+ -- which stay the place they are written and reviewed — this is a copy for the
105
+ -- map, never the source.
106
+ CREATE TABLE IF NOT EXISTS objetivo (
107
+ usuario TEXT NOT NULL,
108
+ n INTEGER NOT NULL, -- O1, O2…
109
+ titulo TEXT NOT NULL,
110
+ como TEXT, -- what signal says it is going well
111
+ medida TEXT, -- the command or query, runnable as written
112
+ partida TEXT, -- what it returned the day it was agreed
113
+ meta TEXT, -- the value to reach
114
+ cuando TEXT, -- a date or a quarter
115
+ estado TEXT, -- not started | in progress | at risk | done
116
+ PRIMARY KEY (usuario, n)
117
+ );