@specferret/core 0.2.0 → 0.4.0

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 (95) hide show
  1. package/dist/audit/index.d.ts +27 -0
  2. package/dist/audit/index.d.ts.map +1 -0
  3. package/dist/audit/index.js +89 -0
  4. package/dist/audit/index.js.map +1 -0
  5. package/dist/config.d.ts +3 -0
  6. package/dist/config.d.ts.map +1 -1
  7. package/dist/config.js.map +1 -1
  8. package/dist/contract.d.ts +16 -0
  9. package/dist/contract.d.ts.map +1 -0
  10. package/dist/contract.js +17 -0
  11. package/dist/contract.js.map +1 -0
  12. package/dist/extractor/__fixtures__/cross-file-id.fixture.d.ts +15 -0
  13. package/dist/extractor/__fixtures__/cross-file-id.fixture.d.ts.map +1 -0
  14. package/dist/extractor/__fixtures__/cross-file-id.fixture.js +9 -0
  15. package/dist/extractor/__fixtures__/cross-file-id.fixture.js.map +1 -0
  16. package/dist/extractor/__fixtures__/cross-file-unresolved.fixture.d.ts +14 -0
  17. package/dist/extractor/__fixtures__/cross-file-unresolved.fixture.d.ts.map +1 -0
  18. package/dist/extractor/__fixtures__/cross-file-unresolved.fixture.js +9 -0
  19. package/dist/extractor/__fixtures__/cross-file-unresolved.fixture.js.map +1 -0
  20. package/dist/extractor/__fixtures__/empty.fixture.d.ts +6 -0
  21. package/dist/extractor/__fixtures__/empty.fixture.d.ts.map +1 -0
  22. package/dist/extractor/__fixtures__/empty.fixture.js +5 -0
  23. package/dist/extractor/__fixtures__/empty.fixture.js.map +1 -0
  24. package/dist/extractor/__fixtures__/external-no-id.fixture.d.ts +8 -0
  25. package/dist/extractor/__fixtures__/external-no-id.fixture.d.ts.map +1 -0
  26. package/dist/extractor/__fixtures__/external-no-id.fixture.js +7 -0
  27. package/dist/extractor/__fixtures__/external-no-id.fixture.js.map +1 -0
  28. package/dist/extractor/__fixtures__/external-with-id.fixture.d.ts +9 -0
  29. package/dist/extractor/__fixtures__/external-with-id.fixture.d.ts.map +1 -0
  30. package/dist/extractor/__fixtures__/external-with-id.fixture.js +8 -0
  31. package/dist/extractor/__fixtures__/external-with-id.fixture.js.map +1 -0
  32. package/dist/extractor/__fixtures__/mixed.fixture.d.ts +24 -0
  33. package/dist/extractor/__fixtures__/mixed.fixture.d.ts.map +1 -0
  34. package/dist/extractor/__fixtures__/mixed.fixture.js +15 -0
  35. package/dist/extractor/__fixtures__/mixed.fixture.js.map +1 -0
  36. package/dist/extractor/__fixtures__/one-contract.fixture.d.ts +10 -0
  37. package/dist/extractor/__fixtures__/one-contract.fixture.d.ts.map +1 -0
  38. package/dist/extractor/__fixtures__/one-contract.fixture.js +10 -0
  39. package/dist/extractor/__fixtures__/one-contract.fixture.js.map +1 -0
  40. package/dist/extractor/__fixtures__/optional-fields.fixture.d.ts +10 -0
  41. package/dist/extractor/__fixtures__/optional-fields.fixture.d.ts.map +1 -0
  42. package/dist/extractor/__fixtures__/optional-fields.fixture.js +10 -0
  43. package/dist/extractor/__fixtures__/optional-fields.fixture.js.map +1 -0
  44. package/dist/extractor/__fixtures__/same-file-consumes.fixture.d.ts +20 -0
  45. package/dist/extractor/__fixtures__/same-file-consumes.fixture.d.ts.map +1 -0
  46. package/dist/extractor/__fixtures__/same-file-consumes.fixture.js +11 -0
  47. package/dist/extractor/__fixtures__/same-file-consumes.fixture.js.map +1 -0
  48. package/dist/extractor/__fixtures__/three-unresolved.fixture.d.ts +38 -0
  49. package/dist/extractor/__fixtures__/three-unresolved.fixture.d.ts.map +1 -0
  50. package/dist/extractor/__fixtures__/three-unresolved.fixture.js +21 -0
  51. package/dist/extractor/__fixtures__/three-unresolved.fixture.js.map +1 -0
  52. package/dist/extractor/__fixtures__/throws-on-import.fixture.d.ts +2 -0
  53. package/dist/extractor/__fixtures__/throws-on-import.fixture.d.ts.map +1 -0
  54. package/dist/extractor/__fixtures__/throws-on-import.fixture.js +5 -0
  55. package/dist/extractor/__fixtures__/throws-on-import.fixture.js.map +1 -0
  56. package/dist/extractor/frontmatter.d.ts +1 -1
  57. package/dist/extractor/frontmatter.d.ts.map +1 -1
  58. package/dist/extractor/typescript-contract.d.ts +3 -0
  59. package/dist/extractor/typescript-contract.d.ts.map +1 -0
  60. package/dist/extractor/typescript-contract.js +67 -0
  61. package/dist/extractor/typescript-contract.js.map +1 -0
  62. package/dist/index.d.ts +5 -0
  63. package/dist/index.d.ts.map +1 -1
  64. package/dist/index.js +5 -0
  65. package/dist/index.js.map +1 -1
  66. package/dist/status/index.d.ts +20 -0
  67. package/dist/status/index.d.ts.map +1 -0
  68. package/dist/status/index.js +46 -0
  69. package/dist/status/index.js.map +1 -0
  70. package/dist/watch/index.d.ts +11 -0
  71. package/dist/watch/index.d.ts.map +1 -0
  72. package/dist/watch/index.js +42 -0
  73. package/dist/watch/index.js.map +1 -0
  74. package/package.json +3 -2
  75. package/src/audit/index.ts +120 -0
  76. package/src/config.ts +3 -0
  77. package/src/contract.test.ts +99 -0
  78. package/src/contract.ts +38 -0
  79. package/src/extractor/__fixtures__/cross-file-id.fixture.ts +9 -0
  80. package/src/extractor/__fixtures__/cross-file-unresolved.fixture.ts +9 -0
  81. package/src/extractor/__fixtures__/empty.fixture.ts +4 -0
  82. package/src/extractor/__fixtures__/external-no-id.fixture.ts +7 -0
  83. package/src/extractor/__fixtures__/external-with-id.fixture.ts +8 -0
  84. package/src/extractor/__fixtures__/mixed.fixture.ts +17 -0
  85. package/src/extractor/__fixtures__/one-contract.fixture.ts +10 -0
  86. package/src/extractor/__fixtures__/optional-fields.fixture.ts +10 -0
  87. package/src/extractor/__fixtures__/same-file-consumes.fixture.ts +12 -0
  88. package/src/extractor/__fixtures__/three-unresolved.fixture.ts +24 -0
  89. package/src/extractor/__fixtures__/throws-on-import.fixture.ts +3 -0
  90. package/src/extractor/frontmatter.ts +1 -1
  91. package/src/extractor/typescript-contract.test.ts +143 -0
  92. package/src/extractor/typescript-contract.ts +76 -0
  93. package/src/index.ts +5 -0
  94. package/src/status/index.ts +68 -0
  95. package/src/watch/index.ts +53 -0
