@mmerterden/multi-agent-pipeline 20.29.0 → 20.33.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 (227) hide show
  1. package/CHANGELOG.md +86 -0
  2. package/README.md +50 -5
  3. package/README.tr.md +64 -5
  4. package/docs/architecture.md +3 -3
  5. package/docs/ecosystem.md +5 -5
  6. package/docs/facts.json +9 -9
  7. package/install/_unattended-profile.mjs +61 -0
  8. package/install/catalog-history.json +1 -1
  9. package/install/claude.mjs +19 -3
  10. package/install/codex.mjs +2 -0
  11. package/install/copilot.mjs +13 -0
  12. package/install/index.mjs +10 -1
  13. package/install/templates/claude-hooks.json +12 -1
  14. package/manifest.json +230 -88
  15. package/package.json +3 -1
  16. package/pipeline/commands/multi-agent/analysis/SKILL.md +4 -4
  17. package/pipeline/commands/multi-agent/autopilot-on/SKILL.md +13 -15
  18. package/pipeline/commands/multi-agent/office-off/SKILL.md +27 -0
  19. package/pipeline/commands/multi-agent/office-on/SKILL.md +51 -0
  20. package/pipeline/commands/multi-agent/office-status/SKILL.md +29 -0
  21. package/pipeline/commands/multi-agent/prune-logs/SKILL.md +4 -1
  22. package/pipeline/commands/multi-agent/review/SKILL.md +4 -3
  23. package/pipeline/commands/multi-agent/scenario-audit/SKILL.md +4 -2
  24. package/pipeline/commands/multi-agent/serve/SKILL.md +4 -2
  25. package/pipeline/commands/multi-agent/stack/SKILL.md +15 -8
  26. package/pipeline/commands/multi-agent/steer/SKILL.md +10 -9
  27. package/pipeline/commands/multi-agent/sync/SKILL.md +15 -3
  28. package/pipeline/commands/multi-agent/test-gen/SKILL.md +29 -3
  29. package/pipeline/contract/CHANGELOG.md +108 -0
  30. package/pipeline/contract/README.md +72 -12
  31. package/pipeline/contract/fixtures/error-invalid-request.json +1 -1
  32. package/pipeline/contract/fixtures/error-unauthorized.json +1 -1
  33. package/pipeline/contract/fixtures/error-unsigned.json +1 -1
  34. package/pipeline/contract/fixtures/launch-plan.json +1 -1
  35. package/pipeline/contract/fixtures/runs-awaiting-question.json +6 -1
  36. package/pipeline/contract/fixtures/runs-empty.json +1 -1
  37. package/pipeline/contract/fixtures/runs-failed.json +6 -1
  38. package/pipeline/contract/fixtures/runs-old-schema.json +6 -1
  39. package/pipeline/contract/fixtures/runs-pr-opened-redacted.json +5 -1
  40. package/pipeline/contract/fixtures/runs-pr-opened.json +6 -1
  41. package/pipeline/contract/fixtures/runs-running.json +6 -1
  42. package/pipeline/contract/manifest.json +506 -27
  43. package/pipeline/contract/types/index.d.ts +829 -4
  44. package/pipeline/lib/bg-launch.mjs +106 -0
  45. package/pipeline/lib/code-digest.mjs +49 -0
  46. package/pipeline/lib/credential-resolve.mjs +42 -2
  47. package/pipeline/multi-agent-refs/cross-cli-contract.md +5 -4
  48. package/pipeline/multi-agent-refs/features/office-threat-model.md +109 -0
  49. package/pipeline/multi-agent-refs/features/unattended-security.md +1 -1
  50. package/pipeline/multi-agent-refs/help/en.md +3 -0
  51. package/pipeline/multi-agent-refs/help/tr.md +3 -0
  52. package/pipeline/multi-agent-refs/phases/modes.md +7 -7
  53. package/pipeline/multi-agent-refs/phases/phase-5-report.md +16 -10
  54. package/pipeline/multi-agent-refs/review-standalone-tracker.md +37 -0
  55. package/pipeline/multi-agent-refs/tracker-contract.md +8 -3
  56. package/pipeline/office/NOTICE.md +45 -0
  57. package/pipeline/office/assets/ARCHIVE_BOXES.png +0 -0
  58. package/pipeline/office/assets/BIN.png +0 -0
  59. package/pipeline/office/assets/BOOKSHELF.png +0 -0
  60. package/pipeline/office/assets/CACTUS.png +0 -0
  61. package/pipeline/office/assets/CLOCK.png +0 -0
  62. package/pipeline/office/assets/COFFEE.png +0 -0
  63. package/pipeline/office/assets/COFFEE_MACHINE.png +0 -0
  64. package/pipeline/office/assets/COFFEE_TABLE.png +0 -0
  65. package/pipeline/office/assets/COUNTER_SINK.png +0 -0
  66. package/pipeline/office/assets/CUSHIONED_BENCH.png +0 -0
  67. package/pipeline/office/assets/CUSHIONED_CHAIR_BACK.png +0 -0
  68. package/pipeline/office/assets/CUSHIONED_CHAIR_FRONT.png +0 -0
  69. package/pipeline/office/assets/CUSHIONED_CHAIR_SIDE.png +0 -0
  70. package/pipeline/office/assets/DESK_FRONT.png +0 -0
  71. package/pipeline/office/assets/DESK_SIDE.png +0 -0
  72. package/pipeline/office/assets/DEVICE_STAND.png +0 -0
  73. package/pipeline/office/assets/DOUBLE_BOOKSHELF.png +0 -0
  74. package/pipeline/office/assets/FILING_CABINET.png +0 -0
  75. package/pipeline/office/assets/FRIDGE.png +0 -0
  76. package/pipeline/office/assets/HANGING_PLANT.png +0 -0
  77. package/pipeline/office/assets/LARGE_PAINTING.png +0 -0
  78. package/pipeline/office/assets/LARGE_PLANT.png +0 -0
  79. package/pipeline/office/assets/MAILBOX.png +0 -0
  80. package/pipeline/office/assets/MOP_BUCKET.png +0 -0
  81. package/pipeline/office/assets/PC_BACK.png +0 -0
  82. package/pipeline/office/assets/PC_FRONT_OFF.png +0 -0
  83. package/pipeline/office/assets/PC_FRONT_ON_1.png +0 -0
  84. package/pipeline/office/assets/PC_FRONT_ON_2.png +0 -0
  85. package/pipeline/office/assets/PC_FRONT_ON_3.png +0 -0
  86. package/pipeline/office/assets/PC_SIDE.png +0 -0
  87. package/pipeline/office/assets/PLANT.png +0 -0
  88. package/pipeline/office/assets/PLANT_2.png +0 -0
  89. package/pipeline/office/assets/POT.png +0 -0
  90. package/pipeline/office/assets/PRINTER.png +0 -0
  91. package/pipeline/office/assets/RECEPTION_DESK.png +0 -0
  92. package/pipeline/office/assets/SERVER_RACK.png +0 -0
  93. package/pipeline/office/assets/SERVER_RACK_2.png +0 -0
  94. package/pipeline/office/assets/SMALL_PAINTING.png +0 -0
  95. package/pipeline/office/assets/SMALL_PAINTING_2.png +0 -0
  96. package/pipeline/office/assets/SMALL_TABLE_FRONT.png +0 -0
  97. package/pipeline/office/assets/SMALL_TABLE_SIDE.png +0 -0
  98. package/pipeline/office/assets/SOFA_BACK.png +0 -0
  99. package/pipeline/office/assets/SOFA_FRONT.png +0 -0
  100. package/pipeline/office/assets/SOFA_SIDE.png +0 -0
  101. package/pipeline/office/assets/TABLE_FRONT.png +0 -0
  102. package/pipeline/office/assets/TOILET_STALL.png +0 -0
  103. package/pipeline/office/assets/VENDING.png +0 -0
  104. package/pipeline/office/assets/WASHBASIN.png +0 -0
  105. package/pipeline/office/assets/WATER_COOLER.png +0 -0
  106. package/pipeline/office/assets/WHITEBOARD.png +0 -0
  107. package/pipeline/office/assets/WOODEN_BENCH.png +0 -0
  108. package/pipeline/office/assets/WOODEN_CHAIR_BACK.png +0 -0
  109. package/pipeline/office/assets/WOODEN_CHAIR_FRONT.png +0 -0
  110. package/pipeline/office/assets/WOODEN_CHAIR_SIDE.png +0 -0
  111. package/pipeline/office/assets/char_0.png +0 -0
  112. package/pipeline/office/assets/char_1.png +0 -0
  113. package/pipeline/office/assets/char_2.png +0 -0
  114. package/pipeline/office/assets/char_3.png +0 -0
  115. package/pipeline/office/assets/char_4.png +0 -0
  116. package/pipeline/office/assets/char_5.png +0 -0
  117. package/pipeline/office/assets/floor_0.png +0 -0
  118. package/pipeline/office/assets/floor_1.png +0 -0
  119. package/pipeline/office/assets/floor_2.png +0 -0
  120. package/pipeline/office/assets/floor_3.png +0 -0
  121. package/pipeline/office/assets/floor_4.png +0 -0
  122. package/pipeline/office/assets/floor_5.png +0 -0
  123. package/pipeline/office/assets/floor_6.png +0 -0
  124. package/pipeline/office/assets/floor_7.png +0 -0
  125. package/pipeline/office/assets/floor_8.png +0 -0
  126. package/pipeline/office/assets/wall_0.png +0 -0
  127. package/pipeline/office/index.html +8431 -0
  128. package/pipeline/office/toolkit.json +3 -0
  129. package/pipeline/schemas/activity-chat.schema.json +78 -0
  130. package/pipeline/schemas/activity-roles.json +48 -0
  131. package/pipeline/schemas/activity-roles.schema.json +49 -0
  132. package/pipeline/schemas/activity.schema.json +613 -0
  133. package/pipeline/schemas/agent-state.schema.json +493 -115
  134. package/pipeline/schemas/autopilot-on-request.schema.json +33 -0
  135. package/pipeline/schemas/autopilot-on.schema.json +111 -0
  136. package/pipeline/schemas/contract-error.schema.json +45 -4
  137. package/pipeline/schemas/issue-maturity.schema.json +68 -0
  138. package/pipeline/schemas/job-change.schema.json +72 -0
  139. package/pipeline/schemas/job-request.schema.json +38 -0
  140. package/pipeline/schemas/launch.json +4 -4
  141. package/pipeline/schemas/ledger.schema.json +202 -0
  142. package/pipeline/schemas/office-credentials.schema.json +71 -0
  143. package/pipeline/schemas/office-jobs.json +253 -0
  144. package/pipeline/schemas/office-jobs.schema.json +62 -0
  145. package/pipeline/schemas/office-memory.schema.json +105 -0
  146. package/pipeline/schemas/office-settings-request.schema.json +30 -0
  147. package/pipeline/schemas/office-settings.schema.json +67 -0
  148. package/pipeline/schemas/permissions.schema.json +47 -0
  149. package/pipeline/schemas/phases.json +10 -2
  150. package/pipeline/schemas/phases.schema.json +86 -19
  151. package/pipeline/schemas/prefs.schema.json +19 -0
  152. package/pipeline/schemas/prs.schema.json +78 -0
  153. package/pipeline/schemas/prune-logs-request.schema.json +26 -0
  154. package/pipeline/schemas/prune-logs.schema.json +52 -0
  155. package/pipeline/schemas/repo-change.schema.json +54 -0
  156. package/pipeline/schemas/repo-request.schema.json +29 -0
  157. package/pipeline/schemas/repos.schema.json +49 -1
  158. package/pipeline/schemas/review-verdict-request.schema.json +20 -0
  159. package/pipeline/schemas/review-verdict.schema.json +62 -0
  160. package/pipeline/schemas/routine-delete.schema.json +59 -0
  161. package/pipeline/schemas/routines.schema.json +38 -0
  162. package/pipeline/schemas/run-evidence.schema.json +29 -0
  163. package/pipeline/schemas/run-results.schema.json +218 -0
  164. package/pipeline/schemas/runs-index.schema.json +257 -46
  165. package/pipeline/schemas/service-read.schema.json +58 -0
  166. package/pipeline/schemas/stack-change.schema.json +82 -0
  167. package/pipeline/schemas/stack-request.schema.json +33 -0
  168. package/pipeline/schemas/stack.schema.json +59 -0
  169. package/pipeline/schemas/steer-request.schema.json +25 -0
  170. package/pipeline/schemas/steer.schema.json +59 -0
  171. package/pipeline/schemas/system-status.schema.json +111 -0
  172. package/pipeline/schemas/tool-call-request.schema.json +19 -0
  173. package/pipeline/schemas/tool-call.schema.json +47 -0
  174. package/pipeline/schemas/tools.schema.json +65 -0
  175. package/pipeline/schemas/unattended-profile.json +7 -2
  176. package/pipeline/scripts/_active-run.mjs +2 -1
  177. package/pipeline/scripts/_cost.mjs +66 -1
  178. package/pipeline/scripts/_office-smoke-lib.sh +115 -0
  179. package/pipeline/scripts/_spawn-async.mjs +77 -0
  180. package/pipeline/scripts/_transcript-tail.mjs +274 -0
  181. package/pipeline/scripts/activity-snapshot.mjs +1223 -0
  182. package/pipeline/scripts/autopilot-control.mjs +214 -9
  183. package/pipeline/scripts/autopilot-runner.mjs +7 -5
  184. package/pipeline/scripts/contract-server.mjs +1853 -197
  185. package/pipeline/scripts/cost-analyze.mjs +2 -53
  186. package/pipeline/scripts/cost-table.json +1 -0
  187. package/pipeline/scripts/gen-mode-dispatch.mjs +3 -1
  188. package/pipeline/scripts/job-launch.mjs +477 -0
  189. package/pipeline/scripts/launch-request.mjs +94 -9
  190. package/pipeline/scripts/office-build.mjs +226 -0
  191. package/pipeline/scripts/office-control.mjs +410 -0
  192. package/pipeline/scripts/office-credentials.mjs +106 -0
  193. package/pipeline/scripts/office-ledger.mjs +409 -0
  194. package/pipeline/scripts/office-memory.mjs +200 -0
  195. package/pipeline/scripts/office-prune.mjs +125 -0
  196. package/pipeline/scripts/office-settings.mjs +145 -0
  197. package/pipeline/scripts/phase-tracker.sh +12 -5
  198. package/pipeline/scripts/prune-logs.sh +53 -2
  199. package/pipeline/scripts/routine-registry.mjs +42 -6
  200. package/pipeline/scripts/run-results.mjs +373 -0
  201. package/pipeline/scripts/runs-index.mjs +62 -2
  202. package/pipeline/scripts/service-read.mjs +244 -0
  203. package/pipeline/scripts/stack-toggle.mjs +285 -0
  204. package/pipeline/scripts/steer-run.mjs +97 -0
  205. package/pipeline/scripts/system-status.mjs +196 -0
  206. package/pipeline/scripts/task-mirror.mjs +150 -0
  207. package/pipeline/scripts/task-mirror.sh +20 -0
  208. package/pipeline/scripts/toolkit-tools.mjs +625 -0
  209. package/pipeline/scripts/transcript-index.mjs +4 -1
  210. package/pipeline/scripts/uninstall.mjs +3 -0
  211. package/pipeline/scripts/work-items.mjs +473 -0
  212. package/pipeline/skills/.skill-manifest.json +23 -11
  213. package/pipeline/skills/.skills-index.json +34 -1
  214. package/pipeline/skills/shared/README.md +6 -3
  215. package/pipeline/skills/shared/core/multi-agent-autopilot-on/SKILL.md +13 -15
  216. package/pipeline/skills/shared/core/multi-agent-office-off/SKILL.md +16 -0
  217. package/pipeline/skills/shared/core/multi-agent-office-on/SKILL.md +21 -0
  218. package/pipeline/skills/shared/core/multi-agent-office-status/SKILL.md +17 -0
  219. package/pipeline/skills/shared/core/multi-agent-prune-logs/SKILL.md +4 -1
  220. package/pipeline/skills/shared/core/multi-agent-review/SKILL.md +19 -0
  221. package/pipeline/skills/shared/core/multi-agent-scenario-audit/SKILL.md +4 -2
  222. package/pipeline/skills/shared/core/multi-agent-serve/SKILL.md +4 -2
  223. package/pipeline/skills/shared/core/multi-agent-stack/SKILL.md +14 -6
  224. package/pipeline/skills/shared/core/multi-agent-steer/SKILL.md +10 -9
  225. package/pipeline/skills/shared/core/multi-agent-sync/SKILL.md +3 -3
  226. package/pipeline/skills/shared/core/multi-agent-test-gen/SKILL.md +26 -3
  227. package/pipeline/skills/skills-index.md +4 -1
