@harness-engineering/graph 0.3.5 → 0.4.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -73,27 +73,29 @@ const results = fusion.search('authentication handler', { topK: 10 });
73
73
 
74
74
  ## Key Classes
75
75
 
76
- | Class | Description |
77
- | ------------------------- | ------------------------------------------------------------------------------- |
78
- | `GraphStore` | In-memory graph backed by LokiJS with indexed node/edge collections |
79
- | `VectorStore` | Optional vector index for semantic similarity search (hnswlib) |
80
- | `ContextQL` | BFS-based graph traversal engine with type filtering and observability pruning |
81
- | `project` | Projection utility to select specific fields from query results |
82
- | `CodeIngestor` | Parses TypeScript/JavaScript files into file, class, function, and method nodes |
83
- | `GitIngestor` | Extracts commit history and co-change relationships from git |
84
- | `KnowledgeIngestor` | Ingests ADRs, learnings, and markdown knowledge artifacts |
85
- | `TopologicalLinker` | Creates structural edges (imports, calls, references) between code nodes |
86
- | `FusionLayer` | Hybrid search combining keyword matching and semantic similarity scores |
87
- | `Assembler` | Phase-aware context assembly with token budgets and coverage reports |
88
- | `SyncManager` | Orchestrates connector syncs with incremental update tracking |
89
- | `GraphEntropyAdapter` | Detects graph drift and dead code for entropy monitoring |
90
- | `GraphConstraintAdapter` | Validates dependency rules and layer boundary violations |
91
- | `GraphFeedbackAdapter` | Computes impact analysis and harness check data from graph state |
92
- | `saveGraph` / `loadGraph` | Serializes and deserializes the graph store to/from disk |
76
+ | Class | Description |
77
+ | ------------------------------ | ------------------------------------------------------------------------------------ |
78
+ | `GraphStore` | In-memory graph backed by LokiJS with indexed node/edge collections |
79
+ | `VectorStore` | Optional vector index for semantic similarity search (hnswlib) |
80
+ | `ContextQL` | BFS-based graph traversal engine with type filtering and observability pruning |
81
+ | `project` | Projection utility to select specific fields from query results |
82
+ | `CodeIngestor` | Parses TypeScript/JavaScript files into file, class, function, and method nodes |
83
+ | `GitIngestor` | Extracts commit history and co-change relationships from git |
84
+ | `KnowledgeIngestor` | Ingests ADRs, learnings, and markdown knowledge artifacts |
85
+ | `TopologicalLinker` | Creates structural edges (imports, calls, references) between code nodes |
86
+ | `FusionLayer` | Hybrid search combining keyword matching and semantic similarity scores |
87
+ | `Assembler` | Phase-aware context assembly with token budgets and coverage reports |
88
+ | `SyncManager` | Orchestrates connector syncs with incremental update tracking |
89
+ | `GraphEntropyAdapter` | Detects graph drift and dead code for entropy monitoring |
90
+ | `GraphConstraintAdapter` | Validates dependency rules and layer boundary violations |
91
+ | `GraphFeedbackAdapter` | Computes impact analysis and harness check data from graph state |
92
+ | `CascadeSimulator` | Probability-weighted BFS for cascading failure simulation (`compute_blast_radius`) |
93
+ | `CompositeProbabilityStrategy` | Default edge probability strategy blending edge type, change frequency, and coupling |
94
+ | `saveGraph` / `loadGraph` | Serializes and deserializes the graph store to/from disk |
93
95
 
94
96
  ## Node Types
95
97
 
96
- 24 node types organized by category:
98
+ 28 node types organized by category:
97
99
 
98
100
  | Category | Types |
99
101
  | ----------------- | -------------------------------------------------------------------------------------- |
@@ -102,19 +104,23 @@ const results = fusion.search('authentication handler', { topK: 10 });
102
104
  | **VCS** | `commit`, `build`, `test_result` |
103
105
  | **Observability** | `span`, `metric`, `log` |
104
106
  | **Structural** | `layer`, `pattern`, `constraint`, `violation` |
107
+ | **Design** | `design_token`, `aesthetic_intent`, `design_constraint` |
108
+ | **Traceability** | `requirement` |
105
109
 
106
110
  Observability types (`span`, `metric`, `log`) are pruned by default in ContextQL queries to reduce noise.
107
111
 
108
112
  ## Edge Types
109
113
 
110
- 17 edge types organized by category:
114
+ 24 edge types organized by category:
111
115
 
