release-skill 0.1.7 → 0.1.9

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 (64) hide show
  1. package/.claude-plugin/marketplace.json +1 -1
  2. package/.claude-plugin/plugin.json +1 -1
  3. package/.codex-plugin/plugin.json +2 -2
  4. package/.kimi-plugin/plugin.json +27 -0
  5. package/CHANGELOG.md +56 -0
  6. package/INSTALL.md +73 -2
  7. package/INSTALL.zh-CN.md +94 -99
  8. package/README.md +65 -39
  9. package/README.zh-CN.md +92 -325
  10. package/adapters/claude/.claude-plugin/marketplace.json +1 -1
  11. package/adapters/claude/.claude-plugin/plugin.json +1 -1
  12. package/adapters/claude/bin/release-skill.bundle.mjs +1114 -183
  13. package/adapters/claude/schemas/.render-manifest.json +4 -4
  14. package/adapters/claude/schemas/release-plan.schema.json +20 -2
  15. package/adapters/claude/schemas/release-project.schema.json +22 -4
  16. package/adapters/claude/schemas/release-run.schema.json +1 -0
  17. package/adapters/codex/.codex-plugin/plugin.json +2 -2
  18. package/adapters/codex/bin/release-skill.bundle.mjs +1114 -183
  19. package/adapters/codex/schemas/.render-manifest.json +4 -4
  20. package/adapters/codex/schemas/release-plan.schema.json +20 -2
  21. package/adapters/codex/schemas/release-project.schema.json +22 -4
  22. package/adapters/codex/schemas/release-run.schema.json +1 -0
  23. package/adapters/kimi/.kimi-plugin/plugin.json +27 -0
  24. package/adapters/kimi/bin/release-skill.bundle.mjs +84467 -0
  25. package/adapters/kimi/bin/release-skill.mjs +54 -0
  26. package/adapters/kimi/native/safe-write/binding.gyp +41 -0
  27. package/adapters/kimi/native/safe-write/prebuilds/darwin-arm64/safe_write.node +0 -0
  28. package/adapters/kimi/native/safe-write/prebuilds.json +24 -0
  29. package/adapters/kimi/native/safe-write/src/safe_write.cc +2032 -0
  30. package/adapters/kimi/schemas/.render-manifest.json +37 -0
  31. package/adapters/kimi/schemas/approval-record.schema.json +115 -0
  32. package/adapters/kimi/schemas/artifact-lock.schema.json +111 -0
  33. package/adapters/kimi/schemas/artifact-plan.schema.json +52 -0
  34. package/adapters/kimi/schemas/artifact-policy.schema.json +76 -0
  35. package/adapters/kimi/schemas/evidence-event.schema.json +89 -0
  36. package/adapters/kimi/schemas/release-plan.schema.json +878 -0
  37. package/adapters/kimi/schemas/release-project.schema.json +895 -0
  38. package/adapters/kimi/schemas/release-run.schema.json +343 -0
  39. package/adapters/kimi/skills/release-assess/SKILL.md +58 -0
  40. package/adapters/kimi/skills/release-help/SKILL.md +84 -0
  41. package/adapters/kimi/skills/release-prepare/SKILL.md +99 -0
  42. package/adapters/kimi/skills/release-publish/SKILL.md +64 -0
  43. package/adapters/kimi/skills/release-reconcile/SKILL.md +80 -0
  44. package/adapters/kimi/skills/release-setup/SKILL.md +102 -0
  45. package/adapters/kimi/skills/release-verify/SKILL.md +77 -0
  46. package/bin/release-skill-cli.mjs +16 -4
  47. package/bin/release-skill.bundle.mjs +1114 -183
  48. package/package.json +4 -2
  49. package/schemas/.render-manifest.json +4 -4
  50. package/schemas/release-plan.schema.json +20 -2
  51. package/schemas/release-project.schema.json +22 -4
  52. package/schemas/release-run.schema.json +1 -0
  53. package/src/adapters/contract.mjs +1 -0
  54. package/src/adapters/plugin-marketplace.mjs +1109 -49
  55. package/src/commands/assess.mjs +50 -1
  56. package/src/commands/prepare.mjs +65 -0
  57. package/src/commands/publish.mjs +3 -0
  58. package/src/commands/reconcile.mjs +3 -0
  59. package/src/commands/setup.mjs +10 -5
  60. package/src/commands/verify.mjs +16 -6
  61. package/src/core/plan.mjs +118 -0
  62. package/src/core/verification-gates.mjs +1 -1
  63. package/src/producers/build-adapters.mjs +38 -8
  64. package/src/snapshot/frozen.mjs +4 -3