@@ -0,0 +1,27 @@
1
+ import type { DBStore } from '../store/types.js';
2
+ import type { ImportIntegrityReport, ReconcileReport } from '../reconciler/index.js';
3
+ import type { UpwardDriftResult } from '../extractor/upward-classifier.js';
4
+ import type { StatusReport } from '../status/index.js';
5
+ export interface AuditSummary {
6
+ totalContracts: number;
7
+ stable: number;
8
+ needsReview: number;
9
+ roadmap: number;
10
+ downwardBreaking: number;
11
+ downwardNonBreaking: number;
12
+ upwardBreaking: number;
13
+ upwardNonBreaking: number;
14
+ integrityViolationCount: number;
15
+ }
16
+ export interface AuditReport {
17
+ version: '1.0';
18
+ timestamp: string;
19
+ summary: AuditSummary;
20
+ downwardDrift: ReconcileReport['flagged'];
21
+ upwardDrift: UpwardDriftResult[];
22
+ integrityViolations: ImportIntegrityReport;
23
+ importSuggestions: ReconcileReport['importSuggestions'];
24
+ statusReport: StatusReport;
25
+ }
26
+ export declare function buildAuditReport(store: DBStore, projectRoot: string): Promise<AuditReport>;
27
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/audit/index.ts"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,mBAAmB,CAAC;AACjD,OAAO,KAAK,EAAE,qBAAqB,EAAE,eAAe,EAAE,MAAM,wBAAwB,CAAC;AACrF,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,mCAAmC,CAAC;AAC3E,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAQvD,MAAM,WAAW,YAAY;IAC3B,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,EAAE,MAAM,CAAC;IACf,WAAW,EAAE,MAAM,CAAC;IACpB,OAAO,EAAE,MAAM,CAAC;IAChB,gBAAgB,EAAE,MAAM,CAAC;IACzB,mBAAmB,EAAE,MAAM,CAAC;IAC5B,cAAc,EAAE,MAAM,CAAC;IACvB,iBAAiB,EAAE,MAAM,CAAC;IAC1B,uBAAuB,EAAE,MAAM,CAAC;CACjC;AAED,MAAM,WAAW,WAAW;IAC1B,OAAO,EAAE,KAAK,CAAC;IACf,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,YAAY,CAAC;IACtB,aAAa,EAAE,eAAe,CAAC,SAAS,CAAC,CAAC;IAC1C,WAAW,EAAE,iBAAiB,EAAE,CAAC;IACjC,mBAAmB,EAAE,qBAAqB,CAAC;IAC3C,iBAAiB,EAAE,eAAe,CAAC,mBAAmB,CAAC,CAAC;IACxD,YAAY,EAAE,YAAY,CAAC;CAC5B;AAED,wBAAsB,gBAAgB,CAAC,KAAK,EAAE,OAAO,EAAE,WAAW,EAAE,MAAM,GAAG,OAAO,CAAC,WAAW,CAAC,CA+EhG"}
@@ -0,0 +1,89 @@
1
+ // Audit layer — read-only bidirectional drift report.
2
+ // Combines downward drift (reconciler), upward drift (code → spec), and status.
3
+ // No mutations. No side effects beyond reading the store and filesystem.
4
+ import * as fs from 'node:fs';
5
+ import * as path from 'node:path';
6
+ import { Reconciler } from '../reconciler/index.js';
7
+ import { classifyUpwardDrift } from '../extractor/upward-classifier.js';
8
+ import { buildStatusReport } from '../status/index.js';
9
+ import { extractContractsFromTypeScript } from '../extractor/typescript.js';
10
+ import { extractFromContractFile } from '../extractor/typescript-contract.js';
11
+ export async function buildAuditReport(store, projectRoot) {
12
+ const reconciler = new Reconciler(store);
13
+ const reconcileReport = await reconciler.reconcile();
14
+ const statusReport = await buildStatusReport(store);
15
+ const contracts = await store.getContracts();
16
+ const breakingTriggerIds = new Set(contracts.filter((c) => c.status === 'needs-review').map((c) => c.id));
17
+ // Upward drift detection — re-extract live TypeScript and compare to declared schema.
18
+ const upwardDrift = [];
19
+ const tsExtractionCache = new Map();
20
+ for (const contract of contracts) {
21
+ if (!contract.code_source_file || !contract.code_source_symbol)
22
+ continue;
23
+ const sourceAbsPath = path.resolve(projectRoot, contract.code_source_file);
24
+ if (!fs.existsSync(sourceAbsPath))
25
+ continue;
26
+ let codeShape;
27
+ try {
28
+ if (sourceAbsPath.endsWith('.contract.ts')) {
29
+ let tsExtraction = tsExtractionCache.get(sourceAbsPath);
30
+ if (!tsExtraction) {
31
+ tsExtraction = await extractFromContractFile(sourceAbsPath);
32
+ tsExtractionCache.set(sourceAbsPath, tsExtraction);
33
+ }
34
+ const found = tsExtraction.contracts.find((c) => c.id === contract.code_source_symbol);
35
+ if (!found)
36
+ continue;
37
+ codeShape = found.shape;
38
+ }
39
+ else {
40
+ const fileContent = fs.readFileSync(sourceAbsPath, 'utf-8');
41
+ const extraction = extractContractsFromTypeScript(sourceAbsPath, fileContent);
42
+ const found = extraction.contracts.find((c) => c.sourceSymbol === contract.code_source_symbol);
43
+ if (!found)
44
+ continue;
45
+ codeShape = found.shape;
46
+ }
47
+ }
48
+ catch {
49
+ continue;
50
+ }
51
+ let declaredSchema = {};
52
+ try {
53
+ declaredSchema = JSON.parse(contract.shape_schema);
54
+ }
55
+ catch { }
56
+ const result = classifyUpwardDrift(contract.id, declaredSchema, codeShape, contract.code_source_file, contract.code_source_symbol);
57
+ if (result.driftClass !== 'NOOP') {
58
+ upwardDrift.push(result);
59
+ }
60
+ }
61
+ const downwardBreaking = reconcileReport.flagged.filter((f) => breakingTriggerIds.has(f.triggeredByContractId)).length;
62
+ const downwardNonBreaking = reconcileReport.flagged.filter((f) => !breakingTriggerIds.has(f.triggeredByContractId)).length;
63
+ const upwardBreaking = upwardDrift.filter((d) => d.driftClass === 'BREAKING').length;
64
+ const upwardNonBreaking = upwardDrift.filter((d) => d.driftClass === 'NON_BREAKING').length;
65
+ const integrityViolationCount = reconcileReport.integrityViolations.unresolvedImports.length +
66
+ reconcileReport.integrityViolations.selfImports.length +
67
+ reconcileReport.integrityViolations.circularImports.length;
68
+ return {
69
+ version: '1.0',
70
+ timestamp: new Date().toISOString(),
71
+ summary: {
72
+ totalContracts: contracts.length,
73
+ stable: statusReport.stable,
74
+ needsReview: statusReport.needsReview,
75
+ roadmap: statusReport.roadmap,
76
+ downwardBreaking,
77
+ downwardNonBreaking,
78
+ upwardBreaking,
79
+ upwardNonBreaking,
80
+ integrityViolationCount,
81
+ },
82
+ downwardDrift: reconcileReport.flagged,
83
+ upwardDrift,
84
+ integrityViolations: reconcileReport.integrityViolations,
85
+ importSuggestions: reconcileReport.importSuggestions,
86
+ statusReport,
87
+ };
88
+ }
89
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/audit/index.ts"],"names":[],"mappings":"AAAA,sDAAsD;AACtD,gFAAgF;AAChF,yEAAyE;AAEzE,OAAO,KAAK,EAAE,MAAM,SAAS,CAAC;AAC9B,OAAO,KAAK,IAAI,MAAM,WAAW,CAAC;AAMlC,OAAO,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AACpD,OAAO,EAAE,mBAAmB,EAAE,MAAM,mCAAmC,CAAC;AACxE,OAAO,EAAE,iBAAiB,EAAE,MAAM,oBAAoB,CAAC;AACvD,OAAO,EAAE,8BAA8B,EAAE,MAAM,4BAA4B,CAAC;AAC5E,OAAO,EAAE,uBAAuB,EAAE,MAAM,qCAAqC,CAAC;AAyB9E,MAAM,CAAC,KAAK,UAAU,gBAAgB,CAAC,KAAc,EAAE,WAAmB;IACxE,MAAM,UAAU,GAAG,IAAI,UAAU,CAAC,KAAK,CAAC,CAAC;IACzC,MAAM,eAAe,GAAG,MAAM,UAAU,CAAC,SAAS,EAAE,CAAC;IACrD,MAAM,YAAY,GAAG,MAAM,iBAAiB,CAAC,KAAK,CAAC,CAAC;IAEpD,MAAM,SAAS,GAAG,MAAM,KAAK,CAAC,YAAY,EAAE,CAAC;IAC7C,MAAM,kBAAkB,GAAG,IAAI,GAAG,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,MAAM,KAAK,cAAc,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;IAE1G,sFAAsF;IACtF,MAAM,WAAW,GAAwB,EAAE,CAAC;IAC5C,MAAM,iBAAiB,GAAG,IAAI,GAAG,EAA4B,CAAC;IAE9D,KAAK,MAAM,QAAQ,IAAI,SAAS,EAAE,CAAC;QACjC,IAAI,CAAC,QAAQ,CAAC,gBAAgB,IAAI,CAAC,QAAQ,CAAC,kBAAkB;YAAE,SAAS;QACzE,MAAM,aAAa,GAAG,IAAI,CAAC,OAAO,CAAC,WAAW,EAAE,QAAQ,CAAC,gBAAgB,CAAC,CAAC;QAC3E,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,aAAa,CAAC;YAAE,SAAS;QAE5C,IAAI,SAAkB,CAAC;QACvB,IAAI,CAAC;YACH,IAAI,aAAa,CAAC,QAAQ,CAAC,cAAc,CAAC,EAAE,CAAC;gBAC3C,IAAI,YAAY,GAAG,iBAAiB,CAAC,GAAG,CAAC,aAAa,CAAC,CAAC;gBACxD,IAAI,CAAC,YAAY,EAAE,CAAC;oBAClB,YAAY,GAAG,MAAM,uBAAuB,CAAC,aAAa,CAAC,CAAC;oBAC5D,iBAAiB,CAAC,GAAG,CAAC,aAAa,EAAE,YAAY,CAAC,CAAC;gBACrD,CAAC;gBACD,MAAM,KAAK,GAAG,YAAY,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,EAAE,KAAK,QAAQ,CAAC,kBAAkB,CAAC,CAAC;gBACvF,IAAI,CAAC,KAAK;oBAAE,SAAS;gBACrB,SAAS,GAAG,KAAK,CAAC,KAAK,CAAC;YAC1B,CAAC;iBAAM,CAAC;gBACN,MAAM,WAAW,GAAG,EAAE,CAAC,YAAY,CAAC,aAAa,EAAE,OAAO,CAAC,CAAC;gBAC5D,MAAM,UAAU,GAAG,8BAA8B,CAAC,aAAa,EAAE,WAAW,CAAC,CAAC;gBAC9E,MAAM,KAAK,GAAG,UAAU,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,YAAY,KAAK,QAAQ,CAAC,kBAAkB,CAAC,CAAC;gBAC/F,IAAI,CAAC,KAAK;oBAAE,SAAS;gBACrB,SAAS,GAAG,KAAK,CAAC,KAAK,CAAC;YAC1B,CAAC;QACH,CAAC;QAAC,MAAM,CAAC;YACP,SAAS;QACX,CAAC;QAED,IAAI,cAAc,GAAY,EAAE,CAAC;QACjC,IAAI,CAAC;YACH,cAAc,GAAG,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAC;QACrD,CAAC;QAAC,MAAM,CAAC,CAAA,CAAC;QAEV,MAAM,MAAM,GAAG,mBAAmB,CAAC,QAAQ,CAAC,EAAE,EAAE,cAAc,EAAE,SAAS,EAAE,QAAQ,CAAC,gBAAgB,EAAE,QAAQ,CAAC,kBAAkB,CAAC,CAAC;QACnI,IAAI,MAAM,CAAC,UAAU,KAAK,MAAM,EAAE,CAAC;YACjC,WAAW,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;QAC3B,CAAC;IACH,CAAC;IAED,MAAM,gBAAgB,GAAG,eAAe,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,kBAAkB,CAAC,GAAG,CAAC,CAAC,CAAC,qBAAqB,CAAC,CAAC,CAAC,MAAM,CAAC;IACvH,MAAM,mBAAmB,GAAG,eAAe,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,kBAAkB,CAAC,GAAG,CAAC,CAAC,CAAC,qBAAqB,CAAC,CAAC,CAAC,MAAM,CAAC;IAC3H,MAAM,cAAc,GAAG,WAAW,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,UAAU,CAAC,CAAC,MAAM,CAAC;IACrF,MAAM,iBAAiB,GAAG,WAAW,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,KAAK,cAAc,CAAC,CAAC,MAAM,CAAC;IAC5F,MAAM,uBAAuB,GAC3B,eAAe,CAAC,mBAAmB,CAAC,iBAAiB,CAAC,MAAM;QAC5D,eAAe,CAAC,mBAAmB,CAAC,WAAW,CAAC,MAAM;QACtD,eAAe,CAAC,mBAAmB,CAAC,eAAe,CAAC,MAAM,CAAC;IAE7D,OAAO;QACL,OAAO,EAAE,KAAK;QACd,SAAS,EAAE,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE;QACnC,OAAO,EAAE;YACP,cAAc,EAAE,SAAS,CAAC,MAAM;YAChC,MAAM,EAAE,YAAY,CAAC,MAAM;YAC3B,WAAW,EAAE,YAAY,CAAC,WAAW;YACrC,OAAO,EAAE,YAAY,CAAC,OAAO;YAC7B,gBAAgB;YAChB,mBAAmB;YACnB,cAAc;YACd,iBAAiB;YACjB,uBAAuB;SACxB;QACD,aAAa,EAAE,eAAe,CAAC,OAAO;QACtC,WAAW;QACX,mBAAmB,EAAE,eAAe,CAAC,mBAAmB;QACxD,iBAAiB,EAAE,eAAe,CAAC,iBAAiB;QACpD,YAAY;KACb,CAAC;AACJ,CAAC"}
package/dist/config.d.ts CHANGED
@@ -10,6 +10,9 @@ export interface FerretConfig {
10
10
  include: string[];
11
11
  watchNodes?: string[];
12
12
  };
