@living-architecture/riviere-cli 0.9.18 → 0.9.20

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 (3) hide show
  1. package/dist/bin.js +1102 -2371
  2. package/dist/index.js +1101 -2370
  3. package/package.json +6 -6
package/dist/bin.js CHANGED
@@ -1498,37 +1498,37 @@ var require_dataType = __commonJS({
1498
1498
  DataType2[DataType2["Wrong"] = 1] = "Wrong";
1499
1499
  })(DataType || (exports.DataType = DataType = {}));
1500
1500
  function getSchemaTypes(schema) {
1501
- const types2 = getJSONTypes(schema.type);
1502
- const hasNull = types2.includes("null");
1501
+ const types = getJSONTypes(schema.type);
1502
+ const hasNull = types.includes("null");
1503
1503
  if (hasNull) {
1504
1504
  if (schema.nullable === false)
1505
1505
  throw new Error("type: null contradicts nullable: false");
1506
1506
  } else {
1507
- if (!types2.length && schema.nullable !== void 0) {
1507
+ if (!types.length && schema.nullable !== void 0) {
1508
1508
  throw new Error('"nullable" cannot be used without "type"');
1509
1509
  }
1510
1510
  if (schema.nullable === true)
1511
- types2.push("null");
1511
+ types.push("null");
1512
1512
  }
1513
- return types2;
1513
+ return types;
1514
1514
  }
1515
1515
  exports.getSchemaTypes = getSchemaTypes;
1516
1516
  function getJSONTypes(ts) {
1517
- const types2 = Array.isArray(ts) ? ts : ts ? [ts] : [];
1518
- if (types2.every(rules_1.isJSONType))
1519
- return types2;
1520
- throw new Error("type must be JSONType or JSONType[]: " + types2.join(","));
1517
+ const types = Array.isArray(ts) ? ts : ts ? [ts] : [];
1518
+ if (types.every(rules_1.isJSONType))
1519
+ return types;
1520
+ throw new Error("type must be JSONType or JSONType[]: " + types.join(","));
1521
1521
  }
1522
1522
  exports.getJSONTypes = getJSONTypes;
1523
- function coerceAndCheckDataType(it, types2) {
1523
+ function coerceAndCheckDataType(it, types) {
1524
1524
  const { gen, data, opts } = it;
1525
- const coerceTo = coerceToTypes(types2, opts.coerceTypes);
1526
- const checkTypes = types2.length > 0 && !(coerceTo.length === 0 && types2.length === 1 && (0, applicability_1.schemaHasRulesForType)(it, types2[0]));
1525
+ const coerceTo = coerceToTypes(types, opts.coerceTypes);
1526
+ const checkTypes = types.length > 0 && !(coerceTo.length === 0 && types.length === 1 && (0, applicability_1.schemaHasRulesForType)(it, types[0]));
1527
1527
  if (checkTypes) {
1528
- const wrongType = checkDataTypes(types2, data, opts.strictNumbers, DataType.Wrong);
1528
+ const wrongType = checkDataTypes(types, data, opts.strictNumbers, DataType.Wrong);
1529
1529
  gen.if(wrongType, () => {
1530
1530
  if (coerceTo.length)
1531
- coerceData(it, types2, coerceTo);
1531
+ coerceData(it, types, coerceTo);
1532
1532
  else
1533
1533
  reportTypeError(it);
1534
1534
  });
@@ -1537,15 +1537,15 @@ var require_dataType = __commonJS({
1537
1537
  }
1538
1538
  exports.coerceAndCheckDataType = coerceAndCheckDataType;
1539
1539
  var COERCIBLE = /* @__PURE__ */ new Set(["string", "number", "integer", "boolean", "null"]);
1540
- function coerceToTypes(types2, coerceTypes) {
1541
- return coerceTypes ? types2.filter((t) => COERCIBLE.has(t) || coerceTypes === "array" && t === "array") : [];
1540
+ function coerceToTypes(types, coerceTypes) {
1541
+ return coerceTypes ? types.filter((t) => COERCIBLE.has(t) || coerceTypes === "array" && t === "array") : [];
1542
1542
  }
1543
- function coerceData(it, types2, coerceTo) {
1543
+ function coerceData(it, types, coerceTo) {
1544
1544
  const { gen, data, opts } = it;
1545
1545
  const dataType = gen.let("dataType", (0, codegen_1._)`typeof ${data}`);
1546
1546
  const coerced = gen.let("coerced", (0, codegen_1._)`undefined`);
1547
1547
  if (opts.coerceTypes === "array") {
1548
- gen.if((0, codegen_1._)`${dataType} == 'object' && Array.isArray(${data}) && ${data}.length == 1`, () => gen.assign(data, (0, codegen_1._)`${data}[0]`).assign(dataType, (0, codegen_1._)`typeof ${data}`).if(checkDataTypes(types2, data, opts.strictNumbers), () => gen.assign(coerced, data)));
1548
+ gen.if((0, codegen_1._)`${dataType} == 'object' && Array.isArray(${data}) && ${data}.length == 1`, () => gen.assign(data, (0, codegen_1._)`${data}[0]`).assign(dataType, (0, codegen_1._)`typeof ${data}`).if(checkDataTypes(types, data, opts.strictNumbers), () => gen.assign(coerced, data)));
1549
1549
  }
1550
1550
  gen.if((0, codegen_1._)`${coerced} !== undefined`);
1551
1551
  for (const t of coerceTo) {
@@ -1621,19 +1621,19 @@ var require_dataType = __commonJS({
1621
1621
  return checkDataType(dataTypes[0], data, strictNums, correct);
1622
1622
  }
1623
1623
  let cond;
1624
- const types2 = (0, util_1.toHash)(dataTypes);
1625
- if (types2.array && types2.object) {
1624
+ const types = (0, util_1.toHash)(dataTypes);
1625
+ if (types.array && types.object) {
1626
1626
  const notObj = (0, codegen_1._)`typeof ${data} != "object"`;
1627
- cond = types2.null ? notObj : (0, codegen_1._)`!${data} || ${notObj}`;
1628
- delete types2.null;
1629
- delete types2.array;
1630
- delete types2.object;
1627
+ cond = types.null ? notObj : (0, codegen_1._)`!${data} || ${notObj}`;
1628
+ delete types.null;
1629
+ delete types.array;
1630
+ delete types.object;
1631
1631
  } else {
1632
1632
  cond = codegen_1.nil;
1633
1633
  }
1634
- if (types2.number)
1635
- delete types2.integer;
1636
- for (const t in types2)
1634
+ if (types.number)
1635
+ delete types.integer;
1636
+ for (const t in types)
1637
1637
  cond = (0, codegen_1.and)(cond, checkDataType(t, data, strictNums, correct));
1638
1638
  return cond;
1639
1639
  }
@@ -2438,9 +2438,9 @@ var require_validate = __commonJS({
2438
2438
  function typeAndKeywords(it, errsCount) {
2439
2439
  if (it.opts.jtd)
2440
2440
  return schemaKeywords(it, [], false, errsCount);
2441
- const types2 = (0, dataType_1.getSchemaTypes)(it.schema);
2442
- const checkedTypes = (0, dataType_1.coerceAndCheckDataType)(it, types2);
2443
- schemaKeywords(it, types2, !checkedTypes, errsCount);
2441
+ const types = (0, dataType_1.getSchemaTypes)(it.schema);
2442
+ const checkedTypes = (0, dataType_1.coerceAndCheckDataType)(it, types);
2443
+ schemaKeywords(it, types, !checkedTypes, errsCount);
2444
2444
  }
2445
2445
  function checkRefsAndKeywords(it) {
2446
2446
  const { schema, errSchemaPath, opts, self } = it;
@@ -2490,7 +2490,7 @@ var require_validate = __commonJS({
2490
2490
  if (items instanceof codegen_1.Name)
2491
2491
  gen.assign((0, codegen_1._)`${evaluated}.items`, items);
2492
2492
  }
2493
- function schemaKeywords(it, types2, typeErrors, errsCount) {
2493
+ function schemaKeywords(it, types, typeErrors, errsCount) {
2494
2494
  const { gen, schema, data, allErrors, opts, self } = it;
2495
2495
  const { RULES } = self;
2496
2496
  if (schema.$ref && (opts.ignoreKeywordsWithRef || !(0, util_1.schemaHasRulesButRef)(schema, RULES))) {
@@ -2498,7 +2498,7 @@ var require_validate = __commonJS({
2498
2498
  return;
2499
2499
  }
2500
2500
  if (!opts.jtd)
2501
- checkStrictTypes(it, types2);
2501
+ checkStrictTypes(it, types);
2502
2502
  gen.block(() => {
2503
2503
  for (const group of RULES.rules)
2504
2504
  groupKeywords(group);
@@ -2510,7 +2510,7 @@ var require_validate = __commonJS({
2510
2510
  if (group.type) {
2511
2511
  gen.if((0, dataType_2.checkDataType)(group.type, data, opts.strictNumbers));
2512
2512
  iterateKeywords(it, group);
2513
- if (types2.length === 1 && types2[0] === group.type && typeErrors) {
2513
+ if (types.length === 1 && types[0] === group.type && typeErrors) {
2514
2514
  gen.else();
2515
2515
  (0, dataType_2.reportTypeError)(it);
2516
2516
  }
@@ -2534,27 +2534,27 @@ var require_validate = __commonJS({
2534
2534
  }
2535
2535
  });
2536
2536
  }
2537
- function checkStrictTypes(it, types2) {
2537
+ function checkStrictTypes(it, types) {
2538
2538
  if (it.schemaEnv.meta || !it.opts.strictTypes)
2539
2539
  return;
2540
- checkContextTypes(it, types2);
2540
+ checkContextTypes(it, types);
2541
2541
  if (!it.opts.allowUnionTypes)
2542
- checkMultipleTypes(it, types2);
2542
+ checkMultipleTypes(it, types);
2543
2543
  checkKeywordTypes(it, it.dataTypes);
2544
2544
  }
2545
- function checkContextTypes(it, types2) {
2546
- if (!types2.length)
2545
+ function checkContextTypes(it, types) {
2546
+ if (!types.length)
2547
2547
  return;
2548
2548
  if (!it.dataTypes.length) {
2549
- it.dataTypes = types2;
2549
+ it.dataTypes = types;
2550
2550
  return;
2551
2551
  }
2552
- types2.forEach((t) => {
2552
+ types.forEach((t) => {
2553
2553
  if (!includesType(it.dataTypes, t)) {
2554
2554
  strictTypesError(it, `type "${t}" not allowed by context "${it.dataTypes.join(",")}"`);
2555
2555
  }
2556
2556
  });
2557
- narrowSchemaTypes(it, types2);
2557
+ narrowSchemaTypes(it, types);
2558
2558
  }
2559
2559
  function checkMultipleTypes(it, ts) {
2560
2560
  if (ts.length > 1 && !(ts.length === 2 && ts.includes("null"))) {
@@ -2980,7 +2980,7 @@ var require_compile = __commonJS({
2980
2980
  const schOrFunc = root.refs[ref];
2981
2981
  if (schOrFunc)
2982
2982
  return schOrFunc;
2983
- let _sch = resolve5.call(this, root, ref);
2983
+ let _sch = resolve6.call(this, root, ref);
2984
2984
  if (_sch === void 0) {
2985
2985
  const schema = (_a2 = root.localRefs) === null || _a2 === void 0 ? void 0 : _a2[ref];
2986
2986
  const { schemaId } = this.opts;
@@ -3007,7 +3007,7 @@ var require_compile = __commonJS({
3007
3007
  function sameSchemaEnv(s1, s2) {
3008
3008
  return s1.schema === s2.schema && s1.root === s2.root && s1.baseId === s2.baseId;
3009
3009
  }
3010
- function resolve5(root, ref) {
3010
+ function resolve6(root, ref) {
3011
3011
  let sch;
3012
3012
  while (typeof (sch = this.refs[ref]) == "string")
3013
3013
  ref = sch;
@@ -3222,8 +3222,8 @@ var require_utils = __commonJS({
3222
3222
  }
3223
3223
  return ind;
3224
3224
  }
3225
- function removeDotSegments(path2) {
3226
- let input = path2;
3225
+ function removeDotSegments(path) {
3226
+ let input = path;
3227
3227
  const output = [];
3228
3228
  let nextSlash = -1;
3229
3229
  let len = 0;
@@ -3422,8 +3422,8 @@ var require_schemes = __commonJS({
3422
3422
  wsComponent.secure = void 0;
3423
3423
  }
3424
3424
  if (wsComponent.resourceName) {
3425
- const [path2, query] = wsComponent.resourceName.split("?");
3426
- wsComponent.path = path2 && path2 !== "/" ? path2 : void 0;
3425
+ const [path, query] = wsComponent.resourceName.split("?");
3426
+ wsComponent.path = path && path !== "/" ? path : void 0;
3427
3427
  wsComponent.query = query;
3428
3428
  wsComponent.resourceName = void 0;
3429
3429
  }
@@ -3582,7 +3582,7 @@ var require_fast_uri = __commonJS({
3582
3582
  }
3583
3583
  return uri;
3584
3584
  }
3585
- function resolve5(baseURI, relativeURI, options) {
3585
+ function resolve6(baseURI, relativeURI, options) {
3586
3586
  const schemelessOptions = options ? Object.assign({ scheme: "null" }, options) : { scheme: "null" };
3587
3587
  const resolved = resolveComponent(parse3(baseURI, schemelessOptions), parse3(relativeURI, schemelessOptions), schemelessOptions, true);
3588
3588
  schemelessOptions.skipEscape = true;
@@ -3809,7 +3809,7 @@ var require_fast_uri = __commonJS({
3809
3809
  var fastUri = {
3810
3810
  SCHEMES,
3811
3811
  normalize,
3812
- resolve: resolve5,
3812
+ resolve: resolve6,
3813
3813
  resolveComponent,
3814
3814
  equal,
3815
3815
  serialize,
@@ -7869,7 +7869,7 @@ function maybePushScalarOverwriteWarning(warnings, componentId, field, existingV
7869
7869
  });
7870
7870
  }
7871
7871
  function mergeNestedObject(existing, incoming, options, warnings, componentId, pathPrefix) {
7872
- const merged = { ...existing ?? {} };
7872
+ const merged = { ...existing };
7873
7873
  for (const [field, incomingValue] of Object.entries(incoming)) {
7874
7874
  if (!isDefined(incomingValue)) {
7875
7875
  continue;
@@ -9072,9 +9072,9 @@ function floatSafeRemainder(val, step) {
9072
9072
  const stepString = step.toString();
9073
9073
  let stepDecCount = (stepString.split(".")[1] || "").length;
9074
9074
  if (stepDecCount === 0 && /\d?e-\d?/.test(stepString)) {
9075
- const match2 = stepString.match(/\d?e-(\d?)/);
9076
- if (match2?.[1]) {
9077
- stepDecCount = Number.parseInt(match2[1]);
9075
+ const match = stepString.match(/\d?e-(\d?)/);
9076
+ if (match?.[1]) {
9077
+ stepDecCount = Number.parseInt(match[1]);
9078
9078
  }
9079
9079
  }
9080
9080
  const decCount = valDecCount > stepDecCount ? valDecCount : stepDecCount;
@@ -9127,10 +9127,10 @@ function mergeDefs(...defs) {
9127
9127
  function cloneDef(schema) {
9128
9128
  return mergeDefs(schema._zod.def);
9129
9129
  }
9130
- function getElementAtPath(obj, path2) {
9131
- if (!path2)
9130
+ function getElementAtPath(obj, path) {
9131
+ if (!path)
9132
9132
  return obj;
9133
- return path2.reduce((acc, key) => acc?.[key], obj);
9133
+ return path.reduce((acc, key) => acc?.[key], obj);
9134
9134
  }
9135
9135
  function promiseAllObject(promisesObj) {
9136
9136
  const keys = Object.keys(promisesObj);
@@ -9513,11 +9513,11 @@ function aborted(x, startIndex = 0) {
9513
9513
  }
9514
9514
  return false;
9515
9515
  }
9516
- function prefixIssues(path2, issues) {
9516
+ function prefixIssues(path, issues) {
9517
9517
  return issues.map((iss) => {
9518
9518
  var _a2;
9519
9519
  (_a2 = iss).path ?? (_a2.path = []);
9520
- iss.path.unshift(path2);
9520
+ iss.path.unshift(path);
9521
9521
  return iss;
9522
9522
  });
9523
9523
  }
@@ -9700,7 +9700,7 @@ function formatError(error48, mapper = (issue2) => issue2.message) {
9700
9700
  }
9701
9701
  function treeifyError(error48, mapper = (issue2) => issue2.message) {
9702
9702
  const result = { errors: [] };
9703
- const processError = (error49, path2 = []) => {
9703
+ const processError = (error49, path = []) => {
9704
9704
  var _a2, _b;
9705
9705
  for (const issue2 of error49.issues) {
9706
9706
  if (issue2.code === "invalid_union" && issue2.errors.length) {
@@ -9710,7 +9710,7 @@ function treeifyError(error48, mapper = (issue2) => issue2.message) {
9710
9710
  } else if (issue2.code === "invalid_element") {
9711
9711
  processError({ issues: issue2.issues }, issue2.path);
9712
9712
  } else {
9713
- const fullpath = [...path2, ...issue2.path];
9713
+ const fullpath = [...path, ...issue2.path];
9714
9714
  if (fullpath.length === 0) {
9715
9715
  result.errors.push(mapper(issue2));
9716
9716
  continue;
@@ -9742,8 +9742,8 @@ function treeifyError(error48, mapper = (issue2) => issue2.message) {
9742
9742
  }
9743
9743
  function toDotPath(_path) {
9744
9744
  const segs = [];
9745
- const path2 = _path.map((seg) => typeof seg === "object" ? seg.key : seg);
9746
- for (const seg of path2) {
9745
+ const path = _path.map((seg) => typeof seg === "object" ? seg.key : seg);
9746
+ for (const seg of path) {
9747
9747
  if (typeof seg === "number")
9748
9748
  segs.push(`[${seg}]`);
9749
9749
  else if (typeof seg === "symbol")
@@ -18856,10 +18856,10 @@ function _property(property, schema, params) {
18856
18856
  });
18857
18857
  }
18858
18858
  // @__NO_SIDE_EFFECTS__
18859
- function _mime(types2, params) {
18859
+ function _mime(types, params) {
18860
18860
  return new $ZodCheckMimeType({
18861
18861
  check: "mime_type",
18862
- mime: types2,
18862
+ mime: types,
18863
18863
  ...normalizeParams(params)
18864
18864
  });
18865
18865
  }
@@ -19385,8 +19385,8 @@ Set the \`cycles\` parameter to \`"ref"\` to resolve cyclical schemas with defs.
19385
19385
  continue;
19386
19386
  }
19387
19387
  if (ctx.external) {
19388
- const ext2 = ctx.external.registry.get(entry[0])?.id;
19389
- if (schema !== entry[0] && ext2) {
19388
+ const ext = ctx.external.registry.get(entry[0])?.id;
19389
+ if (schema !== entry[0] && ext) {
19390
19390
  extractToDef(entry);
19391
19391
  continue;
19392
19392
  }
@@ -21291,7 +21291,7 @@ var ZodFile = /* @__PURE__ */ $constructor("ZodFile", (inst, def) => {
21291
21291
  inst._zod.processJSONSchema = (ctx, json2, params) => fileProcessor(inst, ctx, json2, params);
21292
21292
  inst.min = (size, params) => inst.check(_minSize(size, params));
21293
21293
  inst.max = (size, params) => inst.check(_maxSize(size, params));
21294
- inst.mime = (types2, params) => inst.check(_mime(Array.isArray(types2) ? types2 : [types2], params));
21294
+ inst.mime = (types, params) => inst.check(_mime(Array.isArray(types) ? types : [types], params));
21295
21295
  });
21296
21296
  function file(params) {
21297
21297
  return _file(ZodFile, params);
@@ -21720,13 +21720,13 @@ function resolveRef(ref, ctx) {
21720
21720
  if (!ref.startsWith("#")) {
21721
21721
  throw new Error("External $ref is not supported, only local refs (#/...) are allowed");
21722
21722
  }
21723
- const path2 = ref.slice(1).split("/").filter(Boolean);
21724
- if (path2.length === 0) {
21723
+ const path = ref.slice(1).split("/").filter(Boolean);
21724
+ if (path.length === 0) {
21725
21725
  return ctx.rootSchema;
21726
21726
  }
21727
21727
  const defsKey = ctx.version === "draft-2020-12" ? "$defs" : "definitions";
21728
- if (path2[0] === defsKey) {
21729
- const key = path2[1];
21728
+ if (path[0] === defsKey) {
21729
+ const key = path[1];
21730
21730
  if (!key || !ctx.defs[key]) {
21731
21731
  throw new Error(`Reference not found: ${ref}`);
21732
21732
  }
@@ -24018,9 +24018,9 @@ import { accessSync } from "node:fs";
24018
24018
  function isNodeError(error48) {
24019
24019
  return error48 instanceof Error && "code" in error48;
24020
24020
  }
24021
- function fileExists(path2) {
24021
+ function fileExists(path) {
24022
24022
  try {
24023
- accessSync(path2);
24023
+ accessSync(path);
24024
24024
  return true;
24025
24025
  } catch (error48) {
24026
24026
  if (isNodeError(error48) && error48.code === "ENOENT") {
@@ -24589,11 +24589,11 @@ function failure11(code, message, suggestions = []) {
24589
24589
  function isRestApiWithPath(component) {
24590
24590
  return component.type === "API" && "path" in component && "httpMethod" in component;
24591
24591
  }
24592
- function findApisByPath(graph, path2, method) {
24592
+ function findApisByPath(graph, path, method) {
24593
24593
  const query = new RiviereQuery(graph);
24594
24594
  const allComponents = query.componentsByType("API");
24595
24595
  const apis = allComponents.filter(isRestApiWithPath);
24596
- const matchingPath = apis.filter((api) => api.path === path2);
24596
+ const matchingPath = apis.filter((api) => api.path === path);
24597
24597
  if (method) {
24598
24598
  return matchingPath.filter((api) => api.httpMethod === method);
24599
24599
  }
@@ -25777,21 +25777,19 @@ Examples:
25777
25777
 
25778
25778
  // src/features/extract/infra/persistence/extraction-project/extraction-project-repository.ts
25779
25779
  import {
25780
- existsSync as existsSync4,
25781
- readFileSync as readFileSync3
25780
+ existsSync as existsSync5,
25781
+ readFileSync as readFileSync4
25782
25782
  } from "node:fs";
25783
- import { createRequire } from "node:module";
25784
25783
  import {
25785
- dirname as dirname2,
25786
- posix as posix4,
25787
- resolve as resolve4
25784
+ dirname as dirname3,
25785
+ posix,
25786
+ resolve as resolve5
25788
25787
  } from "node:path";
25789
- import { parse as parseYaml } from "yaml";
25788
+ import { parse as parseYaml2 } from "yaml";
25790
25789
  import { globSync } from "glob";
25791
25790
 
25792
25791
  // ../riviere-extract-ts/dist/features/extraction/domain/component-extraction/extractor.js
25793
25792
  import { Scope } from "ts-morph";
25794
- import { posix } from "node:path";
25795
25793
 
25796
25794
  // ../riviere-extract-ts/dist/features/extraction/domain/predicate-evaluation/evaluate-predicate.js
25797
25795
  import { Node as TsMorphNode } from "ts-morph";
@@ -25915,6 +25913,22 @@ function evaluateInClassWith(node, predicate) {
25915
25913
  return evaluatePredicate(parent, predicate);
25916
25914
  }
25917
25915
 
25916
+ // ../riviere-extract-ts/dist/features/extraction/domain/component-extraction/draft-component.js
25917
+ var DraftComponent = class {
25918
+ type;
25919
+ name;
25920
+ location;
25921
+ domain;
25922
+ module;
25923
+ constructor(params) {
25924
+ this.type = params.type;
25925
+ this.name = params.name;
25926
+ this.location = params.location;
25927
+ this.domain = params.domain;
25928
+ this.module = params.module;
25929
+ }
25930
+ };
25931
+
25918
25932
  // ../riviere-extract-ts/dist/features/extraction/domain/component-extraction/extractor.js
25919
25933
  var COMPONENT_TYPES = [
25920
25934
  "api",
@@ -25924,19 +25938,15 @@ var COMPONENT_TYPES = [
25924
25938
  "eventHandler",
25925
25939
  "ui"
25926
25940
  ];
25927
- function extractComponents(project, sourceFilePaths, config2, globMatcher, configDir) {
25928
- return sourceFilePaths.flatMap((filePath) => extractFromFile(project, filePath, config2, globMatcher, configDir));
25941
+ function extractComponents(project, sourceFilePaths, module) {
25942
+ return sourceFilePaths.flatMap((filePath) => extractFromFile(project, filePath, module));
25929
25943
  }
25930
- function extractFromFile(project, filePath, config2, globMatcher, configDir) {
25944
+ function extractFromFile(project, filePath, module) {
25931
25945
  const sourceFile = project.getSourceFile(filePath);
25932
25946
  if (sourceFile === void 0) {
25933
25947
  return [];
25934
25948
  }
25935
- const matchingModule = findMatchingModule(filePath, config2.modules, globMatcher, configDir);
25936
- if (matchingModule === void 0) {
25937
- return [];
25938
- }
25939
- return extractFromModule(sourceFile, filePath, matchingModule);
25949
+ return extractFromModule(sourceFile, filePath, module);
25940
25950
  }
25941
25951
  function extractFromModule(sourceFile, filePath, module) {
25942
25952
  const context = resolveComponentContext(filePath, module);
@@ -26017,7 +26027,7 @@ function createClassComponent(classDecl, filePath, context, componentType) {
26017
26027
  return [];
26018
26028
  }
26019
26029
  return [
26020
- {
26030
+ new DraftComponent({
26021
26031
  type: componentType,
26022
26032
  name,
26023
26033
  location: {
@@ -26026,13 +26036,13 @@ function createClassComponent(classDecl, filePath, context, componentType) {
26026
26036
  },
26027
26037
  domain: context.domain,
26028
26038
  module: context.module
26029
- }
26039
+ })
26030
26040
  ];
26031
26041
  }
26032
26042
  function createMethodComponent(method, filePath, context, componentType) {
26033
26043
  const name = method.getName();
26034
26044
  return [
26035
- {
26045
+ new DraftComponent({
26036
26046
  type: componentType,
26037
26047
  name,
26038
26048
  location: {
@@ -26041,7 +26051,7 @@ function createMethodComponent(method, filePath, context, componentType) {
26041
26051
  },
26042
26052
  domain: context.domain,
26043
26053
  module: context.module
26044
- }
26054
+ })
26045
26055
  ];
26046
26056
  }
26047
26057
  function createFunctionComponent(func, filePath, context, componentType) {
@@ -26050,7 +26060,7 @@ function createFunctionComponent(func, filePath, context, componentType) {
26050
26060
  return [];
26051
26061
  }
26052
26062
  return [
26053
- {
26063
+ new DraftComponent({
26054
26064
  type: componentType,
26055
26065
  name,
26056
26066
  location: {
@@ -26059,28 +26069,11 @@ function createFunctionComponent(func, filePath, context, componentType) {
26059
26069
  },
26060
26070
  domain: context.domain,
26061
26071
  module: context.module
26062
- }
26072
+ })
26063
26073
  ];
26064
26074
  }
26065
- function findMatchingModule(filePath, modules, globMatcher, configDir) {
26066
- const normalized = filePath.replaceAll(/\\+/g, "/");
26067
- if (configDir === void 0) {
26068
- return modules.find((m) => globMatcher(normalized, posix.join(m.path, m.glob)));
26069
- }
26070
- const normalizedConfigDir = configDir.replaceAll(/\\+/g, "/");
26071
- const pathToMatch = posix.relative(normalizedConfigDir, normalized);
26072
- return modules.find((m) => globMatcher(pathToMatch, posix.join(m.path, m.glob)));
26073
- }
26074
26075
 
26075
26076
  // ../riviere-extract-ts/dist/features/extraction/domain/config-resolution/config-resolution-errors.js
26076
- var ConfigLoaderRequiredError = class extends Error {
26077
- moduleName;
26078
- constructor(moduleName) {
26079
- super(`Module '${moduleName}' uses extends but no config loader was provided.`);
26080
- this.name = "ConfigLoaderRequiredError";
26081
- this.moduleName = moduleName;
26082
- }
26083
- };
26084
26077
  var MissingComponentRuleError = class extends Error {
26085
26078
  moduleName;
26086
26079
  ruleName;
@@ -26093,17 +26086,13 @@ var MissingComponentRuleError = class extends Error {
26093
26086
  };
26094
26087
 
26095
26088
  // ../riviere-extract-ts/dist/features/extraction/domain/config-resolution/resolve-config.js
26096
- function resolveConfig(config2, loader) {
26089
+ function resolveConfig(config2) {
26097
26090
  return {
26098
26091
  ...config2,
26099
- modules: config2.modules.map((m) => resolveModule(m, loader))
26092
+ modules: config2.modules.map(resolveModule)
26100
26093
  };
26101
26094
  }
26102
- function resolveModule(moduleConfig, loader) {
26103
- const extendsSource = moduleConfig.extends;
26104
- if (extendsSource !== void 0) {
26105
- return resolveModuleWithExtends(moduleConfig, extendsSource, loader);
26106
- }
26095
+ function resolveModule(moduleConfig) {
26107
26096
  return {
26108
26097
  name: moduleConfig.name,
26109
26098
  domain: moduleConfig.domain,
@@ -26119,36 +26108,6 @@ function resolveModule(moduleConfig, loader) {
26119
26108
  ...moduleConfig.customTypes !== void 0 && { customTypes: moduleConfig.customTypes }
26120
26109
  };
26121
26110
  }
26122
- function resolveModuleWithExtends(moduleConfig, extendsSource, loader) {
26123
- if (loader === void 0) {
26124
- throw new ConfigLoaderRequiredError(moduleConfig.name);
26125
- }
26126
- const baseModule = loader(extendsSource);
26127
- const mergedCustomTypes = mergeCustomTypes(baseModule.customTypes, moduleConfig.customTypes);
26128
- return {
26129
- name: moduleConfig.name,
26130
- domain: moduleConfig.domain,
26131
- path: moduleConfig.path,
26132
- glob: moduleConfig.glob,
26133
- ...moduleConfig.modules !== void 0 && { modules: moduleConfig.modules },
26134
- api: moduleConfig.api ?? baseModule.api,
26135
- useCase: moduleConfig.useCase ?? baseModule.useCase,
26136
- domainOp: moduleConfig.domainOp ?? baseModule.domainOp,
26137
- event: moduleConfig.event ?? baseModule.event,
26138
- eventHandler: moduleConfig.eventHandler ?? baseModule.eventHandler,
26139
- ui: moduleConfig.ui ?? baseModule.ui,
26140
- ...mergedCustomTypes !== void 0 && { customTypes: mergedCustomTypes }
26141
- };
26142
- }
26143
- function mergeCustomTypes(base, local) {
26144
- if (base === void 0 && local === void 0) {
26145
- return void 0;
26146
- }
26147
- return {
26148
- ...base,
26149
- ...local
26150
- };
26151
- }
26152
26111
  function requireRule(rule, ruleName, moduleName) {
26153
26112
  if (rule === void 0) {
26154
26113
  throw new MissingComponentRuleError(moduleName, ruleName);
@@ -26156,6 +26115,14 @@ function requireRule(rule, ruleName, moduleName) {
26156
26115
  return rule;
26157
26116
  }
26158
26117
 
26118
+ // ../riviere-extract-ts/dist/features/extraction/domain/value-extraction/extraction-result.js
26119
+ var ExtractionResult = class {
26120
+ value;
26121
+ constructor(params) {
26122
+ this.value = params.value;
26123
+ }
26124
+ };
26125
+
26159
26126
  // ../riviere-extract-ts/dist/platform/domain/string-transforms/transforms.js
26160
26127
  function stripSuffix(value, suffix) {
26161
26128
  if (value.endsWith(suffix)) {
@@ -26220,6 +26187,14 @@ var ExtractionError = class extends Error {
26220
26187
  };
26221
26188
  }
26222
26189
  };
26190
+ var LiteralResult = class {
26191
+ kind;
26192
+ value;
26193
+ constructor(params) {
26194
+ this.kind = params.kind;
26195
+ this.value = params.value;
26196
+ }
26197
+ };
26223
26198
  function extractString(expression) {
26224
26199
  return expression.asKindOrThrow(SyntaxKind.StringLiteral).getLiteralValue();
26225
26200
  }
@@ -26242,34 +26217,34 @@ function buildExtractionResult(expression) {
26242
26217
  const syntaxKind = expression.getKind();
26243
26218
  switch (syntaxKind) {
26244
26219
  case SyntaxKind.StringLiteral:
26245
- return {
26220
+ return new LiteralResult({
26246
26221
  kind: "string",
26247
26222
  value: extractString(expression)
26248
- };
26223
+ });
26249
26224
  case SyntaxKind.NumericLiteral:
26250
- return {
26225
+ return new LiteralResult({
26251
26226
  kind: "number",
26252
26227
  value: extractNumber(expression)
26253
- };
26228
+ });
26254
26229
  case SyntaxKind.TrueKeyword:
26255
- return {
26230
+ return new LiteralResult({
26256
26231
  kind: "boolean",
26257
26232
  value: true
26258
- };
26233
+ });
26259
26234
  case SyntaxKind.FalseKeyword:
26260
- return {
26235
+ return new LiteralResult({
26261
26236
  kind: "boolean",
26262
26237
  value: false
26263
- };
26238
+ });
26264
26239
  case SyntaxKind.ArrayLiteralExpression: {
26265
26240
  const values = extractStringArray(expression);
26266
26241
  if (values === void 0) {
26267
26242
  return void 0;
26268
26243
  }
26269
- return {
26244
+ return new LiteralResult({
26270
26245
  kind: "string[]",
26271
26246
  value: values
26272
- };
26247
+ });
26273
26248
  }
26274
26249
  default:
26275
26250
  return void 0;
@@ -26292,1911 +26267,177 @@ function extractLiteralValue(expression, file2, line) {
26292
26267
  return result;
26293
26268
  }
26294
26269
 
26295
- // ../riviere-extract-ts/dist/features/extraction/domain/value-extraction/evaluate-extraction-rule-generic.js
26296
- import { SyntaxKind as SyntaxKind2 } from "ts-morph";
26297
- function getInterfaceTypeArgs(classDecl, interfaceName) {
26298
- const implementsClause = classDecl.getImplements();
26299
- for (const impl of implementsClause) {
26300
- const expression = impl.getExpression();
26301
- if (expression.getText() === interfaceName) {
26302
- return impl.getTypeArguments();
26303
- }
26304
- }
26305
- const extendsClause = classDecl.getExtends();
26306
- if (extendsClause === void 0) {
26307
- return void 0;
26270
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/detect-connections.js
26271
+ import { performance } from "node:perf_hooks";
26272
+
26273
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/async-detection/async-detection-options.js
26274
+ var AsyncDetectionOptions = class {
26275
+ strict;
26276
+ repository;
26277
+ constructor(params) {
26278
+ this.strict = params.strict;
26279
+ this.repository = params.repository;
26308
26280
  }
26309
- const baseClass = classDecl.getBaseClass();
26310
- if (baseClass === void 0)
26311
- return void 0;
26312
- return getInterfaceTypeArgs(baseClass, interfaceName);
26281
+ };
26282
+
26283
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/component-index.js
26284
+ function locationKey(file2, line) {
26285
+ return `${file2}:${line}`;
26313
26286
  }
26314
- function extractTypeNames(typeNode) {
26315
- if (typeNode.getKind() === SyntaxKind2.UnionType) {
26316
- const unionType = typeNode.asKindOrThrow(SyntaxKind2.UnionType);
26317
- return unionType.getTypeNodes().map((t) => t.getText());
26287
+ var ComponentIndex = class {
26288
+ byName;
26289
+ byLocation;
26290
+ constructor(components) {
26291
+ const nameMap = /* @__PURE__ */ new Map();
26292
+ const locationMap = /* @__PURE__ */ new Map();
26293
+ for (const component of components) {
26294
+ nameMap.set(component.name, component);
26295
+ locationMap.set(locationKey(component.location.file, component.location.line), component);
26296
+ }
26297
+ this.byName = nameMap;
26298
+ this.byLocation = locationMap;
26318
26299
  }
26319
- return [typeNode.getText()];
26320
- }
26321
- function evaluateFromGenericArgRule(rule, classDecl) {
26322
- const { interface: interfaceName, position, transform: transform2 } = rule.fromGenericArg;
26323
- const sourceFile = classDecl.getSourceFile();
26324
- const location = {
26325
- filePath: sourceFile.getFilePath(),
26326
- line: classDecl.getStartLineNumber()
26327
- };
26328
- const typeArgs = getInterfaceTypeArgs(classDecl, interfaceName);
26329
- if (typeArgs === void 0) {
26330
- throw new ExtractionError(`Class '${classDecl.getName() ?? "anonymous"}' does not implement interface '${interfaceName}'`, location.filePath, location.line);
26300
+ isComponent(typeName) {
26301
+ return this.byName.has(this.withoutGenericArguments(typeName));
26331
26302
  }
26332
- const typeArg = typeArgs[position];
26333
- if (typeArg === void 0) {
26334
- throw new ExtractionError(`Position ${position} out of bounds. Interface has ${typeArgs.length} type argument(s)`, location.filePath, location.line);
26303
+ getComponentByTypeName(typeName) {
26304
+ return this.byName.get(this.withoutGenericArguments(typeName));
26335
26305
  }
26336
- if (typeArg.getKind() === SyntaxKind2.TypeReference) {
26337
- const typeRef = typeArg.asKindOrThrow(SyntaxKind2.TypeReference);
26338
- const typeName = typeRef.getTypeName();
26339
- if (typeName.getKind() === SyntaxKind2.Identifier) {
26340
- const classTypeParams = classDecl.getTypeParameters();
26341
- const paramName = typeName.getText();
26342
- const isTypeParam = classTypeParams.some((p) => p.getName() === paramName);
26343
- if (isTypeParam) {
26344
- throw new ExtractionError(`Generic argument at position ${position} is type parameter '${paramName}', expected concrete type`, location.filePath, location.line);
26345
- }
26346
- }
26306
+ getComponentByLocation(file2, line) {
26307
+ return this.byLocation.get(locationKey(file2, line));
26347
26308
  }
26348
- const typeNames = extractTypeNames(typeArg);
26349
- if (transform2 === void 0) {
26350
- return { value: typeNames };
26309
+ withoutGenericArguments(typeName) {
26310
+ const index = typeName.indexOf("<");
26311
+ if (index === -1) {
26312
+ return typeName;
26313
+ }
26314
+ return typeName.slice(0, index);
26351
26315
  }
26352
- return { value: typeNames.map((name) => applyTransforms(name, transform2)) };
26353
- }
26316
+ };
26354
26317
 
26355
- // ../riviere-extract-ts/dist/features/extraction/domain/value-extraction/evaluate-extraction-rule.js
26356
- import { SyntaxKind as SyntaxKind3 } from "ts-morph";
26357
- function literal2(value) {
26358
- return { value };
26359
- }
26360
- function evaluateLiteralRule(rule) {
26361
- return literal2(rule.literal);
26362
- }
26363
- function evaluateFromClassNameRule(rule, classDecl) {
26364
- const className = classDecl.getName();
26365
- if (!className) {
26366
- const filePath = classDecl.getSourceFile().getFilePath();
26367
- const lineNumber = classDecl.getStartLineNumber();
26368
- throw new ExtractionError("Expected class name, got undefined", filePath, lineNumber);
26318
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/build-call-graph.js
26319
+ import { Node as Node3, SyntaxKind as SyntaxKind4 } from "ts-morph";
26320
+
26321
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/call-graph-types.js
26322
+ var CallGraphOptions = class {
26323
+ strict;
26324
+ sourceFilePaths;
26325
+ repository;
26326
+ constructor(params) {
26327
+ this.strict = params.strict;
26328
+ this.sourceFilePaths = params.sourceFilePaths;
26329
+ this.repository = params.repository;
26369
26330
  }
26370
- if (rule.fromClassName === true) {
26371
- return { value: className };
26331
+ };
26332
+ var CallSite = class {
26333
+ filePath;
26334
+ lineNumber;
26335
+ methodName;
26336
+ constructor(params) {
26337
+ this.filePath = params.filePath;
26338
+ this.lineNumber = params.lineNumber;
26339
+ this.methodName = params.methodName;
26372
26340
  }
26373
- const transform2 = rule.fromClassName.transform;
26374
- if (transform2 === void 0) {
26375
- return { value: className };
26341
+ };
26342
+ var RawLink = class {
26343
+ source;
26344
+ target;
26345
+ callSite;
26346
+ constructor(params) {
26347
+ this.source = params.source;
26348
+ this.target = params.target;
26349
+ this.callSite = params.callSite;
26350
+ }
26351
+ };
26352
+ var UncertainRawLink = class {
26353
+ source;
26354
+ reason;
26355
+ callSite;
26356
+ constructor(params) {
26357
+ this.source = params.source;
26358
+ this.reason = params.reason;
26359
+ this.callSite = params.callSite;
26376
26360
  }
26377
- return { value: applyTransforms(className, transform2) };
26361
+ };
26362
+
26363
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/component-identity.js
26364
+ function componentIdentity(component) {
26365
+ return ComponentId.create({
26366
+ domain: component.domain,
26367
+ module: component.module,
26368
+ type: component.type,
26369
+ name: component.name
26370
+ }).toString();
26378
26371
  }
26379
- function evaluateFromMethodNameRule(rule, methodDecl) {
26380
- const methodName = methodDecl.getName();
26381
- if (rule.fromMethodName === true) {
26382
- return { value: methodName };
26372
+
26373
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/trace-calls.js
26374
+ import { Node as Node2, SyntaxKind as SyntaxKind3 } from "ts-morph";
26375
+
26376
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/method-level-target.js
26377
+ var MethodLevelTarget = class {
26378
+ classDecl;
26379
+ method;
26380
+ constructor(params) {
26381
+ this.classDecl = params.classDecl;
26382
+ this.method = params.method;
26383
26383
  }
26384
- const transform2 = rule.fromMethodName.transform;
26385
- if (transform2 === void 0) {
26386
- return { value: methodName };
26384
+ };
26385
+
26386
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/type-resolver.js
26387
+ import { CallExpression, SourceFile, Node } from "ts-morph";
26388
+
26389
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/connection-detection-error.js
26390
+ var ConnectionDetectionError = class extends Error {
26391
+ file;
26392
+ line;
26393
+ typeName;
26394
+ reason;
26395
+ constructor(params) {
26396
+ super(`Connection detection failed for ${params.typeName} at ${params.file}:${params.line}: ${params.reason}`);
26397
+ this.name = "ConnectionDetectionError";
26398
+ this.file = params.file;
26399
+ this.line = params.line;
26400
+ this.typeName = params.typeName;
26401
+ this.reason = params.reason;
26387
26402
  }
26388
- return { value: applyTransforms(methodName, transform2) };
26389
- }
26390
- function evaluateFromFilePathRule(rule, filePath) {
26391
- const pattern = rule.fromFilePath.pattern;
26392
- const capture = rule.fromFilePath.capture;
26393
- const transform2 = rule.fromFilePath.transform;
26394
- const regex = new RegExp(pattern);
26395
- const match2 = regex.exec(filePath);
26396
- if (match2 === null) {
26397
- throw new ExtractionError(`Pattern '${pattern}' did not match file path '${filePath}'`, filePath, 0);
26403
+ };
26404
+
26405
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/type-resolver.js
26406
+ var TypeResolution = class _TypeResolution {
26407
+ resolved;
26408
+ typeName;
26409
+ reason;
26410
+ constructor(params) {
26411
+ this.resolved = params.resolved;
26412
+ this.typeName = params.typeName;
26413
+ this.reason = params.reason;
26398
26414
  }
26399
- const capturedValue = match2[capture];
26400
- if (capturedValue === void 0) {
26401
- throw new ExtractionError(`Capture group ${capture} out of bounds. Pattern has ${match2.length - 1} capture groups`, filePath, 0);
26415
+ static resolved(typeName) {
26416
+ return new _TypeResolution({
26417
+ resolved: true,
26418
+ typeName,
26419
+ reason: void 0
26420
+ });
26402
26421
  }
26403
- if (transform2 === void 0) {
26404
- return { value: capturedValue };
26422
+ static unresolved(reason) {
26423
+ return new _TypeResolution({
26424
+ resolved: false,
26425
+ typeName: void 0,
26426
+ reason
26427
+ });
26405
26428
  }
26406
- return { value: applyTransforms(capturedValue, transform2) };
26429
+ };
26430
+ function stripGenerics(typeName) {
26431
+ const angleBracketIndex = typeName.indexOf("<");
26432
+ if (angleBracketIndex === -1)
26433
+ return typeName;
26434
+ return typeName.slice(0, angleBracketIndex);
26407
26435
  }
26408
- function findPropertyInHierarchy(classDecl, propertyName, isStatic) {
26409
- const properties = isStatic ? classDecl.getStaticProperties() : classDecl.getInstanceProperties();
26410
- const property = properties.find((p) => p.getName() === propertyName);
26411
- if (property !== void 0 && "getInitializer" in property) {
26412
- const sourceFile = classDecl.getSourceFile();
26413
- return {
26414
- initializer: property.getInitializer(),
26415
- filePath: sourceFile.getFilePath(),
26416
- line: property.getStartLineNumber()
26417
- };
26418
- }
26419
- if (classDecl.getExtends() === void 0) {
26420
- return void 0;
26436
+ function stripPromise(typeName) {
26437
+ if (typeName.startsWith("Promise<") && typeName.endsWith(">")) {
26438
+ return typeName.slice(8, -1);
26421
26439
  }
26422
- const baseClass = classDecl.getBaseClass();
26423
- if (baseClass === void 0)
26424
- return void 0;
26425
- return findPropertyInHierarchy(baseClass, propertyName, isStatic);
26426
- }
26427
- function evaluateFromPropertyRule(rule, classDecl) {
26428
- const name = rule.fromProperty.name;
26429
- const kind = rule.fromProperty.kind;
26430
- const transform2 = rule.fromProperty.transform;
26431
- const isStatic = kind === "static";
26432
- const propertyInfo = findPropertyInHierarchy(classDecl, name, isStatic);
26433
- if (propertyInfo === void 0) {
26434
- const sourceFile = classDecl.getSourceFile();
26435
- throw new ExtractionError(`Property '${name}' not found on class '${classDecl.getName() ?? "anonymous"}'`, sourceFile.getFilePath(), classDecl.getStartLineNumber());
26436
- }
26437
- const literalResult = extractLiteralValue(propertyInfo.initializer, propertyInfo.filePath, propertyInfo.line);
26438
- if (transform2 === void 0) {
26439
- return { value: literalResult.value };
26440
- }
26441
- if (typeof literalResult.value !== "string") {
26442
- return { value: literalResult.value };
26443
- }
26444
- return { value: applyTransforms(literalResult.value, transform2) };
26445
- }
26446
- function getDecoratorLocation(decorator) {
26447
- const sourceFile = decorator.getSourceFile();
26448
- return {
26449
- filePath: sourceFile.getFilePath(),
26450
- line: decorator.getStartLineNumber()
26451
- };
26452
- }
26453
- function extractPositionalArg(decorator, position) {
26454
- const args = decorator.getArguments();
26455
- const location = getDecoratorLocation(decorator);
26456
- if (args.length === 0) {
26457
- throw new ExtractionError(`Decorator '@${decorator.getName()}' has no arguments`, location.filePath, location.line);
26458
- }
26459
- const arg = args[position];
26460
- if (arg === void 0) {
26461
- throw new ExtractionError(`Argument position ${position} out of bounds. Decorator has ${args.length} argument(s)`, location.filePath, location.line);
26462
- }
26463
- if (arg.getKind() !== SyntaxKind3.StringLiteral) {
26464
- throw new ExtractionError(`Expected string literal at position ${position}, got ${arg.getKindName()}`, location.filePath, location.line);
26465
- }
26466
- return arg.asKindOrThrow(SyntaxKind3.StringLiteral).getLiteralValue();
26467
- }
26468
- function throwNoArguments(decorator, location) {
26469
- throw new ExtractionError(`Decorator '@${decorator.getName()}' has no arguments`, location.filePath, location.line);
26470
- }
26471
- function getFirstArgument(decorator, location) {
26472
- const args = decorator.getArguments();
26473
- const firstArg = args[0];
26474
- if (firstArg === void 0) {
26475
- throwNoArguments(decorator, location);
26476
- }
26477
- return firstArg;
26478
- }
26479
- function extractNamedArg(decorator, name) {
26480
- const location = getDecoratorLocation(decorator);
26481
- const firstArg = getFirstArgument(decorator, location);
26482
- if (firstArg.getKind() !== SyntaxKind3.ObjectLiteralExpression) {
26483
- throw new ExtractionError(`Expected object literal argument, got ${firstArg.getKindName()}`, location.filePath, location.line);
26484
- }
26485
- const objectLiteral = firstArg.asKindOrThrow(SyntaxKind3.ObjectLiteralExpression);
26486
- const property = objectLiteral.getProperty(name);
26487
- if (property === void 0) {
26488
- throw new ExtractionError(`Property '${name}' not found in decorator argument`, location.filePath, location.line);
26489
- }
26490
- if (!("getInitializer" in property)) {
26491
- throw new ExtractionError(`Property '${name}' has no initializer`, location.filePath, location.line);
26492
- }
26493
- const initializer3 = property.getInitializer();
26494
- if (initializer3?.getKind() !== SyntaxKind3.StringLiteral) {
26495
- throw new ExtractionError(`Expected string literal for property '${name}'`, location.filePath, location.line);
26496
- }
26497
- return initializer3.asKindOrThrow(SyntaxKind3.StringLiteral).getLiteralValue();
26498
- }
26499
- function evaluateFromDecoratorArgRule(rule, decorator) {
26500
- const decoratorName = rule.fromDecoratorArg.decorator;
26501
- const position = rule.fromDecoratorArg.position;
26502
- const name = rule.fromDecoratorArg.name;
26503
- const transform2 = rule.fromDecoratorArg.transform;
26504
- if (decoratorName !== void 0 && decorator.getName() !== decoratorName) {
26505
- const location = getDecoratorLocation(decorator);
26506
- throw new ExtractionError(`Expected decorator '@${decoratorName}', got '@${decorator.getName()}'`, location.filePath, location.line);
26507
- }
26508
- const extractValue = () => {
26509
- if (position !== void 0) {
26510
- return extractPositionalArg(decorator, position);
26511
- }
26512
- if (!name) {
26513
- const location = getDecoratorLocation(decorator);
26514
- throw new ExtractionError("Expected name parameter when position is undefined", location.filePath, location.line);
26515
- }
26516
- return extractNamedArg(decorator, name);
26517
- };
26518
- const value = extractValue();
26519
- if (transform2 === void 0) {
26520
- return { value };
26521
- }
26522
- return { value: applyTransforms(value, transform2) };
26523
- }
26524
- function evaluateFromClassDecoratorArgRule(rule, methodDecl) {
26525
- const classDecl = methodDecl.getParentIfKind(SyntaxKind3.ClassDeclaration);
26526
- if (classDecl === void 0) {
26527
- const sourceFile = methodDecl.getSourceFile();
26528
- throw new ExtractionError(`Expected method '${methodDecl.getName()}' to be declared inside a class`, sourceFile.getFilePath(), methodDecl.getStartLineNumber());
26529
- }
26530
- const classDecorator = classDecl.getDecorators().find((decorator) => decorator.getName() === rule.fromClassDecoratorArg.decorator);
26531
- if (classDecorator === void 0) {
26532
- const sourceFile = classDecl.getSourceFile();
26533
- throw new ExtractionError(`Decorator '@${rule.fromClassDecoratorArg.decorator}' not found on containing class '${classDecl.getName() ?? "anonymous"}'`, sourceFile.getFilePath(), classDecl.getStartLineNumber());
26534
- }
26535
- const fromClassDecoratorArg = rule.fromClassDecoratorArg;
26536
- const fromDecoratorArgRule = {
26537
- decorator: fromClassDecoratorArg.decorator,
26538
- ...fromClassDecoratorArg.position === void 0 ? {} : { position: fromClassDecoratorArg.position },
26539
- ...fromClassDecoratorArg.name === void 0 ? {} : { name: fromClassDecoratorArg.name },
26540
- ...fromClassDecoratorArg.transform === void 0 ? {} : { transform: fromClassDecoratorArg.transform }
26541
- };
26542
- return evaluateFromDecoratorArgRule({ fromDecoratorArg: fromDecoratorArgRule }, classDecorator);
26543
- }
26544
- function evaluateFromDecoratorNameRule(rule, decorator) {
26545
- const decoratorName = decorator.getName();
26546
- if (rule.fromDecoratorName === true) {
26547
- return { value: decoratorName };
26548
- }
26549
- const mapping = rule.fromDecoratorName.mapping;
26550
- const transform2 = rule.fromDecoratorName.transform;
26551
- const mappedValue = mapping?.[decoratorName] ?? decoratorName;
26552
- if (transform2 === void 0) {
26553
- return { value: mappedValue };
26554
- }
26555
- return { value: applyTransforms(mappedValue, transform2) };
26556
- }
26557
-
26558
- // ../../node_modules/.pnpm/@isaacs+balanced-match@4.0.1/node_modules/@isaacs/balanced-match/dist/esm/index.js
26559
- var balanced = (a, b, str) => {
26560
- const ma = a instanceof RegExp ? maybeMatch(a, str) : a;
26561
- const mb = b instanceof RegExp ? maybeMatch(b, str) : b;
26562
- const r = ma !== null && mb != null && range(ma, mb, str);
26563
- return r && {
26564
- start: r[0],
26565
- end: r[1],
26566
- pre: str.slice(0, r[0]),
26567
- body: str.slice(r[0] + ma.length, r[1]),
26568
- post: str.slice(r[1] + mb.length)
26569
- };
26570
- };
26571
- var maybeMatch = (reg, str) => {
26572
- const m = str.match(reg);
26573
- return m ? m[0] : null;
26574
- };
26575
- var range = (a, b, str) => {
26576
- let begs, beg, left, right = void 0, result;
26577
- let ai = str.indexOf(a);
26578
- let bi = str.indexOf(b, ai + 1);
26579
- let i = ai;
26580
- if (ai >= 0 && bi > 0) {
26581
- if (a === b) {
26582
- return [ai, bi];
26583
- }
26584
- begs = [];
26585
- left = str.length;
26586
- while (i >= 0 && !result) {
26587
- if (i === ai) {
26588
- begs.push(i);
26589
- ai = str.indexOf(a, i + 1);
26590
- } else if (begs.length === 1) {
26591
- const r = begs.pop();
26592
- if (r !== void 0)
26593
- result = [r, bi];
26594
- } else {
26595
- beg = begs.pop();
26596
- if (beg !== void 0 && beg < left) {
26597
- left = beg;
26598
- right = bi;
26599
- }
26600
- bi = str.indexOf(b, i + 1);
26601
- }
26602
- i = ai < bi && ai >= 0 ? ai : bi;
26603
- }
26604
- if (begs.length && right !== void 0) {
26605
- result = [left, right];
26606
- }
26607
- }
26608
- return result;
26609
- };
26610
-
26611
- // ../../node_modules/.pnpm/@isaacs+brace-expansion@5.0.0/node_modules/@isaacs/brace-expansion/dist/esm/index.js
26612
- var escSlash = "\0SLASH" + Math.random() + "\0";
26613
- var escOpen = "\0OPEN" + Math.random() + "\0";
26614
- var escClose = "\0CLOSE" + Math.random() + "\0";
26615
- var escComma = "\0COMMA" + Math.random() + "\0";
26616
- var escPeriod = "\0PERIOD" + Math.random() + "\0";
26617
- var escSlashPattern = new RegExp(escSlash, "g");
26618
- var escOpenPattern = new RegExp(escOpen, "g");
26619
- var escClosePattern = new RegExp(escClose, "g");
26620
- var escCommaPattern = new RegExp(escComma, "g");
26621
- var escPeriodPattern = new RegExp(escPeriod, "g");
26622
- var slashPattern = /\\\\/g;
26623
- var openPattern = /\\{/g;
26624
- var closePattern = /\\}/g;
26625
- var commaPattern = /\\,/g;
26626
- var periodPattern = /\\./g;
26627
- function numeric(str) {
26628
- return !isNaN(str) ? parseInt(str, 10) : str.charCodeAt(0);
26629
- }
26630
- function escapeBraces(str) {
26631
- return str.replace(slashPattern, escSlash).replace(openPattern, escOpen).replace(closePattern, escClose).replace(commaPattern, escComma).replace(periodPattern, escPeriod);
26632
- }
26633
- function unescapeBraces(str) {
26634
- return str.replace(escSlashPattern, "\\").replace(escOpenPattern, "{").replace(escClosePattern, "}").replace(escCommaPattern, ",").replace(escPeriodPattern, ".");
26635
- }
26636
- function parseCommaParts(str) {
26637
- if (!str) {
26638
- return [""];
26639
- }
26640
- const parts = [];
26641
- const m = balanced("{", "}", str);
26642
- if (!m) {
26643
- return str.split(",");
26644
- }
26645
- const { pre, body, post } = m;
26646
- const p = pre.split(",");
26647
- p[p.length - 1] += "{" + body + "}";
26648
- const postParts = parseCommaParts(post);
26649
- if (post.length) {
26650
- ;
26651
- p[p.length - 1] += postParts.shift();
26652
- p.push.apply(p, postParts);
26653
- }
26654
- parts.push.apply(parts, p);
26655
- return parts;
26656
- }
26657
- function expand(str) {
26658
- if (!str) {
26659
- return [];
26660
- }
26661
- if (str.slice(0, 2) === "{}") {
26662
- str = "\\{\\}" + str.slice(2);
26663
- }
26664
- return expand_(escapeBraces(str), true).map(unescapeBraces);
26665
- }
26666
- function embrace(str) {
26667
- return "{" + str + "}";
26668
- }
26669
- function isPadded(el) {
26670
- return /^-?0\d/.test(el);
26671
- }
26672
- function lte(i, y) {
26673
- return i <= y;
26674
- }
26675
- function gte(i, y) {
26676
- return i >= y;
26677
- }
26678
- function expand_(str, isTop) {
26679
- const expansions = [];
26680
- const m = balanced("{", "}", str);
26681
- if (!m)
26682
- return [str];
26683
- const pre = m.pre;
26684
- const post = m.post.length ? expand_(m.post, false) : [""];
26685
- if (/\$$/.test(m.pre)) {
26686
- for (let k = 0; k < post.length; k++) {
26687
- const expansion = pre + "{" + m.body + "}" + post[k];
26688
- expansions.push(expansion);
26689
- }
26690
- } else {
26691
- const isNumericSequence = /^-?\d+\.\.-?\d+(?:\.\.-?\d+)?$/.test(m.body);
26692
- const isAlphaSequence = /^[a-zA-Z]\.\.[a-zA-Z](?:\.\.-?\d+)?$/.test(m.body);
26693
- const isSequence = isNumericSequence || isAlphaSequence;
26694
- const isOptions = m.body.indexOf(",") >= 0;
26695
- if (!isSequence && !isOptions) {
26696
- if (m.post.match(/,(?!,).*\}/)) {
26697
- str = m.pre + "{" + m.body + escClose + m.post;
26698
- return expand_(str);
26699
- }
26700
- return [str];
26701
- }
26702
- let n;
26703
- if (isSequence) {
26704
- n = m.body.split(/\.\./);
26705
- } else {
26706
- n = parseCommaParts(m.body);
26707
- if (n.length === 1 && n[0] !== void 0) {
26708
- n = expand_(n[0], false).map(embrace);
26709
- if (n.length === 1) {
26710
- return post.map((p) => m.pre + n[0] + p);
26711
- }
26712
- }
26713
- }
26714
- let N;
26715
- if (isSequence && n[0] !== void 0 && n[1] !== void 0) {
26716
- const x = numeric(n[0]);
26717
- const y = numeric(n[1]);
26718
- const width = Math.max(n[0].length, n[1].length);
26719
- let incr = n.length === 3 && n[2] !== void 0 ? Math.abs(numeric(n[2])) : 1;
26720
- let test = lte;
26721
- const reverse = y < x;
26722
- if (reverse) {
26723
- incr *= -1;
26724
- test = gte;
26725
- }
26726
- const pad = n.some(isPadded);
26727
- N = [];
26728
- for (let i = x; test(i, y); i += incr) {
26729
- let c;
26730
- if (isAlphaSequence) {
26731
- c = String.fromCharCode(i);
26732
- if (c === "\\") {
26733
- c = "";
26734
- }
26735
- } else {
26736
- c = String(i);
26737
- if (pad) {
26738
- const need = width - c.length;
26739
- if (need > 0) {
26740
- const z2 = new Array(need + 1).join("0");
26741
- if (i < 0) {
26742
- c = "-" + z2 + c.slice(1);
26743
- } else {
26744
- c = z2 + c;
26745
- }
26746
- }
26747
- }
26748
- }
26749
- N.push(c);
26750
- }
26751
- } else {
26752
- N = [];
26753
- for (let j = 0; j < n.length; j++) {
26754
- N.push.apply(N, expand_(n[j], false));
26755
- }
26756
- }
26757
- for (let j = 0; j < N.length; j++) {
26758
- for (let k = 0; k < post.length; k++) {
26759
- const expansion = pre + N[j] + post[k];
26760
- if (!isTop || isSequence || expansion) {
26761
- expansions.push(expansion);
26762
- }
26763
- }
26764
- }
26765
- }
26766
- return expansions;
26767
- }
26768
-
26769
- // ../../node_modules/.pnpm/minimatch@10.1.1/node_modules/minimatch/dist/esm/assert-valid-pattern.js
26770
- var MAX_PATTERN_LENGTH = 1024 * 64;
26771
- var assertValidPattern = (pattern) => {
26772
- if (typeof pattern !== "string") {
26773
- throw new TypeError("invalid pattern");
26774
- }
26775
- if (pattern.length > MAX_PATTERN_LENGTH) {
26776
- throw new TypeError("pattern is too long");
26777
- }
26778
- };
26779
-
26780
- // ../../node_modules/.pnpm/minimatch@10.1.1/node_modules/minimatch/dist/esm/brace-expressions.js
26781
- var posixClasses = {
26782
- "[:alnum:]": ["\\p{L}\\p{Nl}\\p{Nd}", true],
26783
- "[:alpha:]": ["\\p{L}\\p{Nl}", true],
26784
- "[:ascii:]": ["\\x00-\\x7f", false],
26785
- "[:blank:]": ["\\p{Zs}\\t", true],
26786
- "[:cntrl:]": ["\\p{Cc}", true],
26787
- "[:digit:]": ["\\p{Nd}", true],
26788
- "[:graph:]": ["\\p{Z}\\p{C}", true, true],
26789
- "[:lower:]": ["\\p{Ll}", true],
26790
- "[:print:]": ["\\p{C}", true],
26791
- "[:punct:]": ["\\p{P}", true],
26792
- "[:space:]": ["\\p{Z}\\t\\r\\n\\v\\f", true],
26793
- "[:upper:]": ["\\p{Lu}", true],
26794
- "[:word:]": ["\\p{L}\\p{Nl}\\p{Nd}\\p{Pc}", true],
26795
- "[:xdigit:]": ["A-Fa-f0-9", false]
26796
- };
26797
- var braceEscape = (s) => s.replace(/[[\]\\-]/g, "\\$&");
26798
- var regexpEscape = (s) => s.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&");
26799
- var rangesToString = (ranges) => ranges.join("");
26800
- var parseClass = (glob, position) => {
26801
- const pos = position;
26802
- if (glob.charAt(pos) !== "[") {
26803
- throw new Error("not in a brace expression");
26804
- }
26805
- const ranges = [];
26806
- const negs = [];
26807
- let i = pos + 1;
26808
- let sawStart = false;
26809
- let uflag = false;
26810
- let escaping = false;
26811
- let negate = false;
26812
- let endPos = pos;
26813
- let rangeStart = "";
26814
- WHILE: while (i < glob.length) {
26815
- const c = glob.charAt(i);
26816
- if ((c === "!" || c === "^") && i === pos + 1) {
26817
- negate = true;
26818
- i++;
26819
- continue;
26820
- }
26821
- if (c === "]" && sawStart && !escaping) {
26822
- endPos = i + 1;
26823
- break;
26824
- }
26825
- sawStart = true;
26826
- if (c === "\\") {
26827
- if (!escaping) {
26828
- escaping = true;
26829
- i++;
26830
- continue;
26831
- }
26832
- }
26833
- if (c === "[" && !escaping) {
26834
- for (const [cls, [unip, u, neg]] of Object.entries(posixClasses)) {
26835
- if (glob.startsWith(cls, i)) {
26836
- if (rangeStart) {
26837
- return ["$.", false, glob.length - pos, true];
26838
- }
26839
- i += cls.length;
26840
- if (neg)
26841
- negs.push(unip);
26842
- else
26843
- ranges.push(unip);
26844
- uflag = uflag || u;
26845
- continue WHILE;
26846
- }
26847
- }
26848
- }
26849
- escaping = false;
26850
- if (rangeStart) {
26851
- if (c > rangeStart) {
26852
- ranges.push(braceEscape(rangeStart) + "-" + braceEscape(c));
26853
- } else if (c === rangeStart) {
26854
- ranges.push(braceEscape(c));
26855
- }
26856
- rangeStart = "";
26857
- i++;
26858
- continue;
26859
- }
26860
- if (glob.startsWith("-]", i + 1)) {
26861
- ranges.push(braceEscape(c + "-"));
26862
- i += 2;
26863
- continue;
26864
- }
26865
- if (glob.startsWith("-", i + 1)) {
26866
- rangeStart = c;
26867
- i += 2;
26868
- continue;
26869
- }
26870
- ranges.push(braceEscape(c));
26871
- i++;
26872
- }
26873
- if (endPos < i) {
26874
- return ["", false, 0, false];
26875
- }
26876
- if (!ranges.length && !negs.length) {
26877
- return ["$.", false, glob.length - pos, true];
26878
- }
26879
- if (negs.length === 0 && ranges.length === 1 && /^\\?.$/.test(ranges[0]) && !negate) {
26880
- const r = ranges[0].length === 2 ? ranges[0].slice(-1) : ranges[0];
26881
- return [regexpEscape(r), false, endPos - pos, false];
26882
- }
26883
- const sranges = "[" + (negate ? "^" : "") + rangesToString(ranges) + "]";
26884
- const snegs = "[" + (negate ? "" : "^") + rangesToString(negs) + "]";
26885
- const comb = ranges.length && negs.length ? "(" + sranges + "|" + snegs + ")" : ranges.length ? sranges : snegs;
26886
- return [comb, uflag, endPos - pos, true];
26887
- };
26888
-
26889
- // ../../node_modules/.pnpm/minimatch@10.1.1/node_modules/minimatch/dist/esm/unescape.js
26890
- var unescape2 = (s, { windowsPathsNoEscape = false, magicalBraces = true } = {}) => {
26891
- if (magicalBraces) {
26892
- return windowsPathsNoEscape ? s.replace(/\[([^\/\\])\]/g, "$1") : s.replace(/((?!\\).|^)\[([^\/\\])\]/g, "$1$2").replace(/\\([^\/])/g, "$1");
26893
- }
26894
- return windowsPathsNoEscape ? s.replace(/\[([^\/\\{}])\]/g, "$1") : s.replace(/((?!\\).|^)\[([^\/\\{}])\]/g, "$1$2").replace(/\\([^\/{}])/g, "$1");
26895
- };
26896
-
26897
- // ../../node_modules/.pnpm/minimatch@10.1.1/node_modules/minimatch/dist/esm/ast.js
26898
- var types = /* @__PURE__ */ new Set(["!", "?", "+", "*", "@"]);
26899
- var isExtglobType = (c) => types.has(c);
26900
- var startNoTraversal = "(?!(?:^|/)\\.\\.?(?:$|/))";
26901
- var startNoDot = "(?!\\.)";
26902
- var addPatternStart = /* @__PURE__ */ new Set(["[", "."]);
26903
- var justDots = /* @__PURE__ */ new Set(["..", "."]);
26904
- var reSpecials = new Set("().*{}+?[]^$\\!");
26905
- var regExpEscape = (s) => s.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&");
26906
- var qmark = "[^/]";
26907
- var star = qmark + "*?";
26908
- var starNoEmpty = qmark + "+?";
26909
- var AST = class _AST {
26910
- type;
26911
- #root;
26912
- #hasMagic;
26913
- #uflag = false;
26914
- #parts = [];
26915
- #parent;
26916
- #parentIndex;
26917
- #negs;
26918
- #filledNegs = false;
26919
- #options;
26920
- #toString;
26921
- // set to true if it's an extglob with no children
26922
- // (which really means one child of '')
26923
- #emptyExt = false;
26924
- constructor(type, parent, options = {}) {
26925
- this.type = type;
26926
- if (type)
26927
- this.#hasMagic = true;
26928
- this.#parent = parent;
26929
- this.#root = this.#parent ? this.#parent.#root : this;
26930
- this.#options = this.#root === this ? options : this.#root.#options;
26931
- this.#negs = this.#root === this ? [] : this.#root.#negs;
26932
- if (type === "!" && !this.#root.#filledNegs)
26933
- this.#negs.push(this);
26934
- this.#parentIndex = this.#parent ? this.#parent.#parts.length : 0;
26935
- }
26936
- get hasMagic() {
26937
- if (this.#hasMagic !== void 0)
26938
- return this.#hasMagic;
26939
- for (const p of this.#parts) {
26940
- if (typeof p === "string")
26941
- continue;
26942
- if (p.type || p.hasMagic)
26943
- return this.#hasMagic = true;
26944
- }
26945
- return this.#hasMagic;
26946
- }
26947
- // reconstructs the pattern
26948
- toString() {
26949
- if (this.#toString !== void 0)
26950
- return this.#toString;
26951
- if (!this.type) {
26952
- return this.#toString = this.#parts.map((p) => String(p)).join("");
26953
- } else {
26954
- return this.#toString = this.type + "(" + this.#parts.map((p) => String(p)).join("|") + ")";
26955
- }
26956
- }
26957
- #fillNegs() {
26958
- if (this !== this.#root)
26959
- throw new Error("should only call on root");
26960
- if (this.#filledNegs)
26961
- return this;
26962
- this.toString();
26963
- this.#filledNegs = true;
26964
- let n;
26965
- while (n = this.#negs.pop()) {
26966
- if (n.type !== "!")
26967
- continue;
26968
- let p = n;
26969
- let pp = p.#parent;
26970
- while (pp) {
26971
- for (let i = p.#parentIndex + 1; !pp.type && i < pp.#parts.length; i++) {
26972
- for (const part of n.#parts) {
26973
- if (typeof part === "string") {
26974
- throw new Error("string part in extglob AST??");
26975
- }
26976
- part.copyIn(pp.#parts[i]);
26977
- }
26978
- }
26979
- p = pp;
26980
- pp = p.#parent;
26981
- }
26982
- }
26983
- return this;
26984
- }
26985
- push(...parts) {
26986
- for (const p of parts) {
26987
- if (p === "")
26988
- continue;
26989
- if (typeof p !== "string" && !(p instanceof _AST && p.#parent === this)) {
26990
- throw new Error("invalid part: " + p);
26991
- }
26992
- this.#parts.push(p);
26993
- }
26994
- }
26995
- toJSON() {
26996
- const ret = this.type === null ? this.#parts.slice().map((p) => typeof p === "string" ? p : p.toJSON()) : [this.type, ...this.#parts.map((p) => p.toJSON())];
26997
- if (this.isStart() && !this.type)
26998
- ret.unshift([]);
26999
- if (this.isEnd() && (this === this.#root || this.#root.#filledNegs && this.#parent?.type === "!")) {
27000
- ret.push({});
27001
- }
27002
- return ret;
27003
- }
27004
- isStart() {
27005
- if (this.#root === this)
27006
- return true;
27007
- if (!this.#parent?.isStart())
27008
- return false;
27009
- if (this.#parentIndex === 0)
27010
- return true;
27011
- const p = this.#parent;
27012
- for (let i = 0; i < this.#parentIndex; i++) {
27013
- const pp = p.#parts[i];
27014
- if (!(pp instanceof _AST && pp.type === "!")) {
27015
- return false;
27016
- }
27017
- }
27018
- return true;
27019
- }
27020
- isEnd() {
27021
- if (this.#root === this)
27022
- return true;
27023
- if (this.#parent?.type === "!")
27024
- return true;
27025
- if (!this.#parent?.isEnd())
27026
- return false;
27027
- if (!this.type)
27028
- return this.#parent?.isEnd();
27029
- const pl = this.#parent ? this.#parent.#parts.length : 0;
27030
- return this.#parentIndex === pl - 1;
27031
- }
27032
- copyIn(part) {
27033
- if (typeof part === "string")
27034
- this.push(part);
27035
- else
27036
- this.push(part.clone(this));
27037
- }
27038
- clone(parent) {
27039
- const c = new _AST(this.type, parent);
27040
- for (const p of this.#parts) {
27041
- c.copyIn(p);
27042
- }
27043
- return c;
27044
- }
27045
- static #parseAST(str, ast, pos, opt) {
27046
- let escaping = false;
27047
- let inBrace = false;
27048
- let braceStart = -1;
27049
- let braceNeg = false;
27050
- if (ast.type === null) {
27051
- let i2 = pos;
27052
- let acc2 = "";
27053
- while (i2 < str.length) {
27054
- const c = str.charAt(i2++);
27055
- if (escaping || c === "\\") {
27056
- escaping = !escaping;
27057
- acc2 += c;
27058
- continue;
27059
- }
27060
- if (inBrace) {
27061
- if (i2 === braceStart + 1) {
27062
- if (c === "^" || c === "!") {
27063
- braceNeg = true;
27064
- }
27065
- } else if (c === "]" && !(i2 === braceStart + 2 && braceNeg)) {
27066
- inBrace = false;
27067
- }
27068
- acc2 += c;
27069
- continue;
27070
- } else if (c === "[") {
27071
- inBrace = true;
27072
- braceStart = i2;
27073
- braceNeg = false;
27074
- acc2 += c;
27075
- continue;
27076
- }
27077
- if (!opt.noext && isExtglobType(c) && str.charAt(i2) === "(") {
27078
- ast.push(acc2);
27079
- acc2 = "";
27080
- const ext2 = new _AST(c, ast);
27081
- i2 = _AST.#parseAST(str, ext2, i2, opt);
27082
- ast.push(ext2);
27083
- continue;
27084
- }
27085
- acc2 += c;
27086
- }
27087
- ast.push(acc2);
27088
- return i2;
27089
- }
27090
- let i = pos + 1;
27091
- let part = new _AST(null, ast);
27092
- const parts = [];
27093
- let acc = "";
27094
- while (i < str.length) {
27095
- const c = str.charAt(i++);
27096
- if (escaping || c === "\\") {
27097
- escaping = !escaping;
27098
- acc += c;
27099
- continue;
27100
- }
27101
- if (inBrace) {
27102
- if (i === braceStart + 1) {
27103
- if (c === "^" || c === "!") {
27104
- braceNeg = true;
27105
- }
27106
- } else if (c === "]" && !(i === braceStart + 2 && braceNeg)) {
27107
- inBrace = false;
27108
- }
27109
- acc += c;
27110
- continue;
27111
- } else if (c === "[") {
27112
- inBrace = true;
27113
- braceStart = i;
27114
- braceNeg = false;
27115
- acc += c;
27116
- continue;
27117
- }
27118
- if (isExtglobType(c) && str.charAt(i) === "(") {
27119
- part.push(acc);
27120
- acc = "";
27121
- const ext2 = new _AST(c, part);
27122
- part.push(ext2);
27123
- i = _AST.#parseAST(str, ext2, i, opt);
27124
- continue;
27125
- }
27126
- if (c === "|") {
27127
- part.push(acc);
27128
- acc = "";
27129
- parts.push(part);
27130
- part = new _AST(null, ast);
27131
- continue;
27132
- }
27133
- if (c === ")") {
27134
- if (acc === "" && ast.#parts.length === 0) {
27135
- ast.#emptyExt = true;
27136
- }
27137
- part.push(acc);
27138
- acc = "";
27139
- ast.push(...parts, part);
27140
- return i;
27141
- }
27142
- acc += c;
27143
- }
27144
- ast.type = null;
27145
- ast.#hasMagic = void 0;
27146
- ast.#parts = [str.substring(pos - 1)];
27147
- return i;
27148
- }
27149
- static fromGlob(pattern, options = {}) {
27150
- const ast = new _AST(null, void 0, options);
27151
- _AST.#parseAST(pattern, ast, 0, options);
27152
- return ast;
27153
- }
27154
- // returns the regular expression if there's magic, or the unescaped
27155
- // string if not.
27156
- toMMPattern() {
27157
- if (this !== this.#root)
27158
- return this.#root.toMMPattern();
27159
- const glob = this.toString();
27160
- const [re, body, hasMagic, uflag] = this.toRegExpSource();
27161
- const anyMagic = hasMagic || this.#hasMagic || this.#options.nocase && !this.#options.nocaseMagicOnly && glob.toUpperCase() !== glob.toLowerCase();
27162
- if (!anyMagic) {
27163
- return body;
27164
- }
27165
- const flags = (this.#options.nocase ? "i" : "") + (uflag ? "u" : "");
27166
- return Object.assign(new RegExp(`^${re}$`, flags), {
27167
- _src: re,
27168
- _glob: glob
27169
- });
27170
- }
27171
- get options() {
27172
- return this.#options;
27173
- }
27174
- // returns the string match, the regexp source, whether there's magic
27175
- // in the regexp (so a regular expression is required) and whether or
27176
- // not the uflag is needed for the regular expression (for posix classes)
27177
- // TODO: instead of injecting the start/end at this point, just return
27178
- // the BODY of the regexp, along with the start/end portions suitable
27179
- // for binding the start/end in either a joined full-path makeRe context
27180
- // (where we bind to (^|/), or a standalone matchPart context (where
27181
- // we bind to ^, and not /). Otherwise slashes get duped!
27182
- //
27183
- // In part-matching mode, the start is:
27184
- // - if not isStart: nothing
27185
- // - if traversal possible, but not allowed: ^(?!\.\.?$)
27186
- // - if dots allowed or not possible: ^
27187
- // - if dots possible and not allowed: ^(?!\.)
27188
- // end is:
27189
- // - if not isEnd(): nothing
27190
- // - else: $
27191
- //
27192
- // In full-path matching mode, we put the slash at the START of the
27193
- // pattern, so start is:
27194
- // - if first pattern: same as part-matching mode
27195
- // - if not isStart(): nothing
27196
- // - if traversal possible, but not allowed: /(?!\.\.?(?:$|/))
27197
- // - if dots allowed or not possible: /
27198
- // - if dots possible and not allowed: /(?!\.)
27199
- // end is:
27200
- // - if last pattern, same as part-matching mode
27201
- // - else nothing
27202
- //
27203
- // Always put the (?:$|/) on negated tails, though, because that has to be
27204
- // there to bind the end of the negated pattern portion, and it's easier to
27205
- // just stick it in now rather than try to inject it later in the middle of
27206
- // the pattern.
27207
- //
27208
- // We can just always return the same end, and leave it up to the caller
27209
- // to know whether it's going to be used joined or in parts.
27210
- // And, if the start is adjusted slightly, can do the same there:
27211
- // - if not isStart: nothing
27212
- // - if traversal possible, but not allowed: (?:/|^)(?!\.\.?$)
27213
- // - if dots allowed or not possible: (?:/|^)
27214
- // - if dots possible and not allowed: (?:/|^)(?!\.)
27215
- //
27216
- // But it's better to have a simpler binding without a conditional, for
27217
- // performance, so probably better to return both start options.
27218
- //
27219
- // Then the caller just ignores the end if it's not the first pattern,
27220
- // and the start always gets applied.
27221
- //
27222
- // But that's always going to be $ if it's the ending pattern, or nothing,
27223
- // so the caller can just attach $ at the end of the pattern when building.
27224
- //
27225
- // So the todo is:
27226
- // - better detect what kind of start is needed
27227
- // - return both flavors of starting pattern
27228
- // - attach $ at the end of the pattern when creating the actual RegExp
27229
- //
27230
- // Ah, but wait, no, that all only applies to the root when the first pattern
27231
- // is not an extglob. If the first pattern IS an extglob, then we need all
27232
- // that dot prevention biz to live in the extglob portions, because eg
27233
- // +(*|.x*) can match .xy but not .yx.
27234
- //
27235
- // So, return the two flavors if it's #root and the first child is not an
27236
- // AST, otherwise leave it to the child AST to handle it, and there,
27237
- // use the (?:^|/) style of start binding.
27238
- //
27239
- // Even simplified further:
27240
- // - Since the start for a join is eg /(?!\.) and the start for a part
27241
- // is ^(?!\.), we can just prepend (?!\.) to the pattern (either root
27242
- // or start or whatever) and prepend ^ or / at the Regexp construction.
27243
- toRegExpSource(allowDot) {
27244
- const dot = allowDot ?? !!this.#options.dot;
27245
- if (this.#root === this)
27246
- this.#fillNegs();
27247
- if (!this.type) {
27248
- const noEmpty = this.isStart() && this.isEnd() && !this.#parts.some((s) => typeof s !== "string");
27249
- const src = this.#parts.map((p) => {
27250
- const [re, _, hasMagic, uflag] = typeof p === "string" ? _AST.#parseGlob(p, this.#hasMagic, noEmpty) : p.toRegExpSource(allowDot);
27251
- this.#hasMagic = this.#hasMagic || hasMagic;
27252
- this.#uflag = this.#uflag || uflag;
27253
- return re;
27254
- }).join("");
27255
- let start2 = "";
27256
- if (this.isStart()) {
27257
- if (typeof this.#parts[0] === "string") {
27258
- const dotTravAllowed = this.#parts.length === 1 && justDots.has(this.#parts[0]);
27259
- if (!dotTravAllowed) {
27260
- const aps = addPatternStart;
27261
- const needNoTrav = (
27262
- // dots are allowed, and the pattern starts with [ or .
27263
- dot && aps.has(src.charAt(0)) || // the pattern starts with \., and then [ or .
27264
- src.startsWith("\\.") && aps.has(src.charAt(2)) || // the pattern starts with \.\., and then [ or .
27265
- src.startsWith("\\.\\.") && aps.has(src.charAt(4))
27266
- );
27267
- const needNoDot = !dot && !allowDot && aps.has(src.charAt(0));
27268
- start2 = needNoTrav ? startNoTraversal : needNoDot ? startNoDot : "";
27269
- }
27270
- }
27271
- }
27272
- let end = "";
27273
- if (this.isEnd() && this.#root.#filledNegs && this.#parent?.type === "!") {
27274
- end = "(?:$|\\/)";
27275
- }
27276
- const final2 = start2 + src + end;
27277
- return [
27278
- final2,
27279
- unescape2(src),
27280
- this.#hasMagic = !!this.#hasMagic,
27281
- this.#uflag
27282
- ];
27283
- }
27284
- const repeated = this.type === "*" || this.type === "+";
27285
- const start = this.type === "!" ? "(?:(?!(?:" : "(?:";
27286
- let body = this.#partsToRegExp(dot);
27287
- if (this.isStart() && this.isEnd() && !body && this.type !== "!") {
27288
- const s = this.toString();
27289
- this.#parts = [s];
27290
- this.type = null;
27291
- this.#hasMagic = void 0;
27292
- return [s, unescape2(this.toString()), false, false];
27293
- }
27294
- let bodyDotAllowed = !repeated || allowDot || dot || !startNoDot ? "" : this.#partsToRegExp(true);
27295
- if (bodyDotAllowed === body) {
27296
- bodyDotAllowed = "";
27297
- }
27298
- if (bodyDotAllowed) {
27299
- body = `(?:${body})(?:${bodyDotAllowed})*?`;
27300
- }
27301
- let final = "";
27302
- if (this.type === "!" && this.#emptyExt) {
27303
- final = (this.isStart() && !dot ? startNoDot : "") + starNoEmpty;
27304
- } else {
27305
- const close = this.type === "!" ? (
27306
- // !() must match something,but !(x) can match ''
27307
- "))" + (this.isStart() && !dot && !allowDot ? startNoDot : "") + star + ")"
27308
- ) : this.type === "@" ? ")" : this.type === "?" ? ")?" : this.type === "+" && bodyDotAllowed ? ")" : this.type === "*" && bodyDotAllowed ? `)?` : `)${this.type}`;
27309
- final = start + body + close;
27310
- }
27311
- return [
27312
- final,
27313
- unescape2(body),
27314
- this.#hasMagic = !!this.#hasMagic,
27315
- this.#uflag
27316
- ];
27317
- }
27318
- #partsToRegExp(dot) {
27319
- return this.#parts.map((p) => {
27320
- if (typeof p === "string") {
27321
- throw new Error("string type in extglob ast??");
27322
- }
27323
- const [re, _, _hasMagic, uflag] = p.toRegExpSource(dot);
27324
- this.#uflag = this.#uflag || uflag;
27325
- return re;
27326
- }).filter((p) => !(this.isStart() && this.isEnd()) || !!p).join("|");
27327
- }
27328
- static #parseGlob(glob, hasMagic, noEmpty = false) {
27329
- let escaping = false;
27330
- let re = "";
27331
- let uflag = false;
27332
- for (let i = 0; i < glob.length; i++) {
27333
- const c = glob.charAt(i);
27334
- if (escaping) {
27335
- escaping = false;
27336
- re += (reSpecials.has(c) ? "\\" : "") + c;
27337
- continue;
27338
- }
27339
- if (c === "\\") {
27340
- if (i === glob.length - 1) {
27341
- re += "\\\\";
27342
- } else {
27343
- escaping = true;
27344
- }
27345
- continue;
27346
- }
27347
- if (c === "[") {
27348
- const [src, needUflag, consumed, magic] = parseClass(glob, i);
27349
- if (consumed) {
27350
- re += src;
27351
- uflag = uflag || needUflag;
27352
- i += consumed - 1;
27353
- hasMagic = hasMagic || magic;
27354
- continue;
27355
- }
27356
- }
27357
- if (c === "*") {
27358
- re += noEmpty && glob === "*" ? starNoEmpty : star;
27359
- hasMagic = true;
27360
- continue;
27361
- }
27362
- if (c === "?") {
27363
- re += qmark;
27364
- hasMagic = true;
27365
- continue;
27366
- }
27367
- re += regExpEscape(c);
27368
- }
27369
- return [re, unescape2(glob), !!hasMagic, uflag];
27370
- }
27371
- };
27372
-
27373
- // ../../node_modules/.pnpm/minimatch@10.1.1/node_modules/minimatch/dist/esm/escape.js
27374
- var escape2 = (s, { windowsPathsNoEscape = false, magicalBraces = false } = {}) => {
27375
- if (magicalBraces) {
27376
- return windowsPathsNoEscape ? s.replace(/[?*()[\]{}]/g, "[$&]") : s.replace(/[?*()[\]\\{}]/g, "\\$&");
27377
- }
27378
- return windowsPathsNoEscape ? s.replace(/[?*()[\]]/g, "[$&]") : s.replace(/[?*()[\]\\]/g, "\\$&");
27379
- };
27380
-
27381
- // ../../node_modules/.pnpm/minimatch@10.1.1/node_modules/minimatch/dist/esm/index.js
27382
- var minimatch = (p, pattern, options = {}) => {
27383
- assertValidPattern(pattern);
27384
- if (!options.nocomment && pattern.charAt(0) === "#") {
27385
- return false;
27386
- }
27387
- return new Minimatch(pattern, options).match(p);
27388
- };
27389
- var starDotExtRE = /^\*+([^+@!?\*\[\(]*)$/;
27390
- var starDotExtTest = (ext2) => (f) => !f.startsWith(".") && f.endsWith(ext2);
27391
- var starDotExtTestDot = (ext2) => (f) => f.endsWith(ext2);
27392
- var starDotExtTestNocase = (ext2) => {
27393
- ext2 = ext2.toLowerCase();
27394
- return (f) => !f.startsWith(".") && f.toLowerCase().endsWith(ext2);
27395
- };
27396
- var starDotExtTestNocaseDot = (ext2) => {
27397
- ext2 = ext2.toLowerCase();
27398
- return (f) => f.toLowerCase().endsWith(ext2);
27399
- };
27400
- var starDotStarRE = /^\*+\.\*+$/;
27401
- var starDotStarTest = (f) => !f.startsWith(".") && f.includes(".");
27402
- var starDotStarTestDot = (f) => f !== "." && f !== ".." && f.includes(".");
27403
- var dotStarRE = /^\.\*+$/;
27404
- var dotStarTest = (f) => f !== "." && f !== ".." && f.startsWith(".");
27405
- var starRE = /^\*+$/;
27406
- var starTest = (f) => f.length !== 0 && !f.startsWith(".");
27407
- var starTestDot = (f) => f.length !== 0 && f !== "." && f !== "..";
27408
- var qmarksRE = /^\?+([^+@!?\*\[\(]*)?$/;
27409
- var qmarksTestNocase = ([$0, ext2 = ""]) => {
27410
- const noext = qmarksTestNoExt([$0]);
27411
- if (!ext2)
27412
- return noext;
27413
- ext2 = ext2.toLowerCase();
27414
- return (f) => noext(f) && f.toLowerCase().endsWith(ext2);
27415
- };
27416
- var qmarksTestNocaseDot = ([$0, ext2 = ""]) => {
27417
- const noext = qmarksTestNoExtDot([$0]);
27418
- if (!ext2)
27419
- return noext;
27420
- ext2 = ext2.toLowerCase();
27421
- return (f) => noext(f) && f.toLowerCase().endsWith(ext2);
27422
- };
27423
- var qmarksTestDot = ([$0, ext2 = ""]) => {
27424
- const noext = qmarksTestNoExtDot([$0]);
27425
- return !ext2 ? noext : (f) => noext(f) && f.endsWith(ext2);
27426
- };
27427
- var qmarksTest = ([$0, ext2 = ""]) => {
27428
- const noext = qmarksTestNoExt([$0]);
27429
- return !ext2 ? noext : (f) => noext(f) && f.endsWith(ext2);
27430
- };
27431
- var qmarksTestNoExt = ([$0]) => {
27432
- const len = $0.length;
27433
- return (f) => f.length === len && !f.startsWith(".");
27434
- };
27435
- var qmarksTestNoExtDot = ([$0]) => {
27436
- const len = $0.length;
27437
- return (f) => f.length === len && f !== "." && f !== "..";
27438
- };
27439
- var defaultPlatform = typeof process === "object" && process ? typeof process.env === "object" && process.env && process.env.__MINIMATCH_TESTING_PLATFORM__ || process.platform : "posix";
27440
- var path = {
27441
- win32: { sep: "\\" },
27442
- posix: { sep: "/" }
27443
- };
27444
- var sep = defaultPlatform === "win32" ? path.win32.sep : path.posix.sep;
27445
- minimatch.sep = sep;
27446
- var GLOBSTAR = /* @__PURE__ */ Symbol("globstar **");
27447
- minimatch.GLOBSTAR = GLOBSTAR;
27448
- var qmark2 = "[^/]";
27449
- var star2 = qmark2 + "*?";
27450
- var twoStarDot = "(?:(?!(?:\\/|^)(?:\\.{1,2})($|\\/)).)*?";
27451
- var twoStarNoDot = "(?:(?!(?:\\/|^)\\.).)*?";
27452
- var filter = (pattern, options = {}) => (p) => minimatch(p, pattern, options);
27453
- minimatch.filter = filter;
27454
- var ext = (a, b = {}) => Object.assign({}, a, b);
27455
- var defaults = (def) => {
27456
- if (!def || typeof def !== "object" || !Object.keys(def).length) {
27457
- return minimatch;
27458
- }
27459
- const orig = minimatch;
27460
- const m = (p, pattern, options = {}) => orig(p, pattern, ext(def, options));
27461
- return Object.assign(m, {
27462
- Minimatch: class Minimatch extends orig.Minimatch {
27463
- constructor(pattern, options = {}) {
27464
- super(pattern, ext(def, options));
27465
- }
27466
- static defaults(options) {
27467
- return orig.defaults(ext(def, options)).Minimatch;
27468
- }
27469
- },
27470
- AST: class AST extends orig.AST {
27471
- /* c8 ignore start */
27472
- constructor(type, parent, options = {}) {
27473
- super(type, parent, ext(def, options));
27474
- }
27475
- /* c8 ignore stop */
27476
- static fromGlob(pattern, options = {}) {
27477
- return orig.AST.fromGlob(pattern, ext(def, options));
27478
- }
27479
- },
27480
- unescape: (s, options = {}) => orig.unescape(s, ext(def, options)),
27481
- escape: (s, options = {}) => orig.escape(s, ext(def, options)),
27482
- filter: (pattern, options = {}) => orig.filter(pattern, ext(def, options)),
27483
- defaults: (options) => orig.defaults(ext(def, options)),
27484
- makeRe: (pattern, options = {}) => orig.makeRe(pattern, ext(def, options)),
27485
- braceExpand: (pattern, options = {}) => orig.braceExpand(pattern, ext(def, options)),
27486
- match: (list, pattern, options = {}) => orig.match(list, pattern, ext(def, options)),
27487
- sep: orig.sep,
27488
- GLOBSTAR
27489
- });
27490
- };
27491
- minimatch.defaults = defaults;
27492
- var braceExpand = (pattern, options = {}) => {
27493
- assertValidPattern(pattern);
27494
- if (options.nobrace || !/\{(?:(?!\{).)*\}/.test(pattern)) {
27495
- return [pattern];
27496
- }
27497
- return expand(pattern);
27498
- };
27499
- minimatch.braceExpand = braceExpand;
27500
- var makeRe = (pattern, options = {}) => new Minimatch(pattern, options).makeRe();
27501
- minimatch.makeRe = makeRe;
27502
- var match = (list, pattern, options = {}) => {
27503
- const mm = new Minimatch(pattern, options);
27504
- list = list.filter((f) => mm.match(f));
27505
- if (mm.options.nonull && !list.length) {
27506
- list.push(pattern);
27507
- }
27508
- return list;
27509
- };
27510
- minimatch.match = match;
27511
- var globMagic = /[?*]|[+@!]\(.*?\)|\[|\]/;
27512
- var regExpEscape2 = (s) => s.replace(/[-[\]{}()*+?.,\\^$|#\s]/g, "\\$&");
27513
- var Minimatch = class {
27514
- options;
27515
- set;
27516
- pattern;
27517
- windowsPathsNoEscape;
27518
- nonegate;
27519
- negate;
27520
- comment;
27521
- empty;
27522
- preserveMultipleSlashes;
27523
- partial;
27524
- globSet;
27525
- globParts;
27526
- nocase;
27527
- isWindows;
27528
- platform;
27529
- windowsNoMagicRoot;
27530
- regexp;
27531
- constructor(pattern, options = {}) {
27532
- assertValidPattern(pattern);
27533
- options = options || {};
27534
- this.options = options;
27535
- this.pattern = pattern;
27536
- this.platform = options.platform || defaultPlatform;
27537
- this.isWindows = this.platform === "win32";
27538
- this.windowsPathsNoEscape = !!options.windowsPathsNoEscape || options.allowWindowsEscape === false;
27539
- if (this.windowsPathsNoEscape) {
27540
- this.pattern = this.pattern.replace(/\\/g, "/");
27541
- }
27542
- this.preserveMultipleSlashes = !!options.preserveMultipleSlashes;
27543
- this.regexp = null;
27544
- this.negate = false;
27545
- this.nonegate = !!options.nonegate;
27546
- this.comment = false;
27547
- this.empty = false;
27548
- this.partial = !!options.partial;
27549
- this.nocase = !!this.options.nocase;
27550
- this.windowsNoMagicRoot = options.windowsNoMagicRoot !== void 0 ? options.windowsNoMagicRoot : !!(this.isWindows && this.nocase);
27551
- this.globSet = [];
27552
- this.globParts = [];
27553
- this.set = [];
27554
- this.make();
27555
- }
27556
- hasMagic() {
27557
- if (this.options.magicalBraces && this.set.length > 1) {
27558
- return true;
27559
- }
27560
- for (const pattern of this.set) {
27561
- for (const part of pattern) {
27562
- if (typeof part !== "string")
27563
- return true;
27564
- }
27565
- }
27566
- return false;
27567
- }
27568
- debug(..._) {
27569
- }
27570
- make() {
27571
- const pattern = this.pattern;
27572
- const options = this.options;
27573
- if (!options.nocomment && pattern.charAt(0) === "#") {
27574
- this.comment = true;
27575
- return;
27576
- }
27577
- if (!pattern) {
27578
- this.empty = true;
27579
- return;
27580
- }
27581
- this.parseNegate();
27582
- this.globSet = [...new Set(this.braceExpand())];
27583
- if (options.debug) {
27584
- this.debug = (...args) => console.error(...args);
27585
- }
27586
- this.debug(this.pattern, this.globSet);
27587
- const rawGlobParts = this.globSet.map((s) => this.slashSplit(s));
27588
- this.globParts = this.preprocess(rawGlobParts);
27589
- this.debug(this.pattern, this.globParts);
27590
- let set2 = this.globParts.map((s, _, __) => {
27591
- if (this.isWindows && this.windowsNoMagicRoot) {
27592
- const isUNC = s[0] === "" && s[1] === "" && (s[2] === "?" || !globMagic.test(s[2])) && !globMagic.test(s[3]);
27593
- const isDrive = /^[a-z]:/i.test(s[0]);
27594
- if (isUNC) {
27595
- return [...s.slice(0, 4), ...s.slice(4).map((ss) => this.parse(ss))];
27596
- } else if (isDrive) {
27597
- return [s[0], ...s.slice(1).map((ss) => this.parse(ss))];
27598
- }
27599
- }
27600
- return s.map((ss) => this.parse(ss));
27601
- });
27602
- this.debug(this.pattern, set2);
27603
- this.set = set2.filter((s) => s.indexOf(false) === -1);
27604
- if (this.isWindows) {
27605
- for (let i = 0; i < this.set.length; i++) {
27606
- const p = this.set[i];
27607
- if (p[0] === "" && p[1] === "" && this.globParts[i][2] === "?" && typeof p[3] === "string" && /^[a-z]:$/i.test(p[3])) {
27608
- p[2] = "?";
27609
- }
27610
- }
27611
- }
27612
- this.debug(this.pattern, this.set);
27613
- }
27614
- // various transforms to equivalent pattern sets that are
27615
- // faster to process in a filesystem walk. The goal is to
27616
- // eliminate what we can, and push all ** patterns as far
27617
- // to the right as possible, even if it increases the number
27618
- // of patterns that we have to process.
27619
- preprocess(globParts) {
27620
- if (this.options.noglobstar) {
27621
- for (let i = 0; i < globParts.length; i++) {
27622
- for (let j = 0; j < globParts[i].length; j++) {
27623
- if (globParts[i][j] === "**") {
27624
- globParts[i][j] = "*";
27625
- }
27626
- }
27627
- }
27628
- }
27629
- const { optimizationLevel = 1 } = this.options;
27630
- if (optimizationLevel >= 2) {
27631
- globParts = this.firstPhasePreProcess(globParts);
27632
- globParts = this.secondPhasePreProcess(globParts);
27633
- } else if (optimizationLevel >= 1) {
27634
- globParts = this.levelOneOptimize(globParts);
27635
- } else {
27636
- globParts = this.adjascentGlobstarOptimize(globParts);
27637
- }
27638
- return globParts;
27639
- }
27640
- // just get rid of adjascent ** portions
27641
- adjascentGlobstarOptimize(globParts) {
27642
- return globParts.map((parts) => {
27643
- let gs = -1;
27644
- while (-1 !== (gs = parts.indexOf("**", gs + 1))) {
27645
- let i = gs;
27646
- while (parts[i + 1] === "**") {
27647
- i++;
27648
- }
27649
- if (i !== gs) {
27650
- parts.splice(gs, i - gs);
27651
- }
27652
- }
27653
- return parts;
27654
- });
27655
- }
27656
- // get rid of adjascent ** and resolve .. portions
27657
- levelOneOptimize(globParts) {
27658
- return globParts.map((parts) => {
27659
- parts = parts.reduce((set2, part) => {
27660
- const prev = set2[set2.length - 1];
27661
- if (part === "**" && prev === "**") {
27662
- return set2;
27663
- }
27664
- if (part === "..") {
27665
- if (prev && prev !== ".." && prev !== "." && prev !== "**") {
27666
- set2.pop();
27667
- return set2;
27668
- }
27669
- }
27670
- set2.push(part);
27671
- return set2;
27672
- }, []);
27673
- return parts.length === 0 ? [""] : parts;
27674
- });
27675
- }
27676
- levelTwoFileOptimize(parts) {
27677
- if (!Array.isArray(parts)) {
27678
- parts = this.slashSplit(parts);
27679
- }
27680
- let didSomething = false;
27681
- do {
27682
- didSomething = false;
27683
- if (!this.preserveMultipleSlashes) {
27684
- for (let i = 1; i < parts.length - 1; i++) {
27685
- const p = parts[i];
27686
- if (i === 1 && p === "" && parts[0] === "")
27687
- continue;
27688
- if (p === "." || p === "") {
27689
- didSomething = true;
27690
- parts.splice(i, 1);
27691
- i--;
27692
- }
27693
- }
27694
- if (parts[0] === "." && parts.length === 2 && (parts[1] === "." || parts[1] === "")) {
27695
- didSomething = true;
27696
- parts.pop();
27697
- }
27698
- }
27699
- let dd = 0;
27700
- while (-1 !== (dd = parts.indexOf("..", dd + 1))) {
27701
- const p = parts[dd - 1];
27702
- if (p && p !== "." && p !== ".." && p !== "**") {
27703
- didSomething = true;
27704
- parts.splice(dd - 1, 2);
27705
- dd -= 2;
27706
- }
27707
- }
27708
- } while (didSomething);
27709
- return parts.length === 0 ? [""] : parts;
27710
- }
27711
- // First phase: single-pattern processing
27712
- // <pre> is 1 or more portions
27713
- // <rest> is 1 or more portions
27714
- // <p> is any portion other than ., .., '', or **
27715
- // <e> is . or ''
27716
- //
27717
- // **/.. is *brutal* for filesystem walking performance, because
27718
- // it effectively resets the recursive walk each time it occurs,
27719
- // and ** cannot be reduced out by a .. pattern part like a regexp
27720
- // or most strings (other than .., ., and '') can be.
27721
- //
27722
- // <pre>/**/../<p>/<p>/<rest> -> {<pre>/../<p>/<p>/<rest>,<pre>/**/<p>/<p>/<rest>}
27723
- // <pre>/<e>/<rest> -> <pre>/<rest>
27724
- // <pre>/<p>/../<rest> -> <pre>/<rest>
27725
- // **/**/<rest> -> **/<rest>
27726
- //
27727
- // **/*/<rest> -> */**/<rest> <== not valid because ** doesn't follow
27728
- // this WOULD be allowed if ** did follow symlinks, or * didn't
27729
- firstPhasePreProcess(globParts) {
27730
- let didSomething = false;
27731
- do {
27732
- didSomething = false;
27733
- for (let parts of globParts) {
27734
- let gs = -1;
27735
- while (-1 !== (gs = parts.indexOf("**", gs + 1))) {
27736
- let gss = gs;
27737
- while (parts[gss + 1] === "**") {
27738
- gss++;
27739
- }
27740
- if (gss > gs) {
27741
- parts.splice(gs + 1, gss - gs);
27742
- }
27743
- let next = parts[gs + 1];
27744
- const p = parts[gs + 2];
27745
- const p2 = parts[gs + 3];
27746
- if (next !== "..")
27747
- continue;
27748
- if (!p || p === "." || p === ".." || !p2 || p2 === "." || p2 === "..") {
27749
- continue;
27750
- }
27751
- didSomething = true;
27752
- parts.splice(gs, 1);
27753
- const other = parts.slice(0);
27754
- other[gs] = "**";
27755
- globParts.push(other);
27756
- gs--;
27757
- }
27758
- if (!this.preserveMultipleSlashes) {
27759
- for (let i = 1; i < parts.length - 1; i++) {
27760
- const p = parts[i];
27761
- if (i === 1 && p === "" && parts[0] === "")
27762
- continue;
27763
- if (p === "." || p === "") {
27764
- didSomething = true;
27765
- parts.splice(i, 1);
27766
- i--;
27767
- }
27768
- }
27769
- if (parts[0] === "." && parts.length === 2 && (parts[1] === "." || parts[1] === "")) {
27770
- didSomething = true;
27771
- parts.pop();
27772
- }
27773
- }
27774
- let dd = 0;
27775
- while (-1 !== (dd = parts.indexOf("..", dd + 1))) {
27776
- const p = parts[dd - 1];
27777
- if (p && p !== "." && p !== ".." && p !== "**") {
27778
- didSomething = true;
27779
- const needDot = dd === 1 && parts[dd + 1] === "**";
27780
- const splin = needDot ? ["."] : [];
27781
- parts.splice(dd - 1, 2, ...splin);
27782
- if (parts.length === 0)
27783
- parts.push("");
27784
- dd -= 2;
27785
- }
27786
- }
27787
- }
27788
- } while (didSomething);
27789
- return globParts;
27790
- }
27791
- // second phase: multi-pattern dedupes
27792
- // {<pre>/*/<rest>,<pre>/<p>/<rest>} -> <pre>/*/<rest>
27793
- // {<pre>/<rest>,<pre>/<rest>} -> <pre>/<rest>
27794
- // {<pre>/**/<rest>,<pre>/<rest>} -> <pre>/**/<rest>
27795
- //
27796
- // {<pre>/**/<rest>,<pre>/**/<p>/<rest>} -> <pre>/**/<rest>
27797
- // ^-- not valid because ** doens't follow symlinks
27798
- secondPhasePreProcess(globParts) {
27799
- for (let i = 0; i < globParts.length - 1; i++) {
27800
- for (let j = i + 1; j < globParts.length; j++) {
27801
- const matched = this.partsMatch(globParts[i], globParts[j], !this.preserveMultipleSlashes);
27802
- if (matched) {
27803
- globParts[i] = [];
27804
- globParts[j] = matched;
27805
- break;
27806
- }
27807
- }
27808
- }
27809
- return globParts.filter((gs) => gs.length);
27810
- }
27811
- partsMatch(a, b, emptyGSMatch = false) {
27812
- let ai = 0;
27813
- let bi = 0;
27814
- let result = [];
27815
- let which = "";
27816
- while (ai < a.length && bi < b.length) {
27817
- if (a[ai] === b[bi]) {
27818
- result.push(which === "b" ? b[bi] : a[ai]);
27819
- ai++;
27820
- bi++;
27821
- } else if (emptyGSMatch && a[ai] === "**" && b[bi] === a[ai + 1]) {
27822
- result.push(a[ai]);
27823
- ai++;
27824
- } else if (emptyGSMatch && b[bi] === "**" && a[ai] === b[bi + 1]) {
27825
- result.push(b[bi]);
27826
- bi++;
27827
- } else if (a[ai] === "*" && b[bi] && (this.options.dot || !b[bi].startsWith(".")) && b[bi] !== "**") {
27828
- if (which === "b")
27829
- return false;
27830
- which = "a";
27831
- result.push(a[ai]);
27832
- ai++;
27833
- bi++;
27834
- } else if (b[bi] === "*" && a[ai] && (this.options.dot || !a[ai].startsWith(".")) && a[ai] !== "**") {
27835
- if (which === "a")
27836
- return false;
27837
- which = "b";
27838
- result.push(b[bi]);
27839
- ai++;
27840
- bi++;
27841
- } else {
27842
- return false;
27843
- }
27844
- }
27845
- return a.length === b.length && result;
27846
- }
27847
- parseNegate() {
27848
- if (this.nonegate)
27849
- return;
27850
- const pattern = this.pattern;
27851
- let negate = false;
27852
- let negateOffset = 0;
27853
- for (let i = 0; i < pattern.length && pattern.charAt(i) === "!"; i++) {
27854
- negate = !negate;
27855
- negateOffset++;
27856
- }
27857
- if (negateOffset)
27858
- this.pattern = pattern.slice(negateOffset);
27859
- this.negate = negate;
27860
- }
27861
- // set partial to true to test if, for example,
27862
- // "/a/b" matches the start of "/*/b/*/d"
27863
- // Partial means, if you run out of file before you run
27864
- // out of pattern, then that's fine, as long as all
27865
- // the parts match.
27866
- matchOne(file2, pattern, partial2 = false) {
27867
- const options = this.options;
27868
- if (this.isWindows) {
27869
- const fileDrive = typeof file2[0] === "string" && /^[a-z]:$/i.test(file2[0]);
27870
- const fileUNC = !fileDrive && file2[0] === "" && file2[1] === "" && file2[2] === "?" && /^[a-z]:$/i.test(file2[3]);
27871
- const patternDrive = typeof pattern[0] === "string" && /^[a-z]:$/i.test(pattern[0]);
27872
- const patternUNC = !patternDrive && pattern[0] === "" && pattern[1] === "" && pattern[2] === "?" && typeof pattern[3] === "string" && /^[a-z]:$/i.test(pattern[3]);
27873
- const fdi = fileUNC ? 3 : fileDrive ? 0 : void 0;
27874
- const pdi = patternUNC ? 3 : patternDrive ? 0 : void 0;
27875
- if (typeof fdi === "number" && typeof pdi === "number") {
27876
- const [fd, pd] = [file2[fdi], pattern[pdi]];
27877
- if (fd.toLowerCase() === pd.toLowerCase()) {
27878
- pattern[pdi] = fd;
27879
- if (pdi > fdi) {
27880
- pattern = pattern.slice(pdi);
27881
- } else if (fdi > pdi) {
27882
- file2 = file2.slice(fdi);
27883
- }
27884
- }
27885
- }
27886
- }
27887
- const { optimizationLevel = 1 } = this.options;
27888
- if (optimizationLevel >= 2) {
27889
- file2 = this.levelTwoFileOptimize(file2);
27890
- }
27891
- this.debug("matchOne", this, { file: file2, pattern });
27892
- this.debug("matchOne", file2.length, pattern.length);
27893
- for (var fi = 0, pi = 0, fl = file2.length, pl = pattern.length; fi < fl && pi < pl; fi++, pi++) {
27894
- this.debug("matchOne loop");
27895
- var p = pattern[pi];
27896
- var f = file2[fi];
27897
- this.debug(pattern, p, f);
27898
- if (p === false) {
27899
- return false;
27900
- }
27901
- if (p === GLOBSTAR) {
27902
- this.debug("GLOBSTAR", [pattern, p, f]);
27903
- var fr = fi;
27904
- var pr = pi + 1;
27905
- if (pr === pl) {
27906
- this.debug("** at the end");
27907
- for (; fi < fl; fi++) {
27908
- if (file2[fi] === "." || file2[fi] === ".." || !options.dot && file2[fi].charAt(0) === ".")
27909
- return false;
27910
- }
27911
- return true;
27912
- }
27913
- while (fr < fl) {
27914
- var swallowee = file2[fr];
27915
- this.debug("\nglobstar while", file2, fr, pattern, pr, swallowee);
27916
- if (this.matchOne(file2.slice(fr), pattern.slice(pr), partial2)) {
27917
- this.debug("globstar found match!", fr, fl, swallowee);
27918
- return true;
27919
- } else {
27920
- if (swallowee === "." || swallowee === ".." || !options.dot && swallowee.charAt(0) === ".") {
27921
- this.debug("dot detected!", file2, fr, pattern, pr);
27922
- break;
27923
- }
27924
- this.debug("globstar swallow a segment, and continue");
27925
- fr++;
27926
- }
27927
- }
27928
- if (partial2) {
27929
- this.debug("\n>>> no match, partial?", file2, fr, pattern, pr);
27930
- if (fr === fl) {
27931
- return true;
27932
- }
27933
- }
27934
- return false;
27935
- }
27936
- let hit;
27937
- if (typeof p === "string") {
27938
- hit = f === p;
27939
- this.debug("string match", p, f, hit);
27940
- } else {
27941
- hit = p.test(f);
27942
- this.debug("pattern match", p, f, hit);
27943
- }
27944
- if (!hit)
27945
- return false;
27946
- }
27947
- if (fi === fl && pi === pl) {
27948
- return true;
27949
- } else if (fi === fl) {
27950
- return partial2;
27951
- } else if (pi === pl) {
27952
- return fi === fl - 1 && file2[fi] === "";
27953
- } else {
27954
- throw new Error("wtf?");
27955
- }
27956
- }
27957
- braceExpand() {
27958
- return braceExpand(this.pattern, this.options);
27959
- }
27960
- parse(pattern) {
27961
- assertValidPattern(pattern);
27962
- const options = this.options;
27963
- if (pattern === "**")
27964
- return GLOBSTAR;
27965
- if (pattern === "")
27966
- return "";
27967
- let m;
27968
- let fastTest = null;
27969
- if (m = pattern.match(starRE)) {
27970
- fastTest = options.dot ? starTestDot : starTest;
27971
- } else if (m = pattern.match(starDotExtRE)) {
27972
- fastTest = (options.nocase ? options.dot ? starDotExtTestNocaseDot : starDotExtTestNocase : options.dot ? starDotExtTestDot : starDotExtTest)(m[1]);
27973
- } else if (m = pattern.match(qmarksRE)) {
27974
- fastTest = (options.nocase ? options.dot ? qmarksTestNocaseDot : qmarksTestNocase : options.dot ? qmarksTestDot : qmarksTest)(m);
27975
- } else if (m = pattern.match(starDotStarRE)) {
27976
- fastTest = options.dot ? starDotStarTestDot : starDotStarTest;
27977
- } else if (m = pattern.match(dotStarRE)) {
27978
- fastTest = dotStarTest;
27979
- }
27980
- const re = AST.fromGlob(pattern, this.options).toMMPattern();
27981
- if (fastTest && typeof re === "object") {
27982
- Reflect.defineProperty(re, "test", { value: fastTest });
27983
- }
27984
- return re;
27985
- }
27986
- makeRe() {
27987
- if (this.regexp || this.regexp === false)
27988
- return this.regexp;
27989
- const set2 = this.set;
27990
- if (!set2.length) {
27991
- this.regexp = false;
27992
- return this.regexp;
27993
- }
27994
- const options = this.options;
27995
- const twoStar = options.noglobstar ? star2 : options.dot ? twoStarDot : twoStarNoDot;
27996
- const flags = new Set(options.nocase ? ["i"] : []);
27997
- let re = set2.map((pattern) => {
27998
- const pp = pattern.map((p) => {
27999
- if (p instanceof RegExp) {
28000
- for (const f of p.flags.split(""))
28001
- flags.add(f);
28002
- }
28003
- return typeof p === "string" ? regExpEscape2(p) : p === GLOBSTAR ? GLOBSTAR : p._src;
28004
- });
28005
- pp.forEach((p, i) => {
28006
- const next = pp[i + 1];
28007
- const prev = pp[i - 1];
28008
- if (p !== GLOBSTAR || prev === GLOBSTAR) {
28009
- return;
28010
- }
28011
- if (prev === void 0) {
28012
- if (next !== void 0 && next !== GLOBSTAR) {
28013
- pp[i + 1] = "(?:\\/|" + twoStar + "\\/)?" + next;
28014
- } else {
28015
- pp[i] = twoStar;
28016
- }
28017
- } else if (next === void 0) {
28018
- pp[i - 1] = prev + "(?:\\/|\\/" + twoStar + ")?";
28019
- } else if (next !== GLOBSTAR) {
28020
- pp[i - 1] = prev + "(?:\\/|\\/" + twoStar + "\\/)" + next;
28021
- pp[i + 1] = GLOBSTAR;
28022
- }
28023
- });
28024
- const filtered = pp.filter((p) => p !== GLOBSTAR);
28025
- if (this.partial && filtered.length >= 1) {
28026
- const prefixes = [];
28027
- for (let i = 1; i <= filtered.length; i++) {
28028
- prefixes.push(filtered.slice(0, i).join("/"));
28029
- }
28030
- return "(?:" + prefixes.join("|") + ")";
28031
- }
28032
- return filtered.join("/");
28033
- }).join("|");
28034
- const [open, close] = set2.length > 1 ? ["(?:", ")"] : ["", ""];
28035
- re = "^" + open + re + close + "$";
28036
- if (this.partial) {
28037
- re = "^(?:\\/|" + open + re.slice(1, -1) + close + ")$";
28038
- }
28039
- if (this.negate)
28040
- re = "^(?!" + re + ").+$";
28041
- try {
28042
- this.regexp = new RegExp(re, [...flags].join(""));
28043
- } catch (ex) {
28044
- this.regexp = false;
28045
- }
28046
- return this.regexp;
28047
- }
28048
- slashSplit(p) {
28049
- if (this.preserveMultipleSlashes) {
28050
- return p.split("/");
28051
- } else if (this.isWindows && /^\/\/[^\/]+/.test(p)) {
28052
- return ["", ...p.split(/\/+/)];
28053
- } else {
28054
- return p.split(/\/+/);
28055
- }
28056
- }
28057
- match(f, partial2 = this.partial) {
28058
- this.debug("match", f, this.pattern);
28059
- if (this.comment) {
28060
- return false;
28061
- }
28062
- if (this.empty) {
28063
- return f === "";
28064
- }
28065
- if (f === "/" && partial2) {
28066
- return true;
28067
- }
28068
- const options = this.options;
28069
- if (this.isWindows) {
28070
- f = f.split("\\").join("/");
28071
- }
28072
- const ff = this.slashSplit(f);
28073
- this.debug(this.pattern, "split", ff);
28074
- const set2 = this.set;
28075
- this.debug(this.pattern, "set", set2);
28076
- let filename = ff[ff.length - 1];
28077
- if (!filename) {
28078
- for (let i = ff.length - 2; !filename && i >= 0; i--) {
28079
- filename = ff[i];
28080
- }
28081
- }
28082
- for (let i = 0; i < set2.length; i++) {
28083
- const pattern = set2[i];
28084
- let file2 = ff;
28085
- if (options.matchBase && pattern.length === 1) {
28086
- file2 = [filename];
28087
- }
28088
- const hit = this.matchOne(file2, pattern, partial2);
28089
- if (hit) {
28090
- if (options.flipNegate) {
28091
- return true;
28092
- }
28093
- return !this.negate;
28094
- }
28095
- }
28096
- if (options.flipNegate) {
28097
- return false;
28098
- }
28099
- return this.negate;
28100
- }
28101
- static defaults(def) {
28102
- return minimatch.defaults(def).Minimatch;
28103
- }
28104
- };
28105
- minimatch.AST = AST;
28106
- minimatch.Minimatch = Minimatch;
28107
- minimatch.escape = escape2;
28108
- minimatch.unescape = unescape2;
28109
-
28110
- // ../riviere-extract-ts/dist/platform/infra/external-clients/minimatch/minimatch-glob.js
28111
- function matchesGlob(path2, pattern) {
28112
- return minimatch(path2, pattern);
28113
- }
28114
-
28115
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/detect-connections.js
28116
- import { performance } from "node:perf_hooks";
28117
-
28118
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/call-graph-types.js
28119
- function componentIdentity(component) {
28120
- return ComponentId.create({
28121
- domain: component.domain,
28122
- module: component.module,
28123
- type: component.type,
28124
- name: component.name
28125
- }).toString();
28126
- }
28127
- function stripGenericArgs(typeName) {
28128
- const index = typeName.indexOf("<");
28129
- if (index === -1) {
28130
- return typeName;
28131
- }
28132
- return typeName.slice(0, index);
28133
- }
28134
-
28135
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/component-index.js
28136
- function locationKey(file2, line) {
28137
- return `${file2}:${line}`;
28138
- }
28139
- var ComponentIndex = class {
28140
- byName;
28141
- byLocation;
28142
- constructor(components) {
28143
- const nameMap = /* @__PURE__ */ new Map();
28144
- const locationMap = /* @__PURE__ */ new Map();
28145
- for (const component of components) {
28146
- nameMap.set(component.name, component);
28147
- locationMap.set(locationKey(component.location.file, component.location.line), component);
28148
- }
28149
- this.byName = nameMap;
28150
- this.byLocation = locationMap;
28151
- }
28152
- isComponent(typeName) {
28153
- return this.byName.has(stripGenericArgs(typeName));
28154
- }
28155
- getComponentByTypeName(typeName) {
28156
- return this.byName.get(stripGenericArgs(typeName));
28157
- }
28158
- getComponentByLocation(file2, line) {
28159
- return this.byLocation.get(locationKey(file2, line));
28160
- }
28161
- };
28162
-
28163
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/build-call-graph.js
28164
- import { Node as Node3, SyntaxKind as SyntaxKind6 } from "ts-morph";
28165
-
28166
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/trace-calls.js
28167
- import { Node as Node2, SyntaxKind as SyntaxKind5 } from "ts-morph";
28168
-
28169
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/type-resolver.js
28170
- import { CallExpression, SourceFile, Node } from "ts-morph";
28171
-
28172
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/connection-detection-error.js
28173
- var ConnectionDetectionError = class extends Error {
28174
- file;
28175
- line;
28176
- typeName;
28177
- reason;
28178
- constructor(params) {
28179
- super(`Connection detection failed for ${params.typeName} at ${params.file}:${params.line}: ${params.reason}`);
28180
- this.name = "ConnectionDetectionError";
28181
- this.file = params.file;
28182
- this.line = params.line;
28183
- this.typeName = params.typeName;
28184
- this.reason = params.reason;
28185
- }
28186
- };
28187
-
28188
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/type-resolver.js
28189
- function stripGenerics(typeName) {
28190
- const angleBracketIndex = typeName.indexOf("<");
28191
- if (angleBracketIndex === -1)
28192
- return typeName;
28193
- return typeName.slice(0, angleBracketIndex);
28194
- }
28195
- function stripPromise(typeName) {
28196
- if (typeName.startsWith("Promise<") && typeName.endsWith(">")) {
28197
- return typeName.slice(8, -1);
28198
- }
28199
- return typeName;
26440
+ return typeName;
28200
26441
  }
28201
26442
  var UNRESOLVABLE_TYPES = /* @__PURE__ */ new Set(["any", "unknown", "object"]);
28202
26443
  function isUnresolvableType(typeName) {
@@ -28286,10 +26527,7 @@ function handleUnresolvable(sourceFile, callExpression, rawTypeName, options) {
28286
26527
  if (options.strict) {
28287
26528
  throw buildError(sourceFile, callExpression, rawTypeName, reason);
28288
26529
  }
28289
- return {
28290
- resolved: false,
28291
- reason
28292
- };
26530
+ return TypeResolution.unresolved(reason);
28293
26531
  }
28294
26532
  function resolveCallExpressionReceiverType(callExpression, sourceFile, options) {
28295
26533
  const receiver = getReceiverExpression(callExpression);
@@ -28298,26 +26536,68 @@ function resolveCallExpressionReceiverType(callExpression, sourceFile, options)
28298
26536
  if (options.strict) {
28299
26537
  throw buildError(sourceFile, callExpression, "unknown", reason);
28300
26538
  }
28301
- return {
28302
- resolved: false,
28303
- reason
28304
- };
26539
+ return TypeResolution.unresolved(reason);
28305
26540
  }
28306
26541
  const rawTypeName = resolveReceiverTypeName(receiver);
28307
26542
  if (isUnresolvableType(rawTypeName)) {
28308
26543
  return handleUnresolvable(sourceFile, callExpression, rawTypeName, options);
28309
26544
  }
28310
- return {
28311
- resolved: true,
28312
- typeName: stripGenerics(rawTypeName)
28313
- };
26545
+ return TypeResolution.resolved(stripGenerics(rawTypeName));
28314
26546
  }
28315
26547
 
28316
26548
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/call-graph-shared.js
28317
- import { SyntaxKind as SyntaxKind4 } from "ts-morph";
26549
+ import { SyntaxKind as SyntaxKind2 } from "ts-morph";
26550
+
26551
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/call-graph-outcomes.js
26552
+ var InterfaceResolutionOutcome = class {
26553
+ component;
26554
+ resolvedTypeName;
26555
+ uncertain;
26556
+ constructor(params) {
26557
+ this.component = params.component;
26558
+ this.resolvedTypeName = params.resolvedTypeName;
26559
+ this.uncertain = params.uncertain;
26560
+ }
26561
+ };
26562
+ var MethodLookup = class {
26563
+ method;
26564
+ classFound;
26565
+ constructor(params) {
26566
+ this.method = params.method;
26567
+ this.classFound = params.classFound;
26568
+ }
26569
+ };
28318
26570
 
28319
26571
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/interface-resolution/resolve-interface.js
28320
26572
  import { Project, ClassDeclaration, SourceFile as SourceFile2 } from "ts-morph";
26573
+ var InterfaceResolution = class _InterfaceResolution {
26574
+ resolved;
26575
+ typeName;
26576
+ reason;
26577
+ typeDefinedInSource;
26578
+ constructor(params) {
26579
+ this.resolved = params.resolved;
26580
+ this.typeName = params.typeName;
26581
+ this.reason = params.reason;
26582
+ this.typeDefinedInSource = params.typeDefinedInSource;
26583
+ }
26584
+ static resolved(typeName) {
26585
+ return new _InterfaceResolution({
26586
+ resolved: true,
26587
+ typeName,
26588
+ reason: void 0,
26589
+ typeDefinedInSource: void 0
26590
+ });
26591
+ }
26592
+ static unresolved(params) {
26593
+ return new _InterfaceResolution({
26594
+ resolved: false,
26595
+ typeName: void 0,
26596
+ reason: params.reason,
26597
+ typeDefinedInSource: params.typeDefinedInSource
26598
+ });
26599
+ }
26600
+ };
28321
26601
  function isNodeModulesPath(filePath) {
28322
26602
  return filePath.includes("node_modules");
28323
26603
  }
@@ -28360,10 +26640,7 @@ function resolveInterface(interfaceName, project, sourceFilePaths, options) {
28360
26640
  const implementations = findImplementations(interfaceName, sourceFiles);
28361
26641
  const [singleImpl] = implementations;
28362
26642
  if (implementations.length === 1 && singleImpl) {
28363
- return {
28364
- resolved: true,
28365
- typeName: singleImpl
28366
- };
26643
+ return InterfaceResolution.resolved(singleImpl);
28367
26644
  }
28368
26645
  if (implementations.length === 0) {
28369
26646
  const definedInSource = isDefinedInSourceFiles(interfaceName, sourceFiles);
@@ -28371,50 +26648,56 @@ function resolveInterface(interfaceName, project, sourceFilePaths, options) {
28371
26648
  if (definedInSource && options.strict) {
28372
26649
  throw createError(interfaceName, reason2);
28373
26650
  }
28374
- return {
28375
- resolved: false,
26651
+ return InterfaceResolution.unresolved({
28376
26652
  reason: reason2,
28377
26653
  typeDefinedInSource: definedInSource
28378
- };
26654
+ });
28379
26655
  }
28380
26656
  const reason = `Multiple implementations found for ${interfaceName} (${implementations.length}): ${implementations.join(", ")}`;
28381
26657
  if (options.strict) {
28382
26658
  throw createError(interfaceName, reason);
28383
26659
  }
28384
- return {
28385
- resolved: false,
26660
+ return InterfaceResolution.unresolved({
28386
26661
  reason,
28387
26662
  typeDefinedInSource: true
28388
- };
26663
+ });
28389
26664
  }
28390
26665
 
28391
26666
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/call-graph-shared.js
28392
26667
  function getCalledMethodName(callExpr) {
28393
26668
  const expression = callExpr.getExpression();
28394
- return expression.asKindOrThrow(SyntaxKind4.PropertyAccessExpression).getName();
26669
+ return expression.asKindOrThrow(SyntaxKind2.PropertyAccessExpression).getName();
28395
26670
  }
28396
26671
  function resolveTypeThroughInterface(typeName, project, componentIndex, options) {
28397
26672
  const component = componentIndex.getComponentByTypeName(typeName);
28398
26673
  if (component !== void 0) {
28399
- return {
26674
+ return new InterfaceResolutionOutcome({
28400
26675
  component,
28401
26676
  resolvedTypeName: void 0,
28402
26677
  uncertain: void 0
28403
- };
26678
+ });
28404
26679
  }
28405
26680
  const interfaceResult = resolveInterface(typeName, project, options.sourceFilePaths, { strict: options.strict });
28406
26681
  if (interfaceResult.resolved) {
28407
- return {
28408
- component: componentIndex.getComponentByTypeName(interfaceResult.typeName),
28409
- resolvedTypeName: interfaceResult.typeName,
26682
+ const resolvedTypeName = requireInterfaceTypeName(interfaceResult);
26683
+ return new InterfaceResolutionOutcome({
26684
+ component: componentIndex.getComponentByTypeName(resolvedTypeName),
26685
+ resolvedTypeName,
28410
26686
  uncertain: void 0
28411
- };
26687
+ });
28412
26688
  }
28413
- return {
26689
+ return new InterfaceResolutionOutcome({
28414
26690
  component: void 0,
28415
26691
  resolvedTypeName: void 0,
28416
26692
  uncertain: interfaceResult.typeDefinedInSource ? interfaceResult.reason : void 0
28417
- };
26693
+ });
26694
+ }
26695
+ function requireInterfaceTypeName(interfaceResolution) {
26696
+ const typeName = interfaceResolution.typeName;
26697
+ if (typeName === void 0) {
26698
+ throw new TypeError("Expected interface resolution type name");
26699
+ }
26700
+ return typeName;
28418
26701
  }
28419
26702
  function findClassByNameInProject(project, typeName) {
28420
26703
  for (const sourceFile of project.getSourceFiles()) {
@@ -28443,15 +26726,15 @@ function resolveContainerMethod(project, typeName, calledMethodName, componentIn
28443
26726
  function findMethodInProject(project, typeName, methodName) {
28444
26727
  const lookup = findClassByNameInProject(project, typeName);
28445
26728
  if (lookup === void 0) {
28446
- return {
26729
+ return new MethodLookup({
28447
26730
  method: void 0,
28448
26731
  classFound: false
28449
- };
26732
+ });
28450
26733
  }
28451
- return {
26734
+ return new MethodLookup({
28452
26735
  method: lookup.classDecl.getMethod(methodName),
28453
26736
  classFound: true
28454
- };
26737
+ });
28455
26738
  }
28456
26739
 
28457
26740
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/trace-calls.js
@@ -28480,16 +26763,16 @@ function traceCallExpression(callExpr, ctx) {
28480
26763
  if (!typeResult.resolved) {
28481
26764
  return;
28482
26765
  }
28483
- const typeName = typeResult.typeName;
26766
+ const typeName = requireResolvedTypeName(typeResult);
28484
26767
  const calledMethodName = getCalledMethodName(callExpr);
28485
26768
  const outcome = resolveComponentTarget(typeName, calledMethodName, ctx);
28486
26769
  if (outcome.target !== void 0) {
28487
26770
  if (componentIdentity(ctx.sourceComponent) !== componentIdentity(outcome.target)) {
28488
- ctx.results.push({
26771
+ ctx.results.push(new RawLink({
28489
26772
  source: ctx.sourceComponent,
28490
26773
  target: outcome.target,
28491
26774
  callSite: ctx.originCallSite
28492
- });
26775
+ }));
28493
26776
  }
28494
26777
  return;
28495
26778
  }
@@ -28508,15 +26791,22 @@ function traceIntoNonComponent(typeName, calledMethodName, outcome, ctx) {
28508
26791
  return;
28509
26792
  }
28510
26793
  if (!classFound && outcome.uncertain !== void 0) {
28511
- ctx.uncertainResults.push({
26794
+ ctx.uncertainResults.push(new UncertainRawLink({
28512
26795
  source: ctx.sourceComponent,
28513
26796
  reason: outcome.uncertain,
28514
26797
  callSite: ctx.originCallSite
28515
- });
26798
+ }));
26799
+ }
26800
+ }
26801
+ function requireResolvedTypeName(typeResolution) {
26802
+ const typeName = typeResolution.typeName;
26803
+ if (typeName === void 0) {
26804
+ throw new TypeError("Expected resolved type name");
28516
26805
  }
26806
+ return typeName;
28517
26807
  }
28518
26808
  function traceBody(body, ctx) {
28519
- const callExpressions = body.getDescendantsOfKind(SyntaxKind5.CallExpression);
26809
+ const callExpressions = body.getDescendantsOfKind(SyntaxKind3.CallExpression);
28520
26810
  for (const callExpr of callExpressions) {
28521
26811
  traceCallExpression(callExpr, ctx);
28522
26812
  }
@@ -28548,10 +26838,10 @@ function findMethodLevelComponent(project, component) {
28548
26838
  for (const classDecl of sourceFile.getClasses()) {
28549
26839
  const method = classDecl.getMethods().find((m) => m.getStartLineNumber() === component.location.line);
28550
26840
  if (method !== void 0) {
28551
- return {
26841
+ return new MethodLevelTarget({
28552
26842
  classDecl,
28553
26843
  method
28554
- };
26844
+ });
28555
26845
  }
28556
26846
  }
28557
26847
  return void 0;
@@ -28564,12 +26854,34 @@ function findFunctionInProject(project, component) {
28564
26854
  return sourceFile.getFunctions().find((f) => f.getStartLineNumber() === component.location.line);
28565
26855
  }
28566
26856
 
26857
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/extracted-link.js
26858
+ var ExtractedLink = class {
26859
+ source;
26860
+ target;
26861
+ type;
26862
+ _uncertain;
26863
+ sourceLocation;
26864
+ constructor(params) {
26865
+ this.source = params.source;
26866
+ this.target = params.target;
26867
+ this.type = params.type;
26868
+ this._uncertain = params._uncertain;
26869
+ this.sourceLocation = params.sourceLocation;
26870
+ }
26871
+ };
26872
+
28567
26873
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/deduplicate-links.js
26874
+ var MissingSourceLocationError = class extends Error {
26875
+ constructor() {
26876
+ super("Expected sourceLocation on extracted link");
26877
+ this.name = "MissingSourceLocationError";
26878
+ }
26879
+ };
28568
26880
  function linkKey(source, target, type) {
28569
26881
  return `${source}|${target}|${type}`;
28570
26882
  }
28571
26883
  function buildExtractedLink(source, target, type, callSite, repository) {
28572
- return {
26884
+ const link = new ExtractedLink({
28573
26885
  source,
28574
26886
  target,
28575
26887
  type,
@@ -28579,10 +26891,15 @@ function buildExtractedLink(source, target, type, callSite, repository) {
28579
26891
  lineNumber: callSite.lineNumber,
28580
26892
  methodName: callSite.methodName
28581
26893
  }
28582
- };
26894
+ });
26895
+ const sourceLocation = link.sourceLocation;
26896
+ if (sourceLocation === void 0) {
26897
+ throw new MissingSourceLocationError();
26898
+ }
26899
+ return link;
28583
26900
  }
28584
26901
  function buildUncertainLink(source, reason, callSite, repository) {
28585
- return {
26902
+ return new ExtractedLink({
28586
26903
  source,
28587
26904
  target: "_unresolved",
28588
26905
  type: "sync",
@@ -28593,7 +26910,7 @@ function buildUncertainLink(source, reason, callSite, repository) {
28593
26910
  lineNumber: callSite.lineNumber,
28594
26911
  methodName: callSite.methodName
28595
26912
  }
28596
- };
26913
+ });
28597
26914
  }
28598
26915
  function deduplicateLinks(rawLinks, uncertainLinks, repository = "") {
28599
26916
  const seen = /* @__PURE__ */ new Map();
@@ -28604,7 +26921,7 @@ function deduplicateLinks(rawLinks, uncertainLinks, repository = "") {
28604
26921
  const key = linkKey(sourceId, targetId, type);
28605
26922
  const existing = seen.get(key);
28606
26923
  if (existing !== void 0) {
28607
- if (raw.callSite.lineNumber < existing.sourceLocation.lineNumber) {
26924
+ if (raw.callSite.lineNumber < requireSourceLocation(existing).lineNumber) {
28608
26925
  seen.set(key, buildExtractedLink(sourceId, targetId, type, raw.callSite, repository));
28609
26926
  }
28610
26927
  continue;
@@ -28617,6 +26934,24 @@ function deduplicateLinks(rawLinks, uncertainLinks, repository = "") {
28617
26934
  }
28618
26935
  return result;
28619
26936
  }
26937
+ function requireSourceLocation(link) {
26938
+ const sourceLocation = link.sourceLocation;
26939
+ if (sourceLocation === void 0) {
26940
+ throw new MissingSourceLocationError();
26941
+ }
26942
+ if (sourceLocation.lineNumber === void 0) {
26943
+ throw new MissingSourceLocationError();
26944
+ }
26945
+ if (sourceLocation.methodName === void 0) {
26946
+ throw new MissingSourceLocationError();
26947
+ }
26948
+ return {
26949
+ repository: sourceLocation.repository,
26950
+ filePath: sourceLocation.filePath,
26951
+ lineNumber: sourceLocation.lineNumber,
26952
+ methodName: sourceLocation.methodName
26953
+ };
26954
+ }
28620
26955
 
28621
26956
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/call-graph/build-call-graph.js
28622
26957
  function processCallExpression(callExpr, component, methodName, project, componentIndex, rawLinks, uncertainLinks, options) {
@@ -28625,55 +26960,65 @@ function processCallExpression(callExpr, component, methodName, project, compone
28625
26960
  }
28626
26961
  const sourceFile = callExpr.getSourceFile();
28627
26962
  const typeResult = resolveCallExpressionReceiverType(callExpr, sourceFile, { strict: options.strict });
28628
- const currentCallSite = {
26963
+ const currentCallSite = new CallSite({
28629
26964
  filePath: component.location.file,
28630
26965
  lineNumber: callExpr.getStartLineNumber(),
28631
26966
  methodName
28632
- };
26967
+ });
28633
26968
  if (!typeResult.resolved) {
28634
- uncertainLinks.push({
26969
+ uncertainLinks.push(new UncertainRawLink({
28635
26970
  source: component,
28636
- reason: typeResult.reason,
26971
+ reason: typeResult.reason ?? "Receiver type unresolved",
28637
26972
  callSite: currentCallSite
28638
- });
26973
+ }));
28639
26974
  return;
28640
26975
  }
28641
- const typeName = typeResult.typeName;
26976
+ const typeName = requireResolvedTypeName2(typeResult);
28642
26977
  const calledMethodName = getCalledMethodName(callExpr);
28643
- const { component: targetComponent, resolvedTypeName, uncertain } = resolveTypeThroughInterface(typeName, project, componentIndex, options);
26978
+ const interfaceResolution = resolveTypeThroughInterface(typeName, project, componentIndex, options);
26979
+ const targetComponent = interfaceResolution.component;
26980
+ const resolvedTypeName = interfaceResolution.resolvedTypeName;
26981
+ const uncertain = interfaceResolution.uncertain;
28644
26982
  if (targetComponent !== void 0) {
28645
26983
  if (componentIdentity(component) !== componentIdentity(targetComponent)) {
28646
- rawLinks.push({
26984
+ rawLinks.push(new RawLink({
28647
26985
  source: component,
28648
26986
  target: targetComponent,
28649
26987
  callSite: currentCallSite
28650
- });
26988
+ }));
28651
26989
  }
28652
26990
  return;
28653
26991
  }
28654
26992
  const containerTarget = resolveContainerMethod(project, resolvedTypeName ?? typeName, calledMethodName, componentIndex);
28655
26993
  if (containerTarget !== void 0) {
28656
26994
  if (componentIdentity(component) !== componentIdentity(containerTarget)) {
28657
- rawLinks.push({
26995
+ rawLinks.push(new RawLink({
28658
26996
  source: component,
28659
26997
  target: containerTarget,
28660
26998
  callSite: currentCallSite
28661
- });
26999
+ }));
28662
27000
  }
28663
27001
  return;
28664
27002
  }
28665
27003
  traceNonComponent(project, componentIndex, component, resolvedTypeName ?? typeName, calledMethodName, currentCallSite, rawLinks, uncertainLinks, uncertain, options);
28666
27004
  }
27005
+ function requireResolvedTypeName2(typeResolution) {
27006
+ const typeName = typeResolution.typeName;
27007
+ if (typeName === void 0) {
27008
+ throw new TypeError("Expected resolved type name");
27009
+ }
27010
+ return typeName;
27011
+ }
28667
27012
  function processFunction(funcDecl, component, project, componentIndex, rawLinks, uncertainLinks, options) {
28668
27013
  const functionName = funcDecl.getNameOrThrow();
28669
- const callExpressions = funcDecl.getDescendantsOfKind(SyntaxKind6.CallExpression);
27014
+ const callExpressions = funcDecl.getDescendantsOfKind(SyntaxKind4.CallExpression);
28670
27015
  for (const callExpr of callExpressions) {
28671
27016
  processCallExpression(callExpr, component, functionName, project, componentIndex, rawLinks, uncertainLinks, options);
28672
27017
  }
28673
27018
  }
28674
27019
  function processMethod(method, component, project, componentIndex, rawLinks, uncertainLinks, options) {
28675
27020
  const methodName = method.getName();
28676
- const callExpressions = method.getDescendantsOfKind(SyntaxKind6.CallExpression);
27021
+ const callExpressions = method.getDescendantsOfKind(SyntaxKind4.CallExpression);
28677
27022
  for (const callExpr of callExpressions) {
28678
27023
  processCallExpression(callExpr, component, methodName, project, componentIndex, rawLinks, uncertainLinks, options);
28679
27024
  }
@@ -28710,11 +27055,11 @@ function traceNonComponent(project, componentIndex, source, typeName, calledMeth
28710
27055
  return;
28711
27056
  }
28712
27057
  if (!classFound && interfaceUncertainty !== void 0) {
28713
- uncertainLinks.push({
27058
+ uncertainLinks.push(new UncertainRawLink({
28714
27059
  source,
28715
27060
  reason: interfaceUncertainty,
28716
27061
  callSite
28717
- });
27062
+ }));
28718
27063
  }
28719
27064
  }
28720
27065
 
@@ -28761,13 +27106,13 @@ function handleMissingMetadata(publisher, metadataKey, options) {
28761
27106
  reason: `published event type in "${metadataKey}" metadata is missing or invalid`
28762
27107
  });
28763
27108
  }
28764
- return {
27109
+ return new ExtractedLink({
28765
27110
  source: componentIdentity(publisher),
28766
27111
  target: "_unresolved",
28767
27112
  type: "async",
28768
27113
  sourceLocation: toSourceLocation(publisher, options.repository),
28769
27114
  _uncertain: `event publisher "${publisher.name}" is missing required "${metadataKey}" metadata`
28770
- };
27115
+ });
28771
27116
  }
28772
27117
  function resolvePublishTarget(publisher, publishedEventType, events, options) {
28773
27118
  const matchingEvents = events.filter((e) => e.metadata[EVENT_NAME_FIELD] === publishedEventType);
@@ -28777,7 +27122,7 @@ function resolvePublishTarget(publisher, publishedEventType, events, options) {
28777
27122
  if (matchingEvents.length > 1) {
28778
27123
  return [handleAmbiguousMatch(publisher, publishedEventType, matchingEvents.length, options)];
28779
27124
  }
28780
- return matchingEvents.map((event) => ({
27125
+ return matchingEvents.map((event) => new ExtractedLink({
28781
27126
  source: componentIdentity(publisher),
28782
27127
  target: componentIdentity(event),
28783
27128
  type: "async",
@@ -28793,13 +27138,13 @@ function handleAmbiguousMatch(publisher, publishedEventType, matchCount, options
28793
27138
  reason: `published event "${publishedEventType}" matches ${matchCount} Event components (ambiguous)`
28794
27139
  });
28795
27140
  }
28796
- return {
27141
+ return new ExtractedLink({
28797
27142
  source: componentIdentity(publisher),
28798
27143
  target: "_unresolved",
28799
27144
  type: "async",
28800
27145
  sourceLocation: toSourceLocation(publisher, options.repository),
28801
27146
  _uncertain: `ambiguous: ${matchCount} events match published event type: ${publishedEventType}`
28802
- };
27147
+ });
28803
27148
  }
28804
27149
  function handleNoMatch(publisher, publishedEventType, options) {
28805
27150
  if (options.strict) {
@@ -28810,13 +27155,13 @@ function handleNoMatch(publisher, publishedEventType, options) {
28810
27155
  reason: `published event "${publishedEventType}" does not match any Event component`
28811
27156
  });
28812
27157
  }
28813
- return {
27158
+ return new ExtractedLink({
28814
27159
  source: componentIdentity(publisher),
28815
27160
  target: "_unresolved",
28816
27161
  type: "async",
28817
27162
  sourceLocation: toSourceLocation(publisher, options.repository),
28818
27163
  _uncertain: `no event found for published event type: ${publishedEventType}`
28819
- };
27164
+ });
28820
27165
  }
28821
27166
 
28822
27167
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/async-detection/detect-subscribe-connections.js
@@ -28834,7 +27179,7 @@ function resolveSubscription(handler, eventName, events, options, repository) {
28834
27179
  if (matchingEvents.length > 1) {
28835
27180
  return [handleAmbiguousMatch2(handler, eventName, matchingEvents.length, options, repository)];
28836
27181
  }
28837
- return matchingEvents.map((event) => ({
27182
+ return matchingEvents.map((event) => new ExtractedLink({
28838
27183
  source: componentIdentity(event),
28839
27184
  target: componentIdentity(handler),
28840
27185
  type: "async",
@@ -28850,13 +27195,13 @@ function handleAmbiguousMatch2(handler, eventName, matchCount, options, reposito
28850
27195
  reason: `subscribed event "${eventName}" matches ${matchCount} Event components (ambiguous)`
28851
27196
  });
28852
27197
  }
28853
- return {
27198
+ return new ExtractedLink({
28854
27199
  source: "_unresolved",
28855
27200
  target: componentIdentity(handler),
28856
27201
  type: "async",
28857
27202
  sourceLocation: toSourceLocation(handler, repository),
28858
27203
  _uncertain: `ambiguous: ${matchCount} events match subscribed event name: ${eventName}`
28859
- };
27204
+ });
28860
27205
  }
28861
27206
  function handleNoMatch2(handler, eventName, options, repository) {
28862
27207
  if (options.strict) {
@@ -28867,13 +27212,13 @@ function handleNoMatch2(handler, eventName, options, repository) {
28867
27212
  reason: `subscribed event "${eventName}" does not match any Event component`
28868
27213
  });
28869
27214
  }
28870
- return {
27215
+ return new ExtractedLink({
28871
27216
  source: "_unresolved",
28872
27217
  target: componentIdentity(handler),
28873
27218
  type: "async",
28874
27219
  sourceLocation: toSourceLocation(handler, repository),
28875
27220
  _uncertain: `no event found for subscribed event name: ${eventName}`
28876
- };
27221
+ });
28877
27222
  }
28878
27223
  function getSubscribedEvents(handler) {
28879
27224
  const raw = handler.metadata[SUBSCRIBED_EVENTS_FIELD];
@@ -28883,13 +27228,57 @@ function getSubscribedEvents(handler) {
28883
27228
  return raw.filter((item) => typeof item === "string");
28884
27229
  }
28885
27230
 
27231
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/connection-detection-values.js
27232
+ function assignLinkCollections(target, params) {
27233
+ target.links = params.links;
27234
+ target.externalLinks = params.externalLinks;
27235
+ target.timings = params.timings;
27236
+ }
27237
+ var PerModuleTimings = class {
27238
+ callGraphMs;
27239
+ setupMs;
27240
+ constructor(params) {
27241
+ this.callGraphMs = params.callGraphMs;
27242
+ this.setupMs = params.setupMs;
27243
+ }
27244
+ };
27245
+ var PerModuleDetectionResult = class {
27246
+ constructor(params) {
27247
+ assignLinkCollections(this, params);
27248
+ }
27249
+ };
27250
+ var CrossModuleTimings = class {
27251
+ asyncDetectionMs;
27252
+ constructor(params) {
27253
+ this.asyncDetectionMs = params.asyncDetectionMs;
27254
+ }
27255
+ };
27256
+ var CrossModuleDetectionResult = class {
27257
+ links;
27258
+ timings;
27259
+ constructor(params) {
27260
+ this.links = params.links;
27261
+ this.timings = params.timings;
27262
+ }
27263
+ };
27264
+
27265
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/http-link-resolution-result.js
27266
+ var HttpLinkResolutionResult = class {
27267
+ links;
27268
+ externalLinks;
27269
+ constructor(params) {
27270
+ this.links = params.links;
27271
+ this.externalLinks = params.externalLinks;
27272
+ }
27273
+ };
27274
+
28886
27275
  // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/resolve-http-links.js
28887
27276
  function resolveHttpLinks(links, components, httpLinkConfigs) {
28888
27277
  if (httpLinkConfigs.length === 0) {
28889
- return {
27278
+ return new HttpLinkResolutionResult({
28890
27279
  links: [...links],
28891
27280
  externalLinks: []
28892
- };
27281
+ });
28893
27282
  }
28894
27283
  const resolvedCustomTypes = new Set(httpLinkConfigs.map((config2) => config2.fromCustomType));
28895
27284
  const componentsByIdentity = indexComponentsByIdentity(components);
@@ -28916,15 +27305,18 @@ function resolveHttpLinks(links, components, httpLinkConfigs) {
28916
27305
  externalLinks.push(toExternalLink(link, domainName, targetComponent, config2.matchApiBy));
28917
27306
  continue;
28918
27307
  }
28919
- resolvedLinks.push({
28920
- ...link,
28921
- target: componentIdentity(matchedApi)
28922
- });
27308
+ resolvedLinks.push(new ExtractedLink({
27309
+ source: link.source,
27310
+ target: componentIdentity(matchedApi),
27311
+ ...link.type !== void 0 && { type: link.type },
27312
+ ...link._uncertain !== void 0 && { _uncertain: link._uncertain },
27313
+ ...link.sourceLocation !== void 0 && { sourceLocation: link.sourceLocation }
27314
+ }));
28923
27315
  }
28924
- return {
27316
+ return new HttpLinkResolutionResult({
28925
27317
  links: resolvedLinks,
28926
27318
  externalLinks
28927
- };
27319
+ });
28928
27320
  }
28929
27321
  function stripResolvedCustomTypes(components, httpLinkConfigs, resolvedLinks) {
28930
27322
  const resolvedCustomTypes = new Set(httpLinkConfigs.map((config2) => config2.fromCustomType));
@@ -28995,76 +27387,368 @@ function toExternalLink(link, serviceName, targetComponent, matchApiBy) {
28995
27387
  ...link.sourceLocation !== void 0 && { sourceLocation: link.sourceLocation }
28996
27388
  };
28997
27389
  }
28998
-
28999
- // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/detect-connections.js
29000
- function computeFilteredFilePaths(project, moduleGlobs, globMatcher) {
29001
- return project.getSourceFiles().map((sf) => sf.getFilePath()).filter((filePath) => moduleGlobs.some((glob) => globMatcher(filePath, glob)));
27390
+
27391
+ // ../riviere-extract-ts/dist/features/extraction/domain/connection-detection/detect-connections.js
27392
+ function deduplicateCrossStrategy(links) {
27393
+ const seen = /* @__PURE__ */ new Map();
27394
+ for (const link of links) {
27395
+ const key = `${link.source}|${link.target}|${link.type}`;
27396
+ const existing = seen.get(key);
27397
+ if (existing !== void 0) {
27398
+ if (existing._uncertain !== void 0 && link._uncertain === void 0) {
27399
+ seen.set(key, link);
27400
+ }
27401
+ continue;
27402
+ }
27403
+ seen.set(key, link);
27404
+ }
27405
+ return [...seen.values()];
27406
+ }
27407
+ function detectPerModuleConnections(project, components, options) {
27408
+ const setupStart = performance.now();
27409
+ const visibleComponents = options.allComponents ?? components;
27410
+ const componentIndex = new ComponentIndex(visibleComponents);
27411
+ const sourceFilePaths = options.sourceFilePaths;
27412
+ const setupMs = performance.now() - setupStart;
27413
+ const strict = options.allowIncomplete !== true;
27414
+ const repository = options.repository;
27415
+ const callGraphStart = performance.now();
27416
+ const syncLinks = buildCallGraph(project, components, componentIndex, new CallGraphOptions({
27417
+ strict,
27418
+ sourceFilePaths,
27419
+ repository
27420
+ }));
27421
+ const callGraphMs = performance.now() - callGraphStart;
27422
+ const httpLinkConfigs = options.httpLinks ?? [];
27423
+ const resolved = resolveHttpLinks(syncLinks, visibleComponents, httpLinkConfigs);
27424
+ return new PerModuleDetectionResult({
27425
+ links: resolved.links,
27426
+ externalLinks: resolved.externalLinks,
27427
+ timings: new PerModuleTimings({
27428
+ callGraphMs,
27429
+ setupMs
27430
+ })
27431
+ });
27432
+ }
27433
+ function detectCrossModuleConnections(allComponents, options) {
27434
+ const strict = options.allowIncomplete !== true;
27435
+ const repository = options.repository;
27436
+ const asyncOptions = new AsyncDetectionOptions({
27437
+ strict,
27438
+ repository
27439
+ });
27440
+ const asyncStart = performance.now();
27441
+ const publishLinks = detectEventPublisherConnections(allComponents, options.eventPublishers ?? [], asyncOptions);
27442
+ const subscribeLinks = detectSubscribeConnections(allComponents, asyncOptions);
27443
+ const asyncDetectionMs = performance.now() - asyncStart;
27444
+ return new CrossModuleDetectionResult({
27445
+ links: [...publishLinks, ...subscribeLinks],
27446
+ timings: new CrossModuleTimings({ asyncDetectionMs })
27447
+ });
27448
+ }
27449
+
27450
+ // ../riviere-extract-ts/dist/features/extraction/domain/value-extraction/enriched-component.js
27451
+ var EnrichedComponent = class {
27452
+ type;
27453
+ name;
27454
+ location;
27455
+ domain;
27456
+ module;
27457
+ metadata;
27458
+ _missing;
27459
+ constructor(params) {
27460
+ this.type = params.type;
27461
+ this.name = params.name;
27462
+ this.location = params.location;
27463
+ this.domain = params.domain;
27464
+ this.module = params.module;
27465
+ this.metadata = params.metadata;
27466
+ this._missing = params._missing;
27467
+ }
27468
+ };
27469
+ var EnrichmentFailure = class {
27470
+ component;
27471
+ field;
27472
+ error;
27473
+ constructor(params) {
27474
+ this.component = params.component;
27475
+ this.field = params.field;
27476
+ this.error = params.error;
27477
+ }
27478
+ };
27479
+ var EnrichmentResult = class {
27480
+ components;
27481
+ failures;
27482
+ constructor(params) {
27483
+ this.components = params.components;
27484
+ this.failures = params.failures;
27485
+ }
27486
+ };
27487
+
27488
+ // ../riviere-extract-ts/dist/features/extraction/domain/value-extraction/evaluate-extraction-rule-generic.js
27489
+ import { SyntaxKind as SyntaxKind5 } from "ts-morph";
27490
+ function getInterfaceTypeArgs(classDecl, interfaceName) {
27491
+ const implementsClause = classDecl.getImplements();
27492
+ for (const impl of implementsClause) {
27493
+ const expression = impl.getExpression();
27494
+ if (expression.getText() === interfaceName) {
27495
+ return impl.getTypeArguments();
27496
+ }
27497
+ }
27498
+ const extendsClause = classDecl.getExtends();
27499
+ if (extendsClause === void 0) {
27500
+ return void 0;
27501
+ }
27502
+ const baseClass = classDecl.getBaseClass();
27503
+ if (baseClass === void 0)
27504
+ return void 0;
27505
+ return getInterfaceTypeArgs(baseClass, interfaceName);
27506
+ }
27507
+ function extractTypeNames(typeNode) {
27508
+ if (typeNode.getKind() === SyntaxKind5.UnionType) {
27509
+ const unionType = typeNode.asKindOrThrow(SyntaxKind5.UnionType);
27510
+ return unionType.getTypeNodes().map((t) => t.getText());
27511
+ }
27512
+ return [typeNode.getText()];
27513
+ }
27514
+ function evaluateFromGenericArgRule(rule, classDecl) {
27515
+ const { interface: interfaceName, position, transform: transform2 } = rule.fromGenericArg;
27516
+ const sourceFile = classDecl.getSourceFile();
27517
+ const location = {
27518
+ filePath: sourceFile.getFilePath(),
27519
+ line: classDecl.getStartLineNumber()
27520
+ };
27521
+ const typeArgs = getInterfaceTypeArgs(classDecl, interfaceName);
27522
+ if (typeArgs === void 0) {
27523
+ throw new ExtractionError(`Class '${classDecl.getName() ?? "anonymous"}' does not implement interface '${interfaceName}'`, location.filePath, location.line);
27524
+ }
27525
+ const typeArg = typeArgs[position];
27526
+ if (typeArg === void 0) {
27527
+ throw new ExtractionError(`Position ${position} out of bounds. Interface has ${typeArgs.length} type argument(s)`, location.filePath, location.line);
27528
+ }
27529
+ if (typeArg.getKind() === SyntaxKind5.TypeReference) {
27530
+ const typeRef = typeArg.asKindOrThrow(SyntaxKind5.TypeReference);
27531
+ const typeName = typeRef.getTypeName();
27532
+ if (typeName.getKind() === SyntaxKind5.Identifier) {
27533
+ const classTypeParams = classDecl.getTypeParameters();
27534
+ const paramName = typeName.getText();
27535
+ const isTypeParam = classTypeParams.some((p) => p.getName() === paramName);
27536
+ if (isTypeParam) {
27537
+ throw new ExtractionError(`Generic argument at position ${position} is type parameter '${paramName}', expected concrete type`, location.filePath, location.line);
27538
+ }
27539
+ }
27540
+ }
27541
+ const typeNames = extractTypeNames(typeArg);
27542
+ if (transform2 === void 0) {
27543
+ return new ExtractionResult({ value: typeNames });
27544
+ }
27545
+ return new ExtractionResult({ value: typeNames.map((name) => applyTransforms(name, transform2)) });
27546
+ }
27547
+
27548
+ // ../riviere-extract-ts/dist/features/extraction/domain/value-extraction/evaluate-extraction-rule.js
27549
+ import { SyntaxKind as SyntaxKind6 } from "ts-morph";
27550
+ function literal2(value) {
27551
+ return new ExtractionResult({ value });
27552
+ }
27553
+ function evaluateLiteralRule(rule) {
27554
+ return literal2(rule.literal);
27555
+ }
27556
+ function evaluateFromClassNameRule(rule, classDecl) {
27557
+ const className = classDecl.getName();
27558
+ if (!className) {
27559
+ const filePath = classDecl.getSourceFile().getFilePath();
27560
+ const lineNumber = classDecl.getStartLineNumber();
27561
+ throw new ExtractionError("Expected class name, got undefined", filePath, lineNumber);
27562
+ }
27563
+ if (rule.fromClassName === true) {
27564
+ return new ExtractionResult({ value: className });
27565
+ }
27566
+ const transform2 = rule.fromClassName.transform;
27567
+ if (transform2 === void 0) {
27568
+ return new ExtractionResult({ value: className });
27569
+ }
27570
+ return new ExtractionResult({ value: applyTransforms(className, transform2) });
27571
+ }
27572
+ function evaluateFromMethodNameRule(rule, methodDecl) {
27573
+ const methodName = methodDecl.getName();
27574
+ if (rule.fromMethodName === true) {
27575
+ return new ExtractionResult({ value: methodName });
27576
+ }
27577
+ const transform2 = rule.fromMethodName.transform;
27578
+ if (transform2 === void 0) {
27579
+ return new ExtractionResult({ value: methodName });
27580
+ }
27581
+ return new ExtractionResult({ value: applyTransforms(methodName, transform2) });
27582
+ }
27583
+ function evaluateFromFilePathRule(rule, filePath) {
27584
+ const pattern = rule.fromFilePath.pattern;
27585
+ const capture = rule.fromFilePath.capture;
27586
+ const transform2 = rule.fromFilePath.transform;
27587
+ const regex = new RegExp(pattern);
27588
+ const match = regex.exec(filePath);
27589
+ if (match === null) {
27590
+ throw new ExtractionError(`Pattern '${pattern}' did not match file path '${filePath}'`, filePath, 0);
27591
+ }
27592
+ const capturedValue = match[capture];
27593
+ if (capturedValue === void 0) {
27594
+ throw new ExtractionError(`Capture group ${capture} out of bounds. Pattern has ${match.length - 1} capture groups`, filePath, 0);
27595
+ }
27596
+ if (transform2 === void 0) {
27597
+ return new ExtractionResult({ value: capturedValue });
27598
+ }
27599
+ return new ExtractionResult({ value: applyTransforms(capturedValue, transform2) });
27600
+ }
27601
+ function findPropertyInHierarchy(classDecl, propertyName, isStatic) {
27602
+ const properties = isStatic ? classDecl.getStaticProperties() : classDecl.getInstanceProperties();
27603
+ const property = properties.find((p) => p.getName() === propertyName);
27604
+ if (property !== void 0 && "getInitializer" in property) {
27605
+ const sourceFile = classDecl.getSourceFile();
27606
+ return {
27607
+ initializer: property.getInitializer(),
27608
+ filePath: sourceFile.getFilePath(),
27609
+ line: property.getStartLineNumber()
27610
+ };
27611
+ }
27612
+ if (classDecl.getExtends() === void 0) {
27613
+ return void 0;
27614
+ }
27615
+ const baseClass = classDecl.getBaseClass();
27616
+ if (baseClass === void 0)
27617
+ return void 0;
27618
+ return findPropertyInHierarchy(baseClass, propertyName, isStatic);
27619
+ }
27620
+ function evaluateFromPropertyRule(rule, classDecl) {
27621
+ const name = rule.fromProperty.name;
27622
+ const kind = rule.fromProperty.kind;
27623
+ const transform2 = rule.fromProperty.transform;
27624
+ const isStatic = kind === "static";
27625
+ const propertyInfo = findPropertyInHierarchy(classDecl, name, isStatic);
27626
+ if (propertyInfo === void 0) {
27627
+ const sourceFile = classDecl.getSourceFile();
27628
+ throw new ExtractionError(`Property '${name}' not found on class '${classDecl.getName() ?? "anonymous"}'`, sourceFile.getFilePath(), classDecl.getStartLineNumber());
27629
+ }
27630
+ const literalResult = extractLiteralValue(propertyInfo.initializer, propertyInfo.filePath, propertyInfo.line);
27631
+ if (transform2 === void 0) {
27632
+ return new ExtractionResult({ value: literalResult.value });
27633
+ }
27634
+ if (typeof literalResult.value !== "string") {
27635
+ return new ExtractionResult({ value: literalResult.value });
27636
+ }
27637
+ return new ExtractionResult({ value: applyTransforms(literalResult.value, transform2) });
27638
+ }
27639
+ function getDecoratorLocation(decorator) {
27640
+ const sourceFile = decorator.getSourceFile();
27641
+ return {
27642
+ filePath: sourceFile.getFilePath(),
27643
+ line: decorator.getStartLineNumber()
27644
+ };
27645
+ }
27646
+ function extractPositionalArg(decorator, position) {
27647
+ const args = decorator.getArguments();
27648
+ const location = getDecoratorLocation(decorator);
27649
+ if (args.length === 0) {
27650
+ throw new ExtractionError(`Decorator '@${decorator.getName()}' has no arguments`, location.filePath, location.line);
27651
+ }
27652
+ const arg = args[position];
27653
+ if (arg === void 0) {
27654
+ throw new ExtractionError(`Argument position ${position} out of bounds. Decorator has ${args.length} argument(s)`, location.filePath, location.line);
27655
+ }
27656
+ if (arg.getKind() !== SyntaxKind6.StringLiteral) {
27657
+ throw new ExtractionError(`Expected string literal at position ${position}, got ${arg.getKindName()}`, location.filePath, location.line);
27658
+ }
27659
+ return arg.asKindOrThrow(SyntaxKind6.StringLiteral).getLiteralValue();
27660
+ }
27661
+ function throwNoArguments(decorator, location) {
27662
+ throw new ExtractionError(`Decorator '@${decorator.getName()}' has no arguments`, location.filePath, location.line);
29002
27663
  }
29003
- function deduplicateCrossStrategy(links) {
29004
- const seen = /* @__PURE__ */ new Map();
29005
- for (const link of links) {
29006
- const key = `${link.source}|${link.target}|${link.type}`;
29007
- const existing = seen.get(key);
29008
- if (existing !== void 0) {
29009
- if (existing._uncertain !== void 0 && link._uncertain === void 0) {
29010
- seen.set(key, link);
29011
- }
29012
- continue;
29013
- }
29014
- seen.set(key, link);
27664
+ function getFirstArgument(decorator, location) {
27665
+ const args = decorator.getArguments();
27666
+ const firstArg = args[0];
27667
+ if (firstArg === void 0) {
27668
+ throwNoArguments(decorator, location);
29015
27669
  }
29016
- return [...seen.values()];
27670
+ return firstArg;
29017
27671
  }
29018
- function detectPerModuleConnections(project, components, options, globMatcher) {
29019
- const setupStart = performance.now();
29020
- const visibleComponents = options.allComponents ?? components;
29021
- const componentIndex = new ComponentIndex(visibleComponents);
29022
- const sourceFilePaths = computeFilteredFilePaths(project, options.moduleGlobs, globMatcher);
29023
- const setupMs = performance.now() - setupStart;
29024
- const strict = options.allowIncomplete !== true;
29025
- const repository = options.repository;
29026
- const callGraphStart = performance.now();
29027
- const syncLinks = buildCallGraph(project, components, componentIndex, {
29028
- strict,
29029
- sourceFilePaths,
29030
- repository
29031
- });
29032
- const callGraphMs = performance.now() - callGraphStart;
29033
- const httpLinkConfigs = options.httpLinks ?? [];
29034
- const resolved = resolveHttpLinks(syncLinks, visibleComponents, httpLinkConfigs);
29035
- return {
29036
- links: resolved.links,
29037
- externalLinks: resolved.externalLinks,
29038
- timings: {
29039
- callGraphMs,
29040
- setupMs
27672
+ function extractNamedArg(decorator, name) {
27673
+ const location = getDecoratorLocation(decorator);
27674
+ const firstArg = getFirstArgument(decorator, location);
27675
+ if (firstArg.getKind() !== SyntaxKind6.ObjectLiteralExpression) {
27676
+ throw new ExtractionError(`Expected object literal argument, got ${firstArg.getKindName()}`, location.filePath, location.line);
27677
+ }
27678
+ const objectLiteral = firstArg.asKindOrThrow(SyntaxKind6.ObjectLiteralExpression);
27679
+ const property = objectLiteral.getProperty(name);
27680
+ if (property === void 0) {
27681
+ throw new ExtractionError(`Property '${name}' not found in decorator argument`, location.filePath, location.line);
27682
+ }
27683
+ if (!("getInitializer" in property)) {
27684
+ throw new ExtractionError(`Property '${name}' has no initializer`, location.filePath, location.line);
27685
+ }
27686
+ const initializer3 = property.getInitializer();
27687
+ if (initializer3?.getKind() !== SyntaxKind6.StringLiteral) {
27688
+ throw new ExtractionError(`Expected string literal for property '${name}'`, location.filePath, location.line);
27689
+ }
27690
+ return initializer3.asKindOrThrow(SyntaxKind6.StringLiteral).getLiteralValue();
27691
+ }
27692
+ function evaluateFromDecoratorArgRule(rule, decorator) {
27693
+ const decoratorName = rule.fromDecoratorArg.decorator;
27694
+ const position = rule.fromDecoratorArg.position;
27695
+ const name = rule.fromDecoratorArg.name;
27696
+ const transform2 = rule.fromDecoratorArg.transform;
27697
+ if (decoratorName !== void 0 && decorator.getName() !== decoratorName) {
27698
+ const location = getDecoratorLocation(decorator);
27699
+ throw new ExtractionError(`Expected decorator '@${decoratorName}', got '@${decorator.getName()}'`, location.filePath, location.line);
27700
+ }
27701
+ const extractValue = () => {
27702
+ if (position !== void 0) {
27703
+ return extractPositionalArg(decorator, position);
27704
+ }
27705
+ if (!name) {
27706
+ const location = getDecoratorLocation(decorator);
27707
+ throw new ExtractionError("Expected name parameter when position is undefined", location.filePath, location.line);
29041
27708
  }
27709
+ return extractNamedArg(decorator, name);
29042
27710
  };
27711
+ const value = extractValue();
27712
+ if (transform2 === void 0) {
27713
+ return new ExtractionResult({ value });
27714
+ }
27715
+ return new ExtractionResult({ value: applyTransforms(value, transform2) });
29043
27716
  }
29044
- function detectCrossModuleConnections(allComponents, options) {
29045
- const strict = options.allowIncomplete !== true;
29046
- const repository = options.repository;
29047
- const asyncOptions = {
29048
- strict,
29049
- repository
29050
- };
29051
- const asyncStart = performance.now();
29052
- const publishLinks = detectEventPublisherConnections(allComponents, options.eventPublishers ?? [], asyncOptions);
29053
- const subscribeLinks = detectSubscribeConnections(allComponents, asyncOptions);
29054
- const asyncDetectionMs = performance.now() - asyncStart;
29055
- return {
29056
- links: [...publishLinks, ...subscribeLinks],
29057
- timings: { asyncDetectionMs }
27717
+ function evaluateFromClassDecoratorArgRule(rule, methodDecl) {
27718
+ const classDecl = methodDecl.getParentIfKind(SyntaxKind6.ClassDeclaration);
27719
+ if (classDecl === void 0) {
27720
+ const sourceFile = methodDecl.getSourceFile();
27721
+ throw new ExtractionError(`Expected method '${methodDecl.getName()}' to be declared inside a class`, sourceFile.getFilePath(), methodDecl.getStartLineNumber());
27722
+ }
27723
+ const classDecorator = classDecl.getDecorators().find((decorator) => decorator.getName() === rule.fromClassDecoratorArg.decorator);
27724
+ if (classDecorator === void 0) {
27725
+ const sourceFile = classDecl.getSourceFile();
27726
+ throw new ExtractionError(`Decorator '@${rule.fromClassDecoratorArg.decorator}' not found on containing class '${classDecl.getName() ?? "anonymous"}'`, sourceFile.getFilePath(), classDecl.getStartLineNumber());
27727
+ }
27728
+ const fromClassDecoratorArg = rule.fromClassDecoratorArg;
27729
+ const fromDecoratorArgRule = {
27730
+ decorator: fromClassDecoratorArg.decorator,
27731
+ ...fromClassDecoratorArg.position === void 0 ? {} : { position: fromClassDecoratorArg.position },
27732
+ ...fromClassDecoratorArg.name === void 0 ? {} : { name: fromClassDecoratorArg.name },
27733
+ ...fromClassDecoratorArg.transform === void 0 ? {} : { transform: fromClassDecoratorArg.transform }
29058
27734
  };
27735
+ return evaluateFromDecoratorArgRule({ fromDecoratorArg: fromDecoratorArgRule }, classDecorator);
27736
+ }
27737
+ function evaluateFromDecoratorNameRule(rule, decorator) {
27738
+ const decoratorName = decorator.getName();
27739
+ if (rule.fromDecoratorName === true) {
27740
+ return new ExtractionResult({ value: decoratorName });
27741
+ }
27742
+ const mapping = rule.fromDecoratorName.mapping;
27743
+ const transform2 = rule.fromDecoratorName.transform;
27744
+ const mappedValue = mapping?.[decoratorName] ?? decoratorName;
27745
+ if (transform2 === void 0) {
27746
+ return new ExtractionResult({ value: mappedValue });
27747
+ }
27748
+ return new ExtractionResult({ value: applyTransforms(mappedValue, transform2) });
29059
27749
  }
29060
27750
 
29061
27751
  // ../riviere-extract-ts/dist/features/extraction/domain/value-extraction/enrich-components.js
29062
- import { posix as posix2 } from "node:path";
29063
- function findMatchingModule2(filePath, modules, globMatcher, configDir) {
29064
- const normalized = filePath.replaceAll(/\\+/g, "/");
29065
- const pathToMatch = posix2.relative(configDir.replaceAll(/\\+/g, "/"), normalized);
29066
- return modules.find((m) => globMatcher(pathToMatch, posix2.join(m.path, m.glob)));
29067
- }
29068
27752
  function getBuiltInRule(module, componentType) {
29069
27753
  const ruleMap = {
29070
27754
  api: module.api,
@@ -29199,9 +27883,9 @@ function evaluateMethodRule(rule, draft, project) {
29199
27883
  const typeName = param.getTypeNode()?.getText() ?? "unknown";
29200
27884
  const transform2 = rule.fromParameterType.transform;
29201
27885
  if (transform2 === void 0) {
29202
- return { value: typeName };
27886
+ return new ExtractionResult({ value: typeName });
29203
27887
  }
29204
- return { value: applyTransforms(typeName, transform2) };
27888
+ return new ExtractionResult({ value: applyTransforms(typeName, transform2) });
29205
27889
  }
29206
27890
  return void 0;
29207
27891
  }
@@ -29229,10 +27913,15 @@ function evaluateRule(rule, draft, project) {
29229
27913
  }
29230
27914
  function componentWithEmptyMetadata(draft) {
29231
27915
  return {
29232
- enriched: {
29233
- ...draft,
29234
- metadata: {}
29235
- },
27916
+ enriched: new EnrichedComponent({
27917
+ type: draft.type,
27918
+ name: draft.name,
27919
+ location: draft.location,
27920
+ domain: draft.domain,
27921
+ module: draft.module,
27922
+ metadata: {},
27923
+ _missing: void 0
27924
+ }),
29236
27925
  failures: []
29237
27926
  };
29238
27927
  }
@@ -29251,11 +27940,11 @@ function extractMetadataFields(extractBlock, draft, project) {
29251
27940
  if (shouldIgnoreMissingMetadataField(draft, fieldName, extractionRule, errorMessage)) {
29252
27941
  continue;
29253
27942
  }
29254
- failures.push({
27943
+ failures.push(new EnrichmentFailure({
29255
27944
  component: draft,
29256
27945
  field: fieldName,
29257
27946
  error: errorMessage
29258
- });
27947
+ }));
29259
27948
  missing.push(fieldName);
29260
27949
  }
29261
27950
  }
@@ -29265,40 +27954,38 @@ function extractMetadataFields(extractBlock, draft, project) {
29265
27954
  failures
29266
27955
  };
29267
27956
  }
29268
- function enrichSingleComponent(draft, config2, project, globMatcher, configDir) {
29269
- const module = findMatchingModule2(draft.location.file, config2.modules, globMatcher, configDir);
29270
- if (module === void 0) {
29271
- return componentWithEmptyMetadata(draft);
29272
- }
27957
+ function enrichSingleComponent(draft, module, project) {
29273
27958
  const detectionRule = findDetectionRule(module, draft.type);
29274
27959
  if (detectionRule?.extract === void 0) {
29275
27960
  return componentWithEmptyMetadata(draft);
29276
27961
  }
29277
27962
  const extracted = extractMetadataFields(detectionRule.extract, draft, project);
29278
- const enriched = {
29279
- ...draft,
29280
- metadata: extracted.metadata
29281
- };
29282
- if (extracted.missing.length > 0) {
29283
- enriched._missing = extracted.missing;
29284
- }
27963
+ const enriched = new EnrichedComponent({
27964
+ type: draft.type,
27965
+ name: draft.name,
27966
+ location: draft.location,
27967
+ domain: draft.domain,
27968
+ module: draft.module,
27969
+ metadata: extracted.metadata,
27970
+ _missing: extracted.missing.length > 0 ? extracted.missing : void 0
27971
+ });
29285
27972
  return {
29286
27973
  enriched,
29287
27974
  failures: extracted.failures
29288
27975
  };
29289
27976
  }
29290
- function enrichComponents(draftComponents, config2, project, globMatcher, configDir) {
27977
+ function enrichComponents(draftComponents, module, project) {
29291
27978
  const allComponents = [];
29292
27979
  const allFailures = [];
29293
27980
  for (const draft of draftComponents) {
29294
- const result = enrichSingleComponent(draft, config2, project, globMatcher, configDir);
27981
+ const result = enrichSingleComponent(draft, module, project);
29295
27982
  allComponents.push(result.enriched);
29296
27983
  allFailures.push(...result.failures);
29297
27984
  }
29298
- return {
27985
+ return new EnrichmentResult({
29299
27986
  components: allComponents,
29300
27987
  failures: allFailures
29301
- };
27988
+ });
29302
27989
  }
29303
27990
 
29304
27991
  // ../riviere-extract-config/dist/validation.js
@@ -30475,7 +29162,6 @@ function loadDraftComponentsFromFile(filePath) {
30475
29162
  }
30476
29163
 
30477
29164
  // src/features/extract/domain/extraction-project.ts
30478
- import { posix as posix3 } from "node:path";
30479
29165
  var OrphanedDraftComponentError = class extends Error {
30480
29166
  constructor(orphanedModules, knownModules) {
30481
29167
  super(
@@ -30485,8 +29171,7 @@ var OrphanedDraftComponentError = class extends Error {
30485
29171
  }
30486
29172
  };
30487
29173
  var ExtractionProject = class {
30488
- constructor(configDir, moduleContexts, resolvedConfig, repositoryName, draftComponents = []) {
30489
- this.configDir = configDir;
29174
+ constructor(moduleContexts, resolvedConfig, repositoryName, draftComponents = []) {
30490
29175
  this.moduleContexts = moduleContexts;
30491
29176
  this.resolvedConfig = resolvedConfig;
30492
29177
  this.repositoryName = repositoryName;
@@ -30494,13 +29179,7 @@ var ExtractionProject = class {
30494
29179
  }
30495
29180
  extractDraftComponents(options) {
30496
29181
  const draftComponents = this.moduleContexts.flatMap(
30497
- (moduleContext) => extractComponents(
30498
- moduleContext.project,
30499
- moduleContext.files,
30500
- this.resolvedConfig,
30501
- matchesGlob,
30502
- this.configDir
30503
- )
29182
+ (moduleContext) => extractComponents(moduleContext.project, moduleContext.files, moduleContext.module)
30504
29183
  );
30505
29184
  if (!options.includeConnections) {
30506
29185
  return {
@@ -30573,18 +29252,13 @@ var ExtractionProject = class {
30573
29252
  if (moduleComponents.length === 0) {
30574
29253
  continue;
30575
29254
  }
30576
- const result = detectPerModuleConnections(
30577
- moduleContext.project,
30578
- moduleComponents,
30579
- {
30580
- allComponents: enrichedComponents,
30581
- allowIncomplete,
30582
- moduleGlobs: [posix3.join(moduleContext.module.path, moduleContext.module.glob)],
30583
- httpLinks,
30584
- repository: this.repositoryName
30585
- },
30586
- matchesGlob
30587
- );
29255
+ const result = detectPerModuleConnections(moduleContext.project, moduleComponents, {
29256
+ allComponents: enrichedComponents,
29257
+ allowIncomplete,
29258
+ httpLinks,
29259
+ repository: this.repositoryName,
29260
+ sourceFilePaths: moduleContext.files
29261
+ });
30588
29262
  links.push(...result.links);
30589
29263
  externalLinks.push(...result.externalLinks);
30590
29264
  timings.push({
@@ -30623,13 +29297,7 @@ var ExtractionProject = class {
30623
29297
  if (moduleDrafts.length === 0) {
30624
29298
  continue;
30625
29299
  }
30626
- const result = enrichComponents(
30627
- moduleDrafts,
30628
- this.resolvedConfig,
30629
- moduleContext.project,
30630
- matchesGlob,
30631
- this.configDir
30632
- );
29300
+ const result = enrichComponents(moduleDrafts, moduleContext.module, moduleContext.project);
30633
29301
  components.push(...result.components);
30634
29302
  for (const failure14 of result.failures) {
30635
29303
  failedFieldSet.add(failure14.field);
@@ -30668,42 +29336,17 @@ function groupDraftsByModule(drafts) {
30668
29336
  return grouped;
30669
29337
  }
30670
29338
 
30671
- // src/features/extract/infra/external-clients/ts-morph/create-configured-project.ts
30672
- import { existsSync as existsSync2 } from "node:fs";
30673
- import { resolve as resolve2 } from "node:path";
30674
- import { Project as Project2 } from "ts-morph";
30675
- function createConfiguredProject(configDir, skipTsConfig) {
30676
- if (skipTsConfig) {
30677
- return new Project2();
30678
- }
30679
- const tsConfigPath = resolve2(configDir, "tsconfig.json");
30680
- if (!existsSync2(tsConfigPath)) {
30681
- return new Project2();
30682
- }
30683
- return new Project2({
30684
- tsConfigFilePath: tsConfigPath,
30685
- skipAddingFilesFromTsConfig: true
30686
- });
30687
- }
30688
-
30689
- // src/features/extract/infra/external-clients/ts-morph/find-module-tsconfig-dir.ts
30690
- import { existsSync as existsSync3 } from "node:fs";
30691
- import { resolve as resolve3 } from "node:path";
30692
- function findModuleTsConfigDir(configDir, modulePath) {
30693
- const moduleTsConfigPath = resolve3(configDir, modulePath, "tsconfig.json");
30694
- if (existsSync3(moduleTsConfigPath)) {
30695
- return resolve3(configDir, modulePath);
30696
- }
30697
- return configDir;
30698
- }
30699
-
30700
- // src/features/extract/infra/persistence/extraction-project/extraction-project-repository.ts
30701
- var ModuleRefNotFoundError = class extends Error {
30702
- constructor(ref, filePath) {
30703
- super(`Cannot resolve module reference '${ref}'. File not found: ${filePath}`);
30704
- this.name = "ModuleRefNotFoundError";
30705
- }
30706
- };
29339
+ // src/features/extract/infra/external-clients/extraction-config/load-extended-module.ts
29340
+ import {
29341
+ existsSync as existsSync2,
29342
+ readFileSync as readFileSync3
29343
+ } from "node:fs";
29344
+ import { createRequire } from "node:module";
29345
+ import {
29346
+ dirname as dirname2,
29347
+ resolve as resolve2
29348
+ } from "node:path";
29349
+ import { parse as parseYaml } from "yaml";
30707
29350
  var ConfigSchemaValidationError = class extends Error {
30708
29351
  constructor(source, details) {
30709
29352
  super(`Invalid extended config in '${source}': ${details}`);
@@ -30733,6 +29376,121 @@ var ConfigFileNotFoundError = class extends Error {
30733
29376
  }
30734
29377
  };
30735
29378
  var NOT_USED = { notUsed: true };
29379
+ function loadExtendedModule(params) {
29380
+ const filePath = resolveExtendedConfigPath(params.source, params.configDir);
29381
+ if (!existsSync2(filePath)) {
29382
+ throw new ConfigFileNotFoundError(params.source, filePath);
29383
+ }
29384
+ const content = readFileSync3(filePath, "utf-8");
29385
+ return parseExtendedConfigContent(
29386
+ content,
29387
+ params.source,
29388
+ dirname2(filePath),
29389
+ params.resolveConfigWithExtends
29390
+ );
29391
+ }
29392
+ function resolveExtendedConfigPath(source, configDir) {
29393
+ return isPackageReference(source) ? resolvePackagePath(source, configDir) : resolve2(configDir, source);
29394
+ }
29395
+ function isPackageReference(source) {
29396
+ return !source.startsWith(".") && !source.startsWith("/");
29397
+ }
29398
+ function resolvePackagePath(packageName, configDir) {
29399
+ const require2 = createRequire(resolve2(configDir, "package.json"));
29400
+ try {
29401
+ const packageJsonPath = require2.resolve(`${packageName}/package.json`);
29402
+ const packageDir = dirname2(packageJsonPath);
29403
+ const defaultConfigPath = resolve2(packageDir, "src/default-extraction.config.json");
29404
+ if (existsSync2(defaultConfigPath)) {
29405
+ return defaultConfigPath;
29406
+ }
29407
+ throw new PackageResolveError(packageName);
29408
+ } catch {
29409
+ throw new PackageResolveError(packageName);
29410
+ }
29411
+ }
29412
+ function parseExtendedConfigContent(content, source, configDir, resolveConfigWithExtends) {
29413
+ const parsed = parseYaml(content);
29414
+ if (hasModulesArray(parsed)) {
29415
+ return resolveFirstModuleFromConfig(parsed, source, configDir, resolveConfigWithExtends);
29416
+ }
29417
+ if (isTopLevelRulesConfig(parsed)) {
29418
+ return topLevelRulesToModule(parsed);
29419
+ }
29420
+ const preview = JSON.stringify(parsed, null, 2).slice(0, 200);
29421
+ throw new InvalidConfigFormatError(source, preview);
29422
+ }
29423
+ function resolveFirstModuleFromConfig(parsed, source, configDir, resolveConfigWithExtends) {
29424
+ if (parsed.modules.length === 0) {
29425
+ throw new ConfigSchemaValidationError(source, "Config has empty modules array");
29426
+ }
29427
+ try {
29428
+ const config2 = parseExtractionConfig(parsed);
29429
+ const [first] = resolveConfigWithExtends(config2, configDir).modules;
29430
+ if (first === void 0) {
29431
+ throw new ConfigSchemaValidationError(source, "Config has empty modules array");
29432
+ }
29433
+ return first;
29434
+ } catch (error48) {
29435
+ throw new ConfigSchemaValidationError(source, String(error48));
29436
+ }
29437
+ }
29438
+ function hasModulesArray(value) {
29439
+ return typeof value === "object" && value !== null && "modules" in value && Array.isArray(value.modules);
29440
+ }
29441
+ function isTopLevelRulesConfig(value) {
29442
+ return typeof value === "object" && value !== null && !Array.isArray(value) && !("modules" in value);
29443
+ }
29444
+ function topLevelRulesToModule(parsed) {
29445
+ return {
29446
+ name: "extended",
29447
+ path: ".",
29448
+ glob: "**",
29449
+ api: parsed.api ?? NOT_USED,
29450
+ useCase: parsed.useCase ?? NOT_USED,
29451
+ domainOp: parsed.domainOp ?? NOT_USED,
29452
+ event: parsed.event ?? NOT_USED,
29453
+ eventHandler: parsed.eventHandler ?? NOT_USED,
29454
+ ui: parsed.ui ?? NOT_USED
29455
+ };
29456
+ }
29457
+
29458
+ // src/features/extract/infra/external-clients/ts-morph/create-configured-project.ts
29459
+ import { existsSync as existsSync3 } from "node:fs";
29460
+ import { resolve as resolve3 } from "node:path";
29461
+ import { Project as Project2 } from "ts-morph";
29462
+ function createConfiguredProject(configDir, skipTsConfig) {
29463
+ if (skipTsConfig) {
29464
+ return new Project2();
29465
+ }
29466
+ const tsConfigPath = resolve3(configDir, "tsconfig.json");
29467
+ if (!existsSync3(tsConfigPath)) {
29468
+ return new Project2();
29469
+ }
29470
+ return new Project2({
29471
+ tsConfigFilePath: tsConfigPath,
29472
+ skipAddingFilesFromTsConfig: true
29473
+ });
29474
+ }
29475
+
29476
+ // src/features/extract/infra/external-clients/ts-morph/find-module-tsconfig-dir.ts
29477
+ import { existsSync as existsSync4 } from "node:fs";
29478
+ import { resolve as resolve4 } from "node:path";
29479
+ function findModuleTsConfigDir(configDir, modulePath) {
29480
+ const moduleTsConfigPath = resolve4(configDir, modulePath, "tsconfig.json");
29481
+ if (existsSync4(moduleTsConfigPath)) {
29482
+ return resolve4(configDir, modulePath);
29483
+ }
29484
+ return configDir;
29485
+ }
29486
+
29487
+ // src/features/extract/infra/persistence/extraction-project/extraction-project-repository.ts
29488
+ var ModuleRefNotFoundError = class extends Error {
29489
+ constructor(ref, filePath) {
29490
+ super(`Cannot resolve module reference '${ref}'. File not found: ${filePath}`);
29491
+ this.name = "ModuleRefNotFoundError";
29492
+ }
29493
+ };
30736
29494
  var ExtractionProjectRepository = class {
30737
29495
  loadFromChangedProject(params) {
30738
29496
  const parsedConfigState = this.loadParsedConfigState(params.configPath);
@@ -30768,15 +29526,15 @@ var ExtractionProjectRepository = class {
30768
29526
  return this.createExtractionProject(parsedConfigState, sourceFilePaths, params.useTsConfig);
30769
29527
  }
30770
29528
  loadParsedConfigState(configPath) {
30771
- if (!existsSync4(configPath)) {
29529
+ if (!existsSync5(configPath)) {
30772
29530
  throw new ConfigValidationError(
30773
29531
  "CONFIG_NOT_FOUND" /* ConfigNotFound */,
30774
29532
  `Config file not found: ${configPath}`
30775
29533
  );
30776
29534
  }
30777
- const content = readFileSync3(configPath, "utf-8");
29535
+ const content = readFileSync4(configPath, "utf-8");
30778
29536
  const parsed = this.parseConfigFile(content);
30779
- const configDir = dirname2(resolve4(configPath));
29537
+ const configDir = dirname3(resolve5(configPath));
30780
29538
  const expanded = this.expandModuleRefs(parsed, configDir);
30781
29539
  if (!isValidExtractionConfig(expanded)) {
30782
29540
  const validationResult = validateExtractionConfig(expanded);
@@ -30788,12 +29546,12 @@ ${formatValidationErrors2(validationResult.errors)}`
30788
29546
  }
30789
29547
  return {
30790
29548
  configDir,
30791
- resolvedConfig: resolveConfig(expanded, this.createExtendedConfigLoader(configDir))
29549
+ resolvedConfig: this.resolveConfigWithExtends(expanded, configDir)
30792
29550
  };
30793
29551
  }
30794
29552
  parseConfigFile(content) {
30795
29553
  try {
30796
- const parsed = parseYaml(content);
29554
+ const parsed = parseYaml2(content);
30797
29555
  return parsed;
30798
29556
  } catch (error48) {
30799
29557
  throw new ConfigValidationError(
@@ -30822,93 +29580,66 @@ ${formatValidationErrors2(validationResult.errors)}`
30822
29580
  if (!this.isModuleRef(item)) {
30823
29581
  return item;
30824
29582
  }
30825
- const refPath = resolve4(configDir, item.$ref);
30826
- if (!existsSync4(refPath)) {
29583
+ const refPath = resolve5(configDir, item.$ref);
29584
+ if (!existsSync5(refPath)) {
30827
29585
  throw new ModuleRefNotFoundError(item.$ref, refPath);
30828
29586
  }
30829
- const content = readFileSync3(refPath, "utf-8");
30830
- const parsed = parseYaml(content);
29587
+ const content = readFileSync4(refPath, "utf-8");
29588
+ const parsed = parseYaml2(content);
30831
29589
  return parsed;
30832
29590
  }
30833
- createExtendedConfigLoader(configDir) {
30834
- return (source) => {
30835
- const filePath = this.resolveExtendedConfigPath(source, configDir);
30836
- return this.loadExtendedConfigFile(filePath, source);
30837
- };
30838
- }
30839
- resolveExtendedConfigPath(source, configDir) {
30840
- return this.isPackageReference(source) ? this.resolvePackagePath(source, configDir) : resolve4(configDir, source);
30841
- }
30842
- isPackageReference(source) {
30843
- return !source.startsWith(".") && !source.startsWith("/");
29591
+ resolveConfigWithExtends(config2, configDir) {
29592
+ return resolveConfig({
29593
+ ...config2,
29594
+ modules: config2.modules.map(
29595
+ (moduleConfig) => this.resolveModuleConfig(moduleConfig, configDir)
29596
+ )
29597
+ });
30844
29598
  }
30845
- resolvePackagePath(packageName, configDir) {
30846
- const require2 = createRequire(resolve4(configDir, "package.json"));
30847
- try {
30848
- const packageJsonPath = require2.resolve(`${packageName}/package.json`);
30849
- const packageDir = dirname2(packageJsonPath);
30850
- const defaultConfigPath = resolve4(packageDir, "src/default-extraction.config.json");
30851
- if (existsSync4(defaultConfigPath)) {
30852
- return defaultConfigPath;
29599
+ resolveModuleConfig(moduleConfig, configDir) {
29600
+ const extendsSource = moduleConfig.extends;
29601
+ if (extendsSource === void 0) {
29602
+ const [resolvedModule] = resolveConfig({ modules: [moduleConfig] }).modules;
29603
+ if (resolvedModule === void 0) {
29604
+ throw new TypeError(`Expected resolved module for '${moduleConfig.name}'`);
30853
29605
  }
30854
- throw new PackageResolveError(packageName);
30855
- } catch {
30856
- throw new PackageResolveError(packageName);
30857
- }
30858
- }
30859
- loadExtendedConfigFile(filePath, source) {
30860
- if (!existsSync4(filePath)) {
30861
- throw new ConfigFileNotFoundError(source, filePath);
30862
- }
30863
- const content = readFileSync3(filePath, "utf-8");
30864
- return this.parseExtendedConfigContent(content, source);
30865
- }
30866
- parseExtendedConfigContent(content, source) {
30867
- const parsed = parseYaml(content);
30868
- if (this.hasModulesArray(parsed)) {
30869
- return this.resolveFirstModuleFromConfig(parsed, source);
29606
+ return resolvedModule;
30870
29607
  }
30871
- if (this.isTopLevelRulesConfig(parsed)) {
30872
- return this.topLevelRulesToModule(parsed);
30873
- }
30874
- const preview = JSON.stringify(parsed, null, 2).slice(0, 200);
30875
- throw new InvalidConfigFormatError(source, preview);
29608
+ const baseModule = loadExtendedModule({
29609
+ configDir,
29610
+ source: extendsSource,
29611
+ resolveConfigWithExtends: (config2, nextConfigDir) => this.resolveConfigWithExtends(config2, nextConfigDir)
29612
+ });
29613
+ const mergedCustomTypes = this.mergeCustomTypes(
29614
+ baseModule.customTypes,
29615
+ moduleConfig.customTypes
29616
+ );
29617
+ return {
29618
+ name: moduleConfig.name,
29619
+ domain: moduleConfig.domain,
29620
+ path: moduleConfig.path,
29621
+ glob: moduleConfig.glob,
29622
+ ...moduleConfig.modules !== void 0 && { modules: moduleConfig.modules },
29623
+ api: moduleConfig.api ?? baseModule.api,
29624
+ useCase: moduleConfig.useCase ?? baseModule.useCase,
29625
+ domainOp: moduleConfig.domainOp ?? baseModule.domainOp,
29626
+ event: moduleConfig.event ?? baseModule.event,
29627
+ eventHandler: moduleConfig.eventHandler ?? baseModule.eventHandler,
29628
+ ui: moduleConfig.ui ?? baseModule.ui,
29629
+ ...mergedCustomTypes !== void 0 && { customTypes: mergedCustomTypes }
29630
+ };
30876
29631
  }
30877
- resolveFirstModuleFromConfig(parsed, source) {
30878
- if (parsed.modules.length === 0) {
30879
- throw new ConfigSchemaValidationError(source, "Config has empty modules array");
30880
- }
30881
- try {
30882
- const config2 = parseExtractionConfig(parsed);
30883
- const [first] = resolveConfig(config2).modules;
30884
- if (first === void 0) {
30885
- throw new ConfigSchemaValidationError(source, "Config has empty modules array");
30886
- }
30887
- return first;
30888
- } catch (error48) {
30889
- const message = error48 instanceof Error ? error48.message : String(error48);
30890
- throw new ConfigSchemaValidationError(source, message);
29632
+ mergeCustomTypes(base, local) {
29633
+ if (base === void 0 && local === void 0) {
29634
+ return void 0;
30891
29635
  }
30892
- }
30893
- isTopLevelRulesConfig(value) {
30894
- return typeof value === "object" && value !== null && !Array.isArray(value) && !("modules" in value);
30895
- }
30896
- topLevelRulesToModule(parsed) {
30897
29636
  return {
30898
- name: "extended",
30899
- path: ".",
30900
- glob: "**",
30901
- api: parsed.api ?? NOT_USED,
30902
- useCase: parsed.useCase ?? NOT_USED,
30903
- domainOp: parsed.domainOp ?? NOT_USED,
30904
- event: parsed.event ?? NOT_USED,
30905
- eventHandler: parsed.eventHandler ?? NOT_USED,
30906
- ui: parsed.ui ?? NOT_USED
29637
+ ...base,
29638
+ ...local
30907
29639
  };
30908
29640
  }
30909
29641
  createExtractionProject(parsedConfigState, sourceFilePaths, useTsConfig, draftComponents = []) {
30910
29642
  return new ExtractionProject(
30911
- parsedConfigState.configDir,
30912
29643
  this.createModuleContexts(
30913
29644
  parsedConfigState.configDir,
30914
29645
  parsedConfigState.resolvedConfig,
@@ -30922,10 +29653,10 @@ ${formatValidationErrors2(validationResult.errors)}`
30922
29653
  }
30923
29654
  resolveSourceFilePaths(parsedConfigState) {
30924
29655
  const sourceFilePaths = parsedConfigState.resolvedConfig.modules.flatMap(
30925
- (module) => globSync(posix4.join(module.path, module.glob), { cwd: parsedConfigState.configDir })
30926
- ).map((filePath) => resolve4(parsedConfigState.configDir, filePath));
29656
+ (module) => globSync(posix.join(module.path, module.glob), { cwd: parsedConfigState.configDir })
29657
+ ).map((filePath) => resolve5(parsedConfigState.configDir, filePath));
30927
29658
  if (sourceFilePaths.length === 0) {
30928
- const patterns = parsedConfigState.resolvedConfig.modules.map((module) => posix4.join(module.path, module.glob)).join(", ");
29659
+ const patterns = parsedConfigState.resolvedConfig.modules.map((module) => posix.join(module.path, module.glob)).join(", ");
30929
29660
  throw new ConfigValidationError(
30930
29661
  "VALIDATION_ERROR" /* ValidationError */,
30931
29662
  `No files matched extraction patterns: ${patterns}
@@ -30940,25 +29671,25 @@ Config directory: ${parsedConfigState.configDir}`
30940
29671
  for (const warning of result.warnings) {
30941
29672
  console.error(warning);
30942
29673
  }
30943
- const changedAbsolute = new Set(result.files.map((filePath) => resolve4(filePath)));
29674
+ const changedAbsolute = new Set(result.files.map((filePath) => resolve5(filePath)));
30944
29675
  return allSourceFiles.filter((filePath) => changedAbsolute.has(filePath));
30945
29676
  }
30946
29677
  resolveSelectedSourceFilePaths(allSourceFiles, requestedFiles) {
30947
- const missingFiles = requestedFiles.filter((filePath) => !existsSync4(resolve4(filePath)));
29678
+ const missingFiles = requestedFiles.filter((filePath) => !existsSync5(resolve5(filePath)));
30948
29679
  if (missingFiles.length > 0) {
30949
29680
  throw new ConfigValidationError(
30950
29681
  "VALIDATION_ERROR" /* ValidationError */,
30951
29682
  `Files not found: ${missingFiles.join(", ")}`
30952
29683
  );
30953
29684
  }
30954
- const requestedAbsolute = new Set(requestedFiles.map((filePath) => resolve4(filePath)));
29685
+ const requestedAbsolute = new Set(requestedFiles.map((filePath) => resolve5(filePath)));
30955
29686
  return allSourceFiles.filter((filePath) => requestedAbsolute.has(filePath));
30956
29687
  }
30957
29688
  createModuleContexts(configDir, resolvedConfig, sourceFilePaths, useTsConfig) {
30958
29689
  const sourceFileSet = new Set(sourceFilePaths);
30959
29690
  return resolvedConfig.modules.map((module) => {
30960
- const allModuleFiles = globSync(posix4.join(module.path, module.glob), { cwd: configDir }).map(
30961
- (filePath) => resolve4(configDir, filePath)
29691
+ const allModuleFiles = globSync(posix.join(module.path, module.glob), { cwd: configDir }).map(
29692
+ (filePath) => resolve5(configDir, filePath)
30962
29693
  );
30963
29694
  const moduleFiles = allModuleFiles.filter((filePath) => sourceFileSet.has(filePath));
30964
29695
  const moduleConfigDir = findModuleTsConfigDir(configDir, module.path);
@@ -31339,7 +30070,7 @@ function createExtractCommand(extractDraftComponents, enrichDraftComponents) {
31339
30070
  }
31340
30071
 
31341
30072
  // src/features/query/infra/persistence/riviere-query-repository.ts
31342
- import { readFileSync as readFileSync4 } from "node:fs";
30073
+ import { readFileSync as readFileSync5 } from "node:fs";
31343
30074
  import { join as join2 } from "node:path";
31344
30075
  var DEFAULT_GRAPH_PATH3 = ".riviere/graph.json";
31345
30076
  var RiviereQueryRepository = class {
@@ -31348,7 +30079,7 @@ var RiviereQueryRepository = class {
31348
30079
  if (!fileExists(graphPath)) {
31349
30080
  throw new GraphNotFoundError(graphPath);
31350
30081
  }
31351
- const content = readFileSync4(graphPath, "utf-8");
30082
+ const content = readFileSync5(graphPath, "utf-8");
31352
30083
  try {
31353
30084
  const parsed = JSON.parse(content);
31354
30085
  return RiviereQuery.fromJSON(parsed);
@@ -31442,7 +30173,7 @@ var TraceFlow = class {
31442
30173
  return {
31443
30174
  message: error48.message,
31444
30175
  success: false,
31445
- suggestions: matches.map((match2) => match2.component.id)
30176
+ suggestions: matches.map((match) => match.component.id)
31446
30177
  };
31447
30178
  }
31448
30179
  }
@@ -31668,7 +30399,7 @@ function parsePackageJson(pkg) {
31668
30399
  }
31669
30400
  function loadPackageJson() {
31670
30401
  if (true) {
31671
- return { version: "0.9.17" };
30402
+ return { version: "0.9.19" };
31672
30403
  }
31673
30404
  const require2 = createRequire2(import.meta.url);
31674
30405
  return parsePackageJson(require2("../../package.json"));
@@ -31761,8 +30492,8 @@ program.parseAsync().catch(handleGlobalError);
31761
30492
  /* istanbul ignore next -- @preserve: Methods in object literals have non-class parents; predicate correctly returns false */
31762
30493
  /* istanbul ignore else -- @preserve: false branch is unreachable; FindTarget is exhaustive */
31763
30494
  /* istanbul ignore next -- @preserve: unreachable with valid FindTarget type; defensive fallback */
31764
- /* v8 ignore next -- @preserve: getExtends() !== undefined guarantees getBaseClass() returns a value */
31765
30495
  /* istanbul ignore next -- @preserve: defensive guard; resolvedCustomTypes.has guarantees config exists */
30496
+ /* v8 ignore next -- @preserve: getExtends() !== undefined guarantees getBaseClass() returns a value */
31766
30497
  /* v8 ignore next -- @preserve: decorators.length > 0 guarantees first decorator exists */
31767
30498
  /* istanbul ignore next -- @preserve: catch always receives Error instances from ExtractionError */
31768
30499
  /* v8 ignore start -- @preserve: default executor delegates to execFileSync; tested via CLI integration */