@grafema/core 0.1.1-alpha → 0.2.0-beta
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/dist/Orchestrator.d.ts +7 -0
- package/dist/Orchestrator.d.ts.map +1 -1
- package/dist/Orchestrator.js +25 -3
- package/dist/config/ConfigLoader.d.ts +18 -0
- package/dist/config/ConfigLoader.d.ts.map +1 -1
- package/dist/config/ConfigLoader.js +65 -3
- package/dist/core/FileExplainer.d.ts +101 -0
- package/dist/core/FileExplainer.d.ts.map +1 -0
- package/dist/core/FileExplainer.js +139 -0
- package/dist/core/NodeFactory.d.ts +44 -5
- package/dist/core/NodeFactory.d.ts.map +1 -1
- package/dist/core/NodeFactory.js +52 -7
- package/dist/core/nodes/ArrayLiteralNode.d.ts.map +1 -1
- package/dist/core/nodes/ArrayLiteralNode.js +4 -2
- package/dist/core/nodes/BranchNode.d.ts +41 -0
- package/dist/core/nodes/BranchNode.d.ts.map +1 -0
- package/dist/core/nodes/BranchNode.js +82 -0
- package/dist/core/nodes/CallSiteNode.d.ts +2 -2
- package/dist/core/nodes/CallSiteNode.d.ts.map +1 -1
- package/dist/core/nodes/CallSiteNode.js +9 -5
- package/dist/core/nodes/CaseNode.d.ts +43 -0
- package/dist/core/nodes/CaseNode.d.ts.map +1 -0
- package/dist/core/nodes/CaseNode.js +81 -0
- package/dist/core/nodes/ClassNode.d.ts +2 -2
- package/dist/core/nodes/ClassNode.d.ts.map +1 -1
- package/dist/core/nodes/ClassNode.js +8 -4
- package/dist/core/nodes/ConstantNode.d.ts +2 -2
- package/dist/core/nodes/ConstantNode.d.ts.map +1 -1
- package/dist/core/nodes/ConstantNode.js +6 -4
- package/dist/core/nodes/ConstructorCallNode.d.ts +51 -0
- package/dist/core/nodes/ConstructorCallNode.d.ts.map +1 -0
- package/dist/core/nodes/ConstructorCallNode.js +171 -0
- package/dist/core/nodes/DatabaseQueryNode.d.ts +3 -2
- package/dist/core/nodes/DatabaseQueryNode.d.ts.map +1 -1
- package/dist/core/nodes/DatabaseQueryNode.js +5 -2
- package/dist/core/nodes/DecoratorNode.d.ts +2 -2
- package/dist/core/nodes/DecoratorNode.d.ts.map +1 -1
- package/dist/core/nodes/DecoratorNode.js +5 -3
- package/dist/core/nodes/EnumNode.d.ts +2 -2
- package/dist/core/nodes/EnumNode.d.ts.map +1 -1
- package/dist/core/nodes/EnumNode.js +5 -3
- package/dist/core/nodes/EventListenerNode.d.ts +4 -4
- package/dist/core/nodes/EventListenerNode.d.ts.map +1 -1
- package/dist/core/nodes/EventListenerNode.js +7 -4
- package/dist/core/nodes/ExportNode.d.ts +2 -2
- package/dist/core/nodes/ExportNode.d.ts.map +1 -1
- package/dist/core/nodes/ExportNode.js +8 -4
- package/dist/core/nodes/ExpressionNode.d.ts +2 -2
- package/dist/core/nodes/ExpressionNode.d.ts.map +1 -1
- package/dist/core/nodes/ExpressionNode.js +6 -4
- package/dist/core/nodes/ExternalModuleNode.d.ts +4 -0
- package/dist/core/nodes/ExternalModuleNode.d.ts.map +1 -1
- package/dist/core/nodes/ExternalModuleNode.js +10 -2
- package/dist/core/nodes/HttpRequestNode.d.ts +4 -4
- package/dist/core/nodes/HttpRequestNode.d.ts.map +1 -1
- package/dist/core/nodes/HttpRequestNode.js +7 -4
- package/dist/core/nodes/ImportNode.d.ts +10 -2
- package/dist/core/nodes/ImportNode.d.ts.map +1 -1
- package/dist/core/nodes/ImportNode.js +21 -4
- package/dist/core/nodes/InterfaceNode.d.ts +2 -2
- package/dist/core/nodes/InterfaceNode.d.ts.map +1 -1
- package/dist/core/nodes/InterfaceNode.js +5 -3
- package/dist/core/nodes/LiteralNode.d.ts +2 -2
- package/dist/core/nodes/LiteralNode.d.ts.map +1 -1
- package/dist/core/nodes/LiteralNode.js +6 -4
- package/dist/core/nodes/MethodCallNode.d.ts +2 -2
- package/dist/core/nodes/MethodCallNode.d.ts.map +1 -1
- package/dist/core/nodes/MethodCallNode.js +9 -5
- package/dist/core/nodes/MethodNode.d.ts +2 -2
- package/dist/core/nodes/MethodNode.d.ts.map +1 -1
- package/dist/core/nodes/MethodNode.js +8 -4
- package/dist/core/nodes/ObjectLiteralNode.d.ts.map +1 -1
- package/dist/core/nodes/ObjectLiteralNode.js +4 -2
- package/dist/core/nodes/ParameterNode.d.ts +2 -2
- package/dist/core/nodes/ParameterNode.d.ts.map +1 -1
- package/dist/core/nodes/ParameterNode.js +5 -3
- package/dist/core/nodes/TypeNode.d.ts +2 -2
- package/dist/core/nodes/TypeNode.d.ts.map +1 -1
- package/dist/core/nodes/TypeNode.js +5 -3
- package/dist/core/nodes/VariableDeclarationNode.d.ts +2 -2
- package/dist/core/nodes/VariableDeclarationNode.d.ts.map +1 -1
- package/dist/core/nodes/VariableDeclarationNode.js +9 -5
- package/dist/core/nodes/index.d.ts +3 -0
- package/dist/core/nodes/index.d.ts.map +1 -1
- package/dist/core/nodes/index.js +3 -0
- package/dist/data/builtins/BuiltinRegistry.d.ts +78 -0
- package/dist/data/builtins/BuiltinRegistry.d.ts.map +1 -0
- package/dist/data/builtins/BuiltinRegistry.js +110 -0
- package/dist/data/builtins/definitions.d.ts +28 -0
- package/dist/data/builtins/definitions.d.ts.map +1 -0
- package/dist/data/builtins/definitions.js +250 -0
- package/dist/data/builtins/index.d.ts +10 -0
- package/dist/data/builtins/index.d.ts.map +1 -0
- package/dist/data/builtins/index.js +8 -0
- package/dist/data/builtins/jsGlobals.d.ts +18 -0
- package/dist/data/builtins/jsGlobals.d.ts.map +1 -0
- package/dist/data/builtins/jsGlobals.js +26 -0
- package/dist/data/builtins/types.d.ts +34 -0
- package/dist/data/builtins/types.d.ts.map +1 -0
- package/dist/data/builtins/types.js +7 -0
- package/dist/data/globals/definitions.d.ts +27 -0
- package/dist/data/globals/definitions.d.ts.map +1 -0
- package/dist/data/globals/definitions.js +117 -0
- package/dist/data/globals/index.d.ts +36 -0
- package/dist/data/globals/index.d.ts.map +1 -0
- package/dist/data/globals/index.js +52 -0
- package/dist/diagnostics/DiagnosticReporter.d.ts +23 -0
- package/dist/diagnostics/DiagnosticReporter.d.ts.map +1 -1
- package/dist/diagnostics/DiagnosticReporter.js +88 -0
- package/dist/diagnostics/index.d.ts +1 -1
- package/dist/diagnostics/index.d.ts.map +1 -1
- package/dist/errors/GrafemaError.d.ts +43 -0
- package/dist/errors/GrafemaError.d.ts.map +1 -1
- package/dist/errors/GrafemaError.js +50 -0
- package/dist/index.d.ts +17 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +17 -1
- package/dist/plugins/analysis/DatabaseAnalyzer.d.ts.map +1 -1
- package/dist/plugins/analysis/DatabaseAnalyzer.js +3 -2
- package/dist/plugins/analysis/ExpressAnalyzer.d.ts.map +1 -1
- package/dist/plugins/analysis/ExpressAnalyzer.js +3 -1
- package/dist/plugins/analysis/ExpressResponseAnalyzer.d.ts +148 -0
- package/dist/plugins/analysis/ExpressResponseAnalyzer.d.ts.map +1 -0
- package/dist/plugins/analysis/ExpressResponseAnalyzer.js +495 -0
- package/dist/plugins/analysis/ExpressRouteAnalyzer.d.ts.map +1 -1
- package/dist/plugins/analysis/ExpressRouteAnalyzer.js +53 -18
- package/dist/plugins/analysis/FetchAnalyzer.d.ts +40 -0
- package/dist/plugins/analysis/FetchAnalyzer.d.ts.map +1 -1
- package/dist/plugins/analysis/FetchAnalyzer.js +163 -15
- package/dist/plugins/analysis/JSASTAnalyzer.d.ts +157 -26
- package/dist/plugins/analysis/JSASTAnalyzer.d.ts.map +1 -1
- package/dist/plugins/analysis/JSASTAnalyzer.js +2418 -191
- package/dist/plugins/analysis/RustAnalyzer.js +4 -4
- package/dist/plugins/analysis/SQLiteAnalyzer.d.ts.map +1 -1
- package/dist/plugins/analysis/SQLiteAnalyzer.js +4 -2
- package/dist/plugins/analysis/SocketIOAnalyzer.d.ts +9 -0
- package/dist/plugins/analysis/SocketIOAnalyzer.d.ts.map +1 -1
- package/dist/plugins/analysis/SocketIOAnalyzer.js +91 -7
- package/dist/plugins/analysis/ast/GraphBuilder.d.ts +173 -0
- package/dist/plugins/analysis/ast/GraphBuilder.d.ts.map +1 -1
- package/dist/plugins/analysis/ast/GraphBuilder.js +1256 -65
- package/dist/plugins/analysis/ast/types.d.ts +294 -0
- package/dist/plugins/analysis/ast/types.d.ts.map +1 -1
- package/dist/plugins/analysis/ast/visitors/ASTVisitor.d.ts +5 -1
- package/dist/plugins/analysis/ast/visitors/ASTVisitor.d.ts.map +1 -1
- package/dist/plugins/analysis/ast/visitors/CallExpressionVisitor.d.ts +1 -0
- package/dist/plugins/analysis/ast/visitors/CallExpressionVisitor.d.ts.map +1 -1
- package/dist/plugins/analysis/ast/visitors/CallExpressionVisitor.js +12 -1
- package/dist/plugins/analysis/ast/visitors/FunctionVisitor.d.ts +10 -0
- package/dist/plugins/analysis/ast/visitors/FunctionVisitor.d.ts.map +1 -1
- package/dist/plugins/analysis/ast/visitors/FunctionVisitor.js +62 -0
- package/dist/plugins/analysis/ast/visitors/ImportExportVisitor.d.ts +4 -0
- package/dist/plugins/analysis/ast/visitors/ImportExportVisitor.d.ts.map +1 -1
- package/dist/plugins/analysis/ast/visitors/ImportExportVisitor.js +101 -0
- package/dist/plugins/analysis/ast/visitors/VariableVisitor.d.ts +16 -1
- package/dist/plugins/analysis/ast/visitors/VariableVisitor.d.ts.map +1 -1
- package/dist/plugins/analysis/ast/visitors/VariableVisitor.js +233 -39
- package/dist/plugins/discovery/WorkspaceDiscovery.d.ts.map +1 -1
- package/dist/plugins/discovery/WorkspaceDiscovery.js +9 -4
- package/dist/plugins/enrichment/AliasTracker.d.ts.map +1 -1
- package/dist/plugins/enrichment/AliasTracker.js +16 -1
- package/dist/plugins/enrichment/ArgumentParameterLinker.d.ts +32 -0
- package/dist/plugins/enrichment/ArgumentParameterLinker.d.ts.map +1 -0
- package/dist/plugins/enrichment/ArgumentParameterLinker.js +175 -0
- package/dist/plugins/enrichment/ClosureCaptureEnricher.d.ts +51 -0
- package/dist/plugins/enrichment/ClosureCaptureEnricher.d.ts.map +1 -0
- package/dist/plugins/enrichment/ClosureCaptureEnricher.js +205 -0
- package/dist/plugins/enrichment/ExternalCallResolver.d.ts +42 -0
- package/dist/plugins/enrichment/ExternalCallResolver.d.ts.map +1 -0
- package/dist/plugins/enrichment/ExternalCallResolver.js +213 -0
- package/dist/plugins/enrichment/FunctionCallResolver.d.ts +58 -0
- package/dist/plugins/enrichment/FunctionCallResolver.d.ts.map +1 -0
- package/dist/plugins/enrichment/FunctionCallResolver.js +340 -0
- package/dist/plugins/enrichment/HTTPConnectionEnricher.d.ts +16 -3
- package/dist/plugins/enrichment/HTTPConnectionEnricher.d.ts.map +1 -1
- package/dist/plugins/enrichment/HTTPConnectionEnricher.js +64 -20
- package/dist/plugins/enrichment/MethodCallResolver.d.ts.map +1 -1
- package/dist/plugins/enrichment/MethodCallResolver.js +15 -1
- package/dist/plugins/enrichment/MountPointResolver.d.ts +14 -12
- package/dist/plugins/enrichment/MountPointResolver.d.ts.map +1 -1
- package/dist/plugins/enrichment/MountPointResolver.js +172 -151
- package/dist/plugins/enrichment/NodejsBuiltinsResolver.d.ts +44 -0
- package/dist/plugins/enrichment/NodejsBuiltinsResolver.d.ts.map +1 -0
- package/dist/plugins/enrichment/NodejsBuiltinsResolver.js +271 -0
- package/dist/plugins/enrichment/ValueDomainAnalyzer.d.ts +5 -27
- package/dist/plugins/enrichment/ValueDomainAnalyzer.d.ts.map +1 -1
- package/dist/plugins/enrichment/ValueDomainAnalyzer.js +62 -139
- package/dist/plugins/indexing/JSModuleIndexer.d.ts +15 -0
- package/dist/plugins/indexing/JSModuleIndexer.d.ts.map +1 -1
- package/dist/plugins/indexing/JSModuleIndexer.js +58 -0
- package/dist/plugins/indexing/RustModuleIndexer.d.ts +1 -1
- package/dist/plugins/indexing/RustModuleIndexer.js +4 -4
- package/dist/plugins/validation/BrokenImportValidator.d.ts +31 -0
- package/dist/plugins/validation/BrokenImportValidator.d.ts.map +1 -0
- package/dist/plugins/validation/BrokenImportValidator.js +249 -0
- package/dist/plugins/validation/CallResolverValidator.d.ts +21 -10
- package/dist/plugins/validation/CallResolverValidator.d.ts.map +1 -1
- package/dist/plugins/validation/CallResolverValidator.js +101 -76
- package/dist/plugins/validation/DataFlowValidator.d.ts.map +1 -1
- package/dist/plugins/validation/DataFlowValidator.js +49 -41
- package/dist/plugins/validation/GraphConnectivityValidator.d.ts.map +1 -1
- package/dist/plugins/validation/GraphConnectivityValidator.js +25 -1
- package/dist/plugins/validation/SQLInjectionValidator.d.ts.map +1 -1
- package/dist/plugins/validation/SQLInjectionValidator.js +2 -3
- package/dist/queries/findCallsInFunction.d.ts +52 -0
- package/dist/queries/findCallsInFunction.d.ts.map +1 -0
- package/dist/queries/findCallsInFunction.js +135 -0
- package/dist/queries/findContainingFunction.d.ts +45 -0
- package/dist/queries/findContainingFunction.d.ts.map +1 -0
- package/dist/queries/findContainingFunction.js +54 -0
- package/dist/queries/index.d.ts +14 -0
- package/dist/queries/index.d.ts.map +1 -0
- package/dist/queries/index.js +11 -0
- package/dist/queries/traceValues.d.ts +70 -0
- package/dist/queries/traceValues.d.ts.map +1 -0
- package/dist/queries/traceValues.js +299 -0
- package/dist/queries/types.d.ts +163 -0
- package/dist/queries/types.d.ts.map +1 -0
- package/dist/queries/types.js +9 -0
- package/dist/schema/GraphSchemaExtractor.d.ts +53 -0
- package/dist/schema/GraphSchemaExtractor.d.ts.map +1 -0
- package/dist/schema/GraphSchemaExtractor.js +124 -0
- package/dist/schema/InterfaceSchemaExtractor.d.ts +73 -0
- package/dist/schema/InterfaceSchemaExtractor.d.ts.map +1 -0
- package/dist/schema/InterfaceSchemaExtractor.js +112 -0
- package/dist/schema/index.d.ts +5 -0
- package/dist/schema/index.d.ts.map +1 -0
- package/dist/schema/index.js +2 -0
- package/dist/storage/backends/RFDBServerBackend.d.ts +12 -18
- package/dist/storage/backends/RFDBServerBackend.d.ts.map +1 -1
- package/dist/storage/backends/RFDBServerBackend.js +41 -52
- package/dist/storage/backends/typeValidation.d.ts.map +1 -1
- package/dist/storage/backends/typeValidation.js +1 -0
- package/package.json +3 -3
- package/src/Orchestrator.ts +35 -3
- package/src/config/ConfigLoader.ts +94 -3
- package/src/core/FileExplainer.ts +179 -0
- package/src/core/NodeFactory.ts +72 -8
- package/src/core/nodes/ArrayLiteralNode.ts +3 -2
- package/src/core/nodes/BranchNode.ts +113 -0
- package/src/core/nodes/CallSiteNode.ts +7 -5
- package/src/core/nodes/CaseNode.ts +123 -0
- package/src/core/nodes/ClassNode.ts +6 -4
- package/src/core/nodes/ConstantNode.ts +5 -4
- package/src/core/nodes/ConstructorCallNode.ts +217 -0
- package/src/core/nodes/DatabaseQueryNode.ts +5 -1
- package/src/core/nodes/DecoratorNode.ts +4 -3
- package/src/core/nodes/EnumNode.ts +4 -3
- package/src/core/nodes/EventListenerNode.ts +7 -4
- package/src/core/nodes/ExportNode.ts +6 -4
- package/src/core/nodes/ExpressionNode.ts +5 -4
- package/src/core/nodes/ExternalModuleNode.ts +11 -2
- package/src/core/nodes/HttpRequestNode.ts +7 -4
- package/src/core/nodes/ImportNode.ts +31 -4
- package/src/core/nodes/InterfaceNode.ts +4 -3
- package/src/core/nodes/LiteralNode.ts +5 -4
- package/src/core/nodes/MethodCallNode.ts +7 -5
- package/src/core/nodes/MethodNode.ts +6 -4
- package/src/core/nodes/ObjectLiteralNode.ts +3 -2
- package/src/core/nodes/ParameterNode.ts +4 -3
- package/src/core/nodes/TypeNode.ts +4 -3
- package/src/core/nodes/VariableDeclarationNode.ts +7 -5
- package/src/core/nodes/index.ts +3 -0
- package/src/data/builtins/BuiltinRegistry.ts +124 -0
- package/src/data/builtins/definitions.ts +267 -0
- package/src/data/builtins/index.ts +10 -0
- package/src/data/builtins/jsGlobals.ts +28 -0
- package/src/data/builtins/types.ts +36 -0
- package/src/data/globals/definitions.ts +156 -0
- package/src/data/globals/index.ts +66 -0
- package/src/diagnostics/DiagnosticReporter.ts +120 -0
- package/src/diagnostics/index.ts +1 -1
- package/src/errors/GrafemaError.ts +65 -0
- package/src/index.ts +45 -0
- package/src/plugins/analysis/DatabaseAnalyzer.ts +4 -2
- package/src/plugins/analysis/ExpressAnalyzer.ts +5 -1
- package/src/plugins/analysis/ExpressResponseAnalyzer.ts +636 -0
- package/src/plugins/analysis/ExpressRouteAnalyzer.ts +57 -18
- package/src/plugins/analysis/FetchAnalyzer.ts +204 -16
- package/src/plugins/analysis/JSASTAnalyzer.ts +2958 -260
- package/src/plugins/analysis/RustAnalyzer.ts +4 -4
- package/src/plugins/analysis/SQLiteAnalyzer.ts +5 -2
- package/src/plugins/analysis/SocketIOAnalyzer.ts +121 -7
- package/src/plugins/analysis/ast/GraphBuilder.ts +1578 -70
- package/src/plugins/analysis/ast/types.ts +387 -0
- package/src/plugins/analysis/ast/visitors/ASTVisitor.ts +8 -0
- package/src/plugins/analysis/ast/visitors/CallExpressionVisitor.ts +16 -1
- package/src/plugins/analysis/ast/visitors/FunctionVisitor.ts +77 -2
- package/src/plugins/analysis/ast/visitors/ImportExportVisitor.ts +112 -1
- package/src/plugins/analysis/ast/visitors/VariableVisitor.ts +272 -47
- package/src/plugins/discovery/WorkspaceDiscovery.ts +11 -4
- package/src/plugins/enrichment/AliasTracker.ts +22 -1
- package/src/plugins/enrichment/ArgumentParameterLinker.ts +240 -0
- package/src/plugins/enrichment/ClosureCaptureEnricher.ts +267 -0
- package/src/plugins/enrichment/ExternalCallResolver.ts +262 -0
- package/src/plugins/enrichment/FunctionCallResolver.ts +456 -0
- package/src/plugins/enrichment/HTTPConnectionEnricher.ts +70 -20
- package/src/plugins/enrichment/MethodCallResolver.ts +21 -1
- package/src/plugins/enrichment/MountPointResolver.ts +206 -198
- package/src/plugins/enrichment/NodejsBuiltinsResolver.ts +365 -0
- package/src/plugins/enrichment/ValueDomainAnalyzer.ts +67 -184
- package/src/plugins/indexing/JSModuleIndexer.ts +66 -0
- package/src/plugins/indexing/RustModuleIndexer.ts +4 -4
- package/src/plugins/validation/BrokenImportValidator.ts +325 -0
- package/src/plugins/validation/CallResolverValidator.ts +129 -109
- package/src/plugins/validation/DataFlowValidator.ts +75 -58
- package/src/plugins/validation/GraphConnectivityValidator.ts +39 -1
- package/src/plugins/validation/SQLInjectionValidator.ts +2 -5
- package/src/queries/README.md +46 -0
- package/src/queries/findCallsInFunction.ts +206 -0
- package/src/queries/findContainingFunction.ts +83 -0
- package/src/queries/index.ts +23 -0
- package/src/queries/traceValues.ts +398 -0
- package/src/queries/types.ts +187 -0
- package/src/schema/GraphSchemaExtractor.ts +177 -0
- package/src/schema/InterfaceSchemaExtractor.ts +173 -0
- package/src/schema/index.ts +5 -0
- package/src/storage/backends/RFDBServerBackend.ts +58 -70
- package/src/storage/backends/typeValidation.ts +1 -0
|
@@ -0,0 +1,262 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ExternalCallResolver - creates CALLS edges for external package calls (REG-226)
|
|
3
|
+
*
|
|
4
|
+
* This enrichment plugin runs AFTER FunctionCallResolver (priority 70 vs 80) and:
|
|
5
|
+
* 1. Finds CALL nodes without CALLS edges (excluding method calls)
|
|
6
|
+
* 2. For each, looks for IMPORT with matching local name in same file
|
|
7
|
+
* 3. If import source is non-relative (external package), creates CALLS edge to EXTERNAL_MODULE
|
|
8
|
+
* 4. Recognizes JS built-in global functions (no edge needed, just counts them)
|
|
9
|
+
*
|
|
10
|
+
* CREATES NODES:
|
|
11
|
+
* - EXTERNAL_MODULE (for external packages like lodash, @tanstack/react-query)
|
|
12
|
+
*
|
|
13
|
+
* CREATES EDGES:
|
|
14
|
+
* - CALL -> CALLS -> EXTERNAL_MODULE (for imported external functions)
|
|
15
|
+
*
|
|
16
|
+
* Architecture:
|
|
17
|
+
* - Runs after FunctionCallResolver handles relative imports
|
|
18
|
+
* - Skips method calls (have 'object' attribute)
|
|
19
|
+
* - Skips already resolved calls (have CALLS edge)
|
|
20
|
+
* - Creates EXTERNAL_MODULE nodes lazily (only when needed)
|
|
21
|
+
* - Uses import index for O(1) lookups
|
|
22
|
+
*/
|
|
23
|
+
|
|
24
|
+
import { Plugin, createSuccessResult } from '../Plugin.js';
|
|
25
|
+
import type { PluginContext, PluginResult, PluginMetadata } from '../Plugin.js';
|
|
26
|
+
import type { BaseNodeRecord } from '@grafema/types';
|
|
27
|
+
import { JS_GLOBAL_FUNCTIONS } from '../../data/builtins/index.js';
|
|
28
|
+
|
|
29
|
+
// === INTERFACES ===
|
|
30
|
+
|
|
31
|
+
interface CallNode extends BaseNodeRecord {
|
|
32
|
+
object?: string; // If present, this is a method call - skip
|
|
33
|
+
isDynamic?: boolean; // If true, call target is computed at runtime
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
interface ImportNode extends BaseNodeRecord {
|
|
37
|
+
source?: string;
|
|
38
|
+
importType?: string; // 'default' | 'named' | 'namespace'
|
|
39
|
+
imported?: string; // Original name in source file
|
|
40
|
+
local?: string; // Local binding name
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
// === PLUGIN CLASS ===
|
|
44
|
+
|
|
45
|
+
export class ExternalCallResolver extends Plugin {
|
|
46
|
+
get metadata(): PluginMetadata {
|
|
47
|
+
return {
|
|
48
|
+
name: 'ExternalCallResolver',
|
|
49
|
+
phase: 'ENRICHMENT',
|
|
50
|
+
priority: 70, // After FunctionCallResolver (80)
|
|
51
|
+
creates: {
|
|
52
|
+
nodes: ['EXTERNAL_MODULE'],
|
|
53
|
+
edges: ['CALLS']
|
|
54
|
+
},
|
|
55
|
+
dependencies: ['FunctionCallResolver'] // Requires relative imports to be resolved first
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
async execute(context: PluginContext): Promise<PluginResult> {
|
|
60
|
+
const { graph, onProgress } = context;
|
|
61
|
+
const logger = this.log(context);
|
|
62
|
+
|
|
63
|
+
logger.info('Starting external call resolution');
|
|
64
|
+
|
|
65
|
+
const startTime = Date.now();
|
|
66
|
+
|
|
67
|
+
// Step 1: Build Import Index - Map<file:local, ImportNode>
|
|
68
|
+
// Only index non-relative imports (external packages)
|
|
69
|
+
const importIndex = new Map<string, ImportNode>();
|
|
70
|
+
for await (const node of graph.queryNodes({ nodeType: 'IMPORT' })) {
|
|
71
|
+
const imp = node as ImportNode;
|
|
72
|
+
if (!imp.file || !imp.local || !imp.source) continue;
|
|
73
|
+
|
|
74
|
+
// Only index external imports (non-relative)
|
|
75
|
+
const isRelative = imp.source.startsWith('./') || imp.source.startsWith('../');
|
|
76
|
+
if (isRelative) continue;
|
|
77
|
+
|
|
78
|
+
const key = `${imp.file}:${imp.local}`;
|
|
79
|
+
importIndex.set(key, imp);
|
|
80
|
+
}
|
|
81
|
+
logger.debug('Indexed external imports', { count: importIndex.size });
|
|
82
|
+
|
|
83
|
+
// Step 2: Collect unresolved CALL nodes (excluding method calls)
|
|
84
|
+
const callsToProcess: CallNode[] = [];
|
|
85
|
+
for await (const node of graph.queryNodes({ nodeType: 'CALL' })) {
|
|
86
|
+
const call = node as CallNode;
|
|
87
|
+
|
|
88
|
+
// Skip method calls (have object attribute)
|
|
89
|
+
if (call.object) continue;
|
|
90
|
+
|
|
91
|
+
// Skip if already has CALLS edge
|
|
92
|
+
const existingEdges = await graph.getOutgoingEdges(call.id, ['CALLS']);
|
|
93
|
+
if (existingEdges.length > 0) continue;
|
|
94
|
+
|
|
95
|
+
callsToProcess.push(call);
|
|
96
|
+
}
|
|
97
|
+
logger.info('Found calls to process', { count: callsToProcess.length });
|
|
98
|
+
|
|
99
|
+
// Step 3: Track created EXTERNAL_MODULE nodes to avoid duplicates
|
|
100
|
+
const createdExternalModules = new Set<string>();
|
|
101
|
+
|
|
102
|
+
// Pre-check existing EXTERNAL_MODULE nodes
|
|
103
|
+
for await (const node of graph.queryNodes({ nodeType: 'EXTERNAL_MODULE' })) {
|
|
104
|
+
createdExternalModules.add(node.id as string);
|
|
105
|
+
}
|
|
106
|
+
logger.debug('Existing EXTERNAL_MODULE nodes', { count: createdExternalModules.size });
|
|
107
|
+
|
|
108
|
+
// Step 4: Resolution
|
|
109
|
+
let nodesCreated = 0;
|
|
110
|
+
let edgesCreated = 0;
|
|
111
|
+
let callsProcessed = 0;
|
|
112
|
+
let externalResolved = 0;
|
|
113
|
+
let builtinResolved = 0;
|
|
114
|
+
const unresolvedByReason: Record<string, number> = {
|
|
115
|
+
unknown: 0,
|
|
116
|
+
dynamic: 0
|
|
117
|
+
};
|
|
118
|
+
|
|
119
|
+
for (const callNode of callsToProcess) {
|
|
120
|
+
callsProcessed++;
|
|
121
|
+
|
|
122
|
+
// Progress reporting
|
|
123
|
+
if (onProgress && callsProcessed % 100 === 0) {
|
|
124
|
+
onProgress({
|
|
125
|
+
phase: 'enrichment',
|
|
126
|
+
currentPlugin: 'ExternalCallResolver',
|
|
127
|
+
message: `Processing calls ${callsProcessed}/${callsToProcess.length}`,
|
|
128
|
+
totalFiles: callsToProcess.length,
|
|
129
|
+
processedFiles: callsProcessed
|
|
130
|
+
});
|
|
131
|
+
}
|
|
132
|
+
|
|
133
|
+
const calledName = callNode.name as string;
|
|
134
|
+
const file = callNode.file;
|
|
135
|
+
|
|
136
|
+
if (!calledName || !file) {
|
|
137
|
+
unresolvedByReason.unknown++;
|
|
138
|
+
continue;
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
// Step 4.1: Check if this is a JS builtin
|
|
142
|
+
if (JS_GLOBAL_FUNCTIONS.has(calledName)) {
|
|
143
|
+
builtinResolved++;
|
|
144
|
+
continue; // No edge needed, just count it
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
// Step 4.2: Check if this is a dynamic call
|
|
148
|
+
if (callNode.isDynamic) {
|
|
149
|
+
unresolvedByReason.dynamic++;
|
|
150
|
+
continue;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
// Step 4.3: Find matching import in same file
|
|
154
|
+
const importKey = `${file}:${calledName}`;
|
|
155
|
+
const imp = importIndex.get(importKey);
|
|
156
|
+
|
|
157
|
+
if (!imp) {
|
|
158
|
+
// No import found - this is an unknown call
|
|
159
|
+
unresolvedByReason.unknown++;
|
|
160
|
+
continue;
|
|
161
|
+
}
|
|
162
|
+
|
|
163
|
+
// Step 4.4: Extract package name from import source
|
|
164
|
+
const packageName = this.extractPackageName(imp.source!);
|
|
165
|
+
if (!packageName) {
|
|
166
|
+
unresolvedByReason.unknown++;
|
|
167
|
+
continue;
|
|
168
|
+
}
|
|
169
|
+
|
|
170
|
+
// Step 4.5: Create or reuse EXTERNAL_MODULE node
|
|
171
|
+
const externalModuleId = `EXTERNAL_MODULE:${packageName}`;
|
|
172
|
+
|
|
173
|
+
if (!createdExternalModules.has(externalModuleId)) {
|
|
174
|
+
// Check if node already exists in graph
|
|
175
|
+
const existingNode = await graph.getNode(externalModuleId);
|
|
176
|
+
if (!existingNode) {
|
|
177
|
+
await graph.addNode({
|
|
178
|
+
id: externalModuleId,
|
|
179
|
+
type: 'EXTERNAL_MODULE',
|
|
180
|
+
name: packageName,
|
|
181
|
+
file: '',
|
|
182
|
+
line: 0
|
|
183
|
+
});
|
|
184
|
+
nodesCreated++;
|
|
185
|
+
}
|
|
186
|
+
createdExternalModules.add(externalModuleId);
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
// Step 4.6: Create CALLS edge with metadata
|
|
190
|
+
// Use 'imported' field for exportedName (the original name in source module)
|
|
191
|
+
// For default imports, 'imported' is 'default'
|
|
192
|
+
// For named imports with alias, 'imported' is the original name
|
|
193
|
+
const exportedName = imp.imported || calledName;
|
|
194
|
+
|
|
195
|
+
await graph.addEdge({
|
|
196
|
+
type: 'CALLS',
|
|
197
|
+
src: callNode.id,
|
|
198
|
+
dst: externalModuleId,
|
|
199
|
+
metadata: { exportedName }
|
|
200
|
+
});
|
|
201
|
+
|
|
202
|
+
edgesCreated++;
|
|
203
|
+
externalResolved++;
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
const totalTime = ((Date.now() - startTime) / 1000).toFixed(2);
|
|
207
|
+
logger.info('Complete', {
|
|
208
|
+
nodesCreated,
|
|
209
|
+
edgesCreated,
|
|
210
|
+
callsProcessed,
|
|
211
|
+
externalResolved,
|
|
212
|
+
builtinResolved,
|
|
213
|
+
unresolvedByReason,
|
|
214
|
+
time: `${totalTime}s`
|
|
215
|
+
});
|
|
216
|
+
|
|
217
|
+
return createSuccessResult(
|
|
218
|
+
{ nodes: nodesCreated, edges: edgesCreated },
|
|
219
|
+
{
|
|
220
|
+
callsProcessed,
|
|
221
|
+
externalResolved,
|
|
222
|
+
builtinResolved,
|
|
223
|
+
unresolvedByReason,
|
|
224
|
+
timeMs: Date.now() - startTime
|
|
225
|
+
}
|
|
226
|
+
);
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
/**
|
|
230
|
+
* Extract package name from import source.
|
|
231
|
+
*
|
|
232
|
+
* Handles:
|
|
233
|
+
* - Simple packages: 'lodash' -> 'lodash'
|
|
234
|
+
* - Scoped packages: '@tanstack/react-query' -> '@tanstack/react-query'
|
|
235
|
+
* - Subpath imports: 'lodash/map' -> 'lodash'
|
|
236
|
+
* - Scoped subpath: '@scope/pkg/sub' -> '@scope/pkg'
|
|
237
|
+
*
|
|
238
|
+
* @param source - Import source string
|
|
239
|
+
* @returns Package name or null if invalid
|
|
240
|
+
*/
|
|
241
|
+
private extractPackageName(source: string): string | null {
|
|
242
|
+
if (!source) return null;
|
|
243
|
+
|
|
244
|
+
// Handle scoped packages (@scope/package)
|
|
245
|
+
if (source.startsWith('@')) {
|
|
246
|
+
// @scope/package or @scope/package/subpath
|
|
247
|
+
const parts = source.split('/');
|
|
248
|
+
if (parts.length >= 2) {
|
|
249
|
+
// Return @scope/package (first two parts)
|
|
250
|
+
return `${parts[0]}/${parts[1]}`;
|
|
251
|
+
}
|
|
252
|
+
return null; // Invalid scoped package
|
|
253
|
+
}
|
|
254
|
+
|
|
255
|
+
// Non-scoped package: lodash or lodash/map
|
|
256
|
+
const slashIndex = source.indexOf('/');
|
|
257
|
+
if (slashIndex === -1) {
|
|
258
|
+
return source; // Simple package name
|
|
259
|
+
}
|
|
260
|
+
return source.substring(0, slashIndex); // Package name before subpath
|
|
261
|
+
}
|
|
262
|
+
}
|