13
+ contractParsers?: {
14
+ typescript?: boolean;
15
+ };
13
16
  }
14
17
  export declare const DEFAULT_CONFIG: FerretConfig;
15
18
  /**
@@ -1 +1 @@
1
- {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAIA,MAAM,WAAW,YAAY;IAC3B,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,KAAK,EAAE,QAAQ,GAAG,UAAU,CAAC;IAC7B,iBAAiB,CAAC,EAAE;QAClB,OAAO,CAAC,EAAE,OAAO,CAAC;KACnB,CAAC;IACF,aAAa,CAAC,EAAE;QACd,OAAO,EAAE,MAAM,EAAE,CAAC;QAClB,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;KACvB,CAAC;CACH;AAED,eAAO,MAAM,cAAc,EAAE,YAQ5B,CAAC;AAEF;;;GAGG;AACH,wBAAgB,UAAU,IAAI,YAAY,CAezC"}
1
+ {"version":3,"file":"config.d.ts","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAIA,MAAM,WAAW,YAAY;IAC3B,OAAO,EAAE,MAAM,CAAC;IAChB,WAAW,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,EAAE,MAAM,EAAE,CAAC;IACpB,KAAK,EAAE,QAAQ,GAAG,UAAU,CAAC;IAC7B,iBAAiB,CAAC,EAAE;QAClB,OAAO,CAAC,EAAE,OAAO,CAAC;KACnB,CAAC;IACF,aAAa,CAAC,EAAE;QACd,OAAO,EAAE,MAAM,EAAE,CAAC;QAClB,UAAU,CAAC,EAAE,MAAM,EAAE,CAAC;KACvB,CAAC;IACF,eAAe,CAAC,EAAE;QAChB,UAAU,CAAC,EAAE,OAAO,CAAC;KACtB,CAAC;CACH;AAED,eAAO,MAAM,cAAc,EAAE,YAQ5B,CAAC;AAEF;;;GAGG;AACH,wBAAgB,UAAU,IAAI,YAAY,CAezC"}
@@ -1 +1 @@
1
- {"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,SAAS,CAAC;AAC9B,OAAO,KAAK,IAAI,MAAM,WAAW,CAAC;AAClC,OAAO,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAgBnD,MAAM,CAAC,MAAM,cAAc,GAAiB;IAC1C,OAAO,EAAE,YAAY;IACrB,WAAW,EAAE,kBAAkB;IAC/B,QAAQ,EAAE,CAAC,kBAAkB,CAAC;IAC9B,KAAK,EAAE,QAAQ;IACf,iBAAiB,EAAE;QACjB,OAAO,EAAE,IAAI;KACd;CACF,CAAC;AAEF;;;GAGG;AACH,MAAM,UAAU,UAAU;IACxB,MAAM,IAAI,GAAG,eAAe,EAAE,CAAC;IAC/B,MAAM,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,oBAAoB,CAAC,CAAC;IAEzD,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QAC/B,OAAO,EAAE,GAAG,cAAc,EAAE,CAAC;IAC/B,CAAC;IAED,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,EAAE,CAAC,YAAY,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC;QACjD,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAA0B,CAAC;QACxD,OAAO,EAAE,GAAG,cAAc,EAAE,GAAG,MAAM,EAAE,CAAC;IAC1C,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,GAAG,cAAc,EAAE,CAAC;IAC/B,CAAC;AACH,CAAC"}
1
+ {"version":3,"file":"config.js","sourceRoot":"","sources":["../src/config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,SAAS,CAAC;AAC9B,OAAO,KAAK,IAAI,MAAM,WAAW,CAAC;AAClC,OAAO,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAmBnD,MAAM,CAAC,MAAM,cAAc,GAAiB;IAC1C,OAAO,EAAE,YAAY;IACrB,WAAW,EAAE,kBAAkB;IAC/B,QAAQ,EAAE,CAAC,kBAAkB,CAAC;IAC9B,KAAK,EAAE,QAAQ;IACf,iBAAiB,EAAE;QACjB,OAAO,EAAE,IAAI;KACd;CACF,CAAC;AAEF;;;GAGG;AACH,MAAM,UAAU,UAAU;IACxB,MAAM,IAAI,GAAG,eAAe,EAAE,CAAC;IAC/B,MAAM,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,oBAAoB,CAAC,CAAC;IAEzD,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,UAAU,CAAC,EAAE,CAAC;QAC/B,OAAO,EAAE,GAAG,cAAc,EAAE,CAAC;IAC/B,CAAC;IAED,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,EAAE,CAAC,YAAY,CAAC,UAAU,EAAE,OAAO,CAAC,CAAC;QACjD,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,CAA0B,CAAC;QACxD,OAAO,EAAE,GAAG,cAAc,EAAE,GAAG,MAAM,EAAE,CAAC;IAC1C,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,GAAG,cAAc,EAAE,CAAC;IAC/B,CAAC;AACH,CAAC"}
@@ -0,0 +1,16 @@
1
+ import { z } from 'zod';
2
+ export interface Contract<T extends Record<string, z.ZodTypeAny> = Record<string, z.ZodTypeAny>> {
3
+ id?: string;
4
+ value: string;
5
+ output: T;
6
+ invariants?: Array<(r: z.infer<z.ZodObject<T>>) => boolean>;
7
+ consumes?: Contract[];
8
+ forbids?: string[];
9
+ status?: 'complete' | 'active' | 'pending';
10
+ closedBy?: string;
11
+ closedWhen?: string;
12
+ dependsOn?: Contract[];
13
+ }
14
+ export declare function defineContract<T extends Record<string, z.ZodTypeAny>>(contract: Contract<T>): Contract<T>;
15
+ export declare function isContract(value: unknown): value is Contract;
16
+ //# sourceMappingURL=contract.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"contract.d.ts","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,MAAM,WAAW,QAAQ,CACvB,CAAC,SAAS,MAAM,CAAC,MAAM,EAAE,CAAC,CAAC,UAAU,CAAC,GAAG,MAAM,CAAC,MAAM,EAAE,CAAC,CAAC,UAAU,CAAC;IAErE,EAAE,CAAC,EAAE,MAAM,CAAC;IACZ,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,CAAC,CAAC;IACV,UAAU,CAAC,EAAE,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,KAAK,OAAO,CAAC,CAAC;IAC5D,QAAQ,CAAC,EAAE,QAAQ,EAAE,CAAC;IACtB,OAAO,CAAC,EAAE,MAAM,EAAE,CAAC;IACnB,MAAM,CAAC,EAAE,UAAU,GAAG,QAAQ,GAAG,SAAS,CAAC;IAC3C,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,QAAQ,EAAE,CAAC;CACxB;AAED,wBAAgB,cAAc,CAAC,CAAC,SAAS,MAAM,CAAC,MAAM,EAAE,CAAC,CAAC,UAAU,CAAC,EACnE,QAAQ,EAAE,QAAQ,CAAC,CAAC,CAAC,GACpB,QAAQ,CAAC,CAAC,CAAC,CAKb;AAED,wBAAgB,UAAU,CAAC,KAAK,EAAE,OAAO,GAAG,KAAK,IAAI,QAAQ,CAW5D"}
@@ -0,0 +1,17 @@
1
+ export function defineContract(contract) {
2
+ if ('id' in contract && contract.id !== undefined && contract.id.trim() === '') {
3
+ throw new Error('defineContract: id must be a non-empty string if provided');
4
+ }
5
+ return contract;
6
+ }
7
+ export function isContract(value) {
8
+ return (typeof value === 'object' &&
9
+ value !== null &&
10
+ 'value' in value &&
11
+ typeof value.value === 'string' &&
12
+ 'output' in value &&
13
+ typeof value.output === 'object' &&
14
+ value.output !== null &&
15
+ !Array.isArray(value.output));
16
+ }
17
+ //# sourceMappingURL=contract.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"contract.js","sourceRoot":"","sources":["../src/contract.ts"],"names":[],"mappings":"AAiBA,MAAM,UAAU,cAAc,CAC5B,QAAqB;IAErB,IAAI,IAAI,IAAI,QAAQ,IAAI,QAAQ,CAAC,EAAE,KAAK,SAAS,IAAI,QAAQ,CAAC,EAAE,CAAC,IAAI,EAAE,KAAK,EAAE,EAAE,CAAC;QAC/E,MAAM,IAAI,KAAK,CAAC,2DAA2D,CAAC,CAAC;IAC/E,CAAC;IACD,OAAO,QAAQ,CAAC;AAClB,CAAC;AAED,MAAM,UAAU,UAAU,CAAC,KAAc;IACvC,OAAO,CACL,OAAO,KAAK,KAAK,QAAQ;QACzB,KAAK,KAAK,IAAI;QACd,OAAO,IAAI,KAAK;QAChB,OAAQ,KAAiC,CAAC,KAAK,KAAK,QAAQ;QAC5D,QAAQ,IAAI,KAAK;QACjB,OAAQ,KAAiC,CAAC,MAAM,KAAK,QAAQ;QAC5D,KAAiC,CAAC,MAAM,KAAK,IAAI;QAClD,CAAC,KAAK,CAAC,OAAO,CAAE,KAAiC,CAAC,MAAM,CAAC,CAC1D,CAAC;AACJ,CAAC"}
@@ -0,0 +1,15 @@
1
+ import { z } from 'zod';
2
+ export declare const myContract: {
3
+ value: string;
4
+ output: {
5
+ result: z.ZodString;
6
+ };
7
+ consumes: {
8
+ value: string;
9
+ output: {
10
+ data: z.ZodString;
11
+ };
12
+ id: string;
13
+ }[];
14
+ };
15
+ //# sourceMappingURL=cross-file-id.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cross-file-id.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/cross-file-id.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAIxB,eAAO,MAAM,UAAU;;;;;;;;;;;;CAItB,CAAC"}
@@ -0,0 +1,9 @@
1
+ import { z } from 'zod';
2
+ import { externalWithId } from './external-with-id.fixture.js';
3
+ // Consumes an external contract that has an explicit id — resolves via c.id
4
+ export const myContract = {
5
+ value: 'Contract consuming known external',
6
+ output: { result: z.string() },
7
+ consumes: [externalWithId],
8
+ };
9
+ //# sourceMappingURL=cross-file-id.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cross-file-id.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/cross-file-id.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,EAAE,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAE/D,4EAA4E;AAC5E,MAAM,CAAC,MAAM,UAAU,GAAG;IACxB,KAAK,EAAE,mCAAmC;IAC1C,MAAM,EAAE,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;IAC9B,QAAQ,EAAE,CAAC,cAAc,CAAC;CAC3B,CAAC"}
@@ -0,0 +1,14 @@
1
+ import { z } from 'zod';
2
+ export declare const myContract: {
3
+ value: string;
4
+ output: {
5
+ result: z.ZodString;
6
+ };
7
+ consumes: {
8
+ value: string;
9
+ output: {
10
+ data: z.ZodString;
11
+ };
12
+ }[];
13
+ };
14
+ //# sourceMappingURL=cross-file-unresolved.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cross-file-unresolved.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/cross-file-unresolved.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAIxB,eAAO,MAAM,UAAU;;;;;;;;;;;CAItB,CAAC"}
@@ -0,0 +1,9 @@
1
+ import { z } from 'zod';
2
+ import { externalNoId } from './external-no-id.fixture.js';
3
+ // Consumes an external contract with no id — triggers exactly one warning
4
+ export const myContract = {
5
+ value: 'Contract consuming unresolvable external',
6
+ output: { result: z.string() },
7
+ consumes: [externalNoId],
8
+ };
9
+ //# sourceMappingURL=cross-file-unresolved.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cross-file-unresolved.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/cross-file-unresolved.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,EAAE,YAAY,EAAE,MAAM,6BAA6B,CAAC;AAE3D,0EAA0E;AAC1E,MAAM,CAAC,MAAM,UAAU,GAAG;IACxB,KAAK,EAAE,0CAA0C;IACjD,MAAM,EAAE,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;IAC9B,QAAQ,EAAE,CAAC,YAAY,CAAC;CACzB,CAAC"}
@@ -0,0 +1,6 @@
1
+ export declare const version = "1.0.0";
2
+ export declare const count = 42;
3
+ export declare const config: {
4
+ debug: boolean;
5
+ };
6
+ //# sourceMappingURL=empty.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"empty.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/empty.fixture.ts"],"names":[],"mappings":"AACA,eAAO,MAAM,OAAO,UAAU,CAAC;AAC/B,eAAO,MAAM,KAAK,KAAK,CAAC;AACxB,eAAO,MAAM,MAAM;;CAAkB,CAAC"}
@@ -0,0 +1,5 @@
1
+ // No ferret contracts here — only primitives and non-contract objects
2
+ export const version = '1.0.0';
3
+ export const count = 42;
4
+ export const config = { debug: true };
5
+ //# sourceMappingURL=empty.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"empty.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/empty.fixture.ts"],"names":[],"mappings":"AAAA,sEAAsE;AACtE,MAAM,CAAC,MAAM,OAAO,GAAG,OAAO,CAAC;AAC/B,MAAM,CAAC,MAAM,KAAK,GAAG,EAAE,CAAC;AACxB,MAAM,CAAC,MAAM,MAAM,GAAG,EAAE,KAAK,EAAE,IAAI,EAAE,CAAC"}
@@ -0,0 +1,8 @@
1
+ import { z } from 'zod';
2
+ export declare const externalNoId: {
3
+ value: string;
4
+ output: {
5
+ data: z.ZodString;
6
+ };
7
+ };
8
+ //# sourceMappingURL=external-no-id.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"external-no-id.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/external-no-id.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAGxB,eAAO,MAAM,YAAY;;;;;CAGxB,CAAC"}
@@ -0,0 +1,7 @@
1
+ import { z } from 'zod';
2
+ // External contract with no id — cross-file refs to this will be unresolvable
3
+ export const externalNoId = {
4
+ value: 'External contract without id',
5
+ output: { data: z.string() },
6
+ };
7
+ //# sourceMappingURL=external-no-id.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"external-no-id.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/external-no-id.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,8EAA8E;AAC9E,MAAM,CAAC,MAAM,YAAY,GAAG;IAC1B,KAAK,EAAE,8BAA8B;IACrC,MAAM,EAAE,EAAE,IAAI,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;CAC7B,CAAC"}
@@ -0,0 +1,9 @@
1
+ import { z } from 'zod';
2
+ export declare const externalWithId: {
3
+ value: string;
4
+ output: {
5
+ data: z.ZodString;
6
+ };
7
+ id: string;
8
+ };
9
+ //# sourceMappingURL=external-with-id.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"external-with-id.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/external-with-id.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAGxB,eAAO,MAAM,cAAc;;;;;;CAI1B,CAAC"}
@@ -0,0 +1,8 @@
1
+ import { z } from 'zod';
2
+ // External contract with an explicit id — cross-file refs resolve via c.id
3
+ export const externalWithId = {
4
+ value: 'External contract with explicit id',
5
+ output: { data: z.string() },
6
+ id: 'external.known.id',
7
+ };
8
+ //# sourceMappingURL=external-with-id.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"external-with-id.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/external-with-id.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,2EAA2E;AAC3E,MAAM,CAAC,MAAM,cAAc,GAAG;IAC5B,KAAK,EAAE,oCAAoC;IAC3C,MAAM,EAAE,EAAE,IAAI,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;IAC5B,EAAE,EAAE,mBAAmB;CACxB,CAAC"}
@@ -0,0 +1,24 @@
1
+ import { z } from 'zod';
2
+ export declare const validContract: {
3
+ value: string;
4
+ output: {
5
+ name: z.ZodString;
6
+ };
7
+ };
8
+ export declare const anotherValid: {
9
+ value: string;
10
+ output: {
11
+ count: z.ZodNumber;
12
+ };
13
+ };
14
+ export declare const notAContract = 42;
15
+ export declare const alsoNotAContract = "just a string";
16
+ export declare const missingOutput: {
17
+ value: string;
18
+ };
19
+ export declare const missingValue: {
20
+ output: {
21
+ x: z.ZodString;
22
+ };
23
+ };
24
+ //# sourceMappingURL=mixed.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mixed.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/mixed.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,eAAO,MAAM,aAAa;;;;;CAGzB,CAAC;AAEF,eAAO,MAAM,YAAY;;;;;CAGxB,CAAC;AAGF,eAAO,MAAM,YAAY,KAAK,CAAC;AAC/B,eAAO,MAAM,gBAAgB,kBAAkB,CAAC;AAChD,eAAO,MAAM,aAAa;;CAAoB,CAAC;AAC/C,eAAO,MAAM,YAAY;;;;CAAgC,CAAC"}
@@ -0,0 +1,15 @@
1
+ import { z } from 'zod';
2
+ export const validContract = {
3
+ value: 'valid',
4
+ output: { name: z.string() },
5
+ };
6
+ export const anotherValid = {
7
+ value: 'another valid',
8
+ output: { count: z.number() },
9
+ };
10
+ // These should be skipped by isContract
11
+ export const notAContract = 42;
12
+ export const alsoNotAContract = 'just a string';
13
+ export const missingOutput = { value: 'oops' };
14
+ export const missingValue = { output: { x: z.string() } };
15
+ //# sourceMappingURL=mixed.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"mixed.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/mixed.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,MAAM,CAAC,MAAM,aAAa,GAAG;IAC3B,KAAK,EAAE,OAAO;IACd,MAAM,EAAE,EAAE,IAAI,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;CAC7B,CAAC;AAEF,MAAM,CAAC,MAAM,YAAY,GAAG;IAC1B,KAAK,EAAE,eAAe;IACtB,MAAM,EAAE,EAAE,KAAK,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;CAC9B,CAAC;AAEF,wCAAwC;AACxC,MAAM,CAAC,MAAM,YAAY,GAAG,EAAE,CAAC;AAC/B,MAAM,CAAC,MAAM,gBAAgB,GAAG,eAAe,CAAC;AAChD,MAAM,CAAC,MAAM,aAAa,GAAG,EAAE,KAAK,EAAE,MAAM,EAAE,CAAC;AAC/C,MAAM,CAAC,MAAM,YAAY,GAAG,EAAE,MAAM,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE,EAAE,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { z } from 'zod';
2
+ export declare const userContract: {
3
+ value: string;
4
+ output: {
5
+ id: z.ZodString;
6
+ name: z.ZodString;
7
+ email: z.ZodString;
8
+ };
9
+ };
10
+ //# sourceMappingURL=one-contract.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"one-contract.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/one-contract.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,eAAO,MAAM,YAAY;;;;;;;CAOxB,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { z } from 'zod';
2
+ export const userContract = {
3
+ value: 'User shape contract',
4
+ output: {
5
+ id: z.string().uuid(),
6
+ name: z.string(),
7
+ email: z.string().email(),
8
+ },
9
+ };
10
+ //# sourceMappingURL=one-contract.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"one-contract.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/one-contract.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,MAAM,CAAC,MAAM,YAAY,GAAG;IAC1B,KAAK,EAAE,qBAAqB;IAC5B,MAAM,EAAE;QACN,EAAE,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,IAAI,EAAE;QACrB,IAAI,EAAE,CAAC,CAAC,MAAM,EAAE;QAChB,KAAK,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,KAAK,EAAE;KAC1B;CACF,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { z } from 'zod';
2
+ export declare const optionalFieldsContract: {
3
+ value: string;
4
+ output: {
5
+ required_field: z.ZodString;
6
+ optional_field: z.ZodOptional<z.ZodString>;
7
+ optional_number: z.ZodOptional<z.ZodNumber>;
8
+ };
9
+ };
10
+ //# sourceMappingURL=optional-fields.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"optional-fields.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/optional-fields.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,eAAO,MAAM,sBAAsB;;;;;;;CAOlC,CAAC"}
@@ -0,0 +1,10 @@
1
+ import { z } from 'zod';
2
+ export const optionalFieldsContract = {
3
+ value: 'Contract with optional fields',
4
+ output: {
5
+ required_field: z.string(),
6
+ optional_field: z.string().optional(),
7
+ optional_number: z.number().optional(),
8
+ },
9
+ };
10
+ //# sourceMappingURL=optional-fields.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"optional-fields.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/optional-fields.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,MAAM,CAAC,MAAM,sBAAsB,GAAG;IACpC,KAAK,EAAE,+BAA+B;IACtC,MAAM,EAAE;QACN,cAAc,EAAE,CAAC,CAAC,MAAM,EAAE;QAC1B,cAAc,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;QACrC,eAAe,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;KACvC;CACF,CAAC"}
@@ -0,0 +1,20 @@
1
+ import { z } from 'zod';
2
+ export declare const baseContract: {
3
+ value: string;
4
+ output: {
5
+ token: z.ZodString;
6
+ };
7
+ };
8
+ export declare const dependentContract: {
9
+ value: string;
10
+ output: {
11
+ result: z.ZodString;
12
+ };
13
+ consumes: {
14
+ value: string;
15
+ output: {
16
+ token: z.ZodString;
17
+ };
18
+ }[];
19
+ };
20
+ //# sourceMappingURL=same-file-consumes.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"same-file-consumes.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/same-file-consumes.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,eAAO,MAAM,YAAY;;;;;CAGxB,CAAC;AAEF,eAAO,MAAM,iBAAiB;;;;;;;;;;;CAI7B,CAAC"}
@@ -0,0 +1,11 @@
1
+ import { z } from 'zod';
2
+ export const baseContract = {
3
+ value: 'Base contract',
4
+ output: { token: z.string() },
5
+ };
6
+ export const dependentContract = {
7
+ value: 'Dependent contract that consumes baseContract',
8
+ output: { result: z.string() },
9
+ consumes: [baseContract],
10
+ };
11
+ //# sourceMappingURL=same-file-consumes.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"same-file-consumes.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/same-file-consumes.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,MAAM,CAAC,MAAM,YAAY,GAAG;IAC1B,KAAK,EAAE,eAAe;IACtB,MAAM,EAAE,EAAE,KAAK,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;CAC9B,CAAC;AAEF,MAAM,CAAC,MAAM,iBAAiB,GAAG;IAC/B,KAAK,EAAE,+CAA+C;IACtD,MAAM,EAAE,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;IAC9B,QAAQ,EAAE,CAAC,YAAY,CAAC;CACzB,CAAC"}
@@ -0,0 +1,38 @@
1
+ import { z } from 'zod';
2
+ export declare const contractA: {
3
+ value: string;
4
+ output: {
5
+ x: z.ZodString;
6
+ };
7
+ consumes: {
8
+ value: string;
9
+ output: {
10
+ a: z.ZodString;
11
+ };
12
+ }[];
13
+ };
14
+ export declare const contractB: {
15
+ value: string;
16
+ output: {
17
+ y: z.ZodString;
18
+ };
19
+ consumes: {
20
+ value: string;
21
+ output: {
22
+ b: z.ZodString;
23
+ };
24
+ }[];
25
+ };
26
+ export declare const contractC: {
27
+ value: string;
28
+ output: {
29
+ zField: z.ZodString;
30
+ };
31
+ consumes: {
32
+ value: string;
33
+ output: {
34
+ c: z.ZodString;
35
+ };
36
+ }[];
37
+ };
38
+ //# sourceMappingURL=three-unresolved.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"three-unresolved.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/three-unresolved.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAOxB,eAAO,MAAM,SAAS;;;;;;;;;;;CAIrB,CAAC;AAEF,eAAO,MAAM,SAAS;;;;;;;;;;;CAIrB,CAAC;AAEF,eAAO,MAAM,SAAS;;;;;;;;;;;CAIrB,CAAC"}
@@ -0,0 +1,21 @@
1
+ import { z } from 'zod';
2
+ // Three separate unresolvable external references (not exported, no id)
3
+ const ext1 = { value: 'ext1', output: { a: z.string() } };
4
+ const ext2 = { value: 'ext2', output: { b: z.string() } };
5
+ const ext3 = { value: 'ext3', output: { c: z.string() } };
6
+ export const contractA = {
7
+ value: 'Contract A',
8
+ output: { x: z.string() },
9
+ consumes: [ext1],
10
+ };
11
+ export const contractB = {
12
+ value: 'Contract B',
13
+ output: { y: z.string() },
14
+ consumes: [ext2],
15
+ };
16
+ export const contractC = {
17
+ value: 'Contract C',
18
+ output: { zField: z.string() },
19
+ consumes: [ext3],
20
+ };
21
+ //# sourceMappingURL=three-unresolved.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"three-unresolved.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/three-unresolved.fixture.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AAExB,wEAAwE;AACxE,MAAM,IAAI,GAAG,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE,EAAE,CAAC;AAC1D,MAAM,IAAI,GAAG,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE,EAAE,CAAC;AAC1D,MAAM,IAAI,GAAG,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE,EAAE,CAAC;AAE1D,MAAM,CAAC,MAAM,SAAS,GAAG;IACvB,KAAK,EAAE,YAAY;IACnB,MAAM,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;IACzB,QAAQ,EAAE,CAAC,IAAI,CAAC;CACjB,CAAC;AAEF,MAAM,CAAC,MAAM,SAAS,GAAG;IACvB,KAAK,EAAE,YAAY;IACnB,MAAM,EAAE,EAAE,CAAC,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;IACzB,QAAQ,EAAE,CAAC,IAAI,CAAC;CACjB,CAAC;AAEF,MAAM,CAAC,MAAM,SAAS,GAAG;IACvB,KAAK,EAAE,YAAY;IACnB,MAAM,EAAE,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,EAAE;IAC9B,QAAQ,EAAE,CAAC,IAAI,CAAC;CACjB,CAAC"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=throws-on-import.fixture.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"throws-on-import.fixture.d.ts","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/throws-on-import.fixture.ts"],"names":[],"mappings":""}
@@ -0,0 +1,5 @@
1
+ // Fixture: throws synchronously at module top-level.
2
+ // Used to verify that extractFromContractFile() does not swallow import errors.
3
+ throw new Error('intentional module-level throw');
4
+ export {};
5
+ //# sourceMappingURL=throws-on-import.fixture.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"throws-on-import.fixture.js","sourceRoot":"","sources":["../../../src/extractor/__fixtures__/throws-on-import.fixture.ts"],"names":[],"mappings":"AAAA,qDAAqD;AACrD,gFAAgF;AAChF,MAAM,IAAI,KAAK,CAAC,gCAAgC,CAAC,CAAC"}
@@ -13,7 +13,7 @@ export interface ExtractionResult {
13
13
  /** TypeScript symbol name (code-first contracts only). */
