@aroman22/codegraph-vba-darwin-arm64 1.10.0 → 1.12.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.
- package/lib/dist/bin/codegraph.js +68 -0
- package/lib/dist/bin/codegraph.js.map +1 -1
- package/lib/dist/cli/stats-vba-rules.d.ts +64 -0
- package/lib/dist/cli/stats-vba-rules.d.ts.map +1 -0
- package/lib/dist/cli/stats-vba-rules.js +71 -0
- package/lib/dist/cli/stats-vba-rules.js.map +1 -0
- package/lib/dist/db/queries.d.ts +37 -0
- package/lib/dist/db/queries.d.ts.map +1 -1
- package/lib/dist/db/queries.js +33 -0
- package/lib/dist/db/queries.js.map +1 -1
- package/lib/dist/extraction/frameworks/dysflow-export.d.ts +37 -0
- package/lib/dist/extraction/frameworks/dysflow-export.d.ts.map +1 -0
- package/lib/dist/extraction/frameworks/dysflow-export.js +121 -0
- package/lib/dist/extraction/frameworks/dysflow-export.js.map +1 -0
- package/lib/dist/extraction/frameworks/index.d.ts +20 -0
- package/lib/dist/extraction/frameworks/index.d.ts.map +1 -0
- package/lib/dist/extraction/frameworks/index.js +24 -0
- package/lib/dist/extraction/frameworks/index.js.map +1 -0
- package/lib/dist/extraction/index.d.ts.map +1 -1
- package/lib/dist/extraction/index.js +25 -5
- package/lib/dist/extraction/index.js.map +1 -1
- package/lib/dist/extraction/parse-pool.d.ts +10 -0
- package/lib/dist/extraction/parse-pool.d.ts.map +1 -1
- package/lib/dist/extraction/parse-pool.js +2 -0
- package/lib/dist/extraction/parse-pool.js.map +1 -1
- package/lib/dist/extraction/parse-worker.js +6 -2
- package/lib/dist/extraction/parse-worker.js.map +1 -1
- package/lib/dist/extraction/tree-sitter.d.ts +9 -1
- package/lib/dist/extraction/tree-sitter.d.ts.map +1 -1
- package/lib/dist/extraction/tree-sitter.js +58 -5
- package/lib/dist/extraction/tree-sitter.js.map +1 -1
- package/lib/dist/extraction/vba/call-sweep.d.ts +43 -0
- package/lib/dist/extraction/vba/call-sweep.d.ts.map +1 -1
- package/lib/dist/extraction/vba/call-sweep.js +155 -66
- package/lib/dist/extraction/vba/call-sweep.js.map +1 -1
- package/lib/dist/extraction/vba/calls.d.ts.map +1 -1
- package/lib/dist/extraction/vba/calls.js +6 -0
- package/lib/dist/extraction/vba/calls.js.map +1 -1
- package/lib/dist/extraction/vba/context.d.ts +109 -1
- package/lib/dist/extraction/vba/context.d.ts.map +1 -1
- package/lib/dist/extraction/vba/context.js +155 -2
- package/lib/dist/extraction/vba/context.js.map +1 -1
- package/lib/dist/extraction/vba/declarations.d.ts +38 -2
- package/lib/dist/extraction/vba/declarations.d.ts.map +1 -1
- package/lib/dist/extraction/vba/declarations.js +217 -129
- package/lib/dist/extraction/vba/declarations.js.map +1 -1
- package/lib/dist/extraction/vba/dims.d.ts +35 -1
- package/lib/dist/extraction/vba/dims.d.ts.map +1 -1
- package/lib/dist/extraction/vba/dims.js +185 -109
- package/lib/dist/extraction/vba/dims.js.map +1 -1
- package/lib/dist/extraction/vba/enums-consts.d.ts +47 -7
- package/lib/dist/extraction/vba/enums-consts.d.ts.map +1 -1
- package/lib/dist/extraction/vba/enums-consts.js +215 -139
- package/lib/dist/extraction/vba/enums-consts.js.map +1 -1
- package/lib/dist/extraction/vba/event-synth.d.ts +3 -0
- package/lib/dist/extraction/vba/event-synth.d.ts.map +1 -0
- package/lib/dist/extraction/vba/event-synth.js +176 -0
- package/lib/dist/extraction/vba/event-synth.js.map +1 -0
- package/lib/dist/extraction/vba/implements.d.ts +16 -0
- package/lib/dist/extraction/vba/implements.d.ts.map +1 -1
- package/lib/dist/extraction/vba/implements.js +43 -12
- package/lib/dist/extraction/vba/implements.js.map +1 -1
- package/lib/dist/extraction/vba/procedures.d.ts +20 -0
- package/lib/dist/extraction/vba/procedures.d.ts.map +1 -1
- package/lib/dist/extraction/vba/procedures.js +48 -13
- package/lib/dist/extraction/vba/procedures.js.map +1 -1
- package/lib/dist/extraction/vba/rules.d.ts +129 -0
- package/lib/dist/extraction/vba/rules.d.ts.map +1 -0
- package/lib/dist/extraction/vba/rules.js +63 -0
- package/lib/dist/extraction/vba/rules.js.map +1 -0
- package/lib/dist/extraction/vba/text-utils.d.ts +1 -0
- package/lib/dist/extraction/vba/text-utils.d.ts.map +1 -1
- package/lib/dist/extraction/vba/text-utils.js +4 -2
- package/lib/dist/extraction/vba/text-utils.js.map +1 -1
- package/lib/dist/extraction/vba-extractor.d.ts +77 -1
- package/lib/dist/extraction/vba-extractor.d.ts.map +1 -1
- package/lib/dist/extraction/vba-extractor.js +182 -15
- package/lib/dist/extraction/vba-extractor.js.map +1 -1
- package/lib/dist/extraction/vba-preprocess.d.ts +11 -1
- package/lib/dist/extraction/vba-preprocess.d.ts.map +1 -1
- package/lib/dist/extraction/vba-preprocess.js +45 -16
- package/lib/dist/extraction/vba-preprocess.js.map +1 -1
- package/lib/dist/extraction/vba-timing.d.ts +38 -0
- package/lib/dist/extraction/vba-timing.d.ts.map +1 -0
- package/lib/dist/extraction/vba-timing.js +203 -0
- package/lib/dist/extraction/vba-timing.js.map +1 -0
- package/lib/dist/index.d.ts.map +1 -1
- package/lib/dist/index.js +22 -0
- package/lib/dist/index.js.map +1 -1
- package/lib/dist/project-config.d.ts +31 -0
- package/lib/dist/project-config.d.ts.map +1 -1
- package/lib/dist/project-config.js +75 -22
- package/lib/dist/project-config.js.map +1 -1
- package/lib/dist/resolution/frameworks/index.d.ts.map +1 -1
- package/lib/dist/resolution/frameworks/index.js +7 -0
- package/lib/dist/resolution/frameworks/index.js.map +1 -1
- package/lib/node_modules/.modules.yaml +1 -1
- package/lib/node_modules/.pnpm-workspace-state-v1.json +1 -1
- package/lib/package.json +2 -1
- package/package.json +1 -1
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.RULES = void 0;
|
|
3
4
|
exports.createEnumsConstsClassifier = createEnumsConstsClassifier;
|
|
4
5
|
exports.sweepEnumsAndConsts = sweepEnumsAndConsts;
|
|
5
6
|
/**
|
|
@@ -11,6 +12,7 @@ exports.sweepEnumsAndConsts = sweepEnumsAndConsts;
|
|
|
11
12
|
const tree_sitter_helpers_1 = require("../tree-sitter-helpers");
|
|
12
13
|
const constants_1 = require("./constants");
|
|
13
14
|
const text_utils_1 = require("./text-utils");
|
|
15
|
+
const rules_1 = require("./rules");
|
|
14
16
|
/** `[visibility] Enum <Name>` — opens an enum block. */
|
|
15
17
|
const ENUM_START_RE = /^\s*(?:(Public|Private|Friend|Global)\s+)?Enum\s+(\p{L}[\p{L}\p{N}_]*)/iu;
|
|
16
18
|
/** `End Enum` — closes the current enum block. */
|
|
@@ -25,87 +27,170 @@ const ENUM_MEMBER_RE = /^\s*(\p{L}[\p{L}\p{N}_]*)\s*(?:=|$)/u;
|
|
|
25
27
|
/** `[visibility] Const <decls>` — captures visibility (1) and the rest (2). */
|
|
26
28
|
const CONST_DECL_RE = /^\s*(?:(Public|Private|Friend|Global)\s+)?Const\s+(.+)$/i;
|
|
27
29
|
/**
|
|
28
|
-
* Issue #
|
|
29
|
-
*
|
|
30
|
+
* Issue #153: the declarative rule table for the enum / const concern.
|
|
31
|
+
* Six rules, partitioned by where they fire:
|
|
30
32
|
*
|
|
31
|
-
*
|
|
32
|
-
*
|
|
33
|
-
*
|
|
34
|
-
*
|
|
35
|
-
*
|
|
33
|
+
* - `proc-start` (outside-enum-block) — match a `Sub` /
|
|
34
|
+
* `Function` / `Property` header; push onto
|
|
35
|
+
* `ctx.procStack` and set `ctx.currentProcKey`
|
|
36
|
+
* so subsequent Const writes land in the
|
|
37
|
+
* per-proc resolution bucket.
|
|
38
|
+
* - `proc-end` (outside-enum-block) — match `End Sub` /
|
|
39
|
+
* `End Function` / `End Property`; pop the
|
|
40
|
+
* matching `procStack` entry.
|
|
41
|
+
* - `enum-start` (outside-enum-block) — match `[visibility]
|
|
42
|
+
* Enum <Name>`; emit an `enum` node + `contains`
|
|
43
|
+
* edge and mark `ctx.vbaEnumBlock`.
|
|
44
|
+
* - `enum-end` (inside-enum-block) — match `End Enum`; clear
|
|
45
|
+
* `ctx.vbaEnumBlock`.
|
|
46
|
+
* - `enum-member` (inside-enum-block) — match `<MemberName>
|
|
47
|
+
* [= <value>]`; emit an `enum_member` node + a
|
|
48
|
+
* `contains` edge from the open enum.
|
|
49
|
+
* - `const-decl` (outside-enum-block) — match `[visibility]
|
|
50
|
+
* Const <decls>`; always write the per-scope
|
|
51
|
+
* resolution bucket, and emit a `constant` node
|
|
52
|
+
* + `contains` edge ONLY when not inside a proc
|
|
53
|
+
* (proc-local Consts are not module symbols).
|
|
54
|
+
*
|
|
55
|
+
* The inter-line `ctx.procStack` / `ctx.currentProcKey` state is
|
|
56
|
+
* SHARED with the calls/SQL classifier (issue #52 protocol). The
|
|
57
|
+
* `ctx.vbaEnumBlock` state is local to this concern and lives on
|
|
58
|
+
* `ctx` for the same RULES-table-friendliness reason as
|
|
59
|
+
* `vbaDeclTypeBlock`.
|
|
36
60
|
*/
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
}
|
|
57
|
-
else if (constants_1.PROCEDURE_END_RE.test(line) && ctx.procStack.length > 0) {
|
|
61
|
+
exports.RULES = [
|
|
62
|
+
(0, rules_1.defineRule)({
|
|
63
|
+
id: 'proc-start',
|
|
64
|
+
description: 'Match a `Sub` / `Function` / `Property` header; push `lineNum` onto `ctx.procStack` and set `ctx.currentProcKey` so subsequent Const writes land in the per-proc resolution bucket.',
|
|
65
|
+
pattern: constants_1.PROC_RE,
|
|
66
|
+
requires: 'outside-enum-block',
|
|
67
|
+
emit: (_m, ctx, _line, lineNum) => {
|
|
68
|
+
ctx.procStack.push(lineNum);
|
|
69
|
+
ctx.currentProcKey = String(lineNum);
|
|
70
|
+
return { startLine: lineNum };
|
|
71
|
+
},
|
|
72
|
+
}),
|
|
73
|
+
(0, rules_1.defineRule)({
|
|
74
|
+
id: 'proc-end',
|
|
75
|
+
description: 'Match an `End Sub` / `End Function` / `End Property`; pop the matching `procStack` entry and rewind `ctx.currentProcKey` to the new top (or `module`).',
|
|
76
|
+
pattern: constants_1.PROCEDURE_END_RE,
|
|
77
|
+
requires: 'outside-enum-block',
|
|
78
|
+
emit: (_m, ctx) => {
|
|
79
|
+
if (ctx.procStack.length > 0)
|
|
58
80
|
ctx.procStack.pop();
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
81
|
+
ctx.currentProcKey =
|
|
82
|
+
ctx.procStack.length > 0
|
|
83
|
+
? String(ctx.procStack[ctx.procStack.length - 1])
|
|
84
|
+
: 'module';
|
|
85
|
+
return { kind: 'proc-end' };
|
|
86
|
+
},
|
|
87
|
+
}),
|
|
88
|
+
(0, rules_1.defineRule)({
|
|
89
|
+
id: 'enum-start',
|
|
90
|
+
description: 'Match a `[Public|Private|Friend|Global] Enum <Name>` block header; emit an `enum` node + `contains` edge and mark `ctx.vbaEnumBlock` so subsequent member lines route to `enum-member` / `End Enum` lines route to `enum-end`.',
|
|
91
|
+
pattern: ENUM_START_RE,
|
|
92
|
+
requires: 'outside-enum-block',
|
|
93
|
+
emit: (m, ctx, line, lineNum) => {
|
|
94
|
+
const visibility = (0, text_utils_1.foldVisibility)(m[1] ?? '');
|
|
95
|
+
const name = m[2] ?? '';
|
|
96
|
+
if (!name)
|
|
97
|
+
return null;
|
|
98
|
+
const enumId = (0, tree_sitter_helpers_1.generateNodeId)(ctx.filePath, 'enum', name, lineNum);
|
|
99
|
+
ctx.nodes.push({
|
|
100
|
+
id: enumId,
|
|
101
|
+
kind: 'enum',
|
|
102
|
+
name,
|
|
103
|
+
qualifiedName: name,
|
|
104
|
+
filePath: ctx.filePath,
|
|
105
|
+
language: 'vba',
|
|
106
|
+
startLine: lineNum,
|
|
107
|
+
endLine: lineNum,
|
|
108
|
+
startColumn: 0,
|
|
109
|
+
endColumn: line.length,
|
|
110
|
+
visibility,
|
|
111
|
+
updatedAt: Date.now(),
|
|
112
|
+
});
|
|
113
|
+
ctx.pushContainsFromModule(enumId);
|
|
114
|
+
ctx.vbaEnumBlock = { id: enumId, name };
|
|
115
|
+
return { name, enumId };
|
|
116
|
+
},
|
|
117
|
+
}),
|
|
118
|
+
(0, rules_1.defineRule)({
|
|
119
|
+
id: 'enum-end',
|
|
120
|
+
description: 'Match `End Enum` while inside an enum block; emit nothing and clear `ctx.vbaEnumBlock` so subsequent lines route back to the outside-enum-block rules.',
|
|
121
|
+
pattern: ENUM_END_RE,
|
|
122
|
+
requires: 'inside-enum-block',
|
|
123
|
+
emit: (_m, ctx) => {
|
|
124
|
+
ctx.vbaEnumBlock = null;
|
|
125
|
+
return { kind: 'end-enum-block' };
|
|
126
|
+
},
|
|
127
|
+
}),
|
|
128
|
+
(0, rules_1.defineRule)({
|
|
129
|
+
id: 'enum-member',
|
|
130
|
+
description: 'Match `<MemberName> [= <value>]` inside an open enum block; emit an `enum_member` node + a `contains` edge from the open enum.',
|
|
131
|
+
pattern: ENUM_MEMBER_RE,
|
|
132
|
+
requires: 'inside-enum-block',
|
|
133
|
+
emit: (m, ctx, line, lineNum) => {
|
|
134
|
+
const memberName = m[1] ?? '';
|
|
135
|
+
if (!memberName || !ctx.vbaEnumBlock)
|
|
136
|
+
return null;
|
|
137
|
+
const memberId = (0, tree_sitter_helpers_1.generateNodeId)(ctx.filePath, 'enum_member', memberName, lineNum);
|
|
138
|
+
ctx.nodes.push({
|
|
139
|
+
id: memberId,
|
|
140
|
+
kind: 'enum_member',
|
|
141
|
+
name: memberName,
|
|
142
|
+
qualifiedName: `${ctx.vbaEnumBlock.name}.${memberName}`,
|
|
143
|
+
filePath: ctx.filePath,
|
|
144
|
+
language: 'vba',
|
|
145
|
+
startLine: lineNum,
|
|
146
|
+
endLine: lineNum,
|
|
147
|
+
startColumn: 0,
|
|
148
|
+
endColumn: line.length,
|
|
149
|
+
updatedAt: Date.now(),
|
|
150
|
+
});
|
|
151
|
+
// enum → member: source is known, emit directly (not pending).
|
|
152
|
+
ctx.edges.push({
|
|
153
|
+
source: ctx.vbaEnumBlock.id,
|
|
154
|
+
target: memberId,
|
|
155
|
+
kind: 'contains',
|
|
156
|
+
});
|
|
157
|
+
return { name: memberName };
|
|
158
|
+
},
|
|
159
|
+
}),
|
|
160
|
+
(0, rules_1.defineRule)({
|
|
161
|
+
id: 'const-decl',
|
|
162
|
+
description: 'Match a `[Public|Private|Friend|Global] Const <decls>` declaration; always write the per-scope resolution bucket (issue #52) and additionally emit a `constant` node + `contains` edge ONLY when not inside a proc (proc-local Consts are not module symbols).',
|
|
163
|
+
pattern: CONST_DECL_RE,
|
|
164
|
+
requires: 'outside-enum-block',
|
|
165
|
+
emit: (m, ctx, line, lineNum) => {
|
|
166
|
+
const visibility = (0, text_utils_1.foldVisibility)(m[1] ?? '');
|
|
167
|
+
const body = m[2] ?? '';
|
|
168
|
+
const declarations = (0, text_utils_1.parseConstDeclarations)(body);
|
|
169
|
+
let count = 0;
|
|
170
|
+
for (const declaration of declarations) {
|
|
171
|
+
const constName = declaration.name;
|
|
172
|
+
if (!constName)
|
|
173
|
+
continue;
|
|
174
|
+
// Issue #52: every Const line (module-level or proc-local)
|
|
175
|
+
// writes into a per-scope resolution bucket so
|
|
176
|
+
// `DoCmd.OpenForm FORM_X` later resolves correctly; module-level
|
|
177
|
+
// Consts additionally emit a `constant` graph node + the
|
|
178
|
+
// module→constant `contains` edge. Proc-local Consts skip both
|
|
179
|
+
// (the const is not a module symbol, so the wrong-containment
|
|
180
|
+
// node + edge the pre-fix code emitted are gone), but the
|
|
181
|
+
// per-proc bucket keeps OpenForm/OpenQuery argument
|
|
182
|
+
// resolution working exactly as before.
|
|
183
|
+
if (declaration.value !== null) {
|
|
184
|
+
ctx.setLocalConstInScope(ctx.currentProcKey, constName, declaration.value);
|
|
94
185
|
}
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
if (enumStart) {
|
|
99
|
-
const visibility = (0, text_utils_1.foldVisibility)(enumStart[1] ?? '');
|
|
100
|
-
const name = enumStart[2] ?? '';
|
|
101
|
-
if (!name)
|
|
102
|
-
return;
|
|
103
|
-
const enumId = (0, tree_sitter_helpers_1.generateNodeId)(ctx.filePath, 'enum', name, lineNum);
|
|
186
|
+
if (ctx.procStack.length > 0)
|
|
187
|
+
continue;
|
|
188
|
+
const constId = (0, tree_sitter_helpers_1.generateNodeId)(ctx.filePath, 'constant', constName, lineNum);
|
|
104
189
|
ctx.nodes.push({
|
|
105
|
-
id:
|
|
106
|
-
kind: '
|
|
107
|
-
name,
|
|
108
|
-
qualifiedName:
|
|
190
|
+
id: constId,
|
|
191
|
+
kind: 'constant',
|
|
192
|
+
name: constName,
|
|
193
|
+
qualifiedName: constName,
|
|
109
194
|
filePath: ctx.filePath,
|
|
110
195
|
language: 'vba',
|
|
111
196
|
startLine: lineNum,
|
|
@@ -113,76 +198,67 @@ function createEnumsConstsClassifier() {
|
|
|
113
198
|
startColumn: 0,
|
|
114
199
|
endColumn: line.length,
|
|
115
200
|
visibility,
|
|
201
|
+
metadata: {
|
|
202
|
+
asType: declaration.asType,
|
|
203
|
+
...(declaration.value !== null ? { value: declaration.value } : {}),
|
|
204
|
+
},
|
|
116
205
|
updatedAt: Date.now(),
|
|
117
206
|
});
|
|
118
|
-
ctx.pushContainsFromModule(
|
|
119
|
-
|
|
120
|
-
this.count++;
|
|
121
|
-
return;
|
|
207
|
+
ctx.pushContainsFromModule(constId);
|
|
208
|
+
count++;
|
|
122
209
|
}
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
210
|
+
return { count };
|
|
211
|
+
},
|
|
212
|
+
}),
|
|
213
|
+
];
|
|
214
|
+
/**
|
|
215
|
+
* Issue #83: factory for the enum / const classifier.
|
|
216
|
+
*
|
|
217
|
+
* The body walks the declarative `RULES` table (Issue #153) and
|
|
218
|
+
* honours each rule's `requires` precondition. The inter-line
|
|
219
|
+
* state — `ctx.procStack`, `ctx.currentProcKey`, and
|
|
220
|
+
* `ctx.vbaEnumBlock` — lives on `ctx` so the RULES table's `emit`
|
|
221
|
+
* functions can read/write it without taking a closure reference.
|
|
222
|
+
*
|
|
223
|
+
* Issue #52: the first invocation also resets the shared proc-stack
|
|
224
|
+
* + lookup key so leftover state from a previous `extract()` (only
|
|
225
|
+
* possible in tests that construct a fresh extractor and run twice)
|
|
226
|
+
* never leaks across sweeps. The walk below updates both every
|
|
227
|
+
* iteration; `sweepCallsAndSql` resets again at its own start, so
|
|
228
|
+
* the protocol stays consistent across both classifiers.
|
|
229
|
+
*/
|
|
230
|
+
function createEnumsConstsClassifier() {
|
|
231
|
+
let initialized = false;
|
|
232
|
+
const cls = {
|
|
233
|
+
name: 'enumsConsts',
|
|
234
|
+
count: 0,
|
|
235
|
+
classifyLine(line, i, ctx) {
|
|
236
|
+
if (!initialized) {
|
|
237
|
+
ctx.procStack.length = 0;
|
|
238
|
+
ctx.currentProcKey = 'module';
|
|
239
|
+
initialized = true;
|
|
240
|
+
}
|
|
241
|
+
const lineNum = i + 1;
|
|
242
|
+
for (const rule of exports.RULES) {
|
|
243
|
+
if (rule.requires === 'inside-enum-block' && !ctx.vbaEnumBlock)
|
|
244
|
+
continue;
|
|
245
|
+
if (rule.requires === 'outside-enum-block' && ctx.vbaEnumBlock)
|
|
246
|
+
continue;
|
|
247
|
+
const m = (0, rules_1.matchRule)(rule.pattern, line);
|
|
248
|
+
if (!m)
|
|
249
|
+
continue;
|
|
250
|
+
const result = rule.emit(m, ctx, line, lineNum);
|
|
251
|
+
if (result !== null && result !== undefined) {
|
|
252
|
+
this.count += rule.count ? rule.count(result) : 1;
|
|
164
253
|
}
|
|
254
|
+
// `enum-end` cleared the enum block — nothing else on this
|
|
255
|
+
// line can apply. The legacy cascade did the same short-circuit
|
|
256
|
+
// via `return`.
|
|
257
|
+
if (rule.id === 'enum-end')
|
|
258
|
+
break;
|
|
165
259
|
}
|
|
166
260
|
},
|
|
167
261
|
};
|
|
168
|
-
// Issue #52: reset the shared scope stack + lookup key so leftover
|
|
169
|
-
// state from a previous extract() (impossible in production but
|
|
170
|
-
// possible in unit tests that construct a fresh extractor and run
|
|
171
|
-
// twice) never leaks across sweeps. The walk below updates both
|
|
172
|
-
// every iteration; `sweepCallsAndSql` resets again at its own
|
|
173
|
-
// start, before any OpenForm/OpenQuery reader consults them.
|
|
174
|
-
// We re-bind the classifier to call this reset at the start of
|
|
175
|
-
// its first invocation.
|
|
176
|
-
const originalClassify = cls.classifyLine;
|
|
177
|
-
let initialized = false;
|
|
178
|
-
cls.classifyLine = function (line, i, ctx) {
|
|
179
|
-
if (!initialized) {
|
|
180
|
-
ctx.procStack.length = 0;
|
|
181
|
-
ctx.currentProcKey = 'module';
|
|
182
|
-
initialized = true;
|
|
183
|
-
}
|
|
184
|
-
return originalClassify.call(this, line, i, ctx);
|
|
185
|
-
};
|
|
186
262
|
return cls;
|
|
187
263
|
}
|
|
188
264
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"enums-consts.js","sourceRoot":"","sources":["../../../src/extraction/vba/enums-consts.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"enums-consts.js","sourceRoot":"","sources":["../../../src/extraction/vba/enums-consts.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"event-synth.d.ts","sourceRoot":"","sources":["../../../src/extraction/vba/event-synth.ts"],"names":[],"mappings":"AA+DA,OAAO,EAAE,YAAY,EAAE,MAAM,kBAAkB,CAAC;AAahD,wBAAgB,8BAA8B,CAAC,OAAO,EAAE,YAAY,GAAG,MAAM,CAmF5E"}
|
|
@@ -0,0 +1,176 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.synthesizeVbaEventHandlerEdges = synthesizeVbaEventHandlerEdges;
|
|
4
|
+
function synthesizeVbaEventHandlerEdges(queries) {
|
|
5
|
+
// --- Phase 1: collect pairs ---------------------------------------------
|
|
6
|
+
// Walk every `vba-withevents` `references` edge. The SOURCE is the
|
|
7
|
+
// subscriber's module/class node (its `filePath` scopes the handler
|
|
8
|
+
// Sub lookup); the TARGET is the REAL event-declaring class node
|
|
9
|
+
// (after `resolveVbaReferenceStubs` repointed it from the synthetic
|
|
10
|
+
// class stub). The metadata carries the WithEvents variable name
|
|
11
|
+
// (`m_X`) — issue #150 change to `VbaExtractorContext.emitReference`.
|
|
12
|
+
const bindings = queryWithEventsBindings(queries);
|
|
13
|
+
if (bindings.length === 0)
|
|
14
|
+
return 0;
|
|
15
|
+
// key = eventNodeId (string), value = the pair. We keep the FIRST
|
|
16
|
+
// binding per event node — multiple `WithEvents` vars on the same
|
|
17
|
+
// class binding to the same event from the same file is rare; if it
|
|
18
|
+
// ever happens the second binding's variable name is silently
|
|
19
|
+
// shadowed by the first, which is fine because we only emit one
|
|
20
|
+
// `event-handler` edge per raiser anyway.
|
|
21
|
+
const pairsByEventId = new Map();
|
|
22
|
+
for (const binding of bindings) {
|
|
23
|
+
if (!binding.variableName)
|
|
24
|
+
continue;
|
|
25
|
+
// Find every event node in the real event-declaring class's file.
|
|
26
|
+
// iterateNodesByKind streams the events without materializing the
|
|
27
|
+
// whole table (cheap on a few hundred-event project, O(1) memory
|
|
28
|
+
// for million-event projects).
|
|
29
|
+
for (const eventNode of queries.iterateNodesByKind('event')) {
|
|
30
|
+
if (eventNode.language !== 'vba')
|
|
31
|
+
continue;
|
|
32
|
+
if (eventNode.filePath !== binding.eventClassFilePath)
|
|
33
|
+
continue;
|
|
34
|
+
// Handler Sub name follows the WithEvents naming convention:
|
|
35
|
+
// `m_<variableName>_<eventName>` (e.g. `m_Notifier_DataChanged`).
|
|
36
|
+
const handlerName = `${binding.variableName}_${eventNode.name}`;
|
|
37
|
+
const handlerSub = findHandlerSubInFile(queries, binding.subscriberFilePath, handlerName);
|
|
38
|
+
if (!handlerSub)
|
|
39
|
+
continue;
|
|
40
|
+
if (pairsByEventId.has(eventNode.id))
|
|
41
|
+
continue;
|
|
42
|
+
pairsByEventId.set(eventNode.id, {
|
|
43
|
+
handlerNode: handlerSub,
|
|
44
|
+
variableName: binding.variableName,
|
|
45
|
+
});
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
if (pairsByEventId.size === 0)
|
|
49
|
+
return 0;
|
|
50
|
+
// --- Phase 2: connect at RaiseEvent sites --------------------------------
|
|
51
|
+
const raiseRows = queries.getRaisesEventEdges();
|
|
52
|
+
const seenTuples = new Set();
|
|
53
|
+
const newEdges = [];
|
|
54
|
+
for (const re of raiseRows) {
|
|
55
|
+
const pair = pairsByEventId.get(re.target);
|
|
56
|
+
if (!pair)
|
|
57
|
+
continue;
|
|
58
|
+
const tupleKey = `${re.source}\0${pair.handlerNode.id}`;
|
|
59
|
+
if (seenTuples.has(tupleKey))
|
|
60
|
+
continue;
|
|
61
|
+
if (queries.edgeExists(re.source, pair.handlerNode.id, 'event-handler')) {
|
|
62
|
+
seenTuples.add(tupleKey);
|
|
63
|
+
continue;
|
|
64
|
+
}
|
|
65
|
+
seenTuples.add(tupleKey);
|
|
66
|
+
const meta = parseMetadata(re.metadata);
|
|
67
|
+
const eventName = typeof meta?.eventName === 'string' ? meta.eventName : '';
|
|
68
|
+
newEdges.push({
|
|
69
|
+
source: re.source,
|
|
70
|
+
target: pair.handlerNode.id,
|
|
71
|
+
kind: 'event-handler',
|
|
72
|
+
provenance: 'heuristic',
|
|
73
|
+
metadata: {
|
|
74
|
+
synthesizedBy: 'vba-event-handler',
|
|
75
|
+
eventName,
|
|
76
|
+
variableName: pair.variableName,
|
|
77
|
+
},
|
|
78
|
+
line: re.line ?? undefined,
|
|
79
|
+
column: re.col ?? undefined,
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
if (newEdges.length > 0) {
|
|
83
|
+
queries.insertEdges(newEdges);
|
|
84
|
+
}
|
|
85
|
+
return newEdges.length;
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Discover every WithEvents binding in the project by walking the
|
|
89
|
+
* `vba-withevents` `references` edges. Each binding carries:
|
|
90
|
+
* - `subscriberFilePath` → where the handler Sub must live
|
|
91
|
+
* - `eventClassFilePath` → where the event node lives
|
|
92
|
+
* - `variableName` → the `m_X` part of `m_X_<EventName>`
|
|
93
|
+
*
|
|
94
|
+
* Uses one SQL query (the new `getReferencesBySynthesizedBy` helper)
|
|
95
|
+
* + per-edge `getNodeById` lookups so the cost is O(bindings)
|
|
96
|
+
* regardless of total node count. Cache-friendly: the QueryBuilder's
|
|
97
|
+
* LRU node cache absorbs repeated `getNodeById` calls.
|
|
98
|
+
*/
|
|
99
|
+
function queryWithEventsBindings(queries) {
|
|
100
|
+
const rows = queries.getReferencesBySynthesizedBy('vba-withevents');
|
|
101
|
+
const out = [];
|
|
102
|
+
for (const row of rows) {
|
|
103
|
+
const meta = parseMetadata(row.metadata);
|
|
104
|
+
if (meta?.synthesizedBy !== 'vba-withevents')
|
|
105
|
+
continue;
|
|
106
|
+
const variableName = typeof meta?.variableName === 'string' ? meta.variableName : '';
|
|
107
|
+
if (!variableName)
|
|
108
|
+
continue;
|
|
109
|
+
// Subscriber file: the source is the subscriber's class node.
|
|
110
|
+
const subscriberNode = queries.getNodeById(row.source);
|
|
111
|
+
if (!subscriberNode || !subscriberNode.filePath)
|
|
112
|
+
continue;
|
|
113
|
+
// Event-declaring class file: the target is the real class node
|
|
114
|
+
// (after `resolveVbaReferenceStubs` repointed it from the synthetic
|
|
115
|
+
// class stub). We accept `class` / `module` / `interface` / `enum`
|
|
116
|
+
// / `struct` / `type_alias` — whatever kind the resolver landed on.
|
|
117
|
+
const eventClassNode = queries.getNodeById(row.target);
|
|
118
|
+
if (!eventClassNode || !eventClassNode.filePath)
|
|
119
|
+
continue;
|
|
120
|
+
if (eventClassNode.language !== 'vba')
|
|
121
|
+
continue;
|
|
122
|
+
if (eventClassNode.filePath === subscriberNode.filePath)
|
|
123
|
+
continue;
|
|
124
|
+
out.push({
|
|
125
|
+
subscriberFilePath: subscriberNode.filePath,
|
|
126
|
+
eventClassFilePath: eventClassNode.filePath,
|
|
127
|
+
variableName,
|
|
128
|
+
});
|
|
129
|
+
}
|
|
130
|
+
return out;
|
|
131
|
+
}
|
|
132
|
+
/**
|
|
133
|
+
* Find a function (Sub) node in `filePath` whose name matches
|
|
134
|
+
* `handlerName` (case-insensitive, since VBA identifiers are case-
|
|
135
|
+
* insensitive). Uses a narrow SQL query (the QueryBuilder doesn't
|
|
136
|
+
* expose a public name+file+kind lookup, so we go through
|
|
137
|
+
* `getNodesByFile` and filter — filePath-keyed lookups are fast on
|
|
138
|
+
* the `idx_nodes_file_path` index).
|
|
139
|
+
*/
|
|
140
|
+
function findHandlerSubInFile(queries, filePath, handlerName) {
|
|
141
|
+
const lower = handlerName.toLowerCase();
|
|
142
|
+
// getNodesByFile returns nodes ordered by start_line; the order
|
|
143
|
+
// doesn't matter for the existence check, only the (name, filePath,
|
|
144
|
+
// kind='function') match.
|
|
145
|
+
const candidates = queries.getNodesByFile(filePath);
|
|
146
|
+
for (const node of candidates) {
|
|
147
|
+
if (node.kind !== 'function')
|
|
148
|
+
continue;
|
|
149
|
+
if (node.language !== 'vba')
|
|
150
|
+
continue;
|
|
151
|
+
if (node.name.toLowerCase() !== lower)
|
|
152
|
+
continue;
|
|
153
|
+
return node;
|
|
154
|
+
}
|
|
155
|
+
return null;
|
|
156
|
+
}
|
|
157
|
+
/**
|
|
158
|
+
* Safe-parse the metadata JSON column. The schema stores it as TEXT;
|
|
159
|
+
* an absent or malformed cell returns `null` (treated as "no metadata"
|
|
160
|
+
* by callers). Mirrors the same shape used elsewhere in the codebase.
|
|
161
|
+
*/
|
|
162
|
+
function parseMetadata(raw) {
|
|
163
|
+
if (!raw)
|
|
164
|
+
return null;
|
|
165
|
+
try {
|
|
166
|
+
const parsed = JSON.parse(raw);
|
|
167
|
+
if (parsed && typeof parsed === 'object' && !Array.isArray(parsed)) {
|
|
168
|
+
return parsed;
|
|
169
|
+
}
|
|
170
|
+
}
|
|
171
|
+
catch {
|
|
172
|
+
/* fall through */
|
|
173
|
+
}
|
|
174
|
+
return null;
|
|
175
|
+
}
|
|
176
|
+
//# sourceMappingURL=event-synth.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"event-synth.js","sourceRoot":"","sources":["../../../src/extraction/vba/event-synth.ts"],"names":[],"mappings":"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"}
|