capdag 0.158.370 → 0.162.386
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/README.md +5 -5
- package/RULES.md +6 -6
- package/capdag.js +55 -6
- package/capdag.test.js +241 -241
- package/machine.pegjs +2 -2
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -23,7 +23,7 @@ npm install capdag
|
|
|
23
23
|
const { CapUrn, CapUrnBuilder, CapMatcher } = require('capdag');
|
|
24
24
|
|
|
25
25
|
// Create from string (with required direction specifiers)
|
|
26
|
-
const cap = CapUrn.fromString('cap:in="media:binary";
|
|
26
|
+
const cap = CapUrn.fromString('cap:in="media:binary";extract;out="media:object"');
|
|
27
27
|
console.log(cap.toString());
|
|
28
28
|
|
|
29
29
|
// Use builder pattern
|
|
@@ -35,14 +35,14 @@ const built = new CapUrnBuilder()
|
|
|
35
35
|
.build();
|
|
36
36
|
|
|
37
37
|
// Matching
|
|
38
|
-
const request = CapUrn.fromString('cap:in="media:binary";
|
|
38
|
+
const request = CapUrn.fromString('cap:in="media:binary";extract;out="media:object"');
|
|
39
39
|
console.log(cap.accepts(request)); // true
|
|
40
40
|
|
|
41
41
|
// Find best match by specificity
|
|
42
42
|
const caps = [
|
|
43
|
-
CapUrn.fromString('cap:in=*;
|
|
44
|
-
CapUrn.fromString('cap:in="media:binary";
|
|
45
|
-
CapUrn.fromString('cap:ext=pdf;in="media:binary";
|
|
43
|
+
CapUrn.fromString('cap:in=*;extract;out=*'),
|
|
44
|
+
CapUrn.fromString('cap:in="media:binary";extract;out="media:object"'),
|
|
45
|
+
CapUrn.fromString('cap:ext=pdf;in="media:binary";extract;out="media:object"')
|
|
46
46
|
];
|
|
47
47
|
const best = CapMatcher.findBestMatch(caps, request);
|
|
48
48
|
console.log(best.toString()); // Most specific match
|
package/RULES.md
CHANGED
|
@@ -14,7 +14,7 @@ Cap URNs **must** include `in` and `out` tags that specify input/output media ty
|
|
|
14
14
|
|
|
15
15
|
```javascript
|
|
16
16
|
// Valid cap URN with direction specifiers
|
|
17
|
-
const cap = CapUrn.fromString('cap:in="media:binary";
|
|
17
|
+
const cap = CapUrn.fromString('cap:in="media:binary";extract;out="media:object"');
|
|
18
18
|
|
|
19
19
|
// Invalid - missing direction specifiers
|
|
20
20
|
CapUrn.fromString('cap:op=extract'); // throws ErrorCodes.MISSING_IN_SPEC
|
|
@@ -26,13 +26,13 @@ Direction specifier values must be valid Media URNs or special pattern values:
|
|
|
26
26
|
|
|
27
27
|
```javascript
|
|
28
28
|
// Valid: Media URN value
|
|
29
|
-
'cap:in="media:binary";
|
|
29
|
+
'cap:in="media:binary";extract;out="media:object"'
|
|
30
30
|
|
|
31
31
|
// Valid: Must-have-any (any media type)
|
|
32
|
-
'cap:in=*;
|
|
32
|
+
'cap:in=*;extract;out=*'
|
|
33
33
|
|
|
34
34
|
// Invalid: Not a Media URN or special value
|
|
35
|
-
'cap:in=binary;
|
|
35
|
+
'cap:in=binary;extract;out=object' // throws ErrorCodes.INVALID_MEDIA_URN
|
|
36
36
|
```
|
|
37
37
|
|
|
38
38
|
### 3. Matching Semantics
|
|
@@ -59,8 +59,8 @@ Specificity uses graded scoring:
|
|
|
59
59
|
| Unspecified (K=?) or missing | 0 |
|
|
60
60
|
|
|
61
61
|
Examples:
|
|
62
|
-
- `cap:in="media:binary";
|
|
63
|
-
- `cap:in=*;
|
|
62
|
+
- `cap:in="media:binary";extract;out="media:object"` → 3+3+3 = 9
|
|
63
|
+
- `cap:in=*;extract;out=*` → 2+3+2 = 7
|
|
64
64
|
|
|
65
65
|
## Cap-Specific Error Codes
|
|
66
66
|
|
package/capdag.js
CHANGED
|
@@ -922,7 +922,7 @@ const MEDIA_YAML_RECORD = 'media:record;textable;yaml';
|
|
|
922
922
|
const MEDIA_YAML_LIST = 'media:list;textable;yaml';
|
|
923
923
|
const MEDIA_YAML_LIST_RECORD = 'media:list;record;textable;yaml';
|
|
924
924
|
const MEDIA_CSV = 'media:csv;list;record;textable';
|
|
925
|
-
const MEDIA_CSV_LIST = 'media:csv;list;textable';
|
|
925
|
+
const MEDIA_CSV_LIST = 'media:csv;list;record;textable';
|
|
926
926
|
|
|
927
927
|
// File path type — for arguments that represent filesystem paths.
|
|
928
928
|
// There is a single media URN; cardinality (single file vs many files)
|
|
@@ -4528,6 +4528,24 @@ class CartridgeRepoServer {
|
|
|
4528
4528
|
* Reasons why a cartridge attachment attempt failed.
|
|
4529
4529
|
* Mirrors Rust CartridgeAttachmentErrorKind.
|
|
4530
4530
|
*/
|
|
4531
|
+
const CartridgeLifecycle = Object.freeze({
|
|
4532
|
+
// Discovery scan has found the version directory and is about
|
|
4533
|
+
// to inspect it. Transient.
|
|
4534
|
+
DISCOVERED: 'discovered',
|
|
4535
|
+
// Reading cartridge.json, computing directory hash, validating
|
|
4536
|
+
// on-disk install context. Hashing can take seconds for large
|
|
4537
|
+
// model cartridges; runs on a background queue so other
|
|
4538
|
+
// cartridges' inspections proceed in parallel.
|
|
4539
|
+
INSPECTING: 'inspecting',
|
|
4540
|
+
// Inspection succeeded; awaiting a verdict from the registry
|
|
4541
|
+
// verifier service. Skipped for dev cartridges
|
|
4542
|
+
// (registry_url == null) and bundle cartridges.
|
|
4543
|
+
VERIFYING: 'verifying',
|
|
4544
|
+
// Cleared every gate. Caps are registered with the engine and
|
|
4545
|
+
// dispatch can route requests to this cartridge.
|
|
4546
|
+
OPERATIONAL: 'operational',
|
|
4547
|
+
});
|
|
4548
|
+
|
|
4531
4549
|
const CartridgeAttachmentErrorKind = Object.freeze({
|
|
4532
4550
|
INCOMPATIBLE: 'incompatible',
|
|
4533
4551
|
MANIFEST_INVALID: 'manifest_invalid',
|
|
@@ -4636,9 +4654,9 @@ class CartridgeRuntimeStats {
|
|
|
4636
4654
|
/**
|
|
4637
4655
|
* Full identity of an installed cartridge, including optional attachment error
|
|
4638
4656
|
* and runtime statistics.
|
|
4639
|
-
* Mirrors Rust
|
|
4657
|
+
* Mirrors Rust InstalledCartridgeRecord.
|
|
4640
4658
|
*/
|
|
4641
|
-
class
|
|
4659
|
+
class InstalledCartridgeRecord {
|
|
4642
4660
|
/**
|
|
4643
4661
|
* @param {Object} opts
|
|
4644
4662
|
* @param {string|null} [opts.registryUrl=null]
|
|
@@ -4646,17 +4664,21 @@ class InstalledCartridgeIdentity {
|
|
|
4646
4664
|
* @param {string} opts.id
|
|
4647
4665
|
* @param {string} opts.version
|
|
4648
4666
|
* @param {string} opts.sha256
|
|
4667
|
+
* @param {Array<Object>} [opts.capGroups=[]] - Cartridge's manifest cap_groups; each element is `{name, caps, adapter_urns}`.
|
|
4649
4668
|
* @param {CartridgeAttachmentError|null} [opts.attachmentError=null]
|
|
4650
4669
|
* @param {CartridgeRuntimeStats|null} [opts.runtimeStats=null]
|
|
4670
|
+
* @param {string} [opts.lifecycle='discovered'] - One of `discovered` | `inspecting` | `verifying` | `operational`. Mutually exclusive with attachmentError; see `machfab-mac/docs/cartridge state machine.md`.
|
|
4651
4671
|
*/
|
|
4652
|
-
constructor({ registryUrl = null, channel, id, version, sha256, attachmentError = null, runtimeStats = null }) {
|
|
4672
|
+
constructor({ registryUrl = null, channel, id, version, sha256, capGroups = [], attachmentError = null, runtimeStats = null, lifecycle = 'discovered' }) {
|
|
4653
4673
|
this.registry_url = registryUrl;
|
|
4654
4674
|
this.channel = channel;
|
|
4655
4675
|
this.id = id;
|
|
4656
4676
|
this.version = version;
|
|
4657
4677
|
this.sha256 = sha256;
|
|
4678
|
+
this.cap_groups = capGroups;
|
|
4658
4679
|
this.attachment_error = attachmentError;
|
|
4659
4680
|
this.runtime_stats = runtimeStats;
|
|
4681
|
+
this.lifecycle = lifecycle;
|
|
4660
4682
|
}
|
|
4661
4683
|
|
|
4662
4684
|
toJSON() {
|
|
@@ -4665,24 +4687,50 @@ class InstalledCartridgeIdentity {
|
|
|
4665
4687
|
id: this.id,
|
|
4666
4688
|
version: this.version,
|
|
4667
4689
|
sha256: this.sha256,
|
|
4690
|
+
lifecycle: this.lifecycle,
|
|
4668
4691
|
};
|
|
4669
4692
|
if (this.registry_url !== null) obj.registry_url = this.registry_url;
|
|
4693
|
+
if (this.cap_groups && this.cap_groups.length > 0) obj.cap_groups = this.cap_groups;
|
|
4670
4694
|
if (this.attachment_error !== null) obj.attachment_error = this.attachment_error.toJSON();
|
|
4671
4695
|
if (this.runtime_stats !== null) obj.runtime_stats = this.runtime_stats.toJSON();
|
|
4672
4696
|
return obj;
|
|
4673
4697
|
}
|
|
4674
4698
|
|
|
4675
4699
|
static fromJSON(d) {
|
|
4676
|
-
return new
|
|
4700
|
+
return new InstalledCartridgeRecord({
|
|
4677
4701
|
registryUrl: d.registry_url !== undefined ? d.registry_url : null,
|
|
4678
4702
|
channel: d.channel,
|
|
4679
4703
|
id: d.id,
|
|
4680
4704
|
version: d.version,
|
|
4681
4705
|
sha256: d.sha256,
|
|
4706
|
+
capGroups: Array.isArray(d.cap_groups) ? d.cap_groups : [],
|
|
4682
4707
|
attachmentError: d.attachment_error ? CartridgeAttachmentError.fromJSON(d.attachment_error) : null,
|
|
4683
4708
|
runtimeStats: d.runtime_stats ? CartridgeRuntimeStats.fromJSON(d.runtime_stats) : null,
|
|
4709
|
+
// Default to 'discovered' (the safe sentinel) — never
|
|
4710
|
+
// 'operational' — when the field is missing from the wire.
|
|
4711
|
+
lifecycle: typeof d.lifecycle === 'string' ? d.lifecycle : 'discovered',
|
|
4684
4712
|
});
|
|
4685
4713
|
}
|
|
4714
|
+
|
|
4715
|
+
/**
|
|
4716
|
+
* Flat de-duplicated cap-URN view across this cartridge's groups,
|
|
4717
|
+
* preserving first-seen order.
|
|
4718
|
+
* @returns {Array<string>}
|
|
4719
|
+
*/
|
|
4720
|
+
capUrns() {
|
|
4721
|
+
const seen = new Set();
|
|
4722
|
+
const out = [];
|
|
4723
|
+
for (const group of this.cap_groups) {
|
|
4724
|
+
const caps = (group && Array.isArray(group.caps)) ? group.caps : [];
|
|
4725
|
+
for (const cap of caps) {
|
|
4726
|
+
const urn = (cap && typeof cap.urn === 'string') ? cap.urn : '';
|
|
4727
|
+
if (!urn || seen.has(urn)) continue;
|
|
4728
|
+
seen.add(urn);
|
|
4729
|
+
out.push(urn);
|
|
4730
|
+
}
|
|
4731
|
+
}
|
|
4732
|
+
return out;
|
|
4733
|
+
}
|
|
4686
4734
|
}
|
|
4687
4735
|
|
|
4688
4736
|
// ============================================================================
|
|
@@ -5942,10 +5990,11 @@ module.exports = {
|
|
|
5942
5990
|
CartridgeRepoServer,
|
|
5943
5991
|
CartridgeChannel,
|
|
5944
5992
|
// Bifaci — cartridge attachment & runtime identity
|
|
5993
|
+
CartridgeLifecycle,
|
|
5945
5994
|
CartridgeAttachmentErrorKind,
|
|
5946
5995
|
CartridgeAttachmentError,
|
|
5947
5996
|
CartridgeRuntimeStats,
|
|
5948
|
-
|
|
5997
|
+
InstalledCartridgeRecord,
|
|
5949
5998
|
// Registry slug
|
|
5950
5999
|
DEV_SLUG,
|
|
5951
6000
|
SLUG_HEX_LEN,
|