14
14
  sourceSymbol?: string;
15
15
  }>;
16
- extractedBy: 'gray-matter' | 'tree-sitter';
16
+ extractedBy: 'gray-matter' | 'tree-sitter' | 'typescript';
17
17
  extractedAt: number;
18
18
  warning?: 'no-frontmatter';
19
19
  }
@@ -1 +1 @@
1
- {"version":3,"file":"frontmatter.d.ts","sourceRoot":"","sources":["../../src/extractor/frontmatter.ts"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAExD,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,GAAG,MAAM,CAAC;IAC1B,SAAS,EAAE,KAAK,CAAC;QACf,EAAE,EAAE,MAAM,CAAC;QACX,IAAI,EAAE,YAAY,CAAC;QACnB,KAAK,EAAE,MAAM,CAAC;QACd,UAAU,EAAE,MAAM,CAAC;QACnB,OAAO,EAAE,MAAM,EAAE,CAAC;QAClB,sEAAsE;QACtE,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,0DAA0D;QAC1D,YAAY,CAAC,EAAE,MAAM,CAAC;KACvB,CAAC,CAAC;IACH,WAAW,EAAE,aAAa,GAAG,aAAa,CAAC;IAC3C,WAAW,EAAE,MAAM,CAAC;IACpB,OAAO,CAAC,EAAE,gBAAgB,CAAC;CAC5B;AAED;;;;;;;;GAQG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,gBAAgB,CAkD3F"}
1
+ {"version":3,"file":"frontmatter.d.ts","sourceRoot":"","sources":["../../src/extractor/frontmatter.ts"],"names":[],"mappings":"AAMA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,qBAAqB,CAAC;AAExD,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,MAAM,GAAG,MAAM,CAAC;IAC1B,SAAS,EAAE,KAAK,CAAC;QACf,EAAE,EAAE,MAAM,CAAC;QACX,IAAI,EAAE,YAAY,CAAC;QACnB,KAAK,EAAE,MAAM,CAAC;QACd,UAAU,EAAE,MAAM,CAAC;QACnB,OAAO,EAAE,MAAM,EAAE,CAAC;QAClB,sEAAsE;QACtE,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,0DAA0D;QAC1D,YAAY,CAAC,EAAE,MAAM,CAAC;KACvB,CAAC,CAAC;IACH,WAAW,EAAE,aAAa,GAAG,aAAa,GAAG,YAAY,CAAC;IAC1D,WAAW,EAAE,MAAM,CAAC;IACpB,OAAO,CAAC,EAAE,gBAAgB,CAAC;CAC5B;AAED;;;;;;;;GAQG;AACH,wBAAgB,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,WAAW,EAAE,MAAM,GAAG,gBAAgB,CAkD3F"}
@@ -0,0 +1,3 @@
1
+ import type { ExtractionResult } from './frontmatter.js';
2
+ export declare function extractFromContractFile(filePath: string): Promise<ExtractionResult>;
3
+ //# sourceMappingURL=typescript-contract.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"typescript-contract.d.ts","sourceRoot":"","sources":["../../src/extractor/typescript-contract.ts"],"names":[],"mappings":"AAOA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AAEzD,wBAAsB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,gBAAgB,CAAC,CAkEzF"}