@aiwg/cli 2026.10.5 → 2026.10.7
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.
- package/agentic/code/addons/composition-engine/lib/runtime.mjs +1401 -0
- package/agentic/code/addons/composition-engine/lib/validator.mjs +513 -0
- package/agentic/code/addons/composition-engine/schemas/flow-graph.schema.json +372 -0
- package/agentic/code/providers/model-capabilities.v1.json +74 -50
- package/bin/aiwg.mjs +7 -3
- package/dist/src/a2a/agent-card.js +11 -0
- package/dist/src/api/index.d.ts +1 -0
- package/dist/src/api/index.js +1 -0
- package/dist/src/artifacts/browser-export.js +1 -0
- package/dist/src/artifacts/citation-parser.js +8 -1
- package/dist/src/artifacts/cli.js +57 -6
- package/dist/src/artifacts/fortemi-core-query-adapter.js +2 -0
- package/dist/src/artifacts/fortemi-core-sync.js +26 -8
- package/dist/src/artifacts/fortemi-shard-contract/2.2.0/contract.json +103 -0
- package/dist/src/artifacts/fortemi-shard-contract/2.2.0/full-v1-embedding-config.schema.json +212 -0
- package/dist/src/artifacts/fortemi-shard-contract/2.2.0/full-v1-embedding-set.schema.json +240 -0
- package/dist/src/artifacts/fortemi-shard-contract/2.2.0/full-v1-manifest.schema.json +451 -0
- package/dist/src/artifacts/fortemi-shard-export.js +284 -0
- package/dist/src/artifacts/graph-query.js +18 -8
- package/dist/src/artifacts/index-adapters.js +339 -0
- package/dist/src/artifacts/index-builder.js +143 -14
- package/dist/src/artifacts/index-files.js +15 -4
- package/dist/src/artifacts/index-preparation.js +2 -0
- package/dist/src/artifacts/index-reader.js +44 -0
- package/dist/src/artifacts/index-refresh.js +114 -55
- package/dist/src/artifacts/index-status.js +20 -5
- package/dist/src/artifacts/memory-maintenance.js +503 -0
- package/dist/src/artifacts/prebuilt-relations.js +3 -1
- package/dist/src/artifacts/query-engine.js +263 -108
- package/dist/src/artifacts/relations-builder.js +2 -2
- package/dist/src/artifacts/source-graph.js +2 -2
- package/dist/src/artifacts/types.js +9 -1
- package/dist/src/auth/client.js +5 -1
- package/dist/src/auth/credential-store.js +5 -1
- package/dist/src/auth/sensitive-input.js +151 -0
- package/dist/src/channel/manager.mjs +3 -0
- package/dist/src/cli/handlers/agentcard.js +47 -25
- package/dist/src/cli/handlers/auth.js +22 -2
- package/dist/src/cli/handlers/decision.js +22 -3
- package/dist/src/cli/handlers/effect.js +4 -84
- package/dist/src/cli/handlers/guided-setup.js +470 -0
- package/dist/src/cli/handlers/help.js +2 -2
- package/dist/src/cli/handlers/housekeeper.js +1110 -0
- package/dist/src/cli/handlers/index.js +4 -2
- package/dist/src/cli/handlers/init.js +41 -6
- package/dist/src/cli/handlers/install.js +6 -0
- package/dist/src/cli/handlers/local-executor.js +5 -3
- package/dist/src/cli/handlers/marketplace.js +15 -4
- package/dist/src/cli/handlers/mc.js +509 -53
- package/dist/src/cli/handlers/models.js +32 -2
- package/dist/src/cli/handlers/ralph-launcher.js +76 -4
- package/dist/src/cli/handlers/rules.js +1 -1
- package/dist/src/cli/handlers/script-runner.js +73 -2
- package/dist/src/cli/handlers/serve.js +5 -3
- package/dist/src/cli/handlers/sessions.js +1 -0
- package/dist/src/cli/handlers/setup.js +432 -1
- package/dist/src/cli/handlers/skill-lint.js +1 -1
- package/dist/src/cli/handlers/subcommands.js +118 -8
- package/dist/src/cli/handlers/use.js +335 -107
- package/dist/src/cli/handlers/workspace.js +3 -1
- package/dist/src/cli/prompt-utils.js +81 -0
- package/dist/src/cli/router.js +16 -1
- package/dist/src/config/aiwg-config.js +42 -0
- package/dist/src/config/cli.js +7 -3
- package/dist/src/config/decision-config.js +14 -1
- package/dist/src/config/gitignore.js +4 -0
- package/dist/src/config/native-sandbox-warnings.js +25 -0
- package/dist/src/config/workspace.js +2 -1
- package/dist/src/contributors/validation.js +6 -5
- package/dist/src/decision/adapters/jev.js +20 -31
- package/dist/src/decision/admission.js +7 -3
- package/dist/src/decision/ask.js +6 -1
- package/dist/src/decision/benchmark.js +482 -0
- package/dist/src/decision/ledger.js +22 -3
- package/dist/src/decision/pricing.js +147 -0
- package/dist/src/decision/qualification/gate-evidence.js +23 -18
- package/dist/src/decision/qualification/load-staged.js +576 -0
- package/dist/src/decision/qualification/load.js +109 -33
- package/dist/src/decision/qualification/runner.js +12 -5
- package/dist/src/decision/review/service.js +6 -4
- package/dist/src/decision/review/validate.js +23 -2
- package/dist/src/decision/savings.js +8 -3
- package/dist/src/discovery/index.js +492 -0
- package/dist/src/discovery/interview.js +238 -0
- package/dist/src/discovery/plan-apply.js +567 -0
- package/dist/src/discovery/plan-store.js +171 -0
- package/dist/src/discovery/plan-types.js +2 -0
- package/dist/src/discovery/plan-validation.js +139 -0
- package/dist/src/discovery/types.js +2 -0
- package/dist/src/effects/host.js +91 -0
- package/dist/src/extensions/commands/definitions.js +49 -9
- package/dist/src/extensions/manifest.js +71 -44
- package/dist/src/extensions/project-local-discovery.js +1 -1
- package/dist/src/extensions/project-local-gitignore.js +2 -0
- package/dist/src/extensions/project-quickref.js +18 -17
- package/dist/src/extensions/validation.js +32 -29
- package/dist/src/housekeeper/daemon-config.js +148 -0
- package/dist/src/housekeeper/ipc.js +84 -0
- package/dist/src/housekeeper/lifecycle.js +148 -0
- package/dist/src/housekeeper/platform.js +35 -0
- package/dist/src/housekeeper/status.js +70 -0
- package/dist/src/housekeeper/units.js +114 -0
- package/dist/src/issues/cli.js +16 -5
- package/dist/src/issues/live.js +44 -12
- package/dist/src/jobs/flow.js +22 -21
- package/dist/src/lint/rule-activation.js +20 -5
- package/dist/src/lint/runner.js +1 -1
- package/dist/src/marketplace/exchange.js +18 -6
- package/dist/src/marketplace/provenance.js +3 -2
- package/dist/src/mcp/adapters/codex-runtime.js +46 -76
- package/dist/src/mcp/cli.mjs +22 -96
- package/dist/src/mcp/config-file.mjs +6 -2
- package/dist/src/mcp/config-layers.mjs +23 -7
- package/dist/src/mcp/grok-build-config.mjs +2 -1
- package/dist/src/mcp/muse-native-config.mjs +2 -1
- package/dist/src/mcp/profiles.js +18 -31
- package/dist/src/mcp/profiles.mjs +18 -32
- package/dist/src/mcp/registry.js +7 -27
- package/dist/src/mcp/registry.mjs +7 -28
- package/dist/src/mcp/server.mjs +34 -1
- package/dist/src/mcp/tools/agentic-sandbox.mjs +8 -7
- package/dist/src/mcp/tools/command-run.mjs +3 -2
- package/dist/src/mcp/tools/decision.mjs +49 -48
- package/dist/src/mcp/tools/discovery.mjs +46 -21
- package/dist/src/mcp/tools/orchestration.mjs +22 -22
- package/dist/src/mcp/tools/subsystems.mjs +9 -8
- package/dist/src/mcp/tools/worker-invoke.mjs +30 -6
- package/dist/src/mcp/tools/writer-profiles.mjs +1 -1
- package/dist/src/memory/audit.js +719 -0
- package/dist/src/memory/canonical-context.js +392 -13
- package/dist/src/memory/canonical-maintenance.js +95 -0
- package/dist/src/memory/cli-result.js +22 -0
- package/dist/src/memory/cli.js +176 -0
- package/dist/src/memory/context-pack.js +57 -6
- package/dist/src/memory/cost.js +512 -0
- package/dist/src/memory/firewall-classification.d.mts +7 -0
- package/dist/src/memory/firewall-classification.mjs +32 -0
- package/dist/src/memory/index.js +8 -0
- package/dist/src/memory/line-maintenance.js +68 -0
- package/dist/src/memory/maintenance-cli.js +286 -0
- package/dist/src/memory/maintenance-contract.js +136 -0
- package/dist/src/memory/maintenance-index.js +18 -0
- package/dist/src/memory/maintenance-owner.js +2 -0
- package/dist/src/memory/maintenance-record.js +138 -0
- package/dist/src/memory/maintenance.js +254 -0
- package/dist/src/memory/project-registry.js +2 -1
- package/dist/src/memory/provider-memory-adapter.js +154 -0
- package/dist/src/memory/recommend-cli.js +83 -0
- package/dist/src/memory/recommend.js +269 -0
- package/dist/src/memory/scheduled.js +81 -0
- package/dist/src/memory/taxonomy.js +44 -0
- package/dist/src/mission-protocol/codecs.js +19 -9
- package/dist/src/mission-protocol/worker-status.js +91 -1
- package/dist/src/models/config-loader.js +11 -1
- package/dist/src/models/model-capabilities.v1.json +74 -50
- package/dist/src/models/provider-policy.js +125 -62
- package/dist/src/models/resolver.js +45 -8
- package/dist/src/models/worker-installation.d.mts +8 -1
- package/dist/src/models/worker-installation.mjs +231 -38
- package/dist/src/models/wrapper-route.js +1 -1
- package/dist/src/output-modes/registry.js +8 -7
- package/dist/src/packages/adapters/git.js +99 -23
- package/dist/src/packages/adapters/gitea.js +8 -27
- package/dist/src/packages/adapters/github.js +7 -25
- package/dist/src/packages/registry.js +4 -4
- package/dist/src/plugin/metadata-validator.js +1 -1
- package/dist/src/process/cli-command.d.mts +5 -0
- package/dist/src/process/cli-command.mjs +42 -0
- package/dist/src/providers/deploy-version.d.mts +1 -0
- package/dist/src/providers/deploy-version.mjs +17 -0
- package/dist/src/providers/provider-definitions.js +19 -16
- package/dist/src/providers/skill-ownership.d.mts +11 -2
- package/dist/src/providers/skill-ownership.mjs +35 -17
- package/dist/src/rules/activation.d.mts +11 -2
- package/dist/src/rules/activation.mjs +82 -6
- package/dist/src/rules/inventory.js +1 -1
- package/dist/src/rules/rule-frontmatter.schema.json +2 -0
- package/dist/src/schema/zod-validation.d.mts +6 -0
- package/dist/src/schema/zod-validation.mjs +50 -0
- package/dist/src/serve/executor-registry.js +297 -20
- package/dist/src/serve/executor-token.d.mts +1 -0
- package/dist/src/serve/executor-token.mjs +8 -0
- package/dist/src/serve/shared-host-scheduler.js +1102 -31
- package/dist/src/serve/worker-invocation.js +124 -15
- package/dist/src/sessions/adapters/claude.js +19 -18
- package/dist/src/sessions/adapters/codex.js +10 -9
- package/dist/src/sessions/adapters/copilot.js +14 -13
- package/dist/src/sessions/adapters/cursor.js +19 -18
- package/dist/src/sessions/adapters/deepseek-harness.js +9 -8
- package/dist/src/sessions/adapters/factory.js +11 -10
- package/dist/src/sessions/adapters/generic.js +32 -23
- package/dist/src/sessions/adapters/grokbot.js +35 -35
- package/dist/src/sessions/adapters/hermes.js +20 -19
- package/dist/src/sessions/adapters/muse.js +50 -49
- package/dist/src/sessions/adapters/omp.js +5 -4
- package/dist/src/sessions/adapters/openclaw.js +30 -29
- package/dist/src/sessions/adapters/opencode.js +26 -26
- package/dist/src/sessions/adapters/openhuman.js +24 -23
- package/dist/src/sessions/adapters/pi.js +5 -4
- package/dist/src/sessions/adapters/windsurf.js +8 -8
- package/dist/src/sessions/analytics.js +10 -9
- package/dist/src/sessions/candidates.js +7 -6
- package/dist/src/sessions/contracts.js +63 -53
- package/dist/src/sessions/output-registration.js +11 -10
- package/dist/src/sessions/workspace-discovery.js +3 -4
- package/dist/src/smiths/context-pipeline/aiwg-md.js +18 -1
- package/dist/src/smiths/context-pipeline/claude-hook.js +46 -10
- package/dist/src/smiths/context-pipeline/context-file-safety.js +330 -9
- package/dist/src/smiths/context-pipeline/finalization.js +3 -2
- package/dist/src/smiths/context-pipeline/generator.js +7 -19
- package/dist/src/smiths/context-pipeline/legacy-inject.js +3 -10
- package/dist/src/smiths/context-pipeline/managed-hook.js +5 -5
- package/dist/src/smiths/context-pipeline/parallelism-section.js +72 -5
- package/dist/src/smiths/context-pipeline/workspace-context.js +110 -22
- package/dist/src/tracker/project-inputs.js +2 -0
- package/dist/src/update/checker.d.mts +4 -0
- package/dist/src/update/checker.mjs +14 -0
- package/dist/src/update/notifier.mjs +2 -4
- package/dist/src/writing/exemplar-selection.js +6 -6
- package/dist/src/writing/voice-evaluation.js +24 -23
- package/dist/src/writing/writer-migration.js +14 -13
- package/dist/src/writing/writer-profile.js +19 -18
- package/dist/src/writing/writing-brief.js +18 -17
- package/dist/src/writing/writing-receipt.js +47 -46
- package/package.json +5 -2
- package/schemas/decision/DecisionReview.schema.json +78 -1
- package/schemas/mission-v1.schema.json +3 -0
- package/tools/agents/deploy-agents.mjs +67 -39
- package/tools/agents/providers/antigravity.mjs +6 -1
- package/tools/agents/providers/base.mjs +24 -14
- package/tools/agents/providers/claude.mjs +6 -3
- package/tools/agents/providers/codex.mjs +54 -57
- package/tools/agents/providers/context-write.mjs +28 -0
- package/tools/agents/providers/copilot.mjs +13 -4
- package/tools/agents/providers/cursor.mjs +1 -1
- package/tools/agents/providers/deepseek-harness.mjs +1 -1
- package/tools/agents/providers/factory.mjs +7 -1
- package/tools/agents/providers/grok-build.mjs +18 -2
- package/tools/agents/providers/grokbot.mjs +1 -1
- package/tools/agents/providers/hermes.mjs +12 -15
- package/tools/agents/providers/muse-hooks.mjs +21 -14
- package/tools/agents/providers/muse.mjs +7 -2
- package/tools/agents/providers/omp.mjs +31 -5
- package/tools/agents/providers/opencode.mjs +14 -5
- package/tools/agents/providers/openhuman.mjs +1 -1
- package/tools/agents/providers/pi.mjs +1 -1
- package/tools/agents/providers/provider-prepare-coordinator.mjs +29 -9
- package/tools/agents/providers/rule-delivery.mjs +289 -80
- package/tools/agents/providers/warp.mjs +4 -1
- package/tools/agents/providers/windsurf.mjs +13 -3
- package/tools/cli/workspace-status.mjs +5 -0
- package/tools/commands/deploy-prompts-codex.mjs +11 -8
- package/tools/ralph-external/lib/codex-adapter.mjs +6 -2
- package/tools/ralph-external/lib/consecutive-failure-circuit-breaker.mjs +26 -0
- package/tools/ralph-external/lib/launcher-recovery-evidence.mjs +7 -1
- package/tools/ralph-external/lib/muse-adapter.mjs +12 -2
- package/tools/ralph-external/lib/recovery-probe.mjs +14 -4
- package/tools/ralph-external/lib/worker-health.mjs +1 -1
- package/tools/ralph-external/lib/worker-isolation.mjs +65 -9
- package/tools/ralph-external/process-monitor.mjs +49 -8
- package/tools/ralph-external/session-launcher.mjs +405 -35
- package/tools/skills/deploy-skills-codex.mjs +11 -7
- package/vscode-extension/schemas/aiwg.config.v1.json +11 -1
|
@@ -13,6 +13,7 @@
|
|
|
13
13
|
* @architecture .aiwg/architecture/design-manifest-schema.md
|
|
14
14
|
*/
|
|
15
15
|
import { z } from 'zod';
|
|
16
|
+
import { integer, dateTime, url } from '../schema/zod-validation.mjs';
|
|
16
17
|
import { PlatformCompatibilitySchema, DeploymentConfigSchema, MemoryFootprintSchema, DeprecationSchema, } from './validation.js';
|
|
17
18
|
// ============================================
|
|
18
19
|
// Limits (from #1042 threat model + #1044 design)
|
|
@@ -58,7 +59,7 @@ const ArtifactListsSchema = z.object({
|
|
|
58
59
|
behaviors: z.array(z.string()).max(50).optional(),
|
|
59
60
|
gatePacks: z.array(z.string().min(1).max(128)).max(50).optional(),
|
|
60
61
|
});
|
|
61
|
-
const EntryPathsSchema = z.
|
|
62
|
+
const EntryPathsSchema = z.strictObject({
|
|
62
63
|
agents: safeRelativePath.optional(),
|
|
63
64
|
skills: safeRelativePath.optional(),
|
|
64
65
|
rules: safeRelativePath.optional(),
|
|
@@ -68,37 +69,37 @@ const EntryPathsSchema = z.object({
|
|
|
68
69
|
commands: safeRelativePath.optional(),
|
|
69
70
|
behaviors: safeRelativePath.optional(),
|
|
70
71
|
gatePacks: safeRelativePath.optional(),
|
|
71
|
-
})
|
|
72
|
-
export const AddonConfigSchema = z.
|
|
72
|
+
});
|
|
73
|
+
export const AddonConfigSchema = z.strictObject({
|
|
73
74
|
entry: EntryPathsSchema.optional(),
|
|
74
75
|
...ArtifactListsSchema.shape,
|
|
75
76
|
core: z.boolean().optional(),
|
|
76
77
|
autoInstall: z.boolean().optional(),
|
|
77
|
-
})
|
|
78
|
-
export const FrameworkConfigSchema = z.
|
|
78
|
+
});
|
|
79
|
+
export const FrameworkConfigSchema = z.strictObject({
|
|
79
80
|
path: safeRelativePath.optional(),
|
|
80
81
|
files: z.array(safeRelativePath).max(100).optional(),
|
|
81
82
|
ignore: z.array(safeRelativePath).max(100).optional(),
|
|
82
83
|
gatePacks: z.array(z.string().min(1).max(128)).max(50).optional(),
|
|
83
|
-
entry: z.
|
|
84
|
+
entry: z.strictObject({
|
|
84
85
|
gatePacks: safeRelativePath.optional(),
|
|
85
|
-
}).
|
|
86
|
-
contextContributions: z.
|
|
86
|
+
}).optional(),
|
|
87
|
+
contextContributions: z.strictObject({
|
|
87
88
|
hookFragment: safeRelativePath.optional(),
|
|
88
89
|
sectionsDir: safeRelativePath.optional(),
|
|
89
90
|
sectionsManifest: safeRelativePath.optional(),
|
|
90
|
-
priority:
|
|
91
|
+
priority: integer().min(0).max(100).optional(),
|
|
91
92
|
description: z.string().max(512).optional(),
|
|
92
|
-
}).
|
|
93
|
-
})
|
|
94
|
-
export const ExtensionConfigSchema = z.
|
|
93
|
+
}).optional(),
|
|
94
|
+
});
|
|
95
|
+
export const ExtensionConfigSchema = z.strictObject({
|
|
95
96
|
entry: EntryPathsSchema.optional(),
|
|
96
97
|
...ArtifactListsSchema.shape,
|
|
97
|
-
})
|
|
98
|
-
export const PluginConfigSchema = z.
|
|
98
|
+
});
|
|
99
|
+
export const PluginConfigSchema = z.strictObject({
|
|
99
100
|
payloadType: z.enum(['addon', 'framework', 'extension']),
|
|
100
101
|
payloadPath: safeRelativePath,
|
|
101
|
-
})
|
|
102
|
+
});
|
|
102
103
|
const ProviderCapabilityFeatureSchema = z.enum([
|
|
103
104
|
'cron',
|
|
104
105
|
'agent_teams',
|
|
@@ -116,11 +117,11 @@ const ProviderCapabilityEmulationSchema = z.enum([
|
|
|
116
117
|
'aiwg-daemon',
|
|
117
118
|
'external-trigger',
|
|
118
119
|
]).nullable();
|
|
119
|
-
const ProviderCapabilityOverridesSchema = z.
|
|
120
|
-
nativeFeatures: z.
|
|
121
|
-
emulation: z.
|
|
122
|
-
})
|
|
123
|
-
export const ProviderConfigSchema = z.
|
|
120
|
+
const ProviderCapabilityOverridesSchema = z.strictObject({
|
|
121
|
+
nativeFeatures: z.partialRecord(ProviderCapabilityFeatureSchema, z.boolean()).optional(),
|
|
122
|
+
emulation: z.partialRecord(ProviderCapabilityFeatureSchema, ProviderCapabilityEmulationSchema).optional(),
|
|
123
|
+
});
|
|
124
|
+
export const ProviderConfigSchema = z.strictObject({
|
|
124
125
|
extends: z.enum([
|
|
125
126
|
'claude',
|
|
126
127
|
'codex',
|
|
@@ -142,7 +143,7 @@ export const ProviderConfigSchema = z.object({
|
|
|
142
143
|
displayName: z.string().min(1).max(128).optional(),
|
|
143
144
|
aliases: z.array(z.string().min(1).max(64)).max(20).optional(),
|
|
144
145
|
capabilities: ProviderCapabilityOverridesSchema.optional(),
|
|
145
|
-
})
|
|
146
|
+
});
|
|
146
147
|
/**
|
|
147
148
|
* Review attestation for one gate metric provider (#2831).
|
|
148
149
|
*
|
|
@@ -152,11 +153,11 @@ export const ProviderConfigSchema = z.object({
|
|
|
152
153
|
* registration refuses absent attestations and digest mismatches. Null or
|
|
153
154
|
* unknown digests never verify: they fail closed.
|
|
154
155
|
*/
|
|
155
|
-
export const GateProviderReviewSchema = z.
|
|
156
|
+
export const GateProviderReviewSchema = z.strictObject({
|
|
156
157
|
reviewer: z.string().min(1).max(128),
|
|
157
|
-
reviewedAt:
|
|
158
|
+
reviewedAt: dateTime(),
|
|
158
159
|
codeDigest: z.string().regex(/^sha256:[0-9a-f]{64}$/, 'must be a sha256 digest'),
|
|
159
|
-
})
|
|
160
|
+
});
|
|
160
161
|
/**
|
|
161
162
|
* One addon/extension gate metric provider declared by a bundle manifest
|
|
162
163
|
* (#2831). The module is loaded ONLY through the gates registry from this
|
|
@@ -165,16 +166,16 @@ export const GateProviderReviewSchema = z.object({
|
|
|
165
166
|
* providers remain the default; this field is optional and disabled unless
|
|
166
167
|
* the caller explicitly enables bundle providers.
|
|
167
168
|
*/
|
|
168
|
-
export const GateProviderEntrySchema = z.
|
|
169
|
+
export const GateProviderEntrySchema = z.strictObject({
|
|
169
170
|
id: z.string().min(1).max(128).regex(/^[A-Za-z0-9._-]+\/[A-Za-z0-9._-]+$/, 'must be a namespaced provider id <scope>/<name> (alphanumeric plus . _ -)'),
|
|
170
171
|
version: z.string().regex(/^\d+\.\d+\.\d+/, 'CalVer or SemVer (X.Y.Z[...])'),
|
|
171
172
|
module: safeModuleFile,
|
|
172
173
|
description: z.string().min(1).max(512),
|
|
173
174
|
review: GateProviderReviewSchema.optional(),
|
|
174
175
|
reviewFile: safeJsonFile.optional(),
|
|
175
|
-
}).
|
|
176
|
-
export const GateProvidersSchema = z.array(GateProviderEntrySchema).max(20).refine((entries) => new Set(entries.map((entry) => entry.id)).size === entries.length, {
|
|
177
|
-
export const CliCommandsSchema = z.
|
|
176
|
+
}).refine((entry) => (entry.review !== undefined) !== (entry.reviewFile !== undefined), { error: 'exactly one of review or reviewFile is required' });
|
|
177
|
+
export const GateProvidersSchema = z.array(GateProviderEntrySchema).max(20).refine((entries) => new Set(entries.map((entry) => entry.id)).size === entries.length, { error: 'gate provider ids must be unique within a bundle' }).refine((entries) => new Set(entries.map((entry) => entry.module)).size === entries.length, { error: 'gate provider modules must be unique within a bundle' });
|
|
178
|
+
export const CliCommandsSchema = z.strictObject({
|
|
178
179
|
namespace: z.string()
|
|
179
180
|
.min(1)
|
|
180
181
|
.max(64)
|
|
@@ -184,7 +185,7 @@ export const CliCommandsSchema = z.object({
|
|
|
184
185
|
subcommands: z.record(z.string()
|
|
185
186
|
.min(1)
|
|
186
187
|
.max(64)
|
|
187
|
-
.regex(bundleNamePattern, 'kebab-case alphanumeric, no leading/trailing hyphen'), z.
|
|
188
|
+
.regex(bundleNamePattern, 'kebab-case alphanumeric, no leading/trailing hyphen'), z.strictObject({
|
|
188
189
|
file: safeModuleFile,
|
|
189
190
|
description: z.string().min(1).max(512),
|
|
190
191
|
hook_event: z.enum([
|
|
@@ -195,14 +196,14 @@ export const CliCommandsSchema = z.object({
|
|
|
195
196
|
'PostToolUse',
|
|
196
197
|
'FeatureComplete',
|
|
197
198
|
]).optional(),
|
|
198
|
-
})
|
|
199
|
-
|
|
199
|
+
})).refine((commands) => Object.keys(commands).length > 0, {
|
|
200
|
+
error: 'at least one CLI subcommand is required',
|
|
200
201
|
}),
|
|
201
|
-
})
|
|
202
|
+
});
|
|
202
203
|
// ============================================
|
|
203
204
|
// Top-level BundleManifestSchema
|
|
204
205
|
// ============================================
|
|
205
|
-
export const BundleManifestSchema = z.
|
|
206
|
+
export const BundleManifestSchema = z.strictObject({
|
|
206
207
|
// Required core fields
|
|
207
208
|
id: z.string()
|
|
208
209
|
.min(1)
|
|
@@ -219,7 +220,7 @@ export const BundleManifestSchema = z.object({
|
|
|
219
220
|
// Optional standard metadata
|
|
220
221
|
author: z.string().max(128).optional(),
|
|
221
222
|
license: z.string().max(64).optional(),
|
|
222
|
-
repository:
|
|
223
|
+
repository: url().max(512).optional(),
|
|
223
224
|
// Type-discriminated nested config (exactly one matches `type`)
|
|
224
225
|
addonConfig: AddonConfigSchema.optional(),
|
|
225
226
|
frameworkConfig: FrameworkConfigSchema.optional(),
|
|
@@ -242,7 +243,6 @@ export const BundleManifestSchema = z.object({
|
|
|
242
243
|
// providers remain the default when this field is absent.
|
|
243
244
|
gateProviders: GateProvidersSchema.optional(),
|
|
244
245
|
})
|
|
245
|
-
.strict()
|
|
246
246
|
.refine((m) => {
|
|
247
247
|
// Discriminator alignment: type must match the present *Config block(s)
|
|
248
248
|
const present = {
|
|
@@ -258,18 +258,45 @@ export const BundleManifestSchema = z.object({
|
|
|
258
258
|
return presentCount === 0 || (presentCount === 1 && present.extension);
|
|
259
259
|
}
|
|
260
260
|
return presentCount === 1 && present[m.type];
|
|
261
|
-
}, {
|
|
261
|
+
}, { error: 'type must match its corresponding *Config block (addon→addonConfig, framework→frameworkConfig, plugin→pluginConfig, provider→providerConfig; extension may omit extensionConfig)' });
|
|
262
262
|
/**
|
|
263
263
|
* Convert a Zod error into the structured ManifestValidationError shape used
|
|
264
264
|
* by discovery and `aiwg validate-metadata`.
|
|
265
265
|
*/
|
|
266
|
-
export function zodErrorToValidationErrors(err, manifestPath) {
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
266
|
+
export function zodErrorToValidationErrors(err, manifestPath, input) {
|
|
267
|
+
const hasInput = arguments.length >= 3;
|
|
268
|
+
const issues = err.issues.flatMap(issue => {
|
|
269
|
+
// Partial enum maps report unknown keys at the map in v4; discovery's
|
|
270
|
+
// existing field contract identifies each rejected capability key.
|
|
271
|
+
if (issue.code === 'unrecognized_keys'
|
|
272
|
+
&& issue.path.length === 3 && issue.path[0] === 'providerConfig'
|
|
273
|
+
&& issue.path[1] === 'capabilities'
|
|
274
|
+
&& ['nativeFeatures', 'emulation'].includes(String(issue.path[2]))) {
|
|
275
|
+
return issue.keys.map(key => ({ ...issue, path: [...issue.path, key] }));
|
|
276
|
+
}
|
|
277
|
+
return [issue];
|
|
278
|
+
});
|
|
279
|
+
return issues.map((issue) => {
|
|
280
|
+
let actual = 'invalid';
|
|
281
|
+
if (issue.code === 'invalid_type' && hasInput) {
|
|
282
|
+
let value = input;
|
|
283
|
+
for (const segment of issue.path) {
|
|
284
|
+
value = value !== null && typeof value === 'object' && Object.hasOwn(value, segment)
|
|
285
|
+
? value[segment] : undefined;
|
|
286
|
+
}
|
|
287
|
+
// Emit only the former type classification, never rejected values.
|
|
288
|
+
actual = value === null ? 'null' : Array.isArray(value) ? 'array'
|
|
289
|
+
: typeof value === 'number' && Number.isNaN(value) ? 'nan'
|
|
290
|
+
: issue.expected === 'int' && typeof value === 'number' ? 'float'
|
|
291
|
+
: typeof value;
|
|
292
|
+
}
|
|
293
|
+
return {
|
|
294
|
+
path: manifestPath,
|
|
295
|
+
field: issue.path.join('.') || '(root)',
|
|
296
|
+
expected: issue.message,
|
|
297
|
+
actual,
|
|
298
|
+
severity: 'error',
|
|
299
|
+
};
|
|
300
|
+
});
|
|
274
301
|
}
|
|
275
302
|
//# sourceMappingURL=manifest.js.map
|
|
@@ -228,7 +228,7 @@ export async function loadAndValidateManifest(manifestPath, expectedType, projec
|
|
|
228
228
|
}
|
|
229
229
|
const result = BundleManifestSchema.safeParse(parsed);
|
|
230
230
|
if (!result.success) {
|
|
231
|
-
return { errors: zodErrorToValidationErrors(result.error, manifestPath) };
|
|
231
|
+
return { errors: zodErrorToValidationErrors(result.error, manifestPath, parsed) };
|
|
232
232
|
}
|
|
233
233
|
const manifest = result.data;
|
|
234
234
|
// Cross-check: manifest declared type must match the directory it lives in.
|
|
@@ -21,6 +21,7 @@
|
|
|
21
21
|
import { readFile, writeFile, access } from 'fs/promises';
|
|
22
22
|
import { join } from 'path';
|
|
23
23
|
import { execFile } from 'child_process';
|
|
24
|
+
import { helperEnvironment } from '../process/cli-command.mjs';
|
|
24
25
|
import { promisify } from 'util';
|
|
25
26
|
const execFileP = promisify(execFile);
|
|
26
27
|
/**
|
|
@@ -166,6 +167,7 @@ export async function checkBundleManifestIgnored(projectDir, manifestRelPath) {
|
|
|
166
167
|
// 1 if not ignored, 128 on error. We want a tristate.
|
|
167
168
|
await execFileP('git', ['check-ignore', '-q', manifestRelPath], {
|
|
168
169
|
cwd: projectDir,
|
|
170
|
+
env: helperEnvironment(),
|
|
169
171
|
});
|
|
170
172
|
// exit 0 → ignored
|
|
171
173
|
return true;
|
|
@@ -10,6 +10,7 @@ import { access, mkdir, readFile, readdir, rm, writeFile } from 'fs/promises';
|
|
|
10
10
|
import { basename, dirname, isAbsolute, join, resolve } from 'path';
|
|
11
11
|
import { homedir } from 'os';
|
|
12
12
|
import { z } from 'zod';
|
|
13
|
+
import { integer } from '../schema/zod-validation.mjs';
|
|
13
14
|
import { getProviderDefinition, normalizeProviderDefinitionId, } from '../providers/provider-definitions.js';
|
|
14
15
|
import { resolveHermesHome } from '../providers/hermes-home.js';
|
|
15
16
|
import { OPERATIONAL_SHOW_TYPES } from '../artifacts/types.js';
|
|
@@ -18,45 +19,45 @@ import { appendAiwgSourceTrackBlock } from './project-local-gitignore.js';
|
|
|
18
19
|
import { discoverProjectLocalBundles } from './project-local-discovery.js';
|
|
19
20
|
import { enumerateBundleArtifacts } from './shadow-resolver.js';
|
|
20
21
|
const OWNERSHIP_MARKER = '.aiwg-project-quickref.json';
|
|
21
|
-
const ShowHintSchema = z.
|
|
22
|
+
const ShowHintSchema = z.strictObject({
|
|
22
23
|
type: z.enum(OPERATIONAL_SHOW_TYPES),
|
|
23
24
|
name: z.string().min(1).max(128),
|
|
24
|
-
})
|
|
25
|
-
const QuickrefEntrySchema = z.
|
|
25
|
+
});
|
|
26
|
+
const QuickrefEntrySchema = z.strictObject({
|
|
26
27
|
title: z.string().min(1).max(128),
|
|
27
28
|
summary: z.string().min(1).max(512),
|
|
28
29
|
discover: z.array(z.string().min(1).max(256)).max(10).default([]),
|
|
29
30
|
show: z.array(ShowHintSchema).max(20).default([]),
|
|
30
|
-
}).
|
|
31
|
-
export const ProjectQuickrefSchema = z.
|
|
31
|
+
}).refine(entry => entry.discover.length > 0 || entry.show.length > 0, { error: 'each entry must provide at least one discover or show hint' });
|
|
32
|
+
export const ProjectQuickrefSchema = z.strictObject({
|
|
32
33
|
version: z.literal('1'),
|
|
33
|
-
project: z.
|
|
34
|
+
project: z.strictObject({
|
|
34
35
|
id: z.string().regex(/^[a-z0-9]([a-z0-9-]*[a-z0-9])?$/, 'must be kebab-case'),
|
|
35
36
|
name: z.string().min(1).max(128),
|
|
36
37
|
description: z.string().min(1).max(512),
|
|
37
|
-
})
|
|
38
|
+
}),
|
|
38
39
|
precedence: z.string().min(1).max(1024),
|
|
39
40
|
entries: z.array(QuickrefEntrySchema).min(1).max(50),
|
|
40
|
-
})
|
|
41
|
-
const QuickrefOverrideSchema = z.
|
|
41
|
+
});
|
|
42
|
+
const QuickrefOverrideSchema = z.strictObject({
|
|
42
43
|
title: z.string().min(1).max(128).optional(),
|
|
43
44
|
summary: z.string().min(1).max(512).optional(),
|
|
44
45
|
discover: z.array(z.string().min(1).max(256)).max(10).optional(),
|
|
45
46
|
show: z.array(ShowHintSchema).max(20).optional(),
|
|
46
47
|
hidden: z.boolean().optional(),
|
|
47
|
-
order:
|
|
48
|
-
})
|
|
49
|
-
export const ProjectQuickrefConfigSchema = z.
|
|
48
|
+
order: integer().optional(),
|
|
49
|
+
});
|
|
50
|
+
export const ProjectQuickrefConfigSchema = z.strictObject({
|
|
50
51
|
version: z.literal('1'),
|
|
51
52
|
project: ProjectQuickrefSchema.shape.project.optional(),
|
|
52
53
|
precedence: z.string().min(1).max(1024).optional(),
|
|
53
54
|
entries: z.array(QuickrefEntrySchema).max(50).default([]),
|
|
54
|
-
discovery: z.
|
|
55
|
+
discovery: z.strictObject({
|
|
55
56
|
enabled: z.boolean().default(true),
|
|
56
57
|
excludeBundles: z.array(z.string().min(1)).max(200).default([]),
|
|
57
|
-
overrides: z.record(z.string(), QuickrefOverrideSchema).
|
|
58
|
-
}).
|
|
59
|
-
})
|
|
58
|
+
overrides: z.record(z.string(), QuickrefOverrideSchema).prefault({}),
|
|
59
|
+
}).prefault({ enabled: true, excludeBundles: [], overrides: {} }),
|
|
60
|
+
});
|
|
60
61
|
function sha256(content) {
|
|
61
62
|
return createHash('sha256').update(content).digest('hex');
|
|
62
63
|
}
|
|
@@ -281,7 +282,7 @@ export function renderProjectQuickref(definition) {
|
|
|
281
282
|
lines.push(`- Discover: \`aiwg discover ${JSON.stringify(phrase)}\``);
|
|
282
283
|
}
|
|
283
284
|
for (const hint of entry.show) {
|
|
284
|
-
lines.push(`- Fetch: \`aiwg show ${hint.type} ${hint.name}\``);
|
|
285
|
+
lines.push(`- Fetch: \`aiwg show ${hint.type} ${hint.name} --body\``);
|
|
285
286
|
}
|
|
286
287
|
lines.push('');
|
|
287
288
|
}
|
|
@@ -10,6 +10,7 @@
|
|
|
10
10
|
* @version 1.0.0
|
|
11
11
|
*/
|
|
12
12
|
import { z } from 'zod';
|
|
13
|
+
import { integer, dateTime, url, number } from '../schema/zod-validation.mjs';
|
|
13
14
|
// ============================================
|
|
14
15
|
// Core Enums & Primitives
|
|
15
16
|
// ============================================
|
|
@@ -77,13 +78,13 @@ export const PlatformCompatibilitySchema = z.object({
|
|
|
77
78
|
codex: PlatformSupportSchema.optional(),
|
|
78
79
|
opencode: PlatformSupportSchema.optional(),
|
|
79
80
|
generic: PlatformSupportSchema.optional(),
|
|
80
|
-
}).refine((data) => Object.values(data).some((val) => val !== undefined), {
|
|
81
|
+
}).refine((data) => Object.values(data).some((val) => val !== undefined), { error: 'At least one platform must be specified' });
|
|
81
82
|
/**
|
|
82
83
|
* Deployment configuration
|
|
83
84
|
*/
|
|
84
85
|
export const DeploymentConfigSchema = z.object({
|
|
85
86
|
pathTemplate: z.string().min(1, 'Path template is required'),
|
|
86
|
-
pathOverrides: z.record(z.string()).optional(),
|
|
87
|
+
pathOverrides: z.record(z.string(), z.string()).optional(),
|
|
87
88
|
additionalFiles: z.array(z.string()).optional(),
|
|
88
89
|
autoInstall: z.boolean().optional().default(false),
|
|
89
90
|
core: z.boolean().optional().default(false),
|
|
@@ -106,7 +107,7 @@ export const MemoryFootprintSchema = z.object({
|
|
|
106
107
|
* Deprecation information
|
|
107
108
|
*/
|
|
108
109
|
export const DeprecationSchema = z.object({
|
|
109
|
-
date:
|
|
110
|
+
date: dateTime({ error: 'Date must be ISO 8601 format' }),
|
|
110
111
|
successor: z.string().optional(),
|
|
111
112
|
reason: z.string().min(1, 'Deprecation reason is required'),
|
|
112
113
|
});
|
|
@@ -114,7 +115,7 @@ export const DeprecationSchema = z.object({
|
|
|
114
115
|
* Installation state
|
|
115
116
|
*/
|
|
116
117
|
export const InstallationSchema = z.object({
|
|
117
|
-
installedAt:
|
|
118
|
+
installedAt: dateTime({ error: 'Install timestamp must be ISO 8601 format' }),
|
|
118
119
|
installedFrom: z.enum(['builtin', 'registry', 'local', 'git']),
|
|
119
120
|
installedPath: z.string().min(1),
|
|
120
121
|
enabled: z.boolean(),
|
|
@@ -142,7 +143,7 @@ export const AgentMetadataSchema = z.object({
|
|
|
142
143
|
}),
|
|
143
144
|
tools: z.array(z.string()).min(1, 'At least one tool is required'),
|
|
144
145
|
template: z.string().optional(),
|
|
145
|
-
maxTools:
|
|
146
|
+
maxTools: integer().positive().optional(),
|
|
146
147
|
canDelegate: z.boolean().optional(),
|
|
147
148
|
readOnly: z.boolean().optional(),
|
|
148
149
|
workflow: z.array(z.string()).optional(),
|
|
@@ -157,8 +158,8 @@ export const CommandArgumentSchema = z.object({
|
|
|
157
158
|
description: z.string().min(1),
|
|
158
159
|
required: z.boolean(),
|
|
159
160
|
type: z.enum(['string', 'number', 'boolean']),
|
|
160
|
-
default: z.union([z.string(),
|
|
161
|
-
position:
|
|
161
|
+
default: z.union([z.string(), number(), z.boolean()]).optional(),
|
|
162
|
+
position: integer().nonnegative().optional(),
|
|
162
163
|
});
|
|
163
164
|
/**
|
|
164
165
|
* Command option definition
|
|
@@ -167,7 +168,7 @@ export const CommandOptionSchema = z.object({
|
|
|
167
168
|
name: z.string().min(1),
|
|
168
169
|
description: z.string().min(1),
|
|
169
170
|
type: z.enum(['string', 'boolean', 'number', 'array']),
|
|
170
|
-
default: z.union([z.string(), z.boolean(),
|
|
171
|
+
default: z.union([z.string(), z.boolean(), number()]).optional(),
|
|
171
172
|
short: z.string().length(1).optional(),
|
|
172
173
|
long: z.string().min(2).optional(),
|
|
173
174
|
});
|
|
@@ -229,11 +230,13 @@ export const SkillReferenceSchema = z.object({
|
|
|
229
230
|
* natural-language invocation. Do NOT relax this rule — a blank description
|
|
230
231
|
* is what caused the 107-file regression we are guarding against.
|
|
231
232
|
*/
|
|
232
|
-
export const SkillFrontmatterSchema = z.
|
|
233
|
+
export const SkillFrontmatterSchema = z.looseObject({
|
|
233
234
|
name: z.string().min(1, 'Skill name is required'),
|
|
234
235
|
description: z
|
|
235
236
|
.string({
|
|
236
|
-
|
|
237
|
+
error: issue => issue.input === undefined
|
|
238
|
+
? 'Description is required (Codex rejects SKILL.md without it)'
|
|
239
|
+
: undefined,
|
|
237
240
|
})
|
|
238
241
|
.min(1, 'Description is required and must be non-empty'),
|
|
239
242
|
version: z.string().regex(/^\d+\.\d+\.\d+/, 'Version must be semver or CalVer format (e.g., 1.0.0)').optional(),
|
|
@@ -247,7 +250,7 @@ export const SkillFrontmatterSchema = z.object({
|
|
|
247
250
|
triggers: z
|
|
248
251
|
.array(z
|
|
249
252
|
.string()
|
|
250
|
-
.refine((s) => s.trim().length > 0, {
|
|
253
|
+
.refine((s) => s.trim().length > 0, { error: 'trigger phrases must be non-empty' }))
|
|
251
254
|
.min(1, 'triggers is declared but empty — add at least one phrase or remove the field (empty-triggers anti-pattern, #1623)')
|
|
252
255
|
.optional(),
|
|
253
256
|
aliases: z.array(z.string()).optional(),
|
|
@@ -263,8 +266,8 @@ export const SkillFrontmatterSchema = z.object({
|
|
|
263
266
|
context: z.enum(['fork', 'inherit']).optional(),
|
|
264
267
|
author: z.string().optional(),
|
|
265
268
|
license: z.string().optional(),
|
|
266
|
-
metadata: z.record(z.unknown()).optional(),
|
|
267
|
-
})
|
|
269
|
+
metadata: z.record(z.string(), z.unknown()).optional(),
|
|
270
|
+
});
|
|
268
271
|
/**
|
|
269
272
|
* Validate SKILL.md frontmatter.
|
|
270
273
|
*
|
|
@@ -313,10 +316,10 @@ export const SkillMetadataSchema = z.object({
|
|
|
313
316
|
export const HookMetadataSchema = z.object({
|
|
314
317
|
type: z.literal('hook'),
|
|
315
318
|
event: HookEventSchema,
|
|
316
|
-
priority:
|
|
319
|
+
priority: integer().optional().default(100),
|
|
317
320
|
canModify: z.boolean().optional().default(false),
|
|
318
321
|
canBlock: z.boolean().optional().default(false),
|
|
319
|
-
configSchema: z.record(z.unknown()).optional(),
|
|
322
|
+
configSchema: z.record(z.string(), z.unknown()).optional(),
|
|
320
323
|
});
|
|
321
324
|
/**
|
|
322
325
|
* Tool-specific metadata
|
|
@@ -326,11 +329,11 @@ export const ToolMetadataSchema = z.object({
|
|
|
326
329
|
category: z.enum(['core', 'languages', 'utilities', 'custom']),
|
|
327
330
|
executable: z.string().min(1, 'Executable path is required'),
|
|
328
331
|
verificationStatus: z.enum(['verified', 'unverified']).optional(),
|
|
329
|
-
lastVerified:
|
|
332
|
+
lastVerified: dateTime().optional(),
|
|
330
333
|
manPage: z.string().optional(),
|
|
331
334
|
aliases: z.array(z.string()).optional(),
|
|
332
335
|
relatedTools: z.array(z.string()).optional(),
|
|
333
|
-
platformNotes: z.record(z.string()).optional(),
|
|
336
|
+
platformNotes: z.record(z.string(), z.string()).optional(),
|
|
334
337
|
installHint: z.string().optional(),
|
|
335
338
|
});
|
|
336
339
|
/**
|
|
@@ -348,7 +351,7 @@ export const MCPServerMetadataSchema = z.object({
|
|
|
348
351
|
type: z.literal('mcp-server'),
|
|
349
352
|
mcpVersion: z.string().min(1, 'MCP version is required'),
|
|
350
353
|
transport: z.enum(['stdio', 'http']),
|
|
351
|
-
port:
|
|
354
|
+
port: integer().positive().optional(),
|
|
352
355
|
capabilities: z.object({
|
|
353
356
|
tools: z.boolean(),
|
|
354
357
|
resources: z.boolean(),
|
|
@@ -358,9 +361,9 @@ export const MCPServerMetadataSchema = z.object({
|
|
|
358
361
|
}),
|
|
359
362
|
sourceType: z.enum(['cli', 'api', 'catalog', 'nl', 'extension']),
|
|
360
363
|
sourceCommand: z.string().optional(),
|
|
361
|
-
sourceBaseUrl:
|
|
364
|
+
sourceBaseUrl: url().optional(),
|
|
362
365
|
workingDirectory: z.string().optional(),
|
|
363
|
-
environment: z.record(z.string()).optional(),
|
|
366
|
+
environment: z.record(z.string(), z.string()).optional(),
|
|
364
367
|
tools: z.array(MCPToolSummarySchema).optional(),
|
|
365
368
|
resources: z.array(z.string()).optional(),
|
|
366
369
|
prompts: z.array(z.string()).optional(),
|
|
@@ -379,8 +382,8 @@ export const FrameworkMetadataSchema = z.object({
|
|
|
379
382
|
templates: z.array(z.string()).optional(),
|
|
380
383
|
prompts: z.array(z.string()).optional(),
|
|
381
384
|
}),
|
|
382
|
-
configSchema: z.record(z.unknown()).optional(),
|
|
383
|
-
defaultConfig: z.record(z.unknown()).optional(),
|
|
385
|
+
configSchema: z.record(z.string(), z.unknown()).optional(),
|
|
386
|
+
defaultConfig: z.record(z.string(), z.unknown()).optional(),
|
|
384
387
|
});
|
|
385
388
|
/**
|
|
386
389
|
* Addon-specific metadata
|
|
@@ -476,15 +479,15 @@ export const ExtensionSchema = z.object({
|
|
|
476
479
|
requires: z.array(z.string()).optional(),
|
|
477
480
|
recommends: z.array(z.string()).optional(),
|
|
478
481
|
conflicts: z.array(z.string()).optional(),
|
|
479
|
-
systemDependencies: z.record(z.string()).optional(),
|
|
482
|
+
systemDependencies: z.record(z.string(), z.string()).optional(),
|
|
480
483
|
// Metadata & Documentation
|
|
481
484
|
author: z.string().optional(),
|
|
482
485
|
license: z.string().optional(),
|
|
483
|
-
repository:
|
|
484
|
-
homepage:
|
|
485
|
-
bugs:
|
|
486
|
-
documentation: z.record(z.string()).optional(),
|
|
487
|
-
researchCompliance: z.record(z.array(z.string())).optional(),
|
|
486
|
+
repository: url().optional(),
|
|
487
|
+
homepage: url().optional(),
|
|
488
|
+
bugs: url().optional(),
|
|
489
|
+
documentation: z.record(z.string(), z.string()).optional(),
|
|
490
|
+
researchCompliance: z.record(z.string(), z.array(z.string())).optional(),
|
|
488
491
|
memory: MemoryFootprintSchema.optional(),
|
|
489
492
|
// Type-Specific Data
|
|
490
493
|
metadata: ExtensionMetadataSchema,
|
|
@@ -495,7 +498,7 @@ export const ExtensionSchema = z.object({
|
|
|
495
498
|
// Validation & Quality
|
|
496
499
|
checksum: z.string().optional(),
|
|
497
500
|
signature: SignatureSchema.optional(),
|
|
498
|
-
}).refine((data) => data.type === data.metadata.type, {
|
|
501
|
+
}).refine((data) => data.type === data.metadata.type, { error: 'Extension type must match metadata type' });
|
|
499
502
|
/**
|
|
500
503
|
* Validate an extension manifest
|
|
501
504
|
*
|