112
- | Category | Types |
113
- | ------------- | ----------------------------------------------------------------------------------------- |
114
- | **Code** | `contains`, `imports`, `calls`, `implements`, `inherits`, `references` |
115
- | **Knowledge** | `applies_to`, `caused_by`, `resolved_by`, `documents`, `violates`, `specifies`, `decided` |
116
- | **VCS** | `co_changes_with`, `triggered_by`, `failed_in` |
117
- | **Execution** | `executed_by`, `measured_by` |
116
+ | Category | Types |
117
+ | ---------------- | ----------------------------------------------------------------------------------------- |
118
+ | **Code** | `contains`, `imports`, `calls`, `implements`, `inherits`, `references` |
119
+ | **Knowledge** | `applies_to`, `caused_by`, `resolved_by`, `documents`, `violates`, `specifies`, `decided` |
120
+ | **VCS** | `co_changes_with`, `triggered_by`, `failed_in` |
121
+ | **Execution** | `executed_by`, `measured_by` |
122
+ | **Design** | `uses_token`, `declares_intent`, `violates_design`, `platform_binding` |
123
+ | **Traceability** | `requires`, `verified_by`, `tested_by` |
118
124
 
119
125
  Edges carry an optional `confidence` score (0-1) used by the FusionLayer for ranking.
120
126
 
package/dist/index.d.mts CHANGED
@@ -1,8 +1,8 @@
1
1
  import { z } from 'zod';
2
2
 
3
- declare const NODE_TYPES: readonly ["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint"];
3
+ declare const NODE_TYPES: readonly ["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint", "requirement"];
4
4
  type NodeType = (typeof NODE_TYPES)[number];
5
- declare const EDGE_TYPES: readonly ["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding"];
5
+ declare const EDGE_TYPES: readonly ["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding", "requires", "verified_by", "tested_by"];
6
6
  type EdgeType = (typeof EDGE_TYPES)[number];
7
7
  declare const OBSERVABILITY_TYPES: ReadonlySet<NodeType>;
