@acidicsoil/portable-capabilities 0.1.13 → 0.1.15

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/CHANGELOG.md CHANGED
@@ -1,5 +1,17 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.1.15
4
+
5
+ ### Patch Changes
6
+
7
+ - [#94](https://github.com/AcidicSoil/portable-capabilities/pull/94) [`abdfc16`](https://github.com/AcidicSoil/portable-capabilities/commit/abdfc16269795747b42b97a32b1b3c6d121f6830) Thanks [@AcidicSoil](https://github.com/AcidicSoil)! - Require complete runtime evidence for negotiated surfaces and gate automatic installation paths on usable location evidence.
8
+
9
+ ## 0.1.14
10
+
11
+ ### Patch Changes
12
+
13
+ - [#91](https://github.com/AcidicSoil/portable-capabilities/pull/91) [`9eed159`](https://github.com/AcidicSoil/portable-capabilities/commit/9eed159a134a688765c574f76ae9610f585f6dbf) Thanks [@AcidicSoil](https://github.com/AcidicSoil)! - Emit the input schema referenced by generated skills and verify referenced resources are installed across supported runtimes.
14
+
3
15
  ## 0.1.13
4
16
 
5
17
  ### Patch Changes
@@ -3684,6 +3684,15 @@ function resolveRuntimeEvidence(claim4, runtimeVersion) {
3684
3684
  reason: !applicable ? "version-inapplicable" : !sufficientState ? "insufficient-evidence" : !verified ? "unverified" : !confident ? "low-confidence" : !sourceComplete ? "incomplete-source" : claim4.stability === "deprecated" ? "deprecated" : "usable"
3685
3685
  };
3686
3686
  }
3687
+ function areRuntimeEvidenceClaimsUsable(claimIds, runtimeId, claims, runtimeVersion) {
3688
+ if (claimIds.length === 0) return false;
3689
+ return claimIds.every((claimId) => {
3690
+ const claim4 = claims.find(
3691
+ (candidate) => candidate.id === claimId && candidate.runtimeId === runtimeId
3692
+ );
3693
+ return claim4 !== void 0 && resolveRuntimeEvidence(claim4, runtimeVersion).usableForAutomaticInstall;
3694
+ });
3695
+ }
3687
3696
 
3688
3697
  // packages/compiler/src/negotiation/adapter-registry.ts
3689
3698
  var adapterIds = Object.freeze([
@@ -3706,7 +3715,9 @@ function negotiateCapability(artifact, descriptor, claims, version) {
3706
3715
  return artifact.invocationIntents.map((intent) => {
3707
3716
  const surface = descriptor.surfaces.find(
3708
3717
  (x) => x.semanticKind === intent && (x.versionRange === void 0 || isRuntimeVersionInRange(x.versionRange, version)) && x.evidenceClaimIds.some((claimId) => {
3709
- const claim4 = claims.find((candidate) => candidate.id === claimId);
3718
+ const claim4 = claims.find(
3719
+ (candidate) => candidate.id === claimId && candidate.runtimeId === descriptor.id
3720
+ );
3710
3721
  return claim4 !== void 0 && resolveRuntimeEvidence(claim4, version).reason !== "version-inapplicable";
3711
3722
  })
3712
3723
  );
@@ -3723,8 +3734,12 @@ function negotiateCapability(artifact, descriptor, claims, version) {
3723
3734
  evidenceClaimIds: [],
3724
3735
  reason: "no matching surface"
3725
3736
  };
3726
- const related = claims.filter((c4) => surface.evidenceClaimIds.includes(c4.id));
3727
- const usable = related.length > 0 && related.every((c4) => resolveRuntimeEvidence(c4, version).usableForAutomaticInstall);
3737
+ const usable = areRuntimeEvidenceClaimsUsable(
3738
+ surface.evidenceClaimIds,
3739
+ descriptor.id,
3740
+ claims,
3741
+ version
3742
+ );
3728
3743
  const degraded = descriptor.degradation.find((d) => d.from === intent);
3729
3744
  return {
3730
3745
  intent,
@@ -3985,7 +4000,22 @@ function planSetup(request, artifact, descriptor, claims, ownershipManifest) {
3985
4000
  request.runtimeVersion
3986
4001
  );
3987
4002
  const projectionPlan = planProjection(artifact, descriptor.id, request.scope, negotiations);
3988
- const baseInstallationPlan = planInstallation(projectionPlan, descriptor, request.runtimeVersion);
4003
+ const evidenceBackedDescriptor = {
4004
+ ...descriptor,
4005
+ locations: descriptor.locations.filter(
4006
+ (location) => location.installation === "manual" || location.installation === "unsupported" || areRuntimeEvidenceClaimsUsable(
4007
+ location.evidenceClaimIds,
4008
+ descriptor.id,
4009
+ policyClaims,
4010
+ request.runtimeVersion
4011
+ )
4012
+ )
4013
+ };
4014
+ const baseInstallationPlan = planInstallation(
4015
+ projectionPlan,
4016
+ evidenceBackedDescriptor,
4017
+ request.runtimeVersion
4018
+ );
3989
4019
  const mutatingIntent = request.intent === "setup" || request.intent === "update";
3990
4020
  let installationPlan = mutatingIntent ? baseInstallationPlan : { ...baseInstallationPlan, operations: [] };
3991
4021
  if (request.intent === "remove") {
@@ -11733,7 +11763,7 @@ function writeEnvelope(envelope, format2) {
11733
11763
  }
11734
11764
 
11735
11765
  // packages/cli/src/release.ts
11736
- var cliVersion = true ? "0.1.13" : createRequire(import.meta.url)("../../../package.json").version;
11766
+ var cliVersion = true ? "0.1.15" : createRequire(import.meta.url)("../../../package.json").version;
11737
11767
 
11738
11768
  // packages/adapters/src/antigravity/materialize.ts
11739
11769
  import { resolve as resolve2 } from "node:path";
@@ -15792,6 +15822,7 @@ function operationalContract(role) {
15792
15822
  resources: [
15793
15823
  roleFacet(role, "resources"),
15794
15824
  "Load [resource:resources/contract.json] for the complete role contract.",
15825
+ "Load [resource:resources/input.schema.json] before interpreting capability inputs.",
15795
15826
  "Load [resource:resources/output.schema.json] before constructing the final output."
15796
15827
  ],
15797
15828
  ambiguityAndAbstention: [roleFacet(role, "ambiguity"), roleFacet(role, "abstention")],
@@ -15836,6 +15867,20 @@ async function loadCanonicalArtifact(catalogRoot, capabilityId) {
15836
15867
  if (isAbsolute3(schemaRelativePath) || schemaRelativePath.startsWith(".."))
15837
15868
  throw new Error(`Canonical output schema escapes catalog: ${role.output.schema}`);
15838
15869
  const schemaContent = await readFile6(schemaFile, "utf8");
15870
+ const inputSchemaContent = `${JSON.stringify(
15871
+ {
15872
+ $schema: "https://json-schema.org/draft/2020-12/schema",
15873
+ type: "object",
15874
+ properties: Object.fromEntries(
15875
+ role.inputs.map((input) => [input.name, { description: input.description }])
15876
+ ),
15877
+ required: role.inputs.filter((input) => input.required).map((input) => input.name),
15878
+ additionalProperties: true
15879
+ },
15880
+ null,
15881
+ 2
15882
+ )}
15883
+ `;
15839
15884
  const contract = operationalContract(role);
15840
15885
  const contractContent = `${JSON.stringify(
15841
15886
  { ...role, output: { ...role.output, schema: "resources/output.schema.json" } },
@@ -15844,6 +15889,13 @@ async function loadCanonicalArtifact(catalogRoot, capabilityId) {
15844
15889
  )}
15845
15890
  `;
15846
15891
  const resources = [
15892
+ resource(
15893
+ file,
15894
+ "role.inputs",
15895
+ "resources/input.schema.json",
15896
+ "application/schema+json",
15897
+ inputSchemaContent
15898
+ ),
15847
15899
  resource(
15848
15900
  file,
15849
15901
  role.output.schema,