@fulmenhq/tsfulmen 0.2.0 → 0.2.3
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 +70 -0
- package/README.md +61 -7
- package/config/crucible-ts/agentic/roles/README.md +3 -3
- package/config/crucible-ts/library/fulencode/fixtures/README.md +18 -0
- package/config/crucible-ts/library/fulencode/fixtures/bom/bom.yaml +14 -0
- package/config/crucible-ts/library/fulencode/fixtures/detection/detection.yaml +12 -0
- package/config/crucible-ts/library/fulencode/fixtures/invalid-encodings/base64.yaml +10 -0
- package/config/crucible-ts/library/fulencode/fixtures/normalization/text-safe.yaml +10 -0
- package/config/crucible-ts/library/fulencode/fixtures/telemetry/telemetry-test-cases.yaml +24 -0
- package/config/crucible-ts/library/fulencode/fixtures/valid-encodings/base64.yaml +11 -0
- package/config/crucible-ts/taxonomy/library/platform-modules/v1.0.0/modules.yaml +2 -2
- package/config/crucible-ts/taxonomy/metrics.yaml +79 -1
- package/dist/appidentity/index.d.ts +31 -109
- package/dist/appidentity/index.js +369 -60
- package/dist/appidentity/index.js.map +1 -1
- package/dist/config/index.d.ts +46 -1
- package/dist/config/index.js +427 -62
- package/dist/config/index.js.map +1 -1
- package/dist/crucible/index.js +367 -59
- package/dist/crucible/index.js.map +1 -1
- package/dist/errors/index.d.ts +1 -1
- package/dist/errors/index.js +367 -59
- package/dist/errors/index.js.map +1 -1
- package/dist/foundry/index.d.ts +2 -1
- package/dist/foundry/index.js +368 -60
- package/dist/foundry/index.js.map +1 -1
- package/dist/fulencode/index.d.ts +102 -0
- package/dist/fulencode/index.js +806 -0
- package/dist/fulencode/index.js.map +1 -0
- package/dist/index.d.ts +4 -3
- package/dist/index.js +370 -61
- package/dist/index.js.map +1 -1
- package/dist/pathfinder/index.d.ts +1 -1
- package/dist/pathfinder/index.js +367 -59
- package/dist/pathfinder/index.js.map +1 -1
- package/dist/reports/license-inventory.csv +31 -24
- package/dist/schema/index.d.ts +16 -3
- package/dist/schema/index.js +368 -60
- package/dist/schema/index.js.map +1 -1
- package/dist/signals/index.d.ts +483 -395
- package/dist/signals/index.js +368 -60
- package/dist/signals/index.js.map +1 -1
- package/dist/telemetry/http/index.js +368 -59
- package/dist/telemetry/http/index.js.map +1 -1
- package/dist/telemetry/index.d.ts +1 -1
- package/dist/telemetry/index.js +367 -59
- package/dist/telemetry/index.js.map +1 -1
- package/dist/telemetry/prometheus/index.d.ts +1 -1
- package/dist/telemetry/prometheus/index.js +369 -59
- package/dist/telemetry/prometheus/index.js.map +1 -1
- package/dist/{types-BJswWpQC.d.ts → types-DdoeE7F5.d.ts} +1 -1
- package/dist/types-Dv5TERCM.d.ts +108 -0
- package/package.json +13 -8
- package/schemas/crucible-ts/library/fulencode/v1.0.0/README.md +37 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/bom-result.schema.json +48 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/decode-options.schema.json +60 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/decoding-result.schema.json +70 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/detect-options.schema.json +25 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/detection-result.schema.json +57 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/encode-options.schema.json +71 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/encoding-result.schema.json +57 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/fulencode-config.schema.json +8 -4
- package/schemas/crucible-ts/library/fulencode/v1.0.0/fulencode-error.schema.json +66 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/normalization-result.schema.json +73 -0
- package/schemas/crucible-ts/library/fulencode/v1.0.0/normalize-options.schema.json +44 -0
- package/schemas/crucible-ts/meta/README.md +38 -2
- package/schemas/crucible-ts/meta/draft-04/schema.json +222 -0
- package/schemas/crucible-ts/meta/draft-06/schema.json +218 -0
- package/schemas/crucible-ts/meta/draft-2019-09/meta/applicator.json +93 -0
- package/schemas/crucible-ts/meta/draft-2019-09/meta/content.json +21 -0
- package/schemas/crucible-ts/meta/draft-2019-09/meta/core.json +58 -0
- package/schemas/crucible-ts/meta/draft-2019-09/meta/format.json +15 -0
- package/schemas/crucible-ts/meta/draft-2019-09/meta/meta-data.json +35 -0
- package/schemas/crucible-ts/meta/draft-2019-09/meta/validation.json +119 -0
- package/schemas/crucible-ts/meta/draft-2019-09/offline.schema.json +148 -0
- package/schemas/crucible-ts/meta/draft-2019-09/schema.json +62 -0
- package/schemas/crucible-ts/meta/fixtures/draft-04-sample.json +16 -0
- package/schemas/crucible-ts/meta/fixtures/draft-06-sample.json +16 -0
- package/schemas/crucible-ts/meta/fixtures/draft-07-sample.json +34 -0
- package/schemas/crucible-ts/meta/fixtures/draft-2019-09-sample.json +21 -0
- package/schemas/crucible-ts/meta/fixtures/draft-2020-12-sample.json +21 -0
- package/schemas/crucible-ts/taxonomy/library/fulencode/normalization-profiles/v1.0.0/profiles.yaml +16 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/PROVENANCE.md +64 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/config/classifiers/dimensions/access-tier.dimension.json +103 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/config/classifiers/dimensions/retention-lifecycle.dimension.json +103 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/config/classifiers/dimensions/schema-stability.dimension.json +100 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/config/classifiers/dimensions/sensitivity.dimension.json +130 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/config/classifiers/dimensions/velocity-mode.dimension.json +79 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/config/classifiers/dimensions/volatility.dimension.json +72 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/config/classifiers/dimensions/volume-tier.dimension.json +66 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/catalog/classifiers/README.md +29 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/access-tier-classification.md +163 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/classifiers-framework.md +157 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/data-sensitivity-classification.md +259 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/retention-lifecycle-classification.md +200 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/schema-stability-classification.md +205 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/velocity-mode-classification.md +222 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/volatility-classification.md +209 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/docs/standards/volume-tier-classification.md +200 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/ailink/v0/README.md +48 -0
- package/schemas/crucible-ts/upstream/3leaps/{ailink → crucible/schemas/ailink}/v0/prompt.schema.json +4 -18
- package/schemas/crucible-ts/upstream/3leaps/{ailink → crucible/schemas/ailink}/v0/search-response.schema.json +7 -37
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/classifiers/v0/dimension-definition.schema.json +247 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/classifiers/v0/sensitivity-level.schema.json +67 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/foundation/v0/error-response.schema.json +59 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/foundation/v0/lifecycle-phases.data.json +102 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/foundation/v0/lifecycle-phases.schema.json +101 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/foundation/v0/release-phase.schema.json +18 -0
- package/schemas/crucible-ts/upstream/3leaps/crucible/schemas/foundation/v0/types.schema.json +177 -0
- package/schemas/crucible-ts/upstream/3leaps/PROVENANCE.md +0 -43
- /package/schemas/crucible-ts/upstream/3leaps/{agentic → crucible/schemas/agentic}/v0/role-prompt.schema.json +0 -0
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import addFormats from 'ajv-formats';
|
|
1
2
|
import { spawn } from 'child_process';
|
|
2
3
|
import { readFile, writeFile, access, mkdir } from 'fs/promises';
|
|
3
4
|
import { parse, stringify } from 'yaml';
|
|
@@ -5,7 +6,9 @@ import { dirname, join, relative, extname } from 'path';
|
|
|
5
6
|
import { fileURLToPath } from 'url';
|
|
6
7
|
import glob from 'fast-glob';
|
|
7
8
|
import Ajv from 'ajv';
|
|
8
|
-
import
|
|
9
|
+
import Ajv2019 from 'ajv/dist/2019';
|
|
10
|
+
import Ajv2020 from 'ajv/dist/2020';
|
|
11
|
+
import AjvDraft04 from 'ajv-draft-04';
|
|
9
12
|
import { Readable } from 'stream';
|
|
10
13
|
import picomatch from 'picomatch';
|
|
11
14
|
import { suggest as suggest$1, substringSimilarity, score as score$1, normalize as normalize$1, jaro_winkler, damerau_levenshtein, osa_distance, levenshtein } from '@3leaps/string-metrics-wasm';
|
|
@@ -33,6 +36,27 @@ var init_constants = __esm({
|
|
|
33
36
|
MAX_ANCESTOR_SEARCH_DEPTH = 20;
|
|
34
37
|
}
|
|
35
38
|
});
|
|
39
|
+
function applyFulmenAjvFormats(ajv, options = {}) {
|
|
40
|
+
const mode = options.mode ?? "fast";
|
|
41
|
+
const formats = options.formats ?? DEFAULT_FORMATS;
|
|
42
|
+
addFormats(ajv, { mode, formats });
|
|
43
|
+
return ajv;
|
|
44
|
+
}
|
|
45
|
+
var DEFAULT_FORMATS;
|
|
46
|
+
var init_ajv_formats = __esm({
|
|
47
|
+
"src/schema/ajv-formats.ts"() {
|
|
48
|
+
DEFAULT_FORMATS = [
|
|
49
|
+
"date-time",
|
|
50
|
+
"email",
|
|
51
|
+
"hostname",
|
|
52
|
+
"ipv4",
|
|
53
|
+
"ipv6",
|
|
54
|
+
"uri",
|
|
55
|
+
"uri-reference",
|
|
56
|
+
"uuid"
|
|
57
|
+
];
|
|
58
|
+
}
|
|
59
|
+
});
|
|
36
60
|
|
|
37
61
|
// src/schema/errors.ts
|
|
38
62
|
var errors_exports = {};
|
|
@@ -1485,20 +1509,14 @@ async function loadMetaSchema(draft) {
|
|
|
1485
1509
|
const content = await readFile(metaSchemaPath, "utf-8");
|
|
1486
1510
|
return JSON.parse(content);
|
|
1487
1511
|
}
|
|
1488
|
-
async function loadVocabularySchemas() {
|
|
1512
|
+
async function loadVocabularySchemas(draft) {
|
|
1513
|
+
if (draft !== "draft-2019-09" && draft !== "draft-2020-12") {
|
|
1514
|
+
return [];
|
|
1515
|
+
}
|
|
1489
1516
|
const __filename3 = fileURLToPath(import.meta.url);
|
|
1490
1517
|
const __dirname4 = dirname(__filename3);
|
|
1491
|
-
const vocabDir = join(
|
|
1492
|
-
|
|
1493
|
-
"..",
|
|
1494
|
-
"..",
|
|
1495
|
-
"schemas",
|
|
1496
|
-
"crucible-ts",
|
|
1497
|
-
"meta",
|
|
1498
|
-
"draft-2020-12",
|
|
1499
|
-
"meta"
|
|
1500
|
-
);
|
|
1501
|
-
const vocabFiles = [
|
|
1518
|
+
const vocabDir = join(__dirname4, "..", "..", "schemas", "crucible-ts", "meta", draft, "meta");
|
|
1519
|
+
const vocabFiles = draft === "draft-2020-12" ? [
|
|
1502
1520
|
"core.json",
|
|
1503
1521
|
"applicator.json",
|
|
1504
1522
|
"unevaluated.json",
|
|
@@ -1506,6 +1524,13 @@ async function loadVocabularySchemas() {
|
|
|
1506
1524
|
"meta-data.json",
|
|
1507
1525
|
"format-annotation.json",
|
|
1508
1526
|
"content.json"
|
|
1527
|
+
] : [
|
|
1528
|
+
"core.json",
|
|
1529
|
+
"applicator.json",
|
|
1530
|
+
"validation.json",
|
|
1531
|
+
"meta-data.json",
|
|
1532
|
+
"format.json",
|
|
1533
|
+
"content.json"
|
|
1509
1534
|
];
|
|
1510
1535
|
const schemas = [];
|
|
1511
1536
|
for (const file of vocabFiles) {
|
|
@@ -1560,47 +1585,65 @@ async function loadReferencedSchema(uri) {
|
|
|
1560
1585
|
}
|
|
1561
1586
|
return JSON.parse(content);
|
|
1562
1587
|
}
|
|
1563
|
-
function
|
|
1564
|
-
if (!
|
|
1565
|
-
|
|
1566
|
-
|
|
1567
|
-
|
|
1568
|
-
|
|
1569
|
-
|
|
1570
|
-
|
|
1571
|
-
|
|
1572
|
-
|
|
1573
|
-
}
|
|
1574
|
-
addFormats(ajvInstance, {
|
|
1575
|
-
mode: "fast",
|
|
1576
|
-
formats: ["date-time", "email", "hostname", "ipv4", "ipv6", "uri", "uri-reference"]
|
|
1577
|
-
});
|
|
1578
|
-
metaschemaReady = Promise.all([loadVocabularySchemas(), loadMetaSchema("draft-2020-12")]).then(([vocabSchemas, metaSchema]) => {
|
|
1579
|
-
if (ajvInstance) {
|
|
1580
|
-
for (const vocabSchema of vocabSchemas) {
|
|
1581
|
-
try {
|
|
1582
|
-
ajvInstance.addMetaSchema(vocabSchema);
|
|
1583
|
-
} catch {
|
|
1584
|
-
}
|
|
1585
|
-
}
|
|
1586
|
-
ajvInstance.addMetaSchema(metaSchema);
|
|
1587
|
-
}
|
|
1588
|
-
}).catch((error) => {
|
|
1589
|
-
throw new Error(`Failed to load metaschemas: ${error}`);
|
|
1590
|
-
});
|
|
1588
|
+
function detectDialect(schema) {
|
|
1589
|
+
if (schema && typeof schema === "object" && !Array.isArray(schema)) {
|
|
1590
|
+
const maybeSchema = schema;
|
|
1591
|
+
const declared = maybeSchema.$schema;
|
|
1592
|
+
if (typeof declared === "string") {
|
|
1593
|
+
if (declared.includes("draft-04")) return "draft-04";
|
|
1594
|
+
if (declared.includes("draft-06")) return "draft-06";
|
|
1595
|
+
if (declared.includes("draft-07")) return "draft-07";
|
|
1596
|
+
if (declared.includes("draft/2019-09")) return "draft-2019-09";
|
|
1597
|
+
if (declared.includes("draft/2020-12")) return "draft-2020-12";
|
|
1598
|
+
}
|
|
1591
1599
|
}
|
|
1592
|
-
return
|
|
1600
|
+
return "draft-2020-12";
|
|
1601
|
+
}
|
|
1602
|
+
function createAjv(dialect) {
|
|
1603
|
+
const AjvCtor = dialect === "draft-2020-12" ? Ajv2020 : dialect === "draft-2019-09" ? Ajv2019 : dialect === "draft-04" ? AjvDraft04 : Ajv;
|
|
1604
|
+
const ajv = new AjvCtor({
|
|
1605
|
+
strict: false,
|
|
1606
|
+
allErrors: true,
|
|
1607
|
+
verbose: true,
|
|
1608
|
+
// Allow schemas with $id to be added without replacing existing ones
|
|
1609
|
+
addUsedSchema: false,
|
|
1610
|
+
// draft-04 uses "id"; later drafts use "$id"
|
|
1611
|
+
schemaId: dialect === "draft-04" ? "id" : "$id",
|
|
1612
|
+
// Enable async schema loading for YAML references
|
|
1613
|
+
loadSchema: loadReferencedSchema
|
|
1614
|
+
});
|
|
1615
|
+
applyFulmenAjvFormats(ajv);
|
|
1616
|
+
return ajv;
|
|
1617
|
+
}
|
|
1618
|
+
async function getAjv(dialect) {
|
|
1619
|
+
const existing = ajvInstances.get(dialect);
|
|
1620
|
+
if (existing) {
|
|
1621
|
+
const ready = metaschemaReady.get(dialect);
|
|
1622
|
+
if (ready) await ready;
|
|
1623
|
+
return existing;
|
|
1624
|
+
}
|
|
1625
|
+
const ajv = createAjv(dialect);
|
|
1626
|
+
ajvInstances.set(dialect, ajv);
|
|
1627
|
+
const readyPromise = Promise.all([loadVocabularySchemas(dialect), loadMetaSchema(dialect)]).then(([vocabSchemas, metaSchema]) => {
|
|
1628
|
+
for (const vocabSchema of vocabSchemas) {
|
|
1629
|
+
try {
|
|
1630
|
+
ajv.addMetaSchema(vocabSchema);
|
|
1631
|
+
} catch {
|
|
1632
|
+
}
|
|
1633
|
+
}
|
|
1634
|
+
try {
|
|
1635
|
+
ajv.addMetaSchema(metaSchema);
|
|
1636
|
+
} catch {
|
|
1637
|
+
}
|
|
1638
|
+
}).catch((error) => {
|
|
1639
|
+
throw new Error(`Failed to load metaschemas (${dialect}): ${error}`);
|
|
1640
|
+
});
|
|
1641
|
+
metaschemaReady.set(dialect, readyPromise);
|
|
1642
|
+
await readyPromise;
|
|
1643
|
+
return ajv;
|
|
1593
1644
|
}
|
|
1594
1645
|
async function compileSchema(schema, options = {}) {
|
|
1595
|
-
const
|
|
1596
|
-
if (metaschemaReady) {
|
|
1597
|
-
await metaschemaReady;
|
|
1598
|
-
}
|
|
1599
|
-
const cacheKey = typeof schema === "string" ? schema : JSON.stringify(schema);
|
|
1600
|
-
const cached = schemaCache.get(cacheKey);
|
|
1601
|
-
if (cached !== void 0) {
|
|
1602
|
-
return cached;
|
|
1603
|
-
}
|
|
1646
|
+
const baseKey = typeof schema === "string" ? schema : JSON.stringify(schema);
|
|
1604
1647
|
let parsedSchema;
|
|
1605
1648
|
if (typeof schema === "string") {
|
|
1606
1649
|
try {
|
|
@@ -1618,18 +1661,27 @@ async function compileSchema(schema, options = {}) {
|
|
|
1618
1661
|
} else {
|
|
1619
1662
|
parsedSchema = schema;
|
|
1620
1663
|
}
|
|
1664
|
+
const dialect = detectDialect(parsedSchema);
|
|
1665
|
+
const ajv = await getAjv(dialect);
|
|
1666
|
+
const cacheKey = `${dialect}:${baseKey}`;
|
|
1667
|
+
const cached = schemaCache.get(cacheKey);
|
|
1668
|
+
if (cached !== void 0) {
|
|
1669
|
+
return cached;
|
|
1670
|
+
}
|
|
1621
1671
|
try {
|
|
1622
1672
|
if (options.aliases && options.aliases.length > 0) {
|
|
1623
1673
|
for (const alias of options.aliases) {
|
|
1624
1674
|
if (alias && ajv.getSchema(alias) === void 0) {
|
|
1625
1675
|
try {
|
|
1626
|
-
|
|
1676
|
+
if (typeof parsedSchema === "object" && parsedSchema !== null) {
|
|
1677
|
+
ajv.addSchema(parsedSchema, alias);
|
|
1678
|
+
}
|
|
1627
1679
|
} catch {
|
|
1628
1680
|
}
|
|
1629
1681
|
}
|
|
1630
1682
|
}
|
|
1631
1683
|
}
|
|
1632
|
-
const validator = await ajv.compileAsync(parsedSchema);
|
|
1684
|
+
const validator = typeof parsedSchema === "boolean" ? ajv.compile(parsedSchema) : await ajv.compileAsync(parsedSchema);
|
|
1633
1685
|
schemaCache.set(cacheKey, validator);
|
|
1634
1686
|
return validator;
|
|
1635
1687
|
} catch (error) {
|
|
@@ -1699,8 +1751,39 @@ async function validateFile(filePath, validator) {
|
|
|
1699
1751
|
}
|
|
1700
1752
|
async function validateSchema(schema) {
|
|
1701
1753
|
try {
|
|
1702
|
-
|
|
1703
|
-
|
|
1754
|
+
let parsedSchema;
|
|
1755
|
+
if (typeof schema === "string") {
|
|
1756
|
+
try {
|
|
1757
|
+
parsedSchema = JSON.parse(schema);
|
|
1758
|
+
} catch {
|
|
1759
|
+
parsedSchema = parse(schema);
|
|
1760
|
+
}
|
|
1761
|
+
} else if (Buffer.isBuffer(schema)) {
|
|
1762
|
+
const content = schema.toString("utf-8");
|
|
1763
|
+
try {
|
|
1764
|
+
parsedSchema = JSON.parse(content);
|
|
1765
|
+
} catch {
|
|
1766
|
+
parsedSchema = parse(content);
|
|
1767
|
+
}
|
|
1768
|
+
} else {
|
|
1769
|
+
parsedSchema = schema;
|
|
1770
|
+
}
|
|
1771
|
+
const dialect = detectDialect(parsedSchema);
|
|
1772
|
+
const ajv = await getAjv(dialect);
|
|
1773
|
+
const metaValid = ajv.validateSchema(parsedSchema);
|
|
1774
|
+
if (!metaValid && ajv.errors) {
|
|
1775
|
+
const diagnostics = ajv.errors.map(
|
|
1776
|
+
(error) => createDiagnostic(
|
|
1777
|
+
error.instancePath || "",
|
|
1778
|
+
error.message || "Schema meta-validation failed",
|
|
1779
|
+
error.keyword || "unknown",
|
|
1780
|
+
"ERROR",
|
|
1781
|
+
"ajv"
|
|
1782
|
+
)
|
|
1783
|
+
);
|
|
1784
|
+
return { valid: false, diagnostics, source: "ajv" };
|
|
1785
|
+
}
|
|
1786
|
+
await compileSchema(parsedSchema);
|
|
1704
1787
|
return {
|
|
1705
1788
|
valid: true,
|
|
1706
1789
|
diagnostics: [],
|
|
@@ -1771,14 +1854,16 @@ async function validateFileBySchemaId(filePath, schemaId, registryOptions) {
|
|
|
1771
1854
|
throw error;
|
|
1772
1855
|
}
|
|
1773
1856
|
}
|
|
1774
|
-
var
|
|
1857
|
+
var ajvInstances, metaschemaReady, schemaCache;
|
|
1775
1858
|
var init_validator = __esm({
|
|
1776
1859
|
"src/schema/validator.ts"() {
|
|
1777
1860
|
init_telemetry();
|
|
1861
|
+
init_ajv_formats();
|
|
1778
1862
|
init_errors();
|
|
1779
1863
|
init_registry();
|
|
1780
1864
|
init_utils();
|
|
1781
|
-
|
|
1865
|
+
ajvInstances = /* @__PURE__ */ new Map();
|
|
1866
|
+
metaschemaReady = /* @__PURE__ */ new Map();
|
|
1782
1867
|
schemaCache = /* @__PURE__ */ new Map();
|
|
1783
1868
|
}
|
|
1784
1869
|
});
|
|
@@ -3733,6 +3818,224 @@ var init_capabilities2 = __esm({
|
|
|
3733
3818
|
}
|
|
3734
3819
|
});
|
|
3735
3820
|
|
|
3821
|
+
// src/foundry/signals/config-reload-endpoint.ts
|
|
3822
|
+
function createConfigReloadEndpoint(options) {
|
|
3823
|
+
const { loader, validator, onReload: onReload2, auth, rateLimit, logger, telemetry } = options;
|
|
3824
|
+
return async (payload, req) => {
|
|
3825
|
+
const correlationId = payload.correlation_id ?? generateCorrelationId();
|
|
3826
|
+
const authResult = await auth(req);
|
|
3827
|
+
if (!authResult.authenticated) {
|
|
3828
|
+
if (logger) {
|
|
3829
|
+
logger.warn("Config reload endpoint: authentication failed", {
|
|
3830
|
+
correlation_id: correlationId,
|
|
3831
|
+
reason: authResult.reason
|
|
3832
|
+
});
|
|
3833
|
+
}
|
|
3834
|
+
if (telemetry) {
|
|
3835
|
+
telemetry.emit("fulmen.config.http_endpoint.auth_failed", {
|
|
3836
|
+
correlation_id: correlationId
|
|
3837
|
+
});
|
|
3838
|
+
}
|
|
3839
|
+
return {
|
|
3840
|
+
status: "error",
|
|
3841
|
+
error: "authentication_failed",
|
|
3842
|
+
message: authResult.reason || "Authentication required",
|
|
3843
|
+
statusCode: 401
|
|
3844
|
+
};
|
|
3845
|
+
}
|
|
3846
|
+
const identity = authResult.identity || "unknown";
|
|
3847
|
+
if (rateLimit) {
|
|
3848
|
+
const rateLimitResult = await rateLimit(identity);
|
|
3849
|
+
if (!rateLimitResult.allowed) {
|
|
3850
|
+
if (logger) {
|
|
3851
|
+
logger.warn("Config reload endpoint: rate limit exceeded", {
|
|
3852
|
+
correlation_id: correlationId,
|
|
3853
|
+
identity
|
|
3854
|
+
});
|
|
3855
|
+
}
|
|
3856
|
+
if (telemetry) {
|
|
3857
|
+
telemetry.emit("fulmen.config.http_endpoint.rate_limited", {
|
|
3858
|
+
correlation_id: correlationId
|
|
3859
|
+
});
|
|
3860
|
+
}
|
|
3861
|
+
return {
|
|
3862
|
+
status: "error",
|
|
3863
|
+
error: "rate_limit_exceeded",
|
|
3864
|
+
message: "Rate limit exceeded. Please try again later.",
|
|
3865
|
+
statusCode: 429
|
|
3866
|
+
};
|
|
3867
|
+
}
|
|
3868
|
+
}
|
|
3869
|
+
if (telemetry) {
|
|
3870
|
+
telemetry.emit("fulmen.config.http_endpoint.reload_requested", {
|
|
3871
|
+
correlation_id: correlationId
|
|
3872
|
+
});
|
|
3873
|
+
}
|
|
3874
|
+
try {
|
|
3875
|
+
const config = await loader();
|
|
3876
|
+
if (validator) {
|
|
3877
|
+
const validation = await validator(config);
|
|
3878
|
+
if (!validation.valid) {
|
|
3879
|
+
if (logger) {
|
|
3880
|
+
logger.warn("Config reload endpoint: validation failed", {
|
|
3881
|
+
correlation_id: correlationId,
|
|
3882
|
+
error_count: validation.errors?.length ?? 0
|
|
3883
|
+
});
|
|
3884
|
+
}
|
|
3885
|
+
if (telemetry) {
|
|
3886
|
+
telemetry.emit("fulmen.config.http_endpoint.reload_rejected", {
|
|
3887
|
+
correlation_id: correlationId,
|
|
3888
|
+
reason: "validation_failed"
|
|
3889
|
+
});
|
|
3890
|
+
}
|
|
3891
|
+
return {
|
|
3892
|
+
status: "error",
|
|
3893
|
+
error: "validation_failed",
|
|
3894
|
+
message: "Configuration validation failed",
|
|
3895
|
+
validation_errors: validation.errors,
|
|
3896
|
+
statusCode: 422
|
|
3897
|
+
};
|
|
3898
|
+
}
|
|
3899
|
+
}
|
|
3900
|
+
if (onReload2) {
|
|
3901
|
+
await onReload2(config);
|
|
3902
|
+
}
|
|
3903
|
+
if (telemetry) {
|
|
3904
|
+
telemetry.emit("fulmen.config.http_endpoint.reload_accepted", {
|
|
3905
|
+
correlation_id: correlationId
|
|
3906
|
+
});
|
|
3907
|
+
}
|
|
3908
|
+
if (logger) {
|
|
3909
|
+
logger.info("Config reload endpoint: reload accepted", {
|
|
3910
|
+
correlation_id: correlationId,
|
|
3911
|
+
reason: payload.reason
|
|
3912
|
+
});
|
|
3913
|
+
}
|
|
3914
|
+
return {
|
|
3915
|
+
status: "reloaded",
|
|
3916
|
+
correlation_id: correlationId,
|
|
3917
|
+
message: "Configuration reloaded",
|
|
3918
|
+
statusCode: 200
|
|
3919
|
+
};
|
|
3920
|
+
} catch (error) {
|
|
3921
|
+
if (logger) {
|
|
3922
|
+
logger.warn("Config reload endpoint: reload failed", {
|
|
3923
|
+
correlation_id: correlationId,
|
|
3924
|
+
error: error instanceof Error ? error.message : String(error)
|
|
3925
|
+
});
|
|
3926
|
+
}
|
|
3927
|
+
if (telemetry) {
|
|
3928
|
+
telemetry.emit("fulmen.config.http_endpoint.reload_error", {
|
|
3929
|
+
correlation_id: correlationId,
|
|
3930
|
+
error_type: error instanceof Error ? error.constructor.name : "unknown"
|
|
3931
|
+
});
|
|
3932
|
+
}
|
|
3933
|
+
return {
|
|
3934
|
+
status: "error",
|
|
3935
|
+
error: "reload_failed",
|
|
3936
|
+
message: error instanceof Error ? error.message : String(error),
|
|
3937
|
+
statusCode: 500
|
|
3938
|
+
};
|
|
3939
|
+
}
|
|
3940
|
+
};
|
|
3941
|
+
}
|
|
3942
|
+
function generateCorrelationId() {
|
|
3943
|
+
return `cfg-${Date.now()}-${Math.random().toString(36).substring(2, 9)}`;
|
|
3944
|
+
}
|
|
3945
|
+
var init_config_reload_endpoint = __esm({
|
|
3946
|
+
"src/foundry/signals/config-reload-endpoint.ts"() {
|
|
3947
|
+
}
|
|
3948
|
+
});
|
|
3949
|
+
|
|
3950
|
+
// src/appidentity/runtime.ts
|
|
3951
|
+
function detectRuntime() {
|
|
3952
|
+
const versions = process.versions;
|
|
3953
|
+
if (typeof versions.bun === "string" && versions.bun.length > 0) {
|
|
3954
|
+
return { name: "bun", version: versions.bun };
|
|
3955
|
+
}
|
|
3956
|
+
if (typeof versions.node === "string" && versions.node.length > 0) {
|
|
3957
|
+
return { name: "node", version: versions.node };
|
|
3958
|
+
}
|
|
3959
|
+
return { name: "unknown" };
|
|
3960
|
+
}
|
|
3961
|
+
function buildRuntimeInfo(options = {}) {
|
|
3962
|
+
const runtime = detectRuntime();
|
|
3963
|
+
const serviceName = options.serviceName ?? options.identity?.app.binary_name ?? "unknown-service";
|
|
3964
|
+
const vendor = options.vendor ?? options.identity?.app.vendor;
|
|
3965
|
+
return {
|
|
3966
|
+
service: {
|
|
3967
|
+
name: serviceName,
|
|
3968
|
+
vendor,
|
|
3969
|
+
version: options.version
|
|
3970
|
+
},
|
|
3971
|
+
runtime,
|
|
3972
|
+
platform: {
|
|
3973
|
+
os: process.platform,
|
|
3974
|
+
arch: process.arch
|
|
3975
|
+
}
|
|
3976
|
+
};
|
|
3977
|
+
}
|
|
3978
|
+
var init_runtime = __esm({
|
|
3979
|
+
"src/appidentity/runtime.ts"() {
|
|
3980
|
+
}
|
|
3981
|
+
});
|
|
3982
|
+
|
|
3983
|
+
// src/foundry/signals/control-discovery-endpoint.ts
|
|
3984
|
+
function createControlDiscoveryEndpoint(options) {
|
|
3985
|
+
const { identity, version, endpoints, auth, authSummary, logger, telemetry } = options;
|
|
3986
|
+
return async (req) => {
|
|
3987
|
+
if (auth) {
|
|
3988
|
+
const authResult = await auth(req);
|
|
3989
|
+
if (!authResult.authenticated) {
|
|
3990
|
+
if (logger) {
|
|
3991
|
+
logger.warn("Control discovery endpoint: authentication failed", {
|
|
3992
|
+
reason: authResult.reason
|
|
3993
|
+
});
|
|
3994
|
+
}
|
|
3995
|
+
if (telemetry) {
|
|
3996
|
+
telemetry.emit("fulmen.control.discovery.auth_failed", {
|
|
3997
|
+
service: identity.app.binary_name
|
|
3998
|
+
});
|
|
3999
|
+
}
|
|
4000
|
+
return {
|
|
4001
|
+
status: "error",
|
|
4002
|
+
error: "authentication_failed",
|
|
4003
|
+
message: authResult.reason || "Authentication required",
|
|
4004
|
+
statusCode: 401
|
|
4005
|
+
};
|
|
4006
|
+
}
|
|
4007
|
+
}
|
|
4008
|
+
if (telemetry) {
|
|
4009
|
+
telemetry.emit("fulmen.control.discovery.served", {
|
|
4010
|
+
service: identity.app.binary_name
|
|
4011
|
+
});
|
|
4012
|
+
}
|
|
4013
|
+
const runtime = buildRuntimeInfo({ identity, version });
|
|
4014
|
+
return {
|
|
4015
|
+
status: "ok",
|
|
4016
|
+
service: {
|
|
4017
|
+
name: identity.app.binary_name,
|
|
4018
|
+
vendor: identity.app.vendor,
|
|
4019
|
+
version
|
|
4020
|
+
},
|
|
4021
|
+
runtime: {
|
|
4022
|
+
name: runtime.runtime.name,
|
|
4023
|
+
version: runtime.runtime.version,
|
|
4024
|
+
platform: runtime.platform.os,
|
|
4025
|
+
arch: runtime.platform.arch
|
|
4026
|
+
},
|
|
4027
|
+
auth_summary: authSummary,
|
|
4028
|
+
endpoints,
|
|
4029
|
+
statusCode: 200
|
|
4030
|
+
};
|
|
4031
|
+
};
|
|
4032
|
+
}
|
|
4033
|
+
var init_control_discovery_endpoint = __esm({
|
|
4034
|
+
"src/foundry/signals/control-discovery-endpoint.ts"() {
|
|
4035
|
+
init_runtime();
|
|
4036
|
+
}
|
|
4037
|
+
});
|
|
4038
|
+
|
|
3736
4039
|
// src/foundry/signals/convenience.ts
|
|
3737
4040
|
async function onShutdown(manager, handler, options = {}) {
|
|
3738
4041
|
await manager.register("SIGTERM", handler, options);
|
|
@@ -3992,7 +4295,7 @@ var init_guards = __esm({
|
|
|
3992
4295
|
function createSignalEndpoint(options) {
|
|
3993
4296
|
const { manager, auth, rateLimit, logger, telemetry, allowedSignals } = options;
|
|
3994
4297
|
return async (payload, req) => {
|
|
3995
|
-
const correlationId = payload.correlation_id ??
|
|
4298
|
+
const correlationId = payload.correlation_id ?? generateCorrelationId2();
|
|
3996
4299
|
const authResult = await auth(req);
|
|
3997
4300
|
if (!authResult.authenticated) {
|
|
3998
4301
|
if (logger) {
|
|
@@ -4115,7 +4418,7 @@ function normalizeSignalName(signal) {
|
|
|
4115
4418
|
}
|
|
4116
4419
|
return `SIG${upper}`;
|
|
4117
4420
|
}
|
|
4118
|
-
function
|
|
4421
|
+
function generateCorrelationId2() {
|
|
4119
4422
|
return `sig-${Date.now()}-${Math.random().toString(36).substring(2, 9)}`;
|
|
4120
4423
|
}
|
|
4121
4424
|
function createBearerTokenAuth(expectedToken) {
|
|
@@ -4582,6 +4885,8 @@ var init_signals = __esm({
|
|
|
4582
4885
|
"src/foundry/signals/index.ts"() {
|
|
4583
4886
|
init_capabilities2();
|
|
4584
4887
|
init_catalog();
|
|
4888
|
+
init_config_reload_endpoint();
|
|
4889
|
+
init_control_discovery_endpoint();
|
|
4585
4890
|
init_convenience();
|
|
4586
4891
|
init_double_tap();
|
|
4587
4892
|
init_guards();
|
|
@@ -4727,7 +5032,9 @@ __export(foundry_exports, {
|
|
|
4727
5032
|
clearMimeTypeCache: () => clearMimeTypeCache,
|
|
4728
5033
|
clearPatternCache: () => clearPatternCache,
|
|
4729
5034
|
createBearerTokenAuth: () => createBearerTokenAuth,
|
|
5035
|
+
createConfigReloadEndpoint: () => createConfigReloadEndpoint,
|
|
4730
5036
|
createConfigReloadHandler: () => createConfigReloadHandler,
|
|
5037
|
+
createControlDiscoveryEndpoint: () => createControlDiscoveryEndpoint,
|
|
4731
5038
|
createDoubleTapTracker: () => createDoubleTapTracker,
|
|
4732
5039
|
createSignalEndpoint: () => createSignalEndpoint,
|
|
4733
5040
|
createSignalManager: () => createSignalManager,
|
|
@@ -5759,6 +6066,7 @@ var init_cli = __esm({
|
|
|
5759
6066
|
// src/schema/index.ts
|
|
5760
6067
|
var init_schema = __esm({
|
|
5761
6068
|
"src/schema/index.ts"() {
|
|
6069
|
+
init_ajv_formats();
|
|
5762
6070
|
init_cli();
|
|
5763
6071
|
init_errors();
|
|
5764
6072
|
init_export();
|
|
@@ -5875,7 +6183,8 @@ async function getEnvVar(key, options) {
|
|
|
5875
6183
|
|
|
5876
6184
|
// src/appidentity/index.ts
|
|
5877
6185
|
init_loader2();
|
|
6186
|
+
init_runtime();
|
|
5878
6187
|
|
|
5879
|
-
export { APP_IDENTITY_DIR, APP_IDENTITY_ENV_VAR, APP_IDENTITY_FILENAME, APP_IDENTITY_SCHEMA_ID, AppIdentityError, MAX_ANCESTOR_SEARCH_DEPTH, buildEnvVar, clearEmbeddedIdentity, clearIdentityCache, getBinaryName, getCachedIdentity, getConfigIdentifiers, getConfigName, getEmbeddedIdentity, getEnvPrefix, getEnvVar, getTelemetryNamespace, getVendor, hasEmbeddedIdentity, loadIdentity, registerEmbeddedIdentity };
|
|
6188
|
+
export { APP_IDENTITY_DIR, APP_IDENTITY_ENV_VAR, APP_IDENTITY_FILENAME, APP_IDENTITY_SCHEMA_ID, AppIdentityError, MAX_ANCESTOR_SEARCH_DEPTH, buildEnvVar, buildRuntimeInfo, clearEmbeddedIdentity, clearIdentityCache, getBinaryName, getCachedIdentity, getConfigIdentifiers, getConfigName, getEmbeddedIdentity, getEnvPrefix, getEnvVar, getTelemetryNamespace, getVendor, hasEmbeddedIdentity, loadIdentity, registerEmbeddedIdentity };
|
|
5880
6189
|
//# sourceMappingURL=index.js.map
|
|
5881
6190
|
//# sourceMappingURL=index.js.map
|