@kernlang/evolve 3.0.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/LICENSE +661 -0
- package/dist/concept-gap-adapter.d.ts +17 -0
- package/dist/concept-gap-adapter.js +43 -0
- package/dist/concept-gap-adapter.js.map +1 -0
- package/dist/detector-registry.d.ts +31 -0
- package/dist/detector-registry.js +89 -0
- package/dist/detector-registry.js.map +1 -0
- package/dist/detectors/animation.d.ts +5 -0
- package/dist/detectors/animation.js +67 -0
- package/dist/detectors/animation.js.map +1 -0
- package/dist/detectors/data-fetching.d.ts +5 -0
- package/dist/detectors/data-fetching.js +117 -0
- package/dist/detectors/data-fetching.js.map +1 -0
- package/dist/detectors/express-middleware.d.ts +5 -0
- package/dist/detectors/express-middleware.js +52 -0
- package/dist/detectors/express-middleware.js.map +1 -0
- package/dist/detectors/react-forms.d.ts +5 -0
- package/dist/detectors/react-forms.js +89 -0
- package/dist/detectors/react-forms.js.map +1 -0
- package/dist/detectors/schema-validation.d.ts +5 -0
- package/dist/detectors/schema-validation.js +92 -0
- package/dist/detectors/schema-validation.js.map +1 -0
- package/dist/detectors/state-mgmt.d.ts +5 -0
- package/dist/detectors/state-mgmt.js +102 -0
- package/dist/detectors/state-mgmt.js.map +1 -0
- package/dist/detectors/structural.d.ts +10 -0
- package/dist/detectors/structural.js +271 -0
- package/dist/detectors/structural.js.map +1 -0
- package/dist/detectors/testing.d.ts +5 -0
- package/dist/detectors/testing.js +56 -0
- package/dist/detectors/testing.js.map +1 -0
- package/dist/detectors/vue-composables.d.ts +5 -0
- package/dist/detectors/vue-composables.js +57 -0
- package/dist/detectors/vue-composables.js.map +1 -0
- package/dist/evolve-dedup.d.ts +12 -0
- package/dist/evolve-dedup.js +50 -0
- package/dist/evolve-dedup.js.map +1 -0
- package/dist/evolve-rollback.d.ts +58 -0
- package/dist/evolve-rollback.js +242 -0
- package/dist/evolve-rollback.js.map +1 -0
- package/dist/evolve-runner.d.ts +22 -0
- package/dist/evolve-runner.js +183 -0
- package/dist/evolve-runner.js.map +1 -0
- package/dist/evolve-validator-v4.d.ts +11 -0
- package/dist/evolve-validator-v4.js +253 -0
- package/dist/evolve-validator-v4.js.map +1 -0
- package/dist/evolved-node-loader.d.ts +61 -0
- package/dist/evolved-node-loader.js +228 -0
- package/dist/evolved-node-loader.js.map +1 -0
- package/dist/evolved-types.d.ts +110 -0
- package/dist/evolved-types.js +8 -0
- package/dist/evolved-types.js.map +1 -0
- package/dist/expressibility-scorer.d.ts +19 -0
- package/dist/expressibility-scorer.js +78 -0
- package/dist/expressibility-scorer.js.map +1 -0
- package/dist/gap-detector.d.ts +26 -0
- package/dist/gap-detector.js +141 -0
- package/dist/gap-detector.js.map +1 -0
- package/dist/golden-test-runner.d.ts +27 -0
- package/dist/golden-test-runner.js +120 -0
- package/dist/golden-test-runner.js.map +1 -0
- package/dist/graduation.d.ts +36 -0
- package/dist/graduation.js +175 -0
- package/dist/graduation.js.map +1 -0
- package/dist/index.d.ts +40 -0
- package/dist/index.js +58 -0
- package/dist/index.js.map +1 -0
- package/dist/llm-discovery.d.ts +55 -0
- package/dist/llm-discovery.js +352 -0
- package/dist/llm-discovery.js.map +1 -0
- package/dist/llm-provider.d.ts +35 -0
- package/dist/llm-provider.js +143 -0
- package/dist/llm-provider.js.map +1 -0
- package/dist/node-governance.d.ts +23 -0
- package/dist/node-governance.js +45 -0
- package/dist/node-governance.js.map +1 -0
- package/dist/node-proposer.d.ts +27 -0
- package/dist/node-proposer.js +127 -0
- package/dist/node-proposer.js.map +1 -0
- package/dist/node-validator.d.ts +16 -0
- package/dist/node-validator.js +74 -0
- package/dist/node-validator.js.map +1 -0
- package/dist/pattern-analyzer.d.ts +28 -0
- package/dist/pattern-analyzer.js +181 -0
- package/dist/pattern-analyzer.js.map +1 -0
- package/dist/quality-scorer.d.ts +16 -0
- package/dist/quality-scorer.js +79 -0
- package/dist/quality-scorer.js.map +1 -0
- package/dist/sandboxed-generator.d.ts +26 -0
- package/dist/sandboxed-generator.js +133 -0
- package/dist/sandboxed-generator.js.map +1 -0
- package/dist/staging.d.ts +81 -0
- package/dist/staging.js +414 -0
- package/dist/staging.js.map +1 -0
- package/dist/template-proposer.d.ts +24 -0
- package/dist/template-proposer.js +103 -0
- package/dist/template-proposer.js.map +1 -0
- package/dist/template-validator.d.ts +18 -0
- package/dist/template-validator.js +174 -0
- package/dist/template-validator.js.map +1 -0
- package/dist/types.d.ts +169 -0
- package/dist/types.js +7 -0
- package/dist/types.js.map +1 -0
- package/package.json +27 -0
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Concept Gap Adapter — bridges @kernlang/review concept rules into evolve's PatternGap format.
|
|
3
|
+
*
|
|
4
|
+
* Converts universal concept findings (unguarded-effect, ignored-error, etc.)
|
|
5
|
+
* into PatternGap[] so evolve can report structural issues alongside import-based gaps.
|
|
6
|
+
*/
|
|
7
|
+
import { extractTsConcepts, runConceptRules } from '@kernlang/review';
|
|
8
|
+
let _conceptGapCounter = 0;
|
|
9
|
+
function nextConceptGapId(ruleId) {
|
|
10
|
+
return `concept-gap-${ruleId}-${++_conceptGapCounter}`;
|
|
11
|
+
}
|
|
12
|
+
/** Reset counter for test isolation. */
|
|
13
|
+
export function resetConceptGapIds() {
|
|
14
|
+
_conceptGapCounter = 0;
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Extract concept-based gaps from a TypeScript source file.
|
|
18
|
+
*
|
|
19
|
+
* Runs the universal concept model (effect, guard, state_mutation, error handling)
|
|
20
|
+
* and converts findings into PatternGap[] with patternKind='structural'.
|
|
21
|
+
*/
|
|
22
|
+
export function detectConceptualGaps(sourceFile, filePath) {
|
|
23
|
+
const concepts = extractTsConcepts(sourceFile, filePath);
|
|
24
|
+
const findings = runConceptRules(concepts, filePath);
|
|
25
|
+
return findings.map(f => findingToGap(f, filePath));
|
|
26
|
+
}
|
|
27
|
+
function findingToGap(finding, filePath) {
|
|
28
|
+
const span = finding.primarySpan;
|
|
29
|
+
return {
|
|
30
|
+
id: nextConceptGapId(finding.ruleId),
|
|
31
|
+
detectorId: `concept-${finding.ruleId}`,
|
|
32
|
+
libraryName: 'structural',
|
|
33
|
+
patternKind: 'structural',
|
|
34
|
+
anchorImport: '',
|
|
35
|
+
startLine: span.startLine,
|
|
36
|
+
endLine: span.endLine,
|
|
37
|
+
snippet: finding.message,
|
|
38
|
+
extractedParams: [],
|
|
39
|
+
confidencePct: finding.confidence != null ? finding.confidence * 100 : 80,
|
|
40
|
+
filePath,
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
//# sourceMappingURL=concept-gap-adapter.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"concept-gap-adapter.js","sourceRoot":"","sources":["../src/concept-gap-adapter.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,OAAO,EAAE,iBAAiB,EAAE,eAAe,EAAE,MAAM,kBAAkB,CAAC;AAItE,IAAI,kBAAkB,GAAG,CAAC,CAAC;AAE3B,SAAS,gBAAgB,CAAC,MAAc;IACtC,OAAO,eAAe,MAAM,IAAI,EAAE,kBAAkB,EAAE,CAAC;AACzD,CAAC;AAED,wCAAwC;AACxC,MAAM,UAAU,kBAAkB;IAChC,kBAAkB,GAAG,CAAC,CAAC;AACzB,CAAC;AAED;;;;;GAKG;AACH,MAAM,UAAU,oBAAoB,CAClC,UAAsB,EACtB,QAAgB;IAEhB,MAAM,QAAQ,GAAG,iBAAiB,CAAC,UAAU,EAAE,QAAQ,CAAC,CAAC;IACzD,MAAM,QAAQ,GAAG,eAAe,CAAC,QAAQ,EAAE,QAAQ,CAAC,CAAC;IACrD,OAAO,QAAQ,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,YAAY,CAAC,CAAC,EAAE,QAAQ,CAAC,CAAC,CAAC;AACtD,CAAC;AAED,SAAS,YAAY,CAAC,OAAsB,EAAE,QAAgB;IAC5D,MAAM,IAAI,GAAG,OAAO,CAAC,WAAW,CAAC;IACjC,OAAO;QACL,EAAE,EAAE,gBAAgB,CAAC,OAAO,CAAC,MAAM,CAAC;QACpC,UAAU,EAAE,WAAW,OAAO,CAAC,MAAM,EAAE;QACvC,WAAW,EAAE,YAAY;QACzB,WAAW,EAAE,YAAY;QACzB,YAAY,EAAE,EAAE;QAChB,SAAS,EAAE,IAAI,CAAC,SAAS;QACzB,OAAO,EAAE,IAAI,CAAC,OAAO;QACrB,OAAO,EAAE,OAAO,CAAC,OAAO;QACxB,eAAe,EAAE,EAAE;QACnB,aAAa,EAAE,OAAO,CAAC,UAAU,IAAI,IAAI,CAAC,CAAC,CAAC,OAAO,CAAC,UAAU,GAAG,GAAG,CAAC,CAAC,CAAC,EAAE;QACzE,QAAQ;KACT,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Detector Registry — pluggable detector packs for library pattern detection.
|
|
3
|
+
*
|
|
4
|
+
* Built-in packs ship in detectors/ directory.
|
|
5
|
+
* Users can register custom detectors via kern.config.ts.
|
|
6
|
+
*/
|
|
7
|
+
import type { DetectorPack } from './types.js';
|
|
8
|
+
export declare function registerDetector(pack: DetectorPack): void;
|
|
9
|
+
export declare function unregisterDetector(id: string): void;
|
|
10
|
+
export declare function getDetector(id: string): DetectorPack | undefined;
|
|
11
|
+
export declare function getAllDetectors(): DetectorPack[];
|
|
12
|
+
/**
|
|
13
|
+
* Find detectors that match a given import path.
|
|
14
|
+
* Checks if the import matches any of the detector's packageNames.
|
|
15
|
+
*/
|
|
16
|
+
export declare function getDetectorsForImport(importPath: string): DetectorPack[];
|
|
17
|
+
export declare function clearDetectors(): void;
|
|
18
|
+
export declare function detectorCount(): number;
|
|
19
|
+
/**
|
|
20
|
+
* Load all built-in detector packs.
|
|
21
|
+
*/
|
|
22
|
+
export declare function loadBuiltinDetectors(): Promise<void>;
|
|
23
|
+
/**
|
|
24
|
+
* Get detectors that are universal (import-agnostic, empty packageNames).
|
|
25
|
+
* These run on every file regardless of imports.
|
|
26
|
+
*/
|
|
27
|
+
export declare function getUniversalDetectors(): DetectorPack[];
|
|
28
|
+
/**
|
|
29
|
+
* Synchronously register detector packs (for when they're already imported).
|
|
30
|
+
*/
|
|
31
|
+
export declare function registerDetectors(packs: DetectorPack[]): void;
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Detector Registry — pluggable detector packs for library pattern detection.
|
|
3
|
+
*
|
|
4
|
+
* Built-in packs ship in detectors/ directory.
|
|
5
|
+
* Users can register custom detectors via kern.config.ts.
|
|
6
|
+
*/
|
|
7
|
+
const _registry = new Map();
|
|
8
|
+
export function registerDetector(pack) {
|
|
9
|
+
_registry.set(pack.id, pack);
|
|
10
|
+
}
|
|
11
|
+
export function unregisterDetector(id) {
|
|
12
|
+
_registry.delete(id);
|
|
13
|
+
}
|
|
14
|
+
export function getDetector(id) {
|
|
15
|
+
return _registry.get(id);
|
|
16
|
+
}
|
|
17
|
+
export function getAllDetectors() {
|
|
18
|
+
return Array.from(_registry.values());
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Find detectors that match a given import path.
|
|
22
|
+
* Checks if the import matches any of the detector's packageNames.
|
|
23
|
+
*/
|
|
24
|
+
export function getDetectorsForImport(importPath) {
|
|
25
|
+
const results = [];
|
|
26
|
+
for (const pack of _registry.values()) {
|
|
27
|
+
for (const pkgName of pack.packageNames) {
|
|
28
|
+
if (importPath === pkgName || importPath.startsWith(pkgName + '/')) {
|
|
29
|
+
results.push(pack);
|
|
30
|
+
break;
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
return results;
|
|
35
|
+
}
|
|
36
|
+
export function clearDetectors() {
|
|
37
|
+
_registry.clear();
|
|
38
|
+
}
|
|
39
|
+
export function detectorCount() {
|
|
40
|
+
return _registry.size;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Load all built-in detector packs.
|
|
44
|
+
*/
|
|
45
|
+
export async function loadBuiltinDetectors() {
|
|
46
|
+
try {
|
|
47
|
+
const modules = await Promise.all([
|
|
48
|
+
import('./detectors/react-forms.js'),
|
|
49
|
+
import('./detectors/state-mgmt.js'),
|
|
50
|
+
import('./detectors/animation.js'),
|
|
51
|
+
import('./detectors/data-fetching.js'),
|
|
52
|
+
import('./detectors/schema-validation.js'),
|
|
53
|
+
import('./detectors/express-middleware.js'),
|
|
54
|
+
import('./detectors/vue-composables.js'),
|
|
55
|
+
import('./detectors/testing.js'),
|
|
56
|
+
import('./detectors/structural.js'),
|
|
57
|
+
]);
|
|
58
|
+
for (const mod of modules) {
|
|
59
|
+
for (const pack of mod.detectors) {
|
|
60
|
+
registerDetector(pack);
|
|
61
|
+
}
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
catch (err) {
|
|
65
|
+
throw new Error(`Failed to load builtin detectors: ${err.message}`);
|
|
66
|
+
}
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Get detectors that are universal (import-agnostic, empty packageNames).
|
|
70
|
+
* These run on every file regardless of imports.
|
|
71
|
+
*/
|
|
72
|
+
export function getUniversalDetectors() {
|
|
73
|
+
const results = [];
|
|
74
|
+
for (const pack of _registry.values()) {
|
|
75
|
+
if (pack.packageNames.length === 0) {
|
|
76
|
+
results.push(pack);
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
return results;
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Synchronously register detector packs (for when they're already imported).
|
|
83
|
+
*/
|
|
84
|
+
export function registerDetectors(packs) {
|
|
85
|
+
for (const pack of packs) {
|
|
86
|
+
registerDetector(pack);
|
|
87
|
+
}
|
|
88
|
+
}
|
|
89
|
+
//# sourceMappingURL=detector-registry.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"detector-registry.js","sourceRoot":"","sources":["../src/detector-registry.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAIH,MAAM,SAAS,GAAG,IAAI,GAAG,EAAwB,CAAC;AAElD,MAAM,UAAU,gBAAgB,CAAC,IAAkB;IACjD,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,EAAE,IAAI,CAAC,CAAC;AAC/B,CAAC;AAED,MAAM,UAAU,kBAAkB,CAAC,EAAU;IAC3C,SAAS,CAAC,MAAM,CAAC,EAAE,CAAC,CAAC;AACvB,CAAC;AAED,MAAM,UAAU,WAAW,CAAC,EAAU;IACpC,OAAO,SAAS,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC;AAC3B,CAAC;AAED,MAAM,UAAU,eAAe;IAC7B,OAAO,KAAK,CAAC,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,CAAC,CAAC;AACxC,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,qBAAqB,CAAC,UAAkB;IACtD,MAAM,OAAO,GAAmB,EAAE,CAAC;IACnC,KAAK,MAAM,IAAI,IAAI,SAAS,CAAC,MAAM,EAAE,EAAE,CAAC;QACtC,KAAK,MAAM,OAAO,IAAI,IAAI,CAAC,YAAY,EAAE,CAAC;YACxC,IAAI,UAAU,KAAK,OAAO,IAAI,UAAU,CAAC,UAAU,CAAC,OAAO,GAAG,GAAG,CAAC,EAAE,CAAC;gBACnE,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;gBACnB,MAAM;YACR,CAAC;QACH,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,MAAM,UAAU,cAAc;IAC5B,SAAS,CAAC,KAAK,EAAE,CAAC;AACpB,CAAC;AAED,MAAM,UAAU,aAAa;IAC3B,OAAO,SAAS,CAAC,IAAI,CAAC;AACxB,CAAC;AAED;;GAEG;AACH,MAAM,CAAC,KAAK,UAAU,oBAAoB;IACxC,IAAI,CAAC;QACH,MAAM,OAAO,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC;YAChC,MAAM,CAAC,4BAA4B,CAAC;YACpC,MAAM,CAAC,2BAA2B,CAAC;YACnC,MAAM,CAAC,0BAA0B,CAAC;YAClC,MAAM,CAAC,8BAA8B,CAAC;YACtC,MAAM,CAAC,kCAAkC,CAAC;YAC1C,MAAM,CAAC,mCAAmC,CAAC;YAC3C,MAAM,CAAC,gCAAgC,CAAC;YACxC,MAAM,CAAC,wBAAwB,CAAC;YAChC,MAAM,CAAC,2BAA2B,CAAC;SACpC,CAAC,CAAC;QACH,KAAK,MAAM,GAAG,IAAI,OAAO,EAAE,CAAC;YAC1B,KAAK,MAAM,IAAI,IAAI,GAAG,CAAC,SAAS,EAAE,CAAC;gBACjC,gBAAgB,CAAC,IAAI,CAAC,CAAC;YACzB,CAAC;QACH,CAAC;IACH,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,MAAM,IAAI,KAAK,CAAC,qCAAsC,GAAa,CAAC,OAAO,EAAE,CAAC,CAAC;IACjF,CAAC;AACH,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,qBAAqB;IACnC,MAAM,OAAO,GAAmB,EAAE,CAAC;IACnC,KAAK,MAAM,IAAI,IAAI,SAAS,CAAC,MAAM,EAAE,EAAE,CAAC;QACtC,IAAI,IAAI,CAAC,YAAY,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YACnC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACrB,CAAC;IACH,CAAC;IACD,OAAO,OAAO,CAAC;AACjB,CAAC;AAED;;GAEG;AACH,MAAM,UAAU,iBAAiB,CAAC,KAAqB;IACrD,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,gBAAgB,CAAC,IAAI,CAAC,CAAC;IACzB,CAAC;AACH,CAAC"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Detector pack: Animation libraries (framer-motion)
|
|
3
|
+
*/
|
|
4
|
+
const framerMotionDetector = {
|
|
5
|
+
id: 'framer-motion',
|
|
6
|
+
libraryName: 'Framer Motion',
|
|
7
|
+
packageNames: ['framer-motion', 'motion'],
|
|
8
|
+
patternKind: 'animation',
|
|
9
|
+
detect(sourceFile, fullText) {
|
|
10
|
+
const results = [];
|
|
11
|
+
// Pattern: useAnimation() or useMotionValue() or motion.div with animate prop
|
|
12
|
+
const animateRe = /(?:const|let)\s+(\w+)\s*=\s*useAnimation\s*\(\s*\)/g;
|
|
13
|
+
let match;
|
|
14
|
+
while ((match = animateRe.exec(fullText)) !== null) {
|
|
15
|
+
const varName = match[1];
|
|
16
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
17
|
+
const endLine = startLine;
|
|
18
|
+
const snippet = fullText.substring(match.index, match.index + match[0].length);
|
|
19
|
+
results.push({
|
|
20
|
+
anchorImport: 'useAnimation',
|
|
21
|
+
startLine,
|
|
22
|
+
endLine,
|
|
23
|
+
snippet,
|
|
24
|
+
extractedParams: [
|
|
25
|
+
{ name: 'controlsName', slotType: 'identifier', value: varName, optional: false },
|
|
26
|
+
],
|
|
27
|
+
confidencePct: 80,
|
|
28
|
+
});
|
|
29
|
+
}
|
|
30
|
+
// Pattern: variants object for motion components
|
|
31
|
+
const variantsRe = /(?:export\s+)?const\s+(\w+)\s*(?::\s*Variants)?\s*=\s*\{[^}]*(?:hidden|visible|initial|animate|exit|enter|center|closed|open)\s*:/g;
|
|
32
|
+
while ((match = variantsRe.exec(fullText)) !== null) {
|
|
33
|
+
const hasImport = sourceFile.getImportDeclarations().some(imp => {
|
|
34
|
+
const mod = imp.getModuleSpecifierValue();
|
|
35
|
+
return mod === 'framer-motion' || mod === 'motion' || mod.startsWith('motion/') || mod.startsWith('framer-motion/');
|
|
36
|
+
});
|
|
37
|
+
if (!hasImport)
|
|
38
|
+
continue;
|
|
39
|
+
const varName = match[1];
|
|
40
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
41
|
+
let pos = match.index + match[0].length;
|
|
42
|
+
let braceDepth = 1;
|
|
43
|
+
while (pos < fullText.length && braceDepth > 0) {
|
|
44
|
+
if (fullText[pos] === '{')
|
|
45
|
+
braceDepth++;
|
|
46
|
+
if (fullText[pos] === '}')
|
|
47
|
+
braceDepth--;
|
|
48
|
+
pos++;
|
|
49
|
+
}
|
|
50
|
+
const endLine = fullText.substring(0, pos).split('\n').length;
|
|
51
|
+
const snippet = fullText.substring(match.index, Math.min(pos, match.index + 300));
|
|
52
|
+
results.push({
|
|
53
|
+
anchorImport: 'Variants',
|
|
54
|
+
startLine,
|
|
55
|
+
endLine,
|
|
56
|
+
snippet,
|
|
57
|
+
extractedParams: [
|
|
58
|
+
{ name: 'variantsName', slotType: 'identifier', value: varName, optional: false },
|
|
59
|
+
],
|
|
60
|
+
confidencePct: 75,
|
|
61
|
+
});
|
|
62
|
+
}
|
|
63
|
+
return results;
|
|
64
|
+
},
|
|
65
|
+
};
|
|
66
|
+
export const detectors = [framerMotionDetector];
|
|
67
|
+
//# sourceMappingURL=animation.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"animation.js","sourceRoot":"","sources":["../../src/detectors/animation.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Detector pack: Data fetching libraries (axios, ky)
|
|
3
|
+
*/
|
|
4
|
+
const axiosInstanceDetector = {
|
|
5
|
+
id: 'axios-instance',
|
|
6
|
+
libraryName: 'Axios',
|
|
7
|
+
packageNames: ['axios'],
|
|
8
|
+
patternKind: 'data-fetching',
|
|
9
|
+
detect(sourceFile, fullText) {
|
|
10
|
+
const results = [];
|
|
11
|
+
// Pattern: axios.create({ baseURL, headers, ... })
|
|
12
|
+
const createRe = /(?:export\s+)?const\s+(\w+)\s*=\s*axios\.create\s*\(\s*\{/g;
|
|
13
|
+
let match;
|
|
14
|
+
while ((match = createRe.exec(fullText)) !== null) {
|
|
15
|
+
const varName = match[1];
|
|
16
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
17
|
+
const afterMatch = fullText.substring(match.index);
|
|
18
|
+
const baseUrlMatch = afterMatch.match(/baseURL\s*:\s*['"]([^'"]+)['"]/);
|
|
19
|
+
let pos = match.index + match[0].length;
|
|
20
|
+
let braceDepth = 1;
|
|
21
|
+
while (pos < fullText.length && braceDepth > 0) {
|
|
22
|
+
if (fullText[pos] === '{')
|
|
23
|
+
braceDepth++;
|
|
24
|
+
if (fullText[pos] === '}')
|
|
25
|
+
braceDepth--;
|
|
26
|
+
pos++;
|
|
27
|
+
}
|
|
28
|
+
if (pos < fullText.length && fullText[pos] === ')')
|
|
29
|
+
pos++;
|
|
30
|
+
const endLine = fullText.substring(0, pos).split('\n').length;
|
|
31
|
+
const snippet = fullText.substring(match.index, Math.min(pos, match.index + 300));
|
|
32
|
+
results.push({
|
|
33
|
+
anchorImport: 'axios',
|
|
34
|
+
startLine,
|
|
35
|
+
endLine,
|
|
36
|
+
snippet,
|
|
37
|
+
extractedParams: [
|
|
38
|
+
{ name: 'instanceName', slotType: 'identifier', value: varName, optional: false },
|
|
39
|
+
{ name: 'baseURL', slotType: 'expr', value: baseUrlMatch?.[1] || '/api', optional: true },
|
|
40
|
+
],
|
|
41
|
+
confidencePct: 82,
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
// Pattern: axios interceptor setup
|
|
45
|
+
const interceptorRe = /(\w+)\.interceptors\.(request|response)\.use\s*\(/g;
|
|
46
|
+
while ((match = interceptorRe.exec(fullText)) !== null) {
|
|
47
|
+
const instanceName = match[1];
|
|
48
|
+
const interceptorType = match[2];
|
|
49
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
50
|
+
let pos = match.index + match[0].length;
|
|
51
|
+
let parenDepth = 1;
|
|
52
|
+
while (pos < fullText.length && parenDepth > 0) {
|
|
53
|
+
if (fullText[pos] === '(')
|
|
54
|
+
parenDepth++;
|
|
55
|
+
if (fullText[pos] === ')')
|
|
56
|
+
parenDepth--;
|
|
57
|
+
pos++;
|
|
58
|
+
}
|
|
59
|
+
const endLine = fullText.substring(0, pos).split('\n').length;
|
|
60
|
+
const snippet = fullText.substring(match.index, Math.min(pos, match.index + 300));
|
|
61
|
+
results.push({
|
|
62
|
+
anchorImport: 'axios',
|
|
63
|
+
startLine,
|
|
64
|
+
endLine,
|
|
65
|
+
snippet,
|
|
66
|
+
extractedParams: [
|
|
67
|
+
{ name: 'instanceName', slotType: 'identifier', value: instanceName, optional: false },
|
|
68
|
+
{ name: 'interceptorType', slotType: 'expr', value: interceptorType, optional: false },
|
|
69
|
+
],
|
|
70
|
+
confidencePct: 78,
|
|
71
|
+
});
|
|
72
|
+
}
|
|
73
|
+
return results;
|
|
74
|
+
},
|
|
75
|
+
};
|
|
76
|
+
const kyDetector = {
|
|
77
|
+
id: 'ky-instance',
|
|
78
|
+
libraryName: 'Ky',
|
|
79
|
+
packageNames: ['ky'],
|
|
80
|
+
patternKind: 'data-fetching',
|
|
81
|
+
detect(sourceFile, fullText) {
|
|
82
|
+
const results = [];
|
|
83
|
+
// Pattern: ky.create({ prefixUrl, hooks })
|
|
84
|
+
const createRe = /(?:export\s+)?const\s+(\w+)\s*=\s*ky\.create\s*\(\s*\{/g;
|
|
85
|
+
let match;
|
|
86
|
+
while ((match = createRe.exec(fullText)) !== null) {
|
|
87
|
+
const varName = match[1];
|
|
88
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
89
|
+
let pos = match.index + match[0].length;
|
|
90
|
+
let braceDepth = 1;
|
|
91
|
+
while (pos < fullText.length && braceDepth > 0) {
|
|
92
|
+
if (fullText[pos] === '{')
|
|
93
|
+
braceDepth++;
|
|
94
|
+
if (fullText[pos] === '}')
|
|
95
|
+
braceDepth--;
|
|
96
|
+
pos++;
|
|
97
|
+
}
|
|
98
|
+
if (pos < fullText.length && fullText[pos] === ')')
|
|
99
|
+
pos++;
|
|
100
|
+
const endLine = fullText.substring(0, pos).split('\n').length;
|
|
101
|
+
const snippet = fullText.substring(match.index, Math.min(pos, match.index + 300));
|
|
102
|
+
results.push({
|
|
103
|
+
anchorImport: 'ky',
|
|
104
|
+
startLine,
|
|
105
|
+
endLine,
|
|
106
|
+
snippet,
|
|
107
|
+
extractedParams: [
|
|
108
|
+
{ name: 'instanceName', slotType: 'identifier', value: varName, optional: false },
|
|
109
|
+
],
|
|
110
|
+
confidencePct: 78,
|
|
111
|
+
});
|
|
112
|
+
}
|
|
113
|
+
return results;
|
|
114
|
+
},
|
|
115
|
+
};
|
|
116
|
+
export const detectors = [axiosInstanceDetector, kyDetector];
|
|
117
|
+
//# sourceMappingURL=data-fetching.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"data-fetching.js","sourceRoot":"","sources":["../../src/detectors/data-fetching.ts"],"names":[],"mappings":"AAAA;;GAEG;AAKH,MAAM,qBAAqB,GAAiB;IAC1C,EAAE,EAAE,gBAAgB;IACpB,WAAW,EAAE,OAAO;IACpB,YAAY,EAAE,CAAC,OAAO,CAAC;IACvB,WAAW,EAAE,eAAe;IAC5B,MAAM,CAAC,UAAsB,EAAE,QAAgB;QAC7C,MAAM,OAAO,GAAsB,EAAE,CAAC;QAEtC,mDAAmD;QACnD,MAAM,QAAQ,GAAG,4DAA4D,CAAC;QAC9E,IAAI,KAA6B,CAAC;QAClC,OAAO,CAAC,KAAK,GAAG,QAAQ,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,KAAK,IAAI,EAAE,CAAC;YAClD,MAAM,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;YACzB,MAAM,SAAS,GAAG,QAAQ,CAAC,SAAS,CAAC,CAAC,EAAE,KAAK,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC;YAExE,MAAM,UAAU,GAAG,QAAQ,CAAC,SAAS,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC;YACnD,MAAM,YAAY,GAAG,UAAU,CAAC,KAAK,CAAC,gCAAgC,CAAC,CAAC;YAExE,IAAI,GAAG,GAAG,KAAK,CAAC,KAAK,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC;YACxC,IAAI,UAAU,GAAG,CAAC,CAAC;YACnB,OAAO,GAAG,GAAG,QAAQ,CAAC,MAAM,IAAI,UAAU,GAAG,CAAC,EAAE,CAAC;gBAC/C,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;oBAAE,UAAU,EAAE,CAAC;gBACxC,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;oBAAE,UAAU,EAAE,CAAC;gBACxC,GAAG,EAAE,CAAC;YACR,CAAC;YACD,IAAI,GAAG,GAAG,QAAQ,CAAC,MAAM,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;gBAAE,GAAG,EAAE,CAAC;YAC1D,MAAM,OAAO,GAAG,QAAQ,CAAC,SAAS,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC;YAC9D,MAAM,OAAO,GAAG,QAAQ,CAAC,SAAS,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,KAAK,GAAG,GAAG,CAAC,CAAC,CAAC;YAElF,OAAO,CAAC,IAAI,CAAC;gBACX,YAAY,EAAE,OAAO;gBACrB,SAAS;gBACT,OAAO;gBACP,OAAO;gBACP,eAAe,EAAE;oBACf,EAAE,IAAI,EAAE,cAAc,EAAE,QAAQ,EAAE,YAAY,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,KAAK,EAAE;oBACjF,EAAE,IAAI,EAAE,SAAS,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,YAAY,EAAE,CAAC,CAAC,CAAC,IAAI,MAAM,EAAE,QAAQ,EAAE,IAAI,EAAE;iBAC1F;gBACD,aAAa,EAAE,EAAE;aAClB,CAAC,CAAC;QACL,CAAC;QAED,mCAAmC;QACnC,MAAM,aAAa,GAAG,oDAAoD,CAAC;QAC3E,OAAO,CAAC,KAAK,GAAG,aAAa,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,KAAK,IAAI,EAAE,CAAC;YACvD,MAAM,YAAY,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;YAC9B,MAAM,eAAe,GAAG,KAAK,CAAC,CAAC,CAA2B,CAAC;YAC3D,MAAM,SAAS,GAAG,QAAQ,CAAC,SAAS,CAAC,CAAC,EAAE,KAAK,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC;YAExE,IAAI,GAAG,GAAG,KAAK,CAAC,KAAK,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC;YACxC,IAAI,UAAU,GAAG,CAAC,CAAC;YACnB,OAAO,GAAG,GAAG,QAAQ,CAAC,MAAM,IAAI,UAAU,GAAG,CAAC,EAAE,CAAC;gBAC/C,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;oBAAE,UAAU,EAAE,CAAC;gBACxC,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;oBAAE,UAAU,EAAE,CAAC;gBACxC,GAAG,EAAE,CAAC;YACR,CAAC;YACD,MAAM,OAAO,GAAG,QAAQ,CAAC,SAAS,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC;YAC9D,MAAM,OAAO,GAAG,QAAQ,CAAC,SAAS,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,KAAK,GAAG,GAAG,CAAC,CAAC,CAAC;YAElF,OAAO,CAAC,IAAI,CAAC;gBACX,YAAY,EAAE,OAAO;gBACrB,SAAS;gBACT,OAAO;gBACP,OAAO;gBACP,eAAe,EAAE;oBACf,EAAE,IAAI,EAAE,cAAc,EAAE,QAAQ,EAAE,YAAY,EAAE,KAAK,EAAE,YAAY,EAAE,QAAQ,EAAE,KAAK,EAAE;oBACtF,EAAE,IAAI,EAAE,iBAAiB,EAAE,QAAQ,EAAE,MAAM,EAAE,KAAK,EAAE,eAAe,EAAE,QAAQ,EAAE,KAAK,EAAE;iBACvF;gBACD,aAAa,EAAE,EAAE;aAClB,CAAC,CAAC;QACL,CAAC;QAED,OAAO,OAAO,CAAC;IACjB,CAAC;CACF,CAAC;AAEF,MAAM,UAAU,GAAiB;IAC/B,EAAE,EAAE,aAAa;IACjB,WAAW,EAAE,IAAI;IACjB,YAAY,EAAE,CAAC,IAAI,CAAC;IACpB,WAAW,EAAE,eAAe;IAC5B,MAAM,CAAC,UAAsB,EAAE,QAAgB;QAC7C,MAAM,OAAO,GAAsB,EAAE,CAAC;QAEtC,2CAA2C;QAC3C,MAAM,QAAQ,GAAG,yDAAyD,CAAC;QAC3E,IAAI,KAA6B,CAAC;QAClC,OAAO,CAAC,KAAK,GAAG,QAAQ,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC,KAAK,IAAI,EAAE,CAAC;YAClD,MAAM,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;YACzB,MAAM,SAAS,GAAG,QAAQ,CAAC,SAAS,CAAC,CAAC,EAAE,KAAK,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC;YAExE,IAAI,GAAG,GAAG,KAAK,CAAC,KAAK,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC;YACxC,IAAI,UAAU,GAAG,CAAC,CAAC;YACnB,OAAO,GAAG,GAAG,QAAQ,CAAC,MAAM,IAAI,UAAU,GAAG,CAAC,EAAE,CAAC;gBAC/C,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;oBAAE,UAAU,EAAE,CAAC;gBACxC,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;oBAAE,UAAU,EAAE,CAAC;gBACxC,GAAG,EAAE,CAAC;YACR,CAAC;YACD,IAAI,GAAG,GAAG,QAAQ,CAAC,MAAM,IAAI,QAAQ,CAAC,GAAG,CAAC,KAAK,GAAG;gBAAE,GAAG,EAAE,CAAC;YAC1D,MAAM,OAAO,GAAG,QAAQ,CAAC,SAAS,CAAC,CAAC,EAAE,GAAG,CAAC,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,MAAM,CAAC;YAC9D,MAAM,OAAO,GAAG,QAAQ,CAAC,SAAS,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,KAAK,CAAC,KAAK,GAAG,GAAG,CAAC,CAAC,CAAC;YAElF,OAAO,CAAC,IAAI,CAAC;gBACX,YAAY,EAAE,IAAI;gBAClB,SAAS;gBACT,OAAO;gBACP,OAAO;gBACP,eAAe,EAAE;oBACf,EAAE,IAAI,EAAE,cAAc,EAAE,QAAQ,EAAE,YAAY,EAAE,KAAK,EAAE,OAAO,EAAE,QAAQ,EAAE,KAAK,EAAE;iBAClF;gBACD,aAAa,EAAE,EAAE;aAClB,CAAC,CAAC;QACL,CAAC;QAED,OAAO,OAAO,CAAC;IACjB,CAAC;CACF,CAAC;AAEF,MAAM,CAAC,MAAM,SAAS,GAAmB,CAAC,qBAAqB,EAAE,UAAU,CAAC,CAAC"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Detector pack: Express middleware (cors, helmet, rate-limit)
|
|
3
|
+
*/
|
|
4
|
+
const expressMiddlewareDetector = {
|
|
5
|
+
id: 'express-middleware',
|
|
6
|
+
libraryName: 'Express Middleware',
|
|
7
|
+
packageNames: ['cors', 'helmet', 'express-rate-limit'],
|
|
8
|
+
patternKind: 'middleware',
|
|
9
|
+
detect(sourceFile, fullText) {
|
|
10
|
+
const results = [];
|
|
11
|
+
const imports = sourceFile.getImportDeclarations();
|
|
12
|
+
// Detect app.use(cors(...)) patterns — only multi-middleware stacks are template-worthy
|
|
13
|
+
const appUseRe = /app\.use\s*\(\s*(\w+)\s*\(\s*(\{[^}]*\})?\s*\)\s*\)/g;
|
|
14
|
+
const middlewareCalls = [];
|
|
15
|
+
let match;
|
|
16
|
+
while ((match = appUseRe.exec(fullText)) !== null) {
|
|
17
|
+
const mwName = match[1];
|
|
18
|
+
const config = match[2] || '';
|
|
19
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
20
|
+
const endLine = fullText.substring(0, match.index + match[0].length).split('\n').length;
|
|
21
|
+
const snippet = match[0];
|
|
22
|
+
// Only detect if the middleware import exists
|
|
23
|
+
const hasImport = imports.some(imp => {
|
|
24
|
+
const names = imp.getNamedImports().map(n => n.getName());
|
|
25
|
+
const defaultName = imp.getDefaultImport()?.getText();
|
|
26
|
+
return names.includes(mwName) || defaultName === mwName;
|
|
27
|
+
});
|
|
28
|
+
if (hasImport) {
|
|
29
|
+
middlewareCalls.push({ name: mwName, startLine, endLine, snippet, config });
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
// Only create a detection if there are 2+ middleware calls (pattern worth templating)
|
|
33
|
+
if (middlewareCalls.length >= 2) {
|
|
34
|
+
results.push({
|
|
35
|
+
anchorImport: middlewareCalls[0].name,
|
|
36
|
+
startLine: middlewareCalls[0].startLine,
|
|
37
|
+
endLine: middlewareCalls[middlewareCalls.length - 1].endLine,
|
|
38
|
+
snippet: middlewareCalls.map(m => m.snippet).join('\n'),
|
|
39
|
+
extractedParams: middlewareCalls.map(m => ({
|
|
40
|
+
name: m.name,
|
|
41
|
+
slotType: 'expr',
|
|
42
|
+
value: m.config || '{}',
|
|
43
|
+
optional: true,
|
|
44
|
+
})),
|
|
45
|
+
confidencePct: 72,
|
|
46
|
+
});
|
|
47
|
+
}
|
|
48
|
+
return results;
|
|
49
|
+
},
|
|
50
|
+
};
|
|
51
|
+
export const detectors = [expressMiddlewareDetector];
|
|
52
|
+
//# sourceMappingURL=express-middleware.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"express-middleware.js","sourceRoot":"","sources":["../../src/detectors/express-middleware.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,89 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Detector pack: React form libraries (react-hook-form, formik)
|
|
3
|
+
*/
|
|
4
|
+
const reactHookFormDetector = {
|
|
5
|
+
id: 'react-hook-form',
|
|
6
|
+
libraryName: 'React Hook Form',
|
|
7
|
+
packageNames: ['react-hook-form'],
|
|
8
|
+
patternKind: 'form-hook',
|
|
9
|
+
detect(sourceFile, fullText) {
|
|
10
|
+
const results = [];
|
|
11
|
+
// Pattern: useForm<Schema>() with destructured register, handleSubmit, formState
|
|
12
|
+
const useFormRe = /(?:const|let)\s+\{([^}]+)\}\s*=\s*useForm\s*(?:<\s*(\w+)\s*>)?\s*\(/g;
|
|
13
|
+
let match;
|
|
14
|
+
while ((match = useFormRe.exec(fullText)) !== null) {
|
|
15
|
+
const destructured = match[1].trim();
|
|
16
|
+
const schemaType = match[2] || 'any';
|
|
17
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
18
|
+
// Find the enclosing function/component for end line
|
|
19
|
+
const remaining = fullText.substring(match.index);
|
|
20
|
+
const closingMatch = remaining.match(/\}\s*\)/);
|
|
21
|
+
const endOffset = closingMatch ? match.index + closingMatch.index + closingMatch[0].length : match.index + match[0].length;
|
|
22
|
+
const endLine = fullText.substring(0, endOffset).split('\n').length;
|
|
23
|
+
// Try to extract the component/function name (limit lookback to avoid backtracking)
|
|
24
|
+
const beforeMatch = fullText.substring(Math.max(0, match.index - 500), match.index);
|
|
25
|
+
const fnNameMatch = beforeMatch.match(/(?:function|const)\s+(\w+)\s*(?:=|\(|<)[^]*$/);
|
|
26
|
+
const formName = fnNameMatch ? fnNameMatch[1] : 'Form';
|
|
27
|
+
const snippet = fullText.substring(match.index, Math.min(endOffset, match.index + 300));
|
|
28
|
+
results.push({
|
|
29
|
+
anchorImport: 'useForm',
|
|
30
|
+
startLine,
|
|
31
|
+
endLine,
|
|
32
|
+
snippet,
|
|
33
|
+
extractedParams: [
|
|
34
|
+
{ name: 'formName', slotType: 'identifier', value: formName, optional: false },
|
|
35
|
+
{ name: 'schema', slotType: 'type', value: schemaType, optional: false },
|
|
36
|
+
{ name: 'fields', slotType: 'expr', value: destructured, optional: true },
|
|
37
|
+
],
|
|
38
|
+
confidencePct: schemaType !== 'any' ? 90 : 75,
|
|
39
|
+
});
|
|
40
|
+
}
|
|
41
|
+
return results;
|
|
42
|
+
},
|
|
43
|
+
};
|
|
44
|
+
const formikDetector = {
|
|
45
|
+
id: 'formik',
|
|
46
|
+
libraryName: 'Formik',
|
|
47
|
+
packageNames: ['formik'],
|
|
48
|
+
patternKind: 'form-hook',
|
|
49
|
+
detect(sourceFile, fullText) {
|
|
50
|
+
const results = [];
|
|
51
|
+
// Pattern: useFormik({ initialValues, validationSchema, onSubmit })
|
|
52
|
+
const useFormikRe = /(?:const|let)\s+(\w+)\s*=\s*useFormik\s*(?:<\s*(\w+)\s*>)?\s*\(\s*\{/g;
|
|
53
|
+
let match;
|
|
54
|
+
while ((match = useFormikRe.exec(fullText)) !== null) {
|
|
55
|
+
const varName = match[1];
|
|
56
|
+
const typeParam = match[2] || 'any';
|
|
57
|
+
const startLine = fullText.substring(0, match.index).split('\n').length;
|
|
58
|
+
// Find end of the useFormik call
|
|
59
|
+
let braceDepth = 1;
|
|
60
|
+
let pos = match.index + match[0].length;
|
|
61
|
+
while (pos < fullText.length && braceDepth > 0) {
|
|
62
|
+
if (fullText[pos] === '{')
|
|
63
|
+
braceDepth++;
|
|
64
|
+
if (fullText[pos] === '}')
|
|
65
|
+
braceDepth--;
|
|
66
|
+
pos++;
|
|
67
|
+
}
|
|
68
|
+
// Skip past the closing )
|
|
69
|
+
if (pos < fullText.length && fullText[pos] === ')')
|
|
70
|
+
pos++;
|
|
71
|
+
const endLine = fullText.substring(0, pos).split('\n').length;
|
|
72
|
+
const snippet = fullText.substring(match.index, Math.min(pos, match.index + 300));
|
|
73
|
+
results.push({
|
|
74
|
+
anchorImport: 'useFormik',
|
|
75
|
+
startLine,
|
|
76
|
+
endLine,
|
|
77
|
+
snippet,
|
|
78
|
+
extractedParams: [
|
|
79
|
+
{ name: 'formikName', slotType: 'identifier', value: varName, optional: false },
|
|
80
|
+
{ name: 'valuesType', slotType: 'type', value: typeParam, optional: false },
|
|
81
|
+
],
|
|
82
|
+
confidencePct: typeParam !== 'any' ? 85 : 70,
|
|
83
|
+
});
|
|
84
|
+
}
|
|
85
|
+
return results;
|
|
86
|
+
},
|
|
87
|
+
};
|
|
88
|
+
export const detectors = [reactHookFormDetector, formikDetector];
|
|
89
|
+
//# sourceMappingURL=react-forms.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"react-forms.js","sourceRoot":"","sources":["../../src/detectors/react-forms.ts"],"names":[],"mappings":"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"}
|