8
8
  interface SourceLocation {
@@ -70,7 +70,7 @@ interface GraphMetadata {
70
70
  declare const CURRENT_SCHEMA_VERSION = 1;
71
71
  declare const GraphNodeSchema: z.ZodObject<{
72
72
  id: z.ZodString;
73
- type: z.ZodEnum<["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint"]>;
73
+ type: z.ZodEnum<["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint", "requirement"]>;
74
74
  name: z.ZodString;
75
75
  path: z.ZodOptional<z.ZodString>;
76
76
  location: z.ZodOptional<z.ZodObject<{
@@ -99,7 +99,7 @@ declare const GraphNodeSchema: z.ZodObject<{
99
99
  lastModified: z.ZodOptional<z.ZodString>;
100
100
  }, "strip", z.ZodTypeAny, {
101
101
  id: string;
102
- type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint";
102
+ type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint" | "requirement";
103
103
  name: string;
104
104
  metadata: Record<string, unknown>;
105
105
  path?: string | undefined;
@@ -116,7 +116,7 @@ declare const GraphNodeSchema: z.ZodObject<{
116
116
  lastModified?: string | undefined;
117
117
  }, {
118
118
  id: string;
119
- type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint";
119
+ type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint" | "requirement";
120
120
  name: string;
121
121
  metadata: Record<string, unknown>;
122
122
  path?: string | undefined;
@@ -135,17 +135,17 @@ declare const GraphNodeSchema: z.ZodObject<{
135
135
  declare const GraphEdgeSchema: z.ZodObject<{
136
136
  from: z.ZodString;
137
137
  to: z.ZodString;
138
- type: z.ZodEnum<["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding"]>;
138
+ type: z.ZodEnum<["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding", "requires", "verified_by", "tested_by"]>;
139
139
  confidence: z.ZodOptional<z.ZodNumber>;
140
140
  metadata: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
141
141
  }, "strip", z.ZodTypeAny, {
142
- type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding";
142
+ type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding" | "requires" | "verified_by" | "tested_by";
143
143
  from: string;
144
144
  to: string;
145
145
  metadata?: Record<string, unknown> | undefined;
146
146
  confidence?: number | undefined;
147
147
  }, {
148
- type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding";
148
+ type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding" | "requires" | "verified_by" | "tested_by";
149
149
  from: string;
150
150
  to: string;
151
151
  metadata?: Record<string, unknown> | undefined;
@@ -176,6 +176,8 @@ declare class GraphStore {
176
176
  addEdge(edge: GraphEdge): void;
177
177
  batchAddEdges(edges: readonly GraphEdge[]): void;
178
178
  getEdges(query: EdgeQuery): GraphEdge[];
179
+ /** Pick the most selective index to start from. */
180
+ private selectCandidates;
179
181
  getNeighbors(nodeId: string, direction?: 'outbound' | 'inbound' | 'both'): GraphNode[];
180
182
  get nodeCount(): number;
181
183
  get edgeCount(): number;
@@ -252,6 +254,9 @@ declare class ContextQL {
252
254
 
253
255
  declare function project(nodes: readonly GraphNode[], spec: ProjectionSpec | undefined): Partial<GraphNode>[];
254
256
 
257
+ type NodeCategory = 'tests' | 'docs' | 'code' | 'other';
258
+ /** Classify a graph node into an impact category. */
259
+ declare function classifyNodeCategory(node: GraphNode): NodeCategory;
255
260
  interface ImpactGroups {
256
261
  readonly tests: readonly GraphNode[];
257
262
  readonly docs: readonly GraphNode[];
@@ -301,6 +306,12 @@ declare class CodeIngestor {
301
306
  private computeMaxNesting;
302
307
  private countParameters;
303
308
  private detectLanguage;
309
+ /**
310
+ * Scan file contents for @req annotations and create verified_by edges
311
+ * linking requirement nodes to the annotated files.
312
+ * Format: // @req <feature-name>#<index>
313
+ */
314
+ private extractReqAnnotations;
304
315
  }
305
316
 
306
317
  type GitRunner = (rootDir: string, args: string[]) => Promise<string>;
@@ -348,6 +359,31 @@ declare class KnowledgeIngestor {
348
359
  private findMarkdownFiles;
349
360
  }
350
361
 
362
+ declare class RequirementIngestor {
363
+ private readonly store;
364
+ constructor(store: GraphStore);
365
+ /**
366
+ * Scan a specs directory for `<feature>/proposal.md` files,
367
+ * extract numbered requirements from recognized sections,
368
+ * and create requirement nodes with convention-based edges.
369
+ */
370
+ ingestSpecs(specsDir: string): Promise<IngestResult>;
371
+ /**
372
+ * Parse markdown content and extract numbered items from recognized sections.
373
+ */
374
+ private extractRequirements;
375
+ /**
376
+ * Convention-based linking: match requirement to code/test files
377
+ * by feature name in their path.
378
+ */
379
+ private linkByPathPattern;
380
+ /**
381
+ * Convention-based linking: match requirement text to code nodes
382
+ * by keyword overlap (function/class names appearing in requirement text).
383
+ */
384
+ private linkByKeywordOverlap;
385
+ }
386
+
351
387
  type HttpClient = (url: string, options?: {
352
388
  headers?: Record<string, string>;
353
389
  }) => Promise<{
@@ -810,6 +846,39 @@ declare class Assembler {
810
846
  checkCoverage(): GraphCoverageReport;
811
847
  }
812
848
 
849
+ interface TracedFile {
850
+ readonly path: string;
851
+ readonly confidence: number;
852
+ readonly method: 'convention' | 'annotation' | 'plan-file-map';
853
+ }
854
+ interface RequirementCoverage {
855
+ readonly requirementId: string;
856
+ readonly requirementName: string;
857
+ readonly index: number;
858
+ readonly codeFiles: readonly TracedFile[];
859
+ readonly testFiles: readonly TracedFile[];
860
+ readonly status: 'full' | 'code-only' | 'test-only' | 'none';
861
+ readonly maxConfidence: number;
862
+ }
863
+ interface TraceabilityResult {
864
+ readonly specPath: string;
865
+ readonly featureName: string;
866
+ readonly requirements: readonly RequirementCoverage[];
867
+ readonly summary: {
868
+ readonly total: number;
869
+ readonly withCode: number;
870
+ readonly withTests: number;
871
+ readonly fullyTraced: number;
872
+ readonly untraceable: number;
873
+ readonly coveragePercent: number;
874
+ };
875
+ }
876
+ interface TraceabilityOptions {
877
+ readonly specPath?: string;
878
+ readonly featureName?: string;
879
+ }
880
+ declare function queryTraceability(store: GraphStore, options?: TraceabilityOptions): TraceabilityResult[];
881
+
813
882
  interface GraphDependencyData {
814
883
  readonly nodes: readonly string[];
815
884
  readonly edges: ReadonlyArray<{
@@ -966,6 +1035,91 @@ declare class ConflictPredictor {
966
1035
  private generateVerdict;
967
1036
  }
968
1037
 
969
- declare const VERSION = "0.2.0";
1038
+ interface ProbabilityStrategy {
1039
+ /** Compute failure propagation probability for a single edge (0..1). */
1040
+ getEdgeProbability(edge: GraphEdge, fromNode: GraphNode, toNode: GraphNode): number;
1041
+ }
1042
+ interface CascadeSimulationOptions {
1043
+ /** Minimum cumulative probability to continue traversal. Default: 0.05 */
1044
+ readonly probabilityFloor?: number;
1045
+ /** Maximum BFS depth. Default: 10 */
1046
+ readonly maxDepth?: number;
1047
+ /** Filter to specific edge types. Default: all edge types. */
1048
+ readonly edgeTypes?: readonly string[];
1049
+ /** Pluggable probability strategy. Default: CompositeProbabilityStrategy. */
1050
+ readonly strategy?: ProbabilityStrategy;
1051
+ }
1052
+ interface CascadeNode {
1053
+ readonly nodeId: string;
1054
+ readonly name: string;
1055
+ readonly path?: string;
1056
+ readonly type: string;
1057
+ readonly cumulativeProbability: number;
1058
+ readonly depth: number;
1059
+ readonly incomingEdge: string;
1060
+ readonly parentId: string;
1061
+ }
1062
+ interface CascadeLayer {
1063
+ readonly depth: number;
1064
+ readonly nodes: readonly CascadeNode[];
1065
+ readonly categoryBreakdown: {
1066
+ readonly code: number;
1067
+ readonly tests: number;
1068
+ readonly docs: number;
1069
+ readonly other: number;
1070
+ };
1071
+ }
1072
+ interface CascadeResult {
1073
+ readonly sourceNodeId: string;
1074
+ readonly sourceName: string;
1075
+ readonly layers: readonly CascadeLayer[];
1076
+ readonly flatSummary: readonly CascadeNode[];
1077
+ readonly summary: {
1078
+ readonly totalAffected: number;
1079
+ readonly maxDepthReached: number;
1080
+ readonly highRisk: number;
1081
+ readonly mediumRisk: number;
1082
+ readonly lowRisk: number;
1083
+ readonly categoryBreakdown: {
1084
+ readonly code: number;
1085
+ readonly tests: number;
1086
+ readonly docs: number;
1087
+ readonly other: number;
1088
+ };
1089
+ readonly amplificationPoints: readonly string[];
1090
+ readonly truncated: boolean;
1091
+ };
1092
+ }
1093
+
1094
+ /**
1095
+ * Default probability strategy blending three signals:
1096
+ * - 50% edge type base weight
1097
+ * - 30% normalized change frequency of target node
1098
+ * - 20% normalized coupling strength of target node
1099
+ */
1100
+ declare class CompositeProbabilityStrategy implements ProbabilityStrategy {
1101
+ private readonly changeFreqMap;
1102
+ private readonly couplingMap;
1103
+ static readonly BASE_WEIGHTS: Record<string, number>;
1104
+ private static readonly FALLBACK_WEIGHT;
1105
+ private static readonly EDGE_TYPE_BLEND;
1106
+ private static readonly CHANGE_FREQ_BLEND;
1107
+ private static readonly COUPLING_BLEND;
1108
+ constructor(changeFreqMap: Map<string, number>, couplingMap: Map<string, number>);
1109
+ getEdgeProbability(edge: GraphEdge, _fromNode: GraphNode, toNode: GraphNode): number;
1110
+ }
1111
+
1112
+ declare class CascadeSimulator {
1113
+ private readonly store;
1114
+ constructor(store: GraphStore);
1115
+ simulate(sourceNodeId: string, options?: CascadeSimulationOptions): CascadeResult;
1116
+ private seedQueue;
1117
+ private runBfs;
1118
+ private expandNode;
1119
+ private buildDefaultStrategy;
1120
+ private buildResult;
1121
+ }
1122
+
1123
+ declare const VERSION = "0.4.0";
970
1124
 
971
- export { type AnomalyDetectionOptions, type AnomalyReport, type ArticulationPoint, type AskGraphResult, type AssembledContext, Assembler, CIConnector, CURRENT_SCHEMA_VERSION, type ClassificationResult, CodeIngestor, type ConflictDetail, type ConflictPrediction, ConflictPredictor, type ConflictSeverity, ConfluenceConnector, type ConnectorConfig, ContextQL, type ContextQLParams, type ContextQLResult, DesignConstraintAdapter, DesignIngestor, type DesignStrictness, type DesignViolation, EDGE_TYPES, type EdgeQuery, type EdgeType, EntityExtractor, EntityResolver, FusionLayer, type FusionResult, GitIngestor, type GitRunner, GraphAnomalyAdapter, type GraphBudget, GraphComplexityAdapter, type GraphComplexityHotspot, type GraphComplexityResult, type GraphConnector, GraphConstraintAdapter, GraphCouplingAdapter, type GraphCouplingFileData, type GraphCouplingResult, type GraphCoverageReport, type GraphDeadCodeData, type GraphDependencyData, type GraphDriftData, type GraphEdge, GraphEdgeSchema, GraphEntropyAdapter, GraphFeedbackAdapter, type GraphFilterResult, type GraphHarnessCheckData, type GraphImpactData, type GraphLayerViolation, type GraphMetadata, type GraphNode, GraphNodeSchema, type GraphSnapshotSummary, GraphStore, type HttpClient, INTENTS, type ImpactGroups, type IndependenceCheckParams, type IndependenceResult, type IngestResult, type Intent, IntentClassifier, JiraConnector, KnowledgeIngestor, type LinkResult, NODE_TYPES, type NodeQuery, type NodeType, OBSERVABILITY_TYPES, type OverlapDetail, type PairResult, type ProjectionSpec, type ResolvedEntity, ResponseFormatter, SlackConnector, type SourceLocation, type StatisticalOutlier, SyncManager, type SyncMetadata, type TaskDefinition, TaskIndependenceAnalyzer, TopologicalLinker, VERSION, type VectorSearchResult, VectorStore, askGraph, groupNodesByImpact, linkToCode, loadGraph, project, saveGraph };
1125
+ export { type AnomalyDetectionOptions, type AnomalyReport, type ArticulationPoint, type AskGraphResult, type AssembledContext, Assembler, CIConnector, CURRENT_SCHEMA_VERSION, type CascadeLayer, type CascadeNode, type CascadeResult, type CascadeSimulationOptions, CascadeSimulator, type ClassificationResult, CodeIngestor, CompositeProbabilityStrategy, type ConflictDetail, type ConflictPrediction, ConflictPredictor, type ConflictSeverity, ConfluenceConnector, type ConnectorConfig, ContextQL, type ContextQLParams, type ContextQLResult, DesignConstraintAdapter, DesignIngestor, type DesignStrictness, type DesignViolation, EDGE_TYPES, type EdgeQuery, type EdgeType, EntityExtractor, EntityResolver, FusionLayer, type FusionResult, GitIngestor, type GitRunner, GraphAnomalyAdapter, type GraphBudget, GraphComplexityAdapter, type GraphComplexityHotspot, type GraphComplexityResult, type GraphConnector, GraphConstraintAdapter, GraphCouplingAdapter, type GraphCouplingFileData, type GraphCouplingResult, type GraphCoverageReport, type GraphDeadCodeData, type GraphDependencyData, type GraphDriftData, type GraphEdge, GraphEdgeSchema, GraphEntropyAdapter, GraphFeedbackAdapter, type GraphFilterResult, type GraphHarnessCheckData, type GraphImpactData, type GraphLayerViolation, type GraphMetadata, type GraphNode, GraphNodeSchema, type GraphSnapshotSummary, GraphStore, type HttpClient, INTENTS, type ImpactGroups, type IndependenceCheckParams, type IndependenceResult, type IngestResult, type Intent, IntentClassifier, JiraConnector, KnowledgeIngestor, type LinkResult, NODE_TYPES, type NodeCategory, type NodeQuery, type NodeType, OBSERVABILITY_TYPES, type OverlapDetail, type PairResult, type ProbabilityStrategy, type ProjectionSpec, type RequirementCoverage, RequirementIngestor, type ResolvedEntity, ResponseFormatter, SlackConnector, type SourceLocation, type StatisticalOutlier, SyncManager, type SyncMetadata, type TaskDefinition, TaskIndependenceAnalyzer, TopologicalLinker, type TraceabilityOptions, type TraceabilityResult, type TracedFile, VERSION, type VectorSearchResult, VectorStore, askGraph, classifyNodeCategory, groupNodesByImpact, linkToCode, loadGraph, project, queryTraceability, saveGraph };
package/dist/index.d.ts CHANGED
@@ -1,8 +1,8 @@
1
1
  import { z } from 'zod';
2
2
 
3
- declare const NODE_TYPES: readonly ["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint"];
3
+ declare const NODE_TYPES: readonly ["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint", "requirement"];
4
4
  type NodeType = (typeof NODE_TYPES)[number];
5
- declare const EDGE_TYPES: readonly ["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding"];
5
+ declare const EDGE_TYPES: readonly ["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding", "requires", "verified_by", "tested_by"];
6
6
  type EdgeType = (typeof EDGE_TYPES)[number];
7
7
  declare const OBSERVABILITY_TYPES: ReadonlySet<NodeType>;
8
8
  interface SourceLocation {
@@ -70,7 +70,7 @@ interface GraphMetadata {
70
70
  declare const CURRENT_SCHEMA_VERSION = 1;
71
71
  declare const GraphNodeSchema: z.ZodObject<{
72
72
  id: z.ZodString;
73
- type: z.ZodEnum<["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint"]>;
73
+ type: z.ZodEnum<["repository", "module", "file", "class", "interface", "function", "method", "variable", "adr", "decision", "learning", "failure", "issue", "document", "skill", "conversation", "commit", "build", "test_result", "span", "metric", "log", "layer", "pattern", "constraint", "violation", "design_token", "aesthetic_intent", "design_constraint", "requirement"]>;
74
74
  name: z.ZodString;
75
75
  path: z.ZodOptional<z.ZodString>;
76
76
  location: z.ZodOptional<z.ZodObject<{
@@ -99,7 +99,7 @@ declare const GraphNodeSchema: z.ZodObject<{
99
99
  lastModified: z.ZodOptional<z.ZodString>;
100
100
  }, "strip", z.ZodTypeAny, {
101
101
  id: string;
102
- type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint";
102
+ type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint" | "requirement";
103
103
  name: string;
104
104
  metadata: Record<string, unknown>;
105
105
  path?: string | undefined;
@@ -116,7 +116,7 @@ declare const GraphNodeSchema: z.ZodObject<{
116
116
  lastModified?: string | undefined;
117
117
  }, {
118
118
  id: string;
119
- type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint";
119
+ type: "function" | "repository" | "module" | "file" | "class" | "interface" | "method" | "variable" | "adr" | "decision" | "learning" | "failure" | "issue" | "document" | "skill" | "conversation" | "commit" | "build" | "test_result" | "span" | "metric" | "log" | "layer" | "pattern" | "constraint" | "violation" | "design_token" | "aesthetic_intent" | "design_constraint" | "requirement";
120
120
  name: string;
121
121
  metadata: Record<string, unknown>;
122
122
  path?: string | undefined;
@@ -135,17 +135,17 @@ declare const GraphNodeSchema: z.ZodObject<{
135
135
  declare const GraphEdgeSchema: z.ZodObject<{
136
136
  from: z.ZodString;
137
137
  to: z.ZodString;
138
- type: z.ZodEnum<["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding"]>;
138
+ type: z.ZodEnum<["contains", "imports", "calls", "implements", "inherits", "references", "applies_to", "caused_by", "resolved_by", "documents", "violates", "specifies", "decided", "co_changes_with", "triggered_by", "failed_in", "executed_by", "measured_by", "uses_token", "declares_intent", "violates_design", "platform_binding", "requires", "verified_by", "tested_by"]>;
139
139
  confidence: z.ZodOptional<z.ZodNumber>;
140
140
  metadata: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnknown>>;
141
141
  }, "strip", z.ZodTypeAny, {
142
- type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding";
142
+ type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding" | "requires" | "verified_by" | "tested_by";
143
143
  from: string;
144
144
  to: string;
145
145
  metadata?: Record<string, unknown> | undefined;
146
146
  confidence?: number | undefined;
147
147
  }, {
148
- type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding";
148
+ type: "contains" | "imports" | "calls" | "implements" | "inherits" | "references" | "applies_to" | "caused_by" | "resolved_by" | "documents" | "violates" | "specifies" | "decided" | "co_changes_with" | "triggered_by" | "failed_in" | "executed_by" | "measured_by" | "uses_token" | "declares_intent" | "violates_design" | "platform_binding" | "requires" | "verified_by" | "tested_by";
149
149
  from: string;
150
150
  to: string;
151
151
  metadata?: Record<string, unknown> | undefined;
@@ -176,6 +176,8 @@ declare class GraphStore {
176
176
  addEdge(edge: GraphEdge): void;
177
177
  batchAddEdges(edges: readonly GraphEdge[]): void;
178
178
  getEdges(query: EdgeQuery): GraphEdge[];
179
+ /** Pick the most selective index to start from. */
180
+ private selectCandidates;
179
181
  getNeighbors(nodeId: string, direction?: 'outbound' | 'inbound' | 'both'): GraphNode[];
180
182
  get nodeCount(): number;
181
183
  get edgeCount(): number;
@@ -252,6 +254,9 @@ declare class ContextQL {
252
254
 
253
255
  declare function project(nodes: readonly GraphNode[], spec: ProjectionSpec | undefined): Partial<GraphNode>[];
254
256
 
257
+ type NodeCategory = 'tests' | 'docs' | 'code' | 'other';
258
+ /** Classify a graph node into an impact category. */
259
+ declare function classifyNodeCategory(node: GraphNode): NodeCategory;
255
260
  interface ImpactGroups {
256
261
  readonly tests: readonly GraphNode[];
257
262
  readonly docs: readonly GraphNode[];
@@ -301,6 +306,12 @@ declare class CodeIngestor {
301
306
  private computeMaxNesting;
302
307
  private countParameters;
303
308
  private detectLanguage;
309
+ /**
310
+ * Scan file contents for @req annotations and create verified_by edges
311
+ * linking requirement nodes to the annotated files.
312
+ * Format: // @req <feature-name>#<index>
313
+ */
314
+ private extractReqAnnotations;
304
315
  }
305
316
 
306
317
  type GitRunner = (rootDir: string, args: string[]) => Promise<string>;
@@ -348,6 +359,31 @@ declare class KnowledgeIngestor {
348
359
  private findMarkdownFiles;
349
360
  }
350
361
 
362
+ declare class RequirementIngestor {
363
+ private readonly store;
364
+ constructor(store: GraphStore);
365
+ /**
366
+ * Scan a specs directory for `<feature>/proposal.md` files,
367
+ * extract numbered requirements from recognized sections,
368
+ * and create requirement nodes with convention-based edges.
369
+ */
370
+ ingestSpecs(specsDir: string): Promise<IngestResult>;
371
+ /**
372
+ * Parse markdown content and extract numbered items from recognized sections.
373
+ */
374
+ private extractRequirements;
375
+ /**
376
+ * Convention-based linking: match requirement to code/test files
377
+ * by feature name in their path.
378
+ */
379
+ private linkByPathPattern;
380
+ /**
381
+ * Convention-based linking: match requirement text to code nodes
382
+ * by keyword overlap (function/class names appearing in requirement text).
383
+ */
384
+ private linkByKeywordOverlap;
385
+ }
386
+
351
387
  type HttpClient = (url: string, options?: {
352
388
  headers?: Record<string, string>;
353
389
  }) => Promise<{
@@ -810,6 +846,39 @@ declare class Assembler {
810
846
  checkCoverage(): GraphCoverageReport;
811
847
  }
812
848
 
849
+ interface TracedFile {
850
+ readonly path: string;
851
+ readonly confidence: number;
852
+ readonly method: 'convention' | 'annotation' | 'plan-file-map';
853
+ }
854
+ interface RequirementCoverage {
855
+ readonly requirementId: string;
856
+ readonly requirementName: string;
857
+ readonly index: number;
858
+ readonly codeFiles: readonly TracedFile[];
859
+ readonly testFiles: readonly TracedFile[];
860
+ readonly status: 'full' | 'code-only' | 'test-only' | 'none';
861
+ readonly maxConfidence: number;
862
+ }
863
+ interface TraceabilityResult {
864
+ readonly specPath: string;
865
+ readonly featureName: string;
866
+ readonly requirements: readonly RequirementCoverage[];
867
+ readonly summary: {
868
+ readonly total: number;
869
+ readonly withCode: number;
870
+ readonly withTests: number;
871
+ readonly fullyTraced: number;
872
+ readonly untraceable: number;
873
+ readonly coveragePercent: number;
874
+ };
875
+ }
876
+ interface TraceabilityOptions {
877
+ readonly specPath?: string;
878
+ readonly featureName?: string;
879
+ }
880
+ declare function queryTraceability(store: GraphStore, options?: TraceabilityOptions): TraceabilityResult[];
881
+
813
882
  interface GraphDependencyData {
814
883
  readonly nodes: readonly string[];
815
884
  readonly edges: ReadonlyArray<{
@@ -966,6 +1035,91 @@ declare class ConflictPredictor {
966
1035
  private generateVerdict;
967
1036
  }
968
1037
 
969
- declare const VERSION = "0.2.0";
1038
+ interface ProbabilityStrategy {
1039
+ /** Compute failure propagation probability for a single edge (0..1). */
1040
+ getEdgeProbability(edge: GraphEdge, fromNode: GraphNode, toNode: GraphNode): number;
1041
+ }
1042
+ interface CascadeSimulationOptions {
1043
+ /** Minimum cumulative probability to continue traversal. Default: 0.05 */
1044
+ readonly probabilityFloor?: number;
1045
+ /** Maximum BFS depth. Default: 10 */
1046
+ readonly maxDepth?: number;
1047
+ /** Filter to specific edge types. Default: all edge types. */
1048
+ readonly edgeTypes?: readonly string[];
1049
+ /** Pluggable probability strategy. Default: CompositeProbabilityStrategy. */
1050
+ readonly strategy?: ProbabilityStrategy;
1051
+ }
1052
+ interface CascadeNode {
1053
+ readonly nodeId: string;
1054
+ readonly name: string;
1055
+ readonly path?: string;
1056
+ readonly type: string;
1057
+ readonly cumulativeProbability: number;
1058
+ readonly depth: number;
1059
+ readonly incomingEdge: string;
1060
+ readonly parentId: string;
1061
+ }
1062
+ interface CascadeLayer {
1063
+ readonly depth: number;
1064
+ readonly nodes: readonly CascadeNode[];
1065
+ readonly categoryBreakdown: {
1066
+ readonly code: number;
1067
+ readonly tests: number;
1068
+ readonly docs: number;
1069
+ readonly other: number;
1070
+ };
1071
+ }
1072
+ interface CascadeResult {
1073
+ readonly sourceNodeId: string;
1074
+ readonly sourceName: string;
1075
+ readonly layers: readonly CascadeLayer[];
1076
+ readonly flatSummary: readonly CascadeNode[];
1077
+ readonly summary: {
1078
+ readonly totalAffected: number;
1079
+ readonly maxDepthReached: number;
1080
+ readonly highRisk: number;
1081
+ readonly mediumRisk: number;
1082
+ readonly lowRisk: number;
1083
+ readonly categoryBreakdown: {
1084
+ readonly code: number;
1085
+ readonly tests: number;
1086
+ readonly docs: number;
1087
+ readonly other: number;
1088
+ };
1089
+ readonly amplificationPoints: readonly string[];
1090
+ readonly truncated: boolean;
1091
+ };
1092
+ }
1093
+
1094
+ /**
1095
+ * Default probability strategy blending three signals:
1096
+ * - 50% edge type base weight
1097
+ * - 30% normalized change frequency of target node
1098
+ * - 20% normalized coupling strength of target node
1099
+ */
1100
+ declare class CompositeProbabilityStrategy implements ProbabilityStrategy {
1101
+ private readonly changeFreqMap;
1102
+ private readonly couplingMap;
1103
+ static readonly BASE_WEIGHTS: Record<string, number>;
1104
+ private static readonly FALLBACK_WEIGHT;
1105
+ private static readonly EDGE_TYPE_BLEND;
1106
+ private static readonly CHANGE_FREQ_BLEND;
1107
+ private static readonly COUPLING_BLEND;
1108
+ constructor(changeFreqMap: Map<string, number>, couplingMap: Map<string, number>);
1109
+ getEdgeProbability(edge: GraphEdge, _fromNode: GraphNode, toNode: GraphNode): number;
1110
+ }
1111
+
1112
+ declare class CascadeSimulator {
1113
+ private readonly store;
1114
+ constructor(store: GraphStore);
1115
+ simulate(sourceNodeId: string, options?: CascadeSimulationOptions): CascadeResult;
1116
+ private seedQueue;
1117
+ private runBfs;
1118
+ private expandNode;
1119
+ private buildDefaultStrategy;
1120
+ private buildResult;
1121
+ }
1122
+
1123
+ declare const VERSION = "0.4.0";
970
1124
 
971
- export { type AnomalyDetectionOptions, type AnomalyReport, type ArticulationPoint, type AskGraphResult, type AssembledContext, Assembler, CIConnector, CURRENT_SCHEMA_VERSION, type ClassificationResult, CodeIngestor, type ConflictDetail, type ConflictPrediction, ConflictPredictor, type ConflictSeverity, ConfluenceConnector, type ConnectorConfig, ContextQL, type ContextQLParams, type ContextQLResult, DesignConstraintAdapter, DesignIngestor, type DesignStrictness, type DesignViolation, EDGE_TYPES, type EdgeQuery, type EdgeType, EntityExtractor, EntityResolver, FusionLayer, type FusionResult, GitIngestor, type GitRunner, GraphAnomalyAdapter, type GraphBudget, GraphComplexityAdapter, type GraphComplexityHotspot, type GraphComplexityResult, type GraphConnector, GraphConstraintAdapter, GraphCouplingAdapter, type GraphCouplingFileData, type GraphCouplingResult, type GraphCoverageReport, type GraphDeadCodeData, type GraphDependencyData, type GraphDriftData, type GraphEdge, GraphEdgeSchema, GraphEntropyAdapter, GraphFeedbackAdapter, type GraphFilterResult, type GraphHarnessCheckData, type GraphImpactData, type GraphLayerViolation, type GraphMetadata, type GraphNode, GraphNodeSchema, type GraphSnapshotSummary, GraphStore, type HttpClient, INTENTS, type ImpactGroups, type IndependenceCheckParams, type IndependenceResult, type IngestResult, type Intent, IntentClassifier, JiraConnector, KnowledgeIngestor, type LinkResult, NODE_TYPES, type NodeQuery, type NodeType, OBSERVABILITY_TYPES, type OverlapDetail, type PairResult, type ProjectionSpec, type ResolvedEntity, ResponseFormatter, SlackConnector, type SourceLocation, type StatisticalOutlier, SyncManager, type SyncMetadata, type TaskDefinition, TaskIndependenceAnalyzer, TopologicalLinker, VERSION, type VectorSearchResult, VectorStore, askGraph, groupNodesByImpact, linkToCode, loadGraph, project, saveGraph };
1125
+ export { type AnomalyDetectionOptions, type AnomalyReport, type ArticulationPoint, type AskGraphResult, type AssembledContext, Assembler, CIConnector, CURRENT_SCHEMA_VERSION, type CascadeLayer, type CascadeNode, type CascadeResult, type CascadeSimulationOptions, CascadeSimulator, type ClassificationResult, CodeIngestor, CompositeProbabilityStrategy, type ConflictDetail, type ConflictPrediction, ConflictPredictor, type ConflictSeverity, ConfluenceConnector, type ConnectorConfig, ContextQL, type ContextQLParams, type ContextQLResult, DesignConstraintAdapter, DesignIngestor, type DesignStrictness, type DesignViolation, EDGE_TYPES, type EdgeQuery, type EdgeType, EntityExtractor, EntityResolver, FusionLayer, type FusionResult, GitIngestor, type GitRunner, GraphAnomalyAdapter, type GraphBudget, GraphComplexityAdapter, type GraphComplexityHotspot, type GraphComplexityResult, type GraphConnector, GraphConstraintAdapter, GraphCouplingAdapter, type GraphCouplingFileData, type GraphCouplingResult, type GraphCoverageReport, type GraphDeadCodeData, type GraphDependencyData, type GraphDriftData, type GraphEdge, GraphEdgeSchema, GraphEntropyAdapter, GraphFeedbackAdapter, type GraphFilterResult, type GraphHarnessCheckData, type GraphImpactData, type GraphLayerViolation, type GraphMetadata, type GraphNode, GraphNodeSchema, type GraphSnapshotSummary, GraphStore, type HttpClient, INTENTS, type ImpactGroups, type IndependenceCheckParams, type IndependenceResult, type IngestResult, type Intent, IntentClassifier, JiraConnector, KnowledgeIngestor, type LinkResult, NODE_TYPES, type NodeCategory, type NodeQuery, type NodeType, OBSERVABILITY_TYPES, type OverlapDetail, type PairResult, type ProbabilityStrategy, type ProjectionSpec, type RequirementCoverage, RequirementIngestor, type ResolvedEntity, ResponseFormatter, SlackConnector, type SourceLocation, type StatisticalOutlier, SyncManager, type SyncMetadata, type TaskDefinition, TaskIndependenceAnalyzer, TopologicalLinker, type TraceabilityOptions, type TraceabilityResult, type TracedFile, VERSION, type VectorSearchResult, VectorStore, askGraph, classifyNodeCategory, groupNodesByImpact, linkToCode, loadGraph, project, queryTraceability, saveGraph };