@@ -0,0 +1,878 @@
1
+ {
2
+ "$schema": "http://json-schema.org/draft-07/schema#",
3
+ "$id": "https://release-skill.dev/schemas/release-plan/v1",
4
+ "title": "Release Plan",
5
+ "description": "Schema for frozen release plan produced by the prepare phase",
6
+ "type": "object",
7
+ "required": [
8
+ "planVersion",
9
+ "status",
10
+ "baseline",
11
+ "units",
12
+ "externalActions"
13
+ ],
14
+ "additionalProperties": false,
15
+ "properties": {
16
+ "planVersion": {
17
+ "type": "integer",
18
+ "const": 1
19
+ },
20
+ "status": {
21
+ "type": "string",
22
+ "enum": [
23
+ "DISCOVERED",
24
+ "ASSESSED",
25
+ "PREPARED",
26
+ "APPROVED",
27
+ "PUBLISHING",
28
+ "PUBLISHED",
29
+ "VERIFIED",
30
+ "NEEDS_INPUT",
31
+ "BLOCKED",
32
+ "PARTIAL"
33
+ ]
34
+ },
35
+ "production": {
36
+ "type": "object",
37
+ "required": [
38
+ "mode",
39
+ "assetRoot"
40
+ ],
41
+ "additionalProperties": false,
42
+ "properties": {
43
+ "mode": {
44
+ "const": "github-npm-v1"
45
+ },
46
+ "assetRoot": {
47
+ "type": "string",
48
+ "minLength": 1
49
+ }
50
+ }
51
+ },
52
+ "baseline": {
53
+ "type": "object",
54
+ "required": [
55
+ "gitTreeHash"
56
+ ],
57
+ "additionalProperties": false,
58
+ "properties": {
59
+ "gitTreeHash": {
60
+ "type": "string",
61
+ "minLength": 1
62
+ },
63
+ "workspaceDigest": {
64
+ "type": "string",
65
+ "minLength": 1,
66
+ "description": "Deterministic digest of workspace file state at plan freeze time"
67
+ },
68
+ "workspaceDigestAlgorithm": {
69
+ "type": "string",
70
+ "const": "git-workspace-v2",
71
+ "description": "Versioned algorithm authority for workspaceDigest"
72
+ },
73
+ "headCommit": {
74
+ "type": "string"
75
+ },
76
+ "dirtyFiles": {
77
+ "type": "array",
78
+ "items": {
79
+ "type": "string"
80
+ }
81
+ },
82
+ "capturedAt": {
83
+ "type": "string",
84
+ "format": "date-time"
85
+ }
86
+ }
87
+ },
88
+ "units": {
89
+ "type": "array",
90
+ "minItems": 1,
91
+ "items": {
92
+ "type": "object",
93
+ "required": [
94
+ "id",
95
+ "targetVersion",
96
+ "previousPublicBaseline"
97
+ ],
98
+ "additionalProperties": false,
99
+ "properties": {
100
+ "id": {
101
+ "type": "string",
102
+ "minLength": 1,
103
+ "pattern": "^(?!\\.{1,2}$)[A-Za-z0-9][A-Za-z0-9._-]*$"
104
+ },
105
+ "targetVersion": {
106
+ "type": "string",
107
+ "minLength": 1
108
+ },
109
+ "source": {
110
+ "type": "string"
111
+ },
112
+ "publicRepo": {
113
+ "type": "string"
114
+ },
115
+ "tagTemplate": {
116
+ "type": "string"
117
+ },
118
+ "snapshotDigest": {
119
+ "type": "string",
120
+ "description": "SHA-256 digest of the snapshot content"
121
+ },
122
+ "productionConfig": {
123
+ "type": "object",
124
+ "required": [
125
+ "githubHost",
126
+ "branchTemplate",
127
+ "branchStrategy"
128
+ ],
129
+ "additionalProperties": false,
130
+ "properties": {
131
+ "githubHost": {
132
+ "type": "string"
133
+ },
134
+ "branchTemplate": {
135
+ "type": "string"
136
+ },
137
+ "releaseTitleTemplate": {
138
+ "type": "string"
139
+ },
140
+ "releaseNotes": {
141
+ "type": "string"
142
+ },
143
+ "branchStrategy": {
144
+ "type": "string",
145
+ "enum": [
146
+ "create-release-branch",
147
+ "advance-existing-branch",
148
+ "initialize-default-branch"
149
+ ]
150
+ },
151
+ "setAsDefaultBranch": {
152
+ "type": "boolean"
153
+ },
154
+ "expectedCurrentDefaultBranch": {
155
+ "type": "string",
156
+ "minLength": 1
157
+ }
158
+ },
159
+ "allOf": [
160
+ {
161
+ "if": {
162
+ "properties": {
163
+ "branchStrategy": {
164
+ "const": "initialize-default-branch"
165
+ }
166
+ },
167
+ "required": [
168
+ "branchStrategy"
169
+ ]
170
+ },
171
+ "then": {
172
+ "required": [
173
+ "setAsDefaultBranch",
174
+ "expectedCurrentDefaultBranch"
175
+ ],
176
+ "properties": {
177
+ "setAsDefaultBranch": {
178
+ "const": true
179
+ }
180
+ }
181
+ }
182
+ },
183
+ {
184
+ "if": {
185
+ "properties": {
186
+ "setAsDefaultBranch": {
187
+ "const": true
188
+ }
189
+ },
190
+ "required": [
191
+ "setAsDefaultBranch"
192
+ ]
193
+ },
194
+ "then": {
195
+ "properties": {
196
+ "branchStrategy": {
197
+ "const": "initialize-default-branch"
198
+ }
199
+ }
200
+ }
201
+ }
202
+ ]
203
+ },
204
+ "frozenSnapshot": {
205
+ "type": "object",
206
+ "required": [
207
+ "path",
208
+ "manifestDigest",
209
+ "gitObjectDir",
210
+ "branch",
211
+ "branchStrategy",
212
+ "commit",
213
+ "tree",
214
+ "commitTimestamp"
215
+ ],
216
+ "additionalProperties": false,
217
+ "properties": {
218
+ "path": {
219
+ "type": "string",
220
+ "minLength": 1
221
+ },
222
+ "manifestDigest": {
223
+ "type": "string",
224
+ "pattern": "^[a-f0-9]{64}$"
225
+ },
226
+ "gitObjectDir": {
227
+ "type": "string",
228
+ "minLength": 1
229
+ },
230
+ "branch": {
231
+ "type": "string",
232
+ "minLength": 1
233
+ },
234
+ "commit": {
235
+ "type": "string",
236
+ "pattern": "^[a-f0-9]{40,64}$"
237
+ },
238
+ "tree": {
239
+ "type": "string",
240
+ "pattern": "^[a-f0-9]{40,64}$"
241
+ },
242
+ "commitTimestamp": {
243
+ "type": "string",
244
+ "pattern": "^\\d{4}-\\d{2}-\\d{2}T\\d{2}:\\d{2}:\\d{2}\\+00:00$",
245
+ "description": "Plan freeze timestamp sampled exactly once during production prepare, in canonical UTC second precision. Written verbatim to GIT_AUTHOR_DATE and GIT_COMMITTER_DATE of the frozen release commit, so it always equals the commit's %aI and %cI byte-for-byte, and must equal the plan's createdAt."
246
+ },
247
+ "parentCommit": {
248
+ "type": "string",
249
+ "pattern": "^[a-f0-9]{40,64}$"
250
+ },
251
+ "branchStrategy": {
252
+ "type": "string",
253
+ "enum": [
254
+ "create-release-branch",
255
+ "advance-existing-branch",
256
+ "initialize-default-branch"
257
+ ]
258
+ },
259
+ "npm": {
260
+ "anyOf": [
261
+ {
262
+ "type": "null"
263
+ },
264
+ {
265
+ "type": "object",
266
+ "required": [
267
+ "tarballPath",
268
+ "tarballSha256",
269
+ "integrity",
270
+ "size"
271
+ ],
272
+ "additionalProperties": false,
273
+ "properties": {
274
+ "tarballPath": {
275
+ "type": "string",
276
+ "minLength": 1
277
+ },
278
+ "tarballSha256": {
279
+ "type": "string",
280
+ "pattern": "^[a-f0-9]{64}$"
281
+ },
282
+ "integrity": {
283
+ "type": "string",
284
+ "minLength": 1
285
+ },
286
+ "size": {
287
+ "type": "integer",
288
+ "minimum": 1
289
+ }
290
+ }
291
+ }
292
+ ]
293
+ }
294
+ },
295
+ "allOf": [
296
+ {
297
+ "if": {
298
+ "properties": {
299
+ "branchStrategy": {
300
+ "enum": [
301
+ "advance-existing-branch",
302
+ "initialize-default-branch"
303
+ ]
304
+ }
305
+ },
306
+ "required": [
307
+ "branchStrategy"
308
+ ]
309
+ },
310
+ "then": {
311
+ "required": [
312
+ "parentCommit"
313
+ ]
314
+ }
315
+ },
316
+ {
317
+ "if": {
318
+ "properties": {
319
+ "branchStrategy": {
320
+ "const": "create-release-branch"
321
+ }
322
+ },
323
+ "required": [
324
+ "branchStrategy"
325
+ ]
326
+ },
327
+ "then": {
328
+ "not": {
329
+ "required": [
330
+ "parentCommit"
331
+ ]
332
+ }
333
+ }
334
+ }
335
+ ]
336
+ },
337
+ "distributions": {
338
+ "type": "array",
339
+ "items": {
340
+ "type": "object",
341
+ "required": [
342
+ "type"
343
+ ],
344
+ "additionalProperties": false,
345
+ "properties": {
346
+ "type": {
347
+ "type": "string",
348
+ "enum": [
349
+ "npm",
350
+ "claude-plugin",
351
+ "codex-plugin",
352
+ "kimi-plugin"
353
+ ]
354
+ },
355
+ "package": {
356
+ "type": "string",
357
+ "maxLength": 214,
358
+ "pattern": "^(?:@[a-z0-9][a-z0-9._-]*/[a-z0-9][a-z0-9._-]*|[a-z0-9][a-z0-9._-]*)$"
359
+ },
360
+ "access": {
361
+ "type": "string",
362
+ "enum": [
363
+ "public",
364
+ "restricted"
365
+ ]
366
+ },
367
+ "provenance": {
368
+ "type": "boolean"
369
+ },
370
+ "tag": {
371
+ "type": "string",
372
+ "minLength": 1
373
+ },
374
+ "registry": {
375
+ "type": "string",
376
+ "minLength": 1,
377
+ "pattern": "^https://[^\\s]+$",
378
+ "description": "Normalized HTTPS URL of the npm registry"
379
+ },
380
+ "publisher": {
381
+ "type": "string",
382
+ "minLength": 1,
383
+ "pattern": "^[a-z0-9][a-z0-9._-]*$",
384
+ "description": "Expected npm whoami username for this registry"
385
+ },
386
+ "plugin": {
387
+ "type": "string",
388
+ "minLength": 1,
389
+ "pattern": "^[a-z0-9][a-z0-9._-]*$"
390
+ },
391
+ "marketplace": {
392
+ "type": "string",
393
+ "minLength": 1,
394
+ "pattern": "^[a-z0-9][a-z0-9._-]*$"
395
+ },
396
+ "entrySkill": {
397
+ "type": "string",
398
+ "minLength": 1,
399
+ "pattern": "^[a-z0-9][a-z0-9-]*$"
400
+ },
401
+ "smokeBin": {
402
+ "type": "string",
403
+ "minLength": 1
404
+ },
405
+ "smokeArgs": {
406
+ "type": "array",
407
+ "items": {
408
+ "type": "string"
409
+ }
410
+ },
411
+ "smokeExpectedJson": {
412
+ "type": "object"
413
+ }
414
+ },
415
+ "allOf": [
416
+ {
417
+ "if": {
418
+ "properties": {
419
+ "type": {
420
+ "const": "npm"
421
+ }
422
+ }
423
+ },
424
+ "then": {
425
+ "required": [
426
+ "package",
427
+ "registry",
428
+ "publisher"
429
+ ]
430
+ }
431
+ },
432
+ {
433
+ "if": {
434
+ "properties": {
435
+ "type": {
436
+ "enum": [
437
+ "claude-plugin",
438
+ "codex-plugin"
439
+ ]
440
+ }
441
+ }
442
+ },
443
+ "then": {
444
+ "required": [
445
+ "plugin",
446
+ "marketplace",
447
+ "entrySkill"
448
+ ]
449
+ }
450
+ },
451
+ {
452
+ "if": {
453
+ "properties": {
454
+ "type": {
455
+ "const": "kimi-plugin"
456
+ }
457
+ }
458
+ },
459
+ "then": {
460
+ "required": [
461
+ "plugin",
462
+ "entrySkill"
463
+ ]
464
+ }
465
+ },
466
+ {
467
+ "if": {
468
+ "required": [
469
+ "smokeExpectedJson"
470
+ ],
471
+ "properties": {
472
+ "smokeBin": {
473
+ "minLength": 1
474
+ }
475
+ }
476
+ },
477
+ "then": {
478
+ "required": [
479
+ "smokeBin"
480
+ ]
481
+ }
482
+ },
483
+ {
484
+ "if": {
485
+ "required": [
486
+ "smokeArgs"
487
+ ],
488
+ "properties": {
489
+ "smokeBin": {
490
+ "minLength": 1
491
+ }
492
+ }
493
+ },
494
+ "then": {
495
+ "required": [
496
+ "smokeBin"
497
+ ]
498
+ }
499
+ }
500
+ ]
501
+ }
502
+ },
503
+ "previousPublicBaseline": {
504
+ "type": "object",
505
+ "required": [
506
+ "mode",
507
+ "status"
508
+ ],
509
+ "additionalProperties": false,
510
+ "properties": {
511
+ "mode": {
512
+ "type": "string",
513
+ "enum": [
514
+ "none",
515
+ "bound"
516
+ ]
517
+ },
518
+ "githubHost": {
519
+ "type": "string"
520
+ },
521
+ "repo": {
522
+ "type": "string"
523
+ },
524
+ "ref": {
525
+ "type": "string"
526
+ },
527
+ "commit": {
528
+ "type": "string"
529
+ },
530
+ "tree": {
531
+ "type": "string"
532
+ },
533
+ "manifestDigest": {
534
+ "type": "string"
535
+ },
536
+ "observedCommit": {
537
+ "type": "string"
538
+ },
539
+ "observedAt": {
540
+ "type": "string",
541
+ "format": "date-time"
542
+ },
543
+ "status": {
544
+ "type": "string",
545
+ "enum": [
546
+ "consistent",
547
+ "drifted",
548
+ "unknown",
549
+ "unobserved-offline",
550
+ "blocking"
551
+ ]
552
+ }
553
+ },
554
+ "if": {
555
+ "properties": {
556
+ "mode": {
557
+ "const": "bound"
558
+ }
559
+ }
560
+ },
561
+ "then": {
562
+ "required": [
563
+ "repo",
564
+ "ref",
565
+ "commit"
566
+ ]
567
+ },
568
+ "else": {
569
+ "allOf": [
570
+ {
571
+ "not": {
572
+ "required": [
573
+ "repo"
574
+ ]
575
+ }
576
+ },
577
+ {
578
+ "not": {
579
+ "required": [
580
+ "githubHost"
581
+ ]
582
+ }
583
+ },
584
+ {
585
+ "not": {
586
+ "required": [
587
+ "ref"
588
+ ]
589
+ }
590
+ },
591
+ {
592
+ "not": {
593
+ "required": [
594
+ "commit"
595
+ ]
596
+ }
597
+ },
598
+ {
599
+ "not": {
600
+ "required": [
601
+ "tree"
602
+ ]
603
+ }
604
+ },
605
+ {
606
+ "not": {
607
+ "required": [
608
+ "manifestDigest"
609
+ ]
610
+ }
611
+ },
612
+ {
613
+ "not": {
614
+ "required": [
615
+ "observedCommit"
616
+ ]
617
+ }
618
+ },
619
+ {
620
+ "not": {
621
+ "required": [
622
+ "observedAt"
623
+ ]
624
+ }
625
+ }
626
+ ]
627
+ }
628
+ }
629
+ }
630
+ }
631
+ },
632
+ "configDigest": {
633
+ "type": "string",
634
+ "minLength": 1,
635
+ "description": "Digest of the project configuration at plan freeze time"
636
+ },
637
+ "verificationGates": {
638
+ "type": "array",
639
+ "items": {
640
+ "$ref": "#/definitions/verificationGate"
641
+ }
642
+ },
643
+ "externalActions": {
644
+ "type": "array",
645
+ "minItems": 1,
646
+ "items": {
647
+ "type": "object",
648
+ "required": [
649
+ "id",
650
+ "type",
651
+ "adapter"
652
+ ],
653
+ "additionalProperties": false,
654
+ "properties": {
655
+ "id": {
656
+ "type": "string",
657
+ "minLength": 1
658
+ },
659
+ "type": {
660
+ "type": "string",
661
+ "enum": [
662
+ "push-commit",
663
+ "push-snapshot",
664
+ "create-tag",
665
+ "npm-publish",
666
+ "github-release",
667
+ "claude-marketplace-install",
668
+ "codex-marketplace-install",
669
+ "kimi-marketplace-install",
670
+ "set-default-branch"
671
+ ]
672
+ },
673
+ "adapter": {
674
+ "type": "string",
675
+ "minLength": 1
676
+ },
677
+ "unitId": {
678
+ "type": "string"
679
+ },
680
+ "parameters": {
681
+ "type": "object"
682
+ },
683
+ "expected": {
684
+ "type": "object",
685
+ "description": "Expected observation state for verification"
686
+ },
687
+ "status": {
688
+ "type": "string",
689
+ "enum": [
690
+ "PENDING",
691
+ "SUCCEEDED",
692
+ "FAILED",
693
+ "SKIPPED"
694
+ ],
695
+ "description": "Action execution status"
696
+ }
697
+ }
698
+ }
699
+ },
700
+ "createdAt": {
701
+ "type": "string",
702
+ "format": "date-time"
703
+ },
704
+ "publishedAt": {
705
+ "type": "string",
706
+ "format": "date-time",
707
+ "description": "ISO 8601 timestamp when the plan was published"
708
+ },
709
+ "reconciledAt": {
710
+ "type": "string",
711
+ "format": "date-time",
712
+ "description": "ISO 8601 timestamp when the plan was last reconciled"
713
+ },
714
+ "snapshotDigest": {
715
+ "type": "string",
716
+ "description": "Overall snapshot digest across all units"
717
+ },
718
+ "digest": {
719
+ "type": "string",
720
+ "minLength": 1
721
+ },
722
+ "waivers": {
723
+ "type": "array",
724
+ "items": {
725
+ "type": "object",
726
+ "required": [
727
+ "rule",
728
+ "reason",
729
+ "responsible",
730
+ "expiresAt"
731
+ ],
732
+ "additionalProperties": false,
733
+ "properties": {
734
+ "rule": {
735
+ "type": "string",
736
+ "minLength": 1
737
+ },
738
+ "reason": {
739
+ "type": "string",
740
+ "minLength": 1
741
+ },
742
+ "responsible": {
743
+ "type": "string",
744
+ "minLength": 1
745
+ },
746
+ "expiresAt": {
747
+ "type": "string",
748
+ "format": "date-time"
749
+ }
750
+ }
751
+ }
752
+ }
753
+ },
754
+ "definitions": {
755
+ "verificationGate": {
756
+ "type": "object",
757
+ "required": [
758
+ "id",
759
+ "phase",
760
+ "scope",
761
+ "command",
762
+ "cwd",
763
+ "timeoutMs",
764
+ "envAllowlist"
765
+ ],
766
+ "additionalProperties": false,
767
+ "properties": {
768
+ "id": {
769
+ "type": "string",
770
+ "pattern": "^[a-z0-9][a-z0-9._-]*$"
771
+ },
772
+ "phase": {
773
+ "type": "string",
774
+ "enum": [
775
+ "snapshot-verify",
776
+ "consumer-verify"
777
+ ]
778
+ },
779
+ "scope": {
780
+ "type": "object",
781
+ "required": [
782
+ "unit"
783
+ ],
784
+ "additionalProperties": false,
785
+ "properties": {
786
+ "unit": {
787
+ "type": "string",
788
+ "pattern": "^(?!\\.{1,2}$)[A-Za-z0-9][A-Za-z0-9._-]*$"
789
+ },
790
+ "distribution": {
791
+ "type": "string",
792
+ "enum": [
793
+ "npm",
794
+ "claude-plugin",
795
+ "codex-plugin",
796
+ "kimi-plugin"
797
+ ]
798
+ }
799
+ }
800
+ },
801
+ "command": {
802
+ "type": "array",
803
+ "minItems": 1,
804
+ "items": {
805
+ "type": "string"
806
+ }
807
+ },
808
+ "cwd": {
809
+ "type": "string",
810
+ "pattern": "^(?:\\.$|(?!\\/)(?!\\.\\/)(?!.*\\\\)(?!.*:)(?!\\.\\.(?:\\/|$))(?!.*\\/\\.\\.\\/)(?!.*\\/\\.\\.$)(?!.*\\/\\.\\/)(?!.*\\/\\/)(?!.*\\0)(?!.*\\/\\.$)(?!.*\\/\\/$)(?!.*\\/$).*)$"
811
+ },
812
+ "timeoutMs": {
813
+ "type": "integer",
814
+ "minimum": 1000,
815
+ "maximum": 7200000
816
+ },
817
+ "envAllowlist": {
818
+ "type": "array",
819
+ "items": {
820
+ "type": "string",
821
+ "pattern": "^[A-Z_][A-Z0-9_]*$"
822
+ },
823
+ "uniqueItems": true
824
+ },
825
+ "expectedJson": {
826
+ "type": "object"
827
+ }
828
+ },
829
+ "allOf": [
830
+ {
831
+ "if": {
832
+ "properties": {
833
+ "phase": {
834
+ "const": "consumer-verify"
835
+ }
836
+ },
837
+ "required": [
838
+ "phase"
839
+ ]
840
+ },
841
+ "then": {
842
+ "properties": {
843
+ "scope": {
844
+ "required": [
845
+ "unit",
846
+ "distribution"
847
+ ]
848
+ }
849
+ }
850
+ }
851
+ },
852
+ {
853
+ "if": {
854
+ "properties": {
855
+ "phase": {
856
+ "const": "snapshot-verify"
857
+ }
858
+ },
859
+ "required": [
860
+ "phase"
861
+ ]
862
+ },
863
+ "then": {
864
+ "properties": {
865
+ "scope": {
866
+ "not": {
867
+ "required": [
868
+ "distribution"
869
+ ]
870
+ }
871
+ }
872
+ }
873
+ }
874
+ }
875
+ ]
876
+ }
877
+ }
878
+ }