@@ -0,0 +1,3 @@
1
+ {
2
+ "toolkitVersion": "3.26.0"
3
+ }
@@ -0,0 +1,78 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://github.com/mmerterden/multi-agent-pipeline/pipeline/schemas/activity-chat.schema.json",
4
+ "title": "Agent chat page",
5
+ "description": "What GET /v1/agents/{sessionId}/{agentId}/chat returns and `activity-snapshot.mjs chat` prints: one page of an agent's transcript read from its end, oldest first, at most `limit` messages. Only user and assistant records are read; api-request records are never parsed and thinking blocks are never emitted. Every text has been through the redactor; a text the outbound gate still flags is replaced by a marker. `before` is the byte offset to send back for the previous page, null at the start of the file.",
6
+ "type": "object",
7
+ "additionalProperties": false,
8
+ "required": ["contractVersion", "sessionId", "agentId", "messages", "before", "redacted"],
9
+ "properties": {
10
+ "contractVersion": {
11
+ "type": "string",
12
+ "pattern": "^1\\.[0-9]+\\.[0-9]+$",
13
+ "x-sensitivity": "none"
14
+ },
15
+ "sessionId": { "type": "string", "x-sensitivity": "none" },
16
+ "agentId": {
17
+ "type": ["string", "null"],
18
+ "description": "null for the session's own transcript (the orchestrator).",
19
+ "x-sensitivity": "none"
20
+ },
21
+ "messages": {
22
+ "type": "array",
23
+ "x-sensitivity": "none",
24
+ "items": {
25
+ "type": "object",
26
+ "additionalProperties": false,
27
+ "required": ["offset", "role", "at", "blocks"],
28
+ "properties": {
29
+ "offset": { "type": "integer", "minimum": 0 },
30
+ "role": { "enum": ["user", "assistant"] },
31
+ "at": { "type": ["string", "null"] },
32
+ "blocks": {
33
+ "type": "array",
34
+ "items": {
35
+ "oneOf": [
36
+ {
37
+ "type": "object",
38
+ "additionalProperties": false,
39
+ "required": ["kind", "text"],
40
+ "properties": { "kind": { "const": "text" }, "text": { "type": "string" } }
41
+ },
42
+ {
43
+ "type": "object",
44
+ "additionalProperties": false,
45
+ "required": ["kind", "name", "summary", "toolUseId"],
46
+ "properties": {
47
+ "kind": { "const": "tool" },
48
+ "name": { "type": "string" },
49
+ "summary": { "type": "string" },
50
+ "toolUseId": { "type": ["string", "null"] }
51
+ }
52
+ },
53
+ {
54
+ "type": "object",
55
+ "additionalProperties": false,
56
+ "required": ["kind", "toolUseId", "text", "isError"],
57
+ "properties": {
58
+ "kind": { "const": "result" },
59
+ "toolUseId": { "type": ["string", "null"] },
60
+ "text": { "type": "string" },
61
+ "isError": { "type": "boolean" }
62
+ }
63
+ }
64
+ ]
65
+ }
66
+ }
67
+ }
68
+ }
69
+ },
70
+ "before": { "type": ["integer", "null"], "minimum": 0, "x-sensitivity": "none" },
71
+ "redacted": {
72
+ "type": "integer",
73
+ "minimum": 0,
74
+ "description": "How many items the redactor replaced on this page.",
75
+ "x-sensitivity": "none"
76
+ }
77
+ }
78
+ }
@@ -0,0 +1,48 @@
1
+ {
2
+ "$schema": "./activity-roles.schema.json",
3
+ "contractVersion": "1.0.0",
4
+ "description": "The role label shown above each agent in the office view, by agent type. activity-snapshot.mjs reads it and nothing else names a role. Labels stay English (they are technical names). A type in `untyped` takes its role from the run phase it was spawned in; a type in neither list is shown as its raw agentType, never guessed. smoke-activity-roles.sh fails when an agent under pipeline/agents/ is missing from `agentTypes`.",
5
+ "orchestrator": "Orchestrator",
6
+ "agentTypes": {
7
+ "task-clarifier": "Clarifier",
8
+ "test-gen-analyst": "Test Gap Analyst",
9
+ "explorer": "Explorer",
10
+ "Explore": "Explorer",
11
+ "Plan": "Planner",
12
+ "plan-critic": "Plan Critic",
13
+ "ios-architect": "iOS Architect",
14
+ "android-architect": "Android Architect",
15
+ "backend-architect": "Backend Architect",
16
+ "dev-critic": "Dev Critic",
17
+ "code-reviewer": "Reviewer",
18
+ "security-auditor": "Security Auditor",
19
+ "bulk-reader": "Reader"
20
+ },
21
+ "untyped": ["general-purpose", "claude", "fork"],
22
+ "phaseRoles": {
23
+ "1": "Planner",
24
+ "2": "Developer",
25
+ "3": "Reviewer",
26
+ "4": "Committer",
27
+ "5": "Reporter"
28
+ },
29
+ "styles": {
30
+ "Orchestrator": { "sprite": 0, "color": "#3d6fd8" },
31
+ "Clarifier": { "sprite": 1, "color": "#8a63d2" },
32
+ "Explorer": { "sprite": 2, "color": "#1f9e89" },
33
+ "Planner": { "sprite": 3, "color": "#d98b1f" },
34
+ "Plan Critic": { "sprite": 4, "color": "#c2553d" },
35
+ "iOS Architect": { "sprite": 5, "color": "#2b8bd6" },
36
+ "Android Architect": { "sprite": 5, "color": "#3f9c35" },
37
+ "Backend Architect": { "sprite": 5, "color": "#7a6a55" },
38
+ "Developer": { "sprite": 6, "color": "#2f8f5b" },
39
+ "Dev Critic": { "sprite": 4, "color": "#b5487a" },
40
+ "Test Gap Analyst": { "sprite": 2, "color": "#9a7b1c" },
41
+ "Reviewer": { "sprite": 7, "color": "#c43d3d" },
42
+ "Security Auditor": { "sprite": 8, "color": "#4a4a4a" },
43
+ "Reader": { "sprite": 2, "color": "#6b7f99" },
44
+ "Committer": { "sprite": 9, "color": "#5c6bc0" },
45
+ "Reporter": { "sprite": 9, "color": "#00897b" }
46
+ },
47
+ "unknownStyle": { "sprite": 10, "color": "#888888" }
48
+ }
@@ -0,0 +1,49 @@
1
+ {
2
+ "$schema": "https://json-schema.org/draft/2020-12/schema",
3
+ "$id": "https://github.com/mmerterden/multi-agent-pipeline/pipeline/schemas/activity-roles.schema.json",
4
+ "title": "Office role table",
5
+ "description": "The shape of activity-roles.json: the role label per agent type, the agent types whose role follows the run phase, the phase-to-role map and one fixed sprite and color per role.",
6
+ "type": "object",
7
+ "additionalProperties": false,
8
+ "required": [
9
+ "contractVersion",
10
+ "orchestrator",
11
+ "agentTypes",
12
+ "untyped",
13
+ "phaseRoles",
14
+ "styles",
15
+ "unknownStyle"
16
+ ],
17
+ "properties": {
18
+ "$schema": { "type": "string" },
19
+ "contractVersion": { "type": "string", "pattern": "^1\\.[0-9]+\\.[0-9]+$" },
20
+ "description": { "type": "string" },
21
+ "orchestrator": { "type": "string", "minLength": 1 },
22
+ "agentTypes": {
23
+ "type": "object",
24
+ "additionalProperties": { "type": "string", "minLength": 1 }
25
+ },
26
+ "untyped": { "type": "array", "items": { "type": "string", "minLength": 1 } },
27
+ "phaseRoles": {
28
+ "type": "object",
29
+ "propertyNames": { "pattern": "^[0-9]+$" },
30
+ "additionalProperties": { "type": "string", "minLength": 1 }
31
+ },
32
+ "styles": {
33
+ "type": "object",
34
+ "additionalProperties": { "$ref": "#/$defs/style" }
35
+ },
36
+ "unknownStyle": { "$ref": "#/$defs/style" }
37
+ },
38
+ "$defs": {
39
+ "style": {
40
+ "type": "object",
41
+ "additionalProperties": false,
42
+ "required": ["sprite", "color"],
43
+ "properties": {
44
+ "sprite": { "type": "integer", "minimum": 0, "maximum": 15 },
45
+ "color": { "type": "string", "pattern": "^#[0-9a-f]{6}$" }
46
+ }
47
+ }
48
+ }
49
+ }