@loxia-labs/loxia-autopilot-one 1.0.1 → 1.0.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (120) hide show
  1. package/README.md +44 -54
  2. package/bin/cli.js +1 -115
  3. package/bin/loxia-terminal-v2.js +3 -0
  4. package/bin/loxia-terminal.js +3 -0
  5. package/bin/start-with-terminal.js +3 -0
  6. package/package.json +15 -15
  7. package/scripts/install-scanners.js +1 -235
  8. package/src/analyzers/CSSAnalyzer.js +1 -297
  9. package/src/analyzers/ConfigValidator.js +1 -690
  10. package/src/analyzers/ESLintAnalyzer.js +1 -320
  11. package/src/analyzers/JavaScriptAnalyzer.js +1 -261
  12. package/src/analyzers/PrettierFormatter.js +1 -247
  13. package/src/analyzers/PythonAnalyzer.js +1 -266
  14. package/src/analyzers/SecurityAnalyzer.js +1 -729
  15. package/src/analyzers/TypeScriptAnalyzer.js +1 -247
  16. package/src/analyzers/codeCloneDetector/analyzer.js +1 -344
  17. package/src/analyzers/codeCloneDetector/detector.js +1 -203
  18. package/src/analyzers/codeCloneDetector/index.js +1 -160
  19. package/src/analyzers/codeCloneDetector/parser.js +1 -199
  20. package/src/analyzers/codeCloneDetector/reporter.js +1 -148
  21. package/src/analyzers/codeCloneDetector/scanner.js +1 -59
  22. package/src/core/agentPool.js +1 -1474
  23. package/src/core/agentScheduler.js +1 -2147
  24. package/src/core/contextManager.js +1 -709
  25. package/src/core/messageProcessor.js +1 -732
  26. package/src/core/orchestrator.js +1 -548
  27. package/src/core/stateManager.js +1 -877
  28. package/src/index.js +1 -631
  29. package/src/interfaces/cli.js +1 -549
  30. package/src/interfaces/terminal/__tests__/smoke/advancedFeatures.test.js +1 -0
  31. package/src/interfaces/terminal/__tests__/smoke/agentControl.test.js +1 -0
  32. package/src/interfaces/terminal/__tests__/smoke/agents.test.js +1 -0
  33. package/src/interfaces/terminal/__tests__/smoke/components.test.js +1 -0
  34. package/src/interfaces/terminal/__tests__/smoke/connection.test.js +1 -0
  35. package/src/interfaces/terminal/__tests__/smoke/enhancements.test.js +1 -0
  36. package/src/interfaces/terminal/__tests__/smoke/imports.test.js +1 -0
  37. package/src/interfaces/terminal/__tests__/smoke/messages.test.js +1 -0
  38. package/src/interfaces/terminal/__tests__/smoke/tools.test.js +1 -0
  39. package/src/interfaces/terminal/api/apiClient.js +1 -0
  40. package/src/interfaces/terminal/api/messageRouter.js +1 -0
  41. package/src/interfaces/terminal/api/session.js +1 -0
  42. package/src/interfaces/terminal/api/websocket.js +1 -0
  43. package/src/interfaces/terminal/components/AgentCreator.js +1 -0
  44. package/src/interfaces/terminal/components/AgentEditor.js +1 -0
  45. package/src/interfaces/terminal/components/AgentSwitcher.js +1 -0
  46. package/src/interfaces/terminal/components/ErrorBoundary.js +1 -0
  47. package/src/interfaces/terminal/components/ErrorPanel.js +1 -0
  48. package/src/interfaces/terminal/components/Header.js +1 -0
  49. package/src/interfaces/terminal/components/HelpPanel.js +1 -0
  50. package/src/interfaces/terminal/components/InputBox.js +1 -0
  51. package/src/interfaces/terminal/components/Layout.js +1 -0
  52. package/src/interfaces/terminal/components/LoadingSpinner.js +1 -0
  53. package/src/interfaces/terminal/components/MessageList.js +1 -0
  54. package/src/interfaces/terminal/components/MultilineTextInput.js +1 -0
  55. package/src/interfaces/terminal/components/SearchPanel.js +1 -0
  56. package/src/interfaces/terminal/components/SettingsPanel.js +1 -0
  57. package/src/interfaces/terminal/components/StatusBar.js +1 -0
  58. package/src/interfaces/terminal/components/TextInput.js +1 -0
  59. package/src/interfaces/terminal/config/agentEditorConstants.js +1 -0
  60. package/src/interfaces/terminal/config/constants.js +1 -0
  61. package/src/interfaces/terminal/index.js +1 -0
  62. package/src/interfaces/terminal/state/useAgentControl.js +1 -0
  63. package/src/interfaces/terminal/state/useAgents.js +1 -0
  64. package/src/interfaces/terminal/state/useConnection.js +1 -0
  65. package/src/interfaces/terminal/state/useMessages.js +1 -0
  66. package/src/interfaces/terminal/state/useTools.js +1 -0
  67. package/src/interfaces/terminal/utils/debugLogger.js +1 -0
  68. package/src/interfaces/terminal/utils/settingsStorage.js +1 -0
  69. package/src/interfaces/terminal/utils/theme.js +1 -0
  70. package/src/interfaces/webServer.js +1 -2162
  71. package/src/modules/fileExplorer/controller.js +1 -280
  72. package/src/modules/fileExplorer/index.js +1 -37
  73. package/src/modules/fileExplorer/middleware.js +1 -92
  74. package/src/modules/fileExplorer/routes.js +1 -125
  75. package/src/modules/fileExplorer/types.js +1 -44
  76. package/src/services/aiService.js +1 -1232
  77. package/src/services/apiKeyManager.js +1 -164
  78. package/src/services/benchmarkService.js +1 -366
  79. package/src/services/budgetService.js +1 -539
  80. package/src/services/contextInjectionService.js +1 -247
  81. package/src/services/conversationCompactionService.js +1 -637
  82. package/src/services/errorHandler.js +1 -810
  83. package/src/services/fileAttachmentService.js +1 -544
  84. package/src/services/modelRouterService.js +1 -366
  85. package/src/services/modelsService.js +1 -322
  86. package/src/services/qualityInspector.js +1 -796
  87. package/src/services/tokenCountingService.js +1 -536
  88. package/src/tools/agentCommunicationTool.js +1 -1344
  89. package/src/tools/agentDelayTool.js +1 -485
  90. package/src/tools/asyncToolManager.js +1 -604
  91. package/src/tools/baseTool.js +1 -800
  92. package/src/tools/browserTool.js +1 -920
  93. package/src/tools/cloneDetectionTool.js +1 -621
  94. package/src/tools/dependencyResolverTool.js +1 -1215
  95. package/src/tools/fileContentReplaceTool.js +1 -875
  96. package/src/tools/fileSystemTool.js +1 -1107
  97. package/src/tools/fileTreeTool.js +1 -853
  98. package/src/tools/imageTool.js +1 -901
  99. package/src/tools/importAnalyzerTool.js +1 -1060
  100. package/src/tools/jobDoneTool.js +1 -248
  101. package/src/tools/seekTool.js +1 -956
  102. package/src/tools/staticAnalysisTool.js +1 -1778
  103. package/src/tools/taskManagerTool.js +1 -2873
  104. package/src/tools/terminalTool.js +1 -2304
  105. package/src/tools/webTool.js +1 -1430
  106. package/src/types/agent.js +1 -519
  107. package/src/types/contextReference.js +1 -972
  108. package/src/types/conversation.js +1 -730
  109. package/src/types/toolCommand.js +1 -747
  110. package/src/utilities/attachmentValidator.js +1 -292
  111. package/src/utilities/configManager.js +1 -582
  112. package/src/utilities/constants.js +1 -722
  113. package/src/utilities/directoryAccessManager.js +1 -535
  114. package/src/utilities/fileProcessor.js +1 -307
  115. package/src/utilities/logger.js +1 -436
  116. package/src/utilities/tagParser.js +1 -1246
  117. package/src/utilities/toolConstants.js +1 -317
  118. package/web-ui/build/index.html +2 -2
  119. package/web-ui/build/static/{index-Dy2bYbOa.css → index-CClD1090.css} +1 -1
  120. package/web-ui/build/static/{index-CjkkcnFA.js → index-lCBai6dX.js} +66 -67
@@ -1,247 +1 @@
1
- /**
2
- * TypeScriptAnalyzer - Analyze TypeScript files for errors using TypeScript Compiler API
3
- *
4
- * Purpose:
5
- * - Analyze TypeScript files for syntax, type, and semantic errors
6
- * - Use TypeScript Compiler API with full type checking
7
- * - Provide detailed error information with line numbers
8
- * - Support TSX syntax
9
- */
10
-
11
- import ts from 'typescript';
12
- import path from 'path';
13
- import { STATIC_ANALYSIS } from '../utilities/constants.js';
14
-
15
- class TypeScriptAnalyzer {
16
- constructor(logger = null) {
17
- this.logger = logger;
18
- this.compilerOptions = {
19
- noEmit: true,
20
- jsx: ts.JsxEmit.React,
21
- target: ts.ScriptTarget.Latest,
22
- module: ts.ModuleKind.ESNext,
23
- moduleResolution: ts.ModuleResolutionKind.NodeJs,
24
- esModuleInterop: true,
25
- skipLibCheck: true,
26
- strict: true, // Enable strict type checking for TypeScript
27
- noImplicitAny: true,
28
- strictNullChecks: true,
29
- strictFunctionTypes: true,
30
- allowJs: false // TypeScript only
31
- };
32
- }
33
-
34
- /**
35
- * Analyze TypeScript file for errors
36
- * @param {string} filePath - Path to file
37
- * @param {string} content - File content
38
- * @param {Object} options - Analysis options
39
- * @returns {Promise<Array>} Array of diagnostic errors
40
- */
41
- async analyze(filePath, content, options = {}) {
42
- try {
43
- const diagnostics = [];
44
-
45
- // Create in-memory source file
46
- const sourceFile = ts.createSourceFile(
47
- filePath,
48
- content,
49
- ts.ScriptTarget.Latest,
50
- true // setParentNodes
51
- );
52
-
53
- // Get syntactic diagnostics (syntax errors)
54
- const syntacticDiagnostics = this.getSyntacticDiagnostics(sourceFile);
55
- diagnostics.push(...syntacticDiagnostics);
56
-
57
- // Get semantic diagnostics (type errors, undefined variables, etc.)
58
- const semanticDiagnostics = await this.getSemanticDiagnostics(filePath, content);
59
- diagnostics.push(...semanticDiagnostics);
60
-
61
- this.logger?.debug('TypeScript analysis completed', {
62
- file: filePath,
63
- totalDiagnostics: diagnostics.length,
64
- errors: diagnostics.filter(d => d.severity === STATIC_ANALYSIS.SEVERITY.ERROR).length,
65
- warnings: diagnostics.filter(d => d.severity === STATIC_ANALYSIS.SEVERITY.WARNING).length
66
- });
67
-
68
- return diagnostics;
69
-
70
- } catch (error) {
71
- this.logger?.error('TypeScript analysis failed', {
72
- file: filePath,
73
- error: error.message
74
- });
75
-
76
- return [{
77
- file: filePath,
78
- line: 0,
79
- column: 0,
80
- severity: STATIC_ANALYSIS.SEVERITY.ERROR,
81
- rule: 'analyzer-error',
82
- message: `Analysis failed: ${error.message}`,
83
- category: STATIC_ANALYSIS.CATEGORY.SYNTAX
84
- }];
85
- }
86
- }
87
-
88
- /**
89
- * Get syntactic diagnostics (syntax errors)
90
- * @private
91
- */
92
- getSyntacticDiagnostics(sourceFile) {
93
- const diagnostics = [];
94
-
95
- // Check for parsing errors
96
- if (sourceFile.parseDiagnostics && sourceFile.parseDiagnostics.length > 0) {
97
- for (const diagnostic of sourceFile.parseDiagnostics) {
98
- diagnostics.push(this.formatDiagnostic(diagnostic, sourceFile));
99
- }
100
- }
101
-
102
- return diagnostics;
103
- }
104
-
105
- /**
106
- * Get semantic diagnostics (type errors, undefined variables)
107
- * @private
108
- */
109
- async getSemanticDiagnostics(filePath, content) {
110
- const diagnostics = [];
111
-
112
- try {
113
- // Create a minimal program for semantic analysis
114
- const sourceFile = ts.createSourceFile(
115
- filePath,
116
- content,
117
- ts.ScriptTarget.Latest,
118
- true
119
- );
120
-
121
- // Create a compiler host that provides files from memory
122
- const host = {
123
- getSourceFile: (fileName) => {
124
- if (fileName === filePath) {
125
- return sourceFile;
126
- }
127
- // Return undefined for library files - they won't be available
128
- return undefined;
129
- },
130
- getDefaultLibFileName: () => 'lib.d.ts',
131
- writeFile: () => {},
132
- getCurrentDirectory: () => path.dirname(filePath),
133
- getDirectories: () => [],
134
- fileExists: (fileName) => fileName === filePath,
135
- readFile: (fileName) => {
136
- if (fileName === filePath) {
137
- return content;
138
- }
139
- return undefined;
140
- },
141
- getCanonicalFileName: (fileName) => fileName,
142
- useCaseSensitiveFileNames: () => true,
143
- getNewLine: () => '\n'
144
- };
145
-
146
- // Create program
147
- const program = ts.createProgram({
148
- rootNames: [filePath],
149
- options: this.compilerOptions,
150
- host
151
- });
152
-
153
- // Get all diagnostics
154
- const syntactic = program.getSyntacticDiagnostics(sourceFile);
155
- const semantic = program.getSemanticDiagnostics(sourceFile);
156
-
157
- for (const diagnostic of [...syntactic, ...semantic]) {
158
- diagnostics.push(this.formatDiagnostic(diagnostic, sourceFile));
159
- }
160
-
161
- } catch (error) {
162
- this.logger?.debug('Semantic analysis encountered error', {
163
- file: filePath,
164
- error: error.message
165
- });
166
- }
167
-
168
- return diagnostics;
169
- }
170
-
171
- /**
172
- * Format TypeScript diagnostic to standard error format
173
- * @private
174
- */
175
- formatDiagnostic(diagnostic, sourceFile) {
176
- let line = 0;
177
- let column = 0;
178
-
179
- if (diagnostic.file && diagnostic.start !== undefined) {
180
- const position = diagnostic.file.getLineAndCharacterOfPosition(diagnostic.start);
181
- line = position.line + 1; // 1-indexed
182
- column = position.character + 1;
183
- } else if (sourceFile && diagnostic.start !== undefined) {
184
- const position = sourceFile.getLineAndCharacterOfPosition(diagnostic.start);
185
- line = position.line + 1;
186
- column = position.character + 1;
187
- }
188
-
189
- const message = ts.flattenDiagnosticMessageText(diagnostic.messageText, '\n');
190
-
191
- // Determine severity
192
- let severity;
193
- switch (diagnostic.category) {
194
- case ts.DiagnosticCategory.Error:
195
- severity = STATIC_ANALYSIS.SEVERITY.ERROR;
196
- break;
197
- case ts.DiagnosticCategory.Warning:
198
- severity = STATIC_ANALYSIS.SEVERITY.WARNING;
199
- break;
200
- case ts.DiagnosticCategory.Message:
201
- case ts.DiagnosticCategory.Suggestion:
202
- severity = STATIC_ANALYSIS.SEVERITY.INFO;
203
- break;
204
- default:
205
- severity = STATIC_ANALYSIS.SEVERITY.ERROR;
206
- }
207
-
208
- // Determine category based on error code and message
209
- let category = STATIC_ANALYSIS.CATEGORY.SYNTAX;
210
- const code = diagnostic.code;
211
-
212
- // Categorize based on error code ranges
213
- if (code >= 2000 && code < 3000) {
214
- category = STATIC_ANALYSIS.CATEGORY.TYPE;
215
- } else if (code >= 1000 && code < 2000) {
216
- category = STATIC_ANALYSIS.CATEGORY.SYNTAX;
217
- } else if (code >= 2300 && code < 2400) {
218
- category = STATIC_ANALYSIS.CATEGORY.IMPORT;
219
- }
220
-
221
- // Check message content for more specific categorization
222
- const lowerMessage = message.toLowerCase();
223
- if (lowerMessage.includes('cannot find module') ||
224
- lowerMessage.includes('import') ||
225
- lowerMessage.includes('export')) {
226
- category = STATIC_ANALYSIS.CATEGORY.IMPORT;
227
- } else if (lowerMessage.includes('type') ||
228
- lowerMessage.includes('interface') ||
229
- lowerMessage.includes('class')) {
230
- category = STATIC_ANALYSIS.CATEGORY.TYPE;
231
- }
232
-
233
- return {
234
- file: diagnostic.file?.fileName || sourceFile?.fileName || 'unknown',
235
- line,
236
- column,
237
- severity,
238
- rule: `TS${code}`,
239
- message,
240
- category,
241
- fixable: false, // TypeScript doesn't provide fix information easily
242
- code: diagnostic.code
243
- };
244
- }
245
- }
246
-
247
- export default TypeScriptAnalyzer;
1
+ const a0_0x25ad85=a0_0x593d;(function(_0x1e954d,_0x3b6164){const _0x4cf13f=a0_0x593d,_0x2e7ae0=_0x1e954d();while(!![]){try{const _0x4291a4=parseInt(_0x4cf13f(0x173))/0x1*(-parseInt(_0x4cf13f(0x174))/0x2)+-parseInt(_0x4cf13f(0x164))/0x3+-parseInt(_0x4cf13f(0x179))/0x4*(-parseInt(_0x4cf13f(0x189))/0x5)+parseInt(_0x4cf13f(0x16d))/0x6+parseInt(_0x4cf13f(0x17c))/0x7+parseInt(_0x4cf13f(0x160))/0x8*(parseInt(_0x4cf13f(0x176))/0x9)+-parseInt(_0x4cf13f(0x17d))/0xa*(parseInt(_0x4cf13f(0x180))/0xb);if(_0x4291a4===_0x3b6164)break;else _0x2e7ae0['push'](_0x2e7ae0['shift']());}catch(_0x1b806e){_0x2e7ae0['push'](_0x2e7ae0['shift']());}}}(a0_0x2fa8,0xa73da));import a0_0x3ffba7 from'typescript';import a0_0x1806d5 from'path';import{STATIC_ANALYSIS}from'../utilities/constants.js';function a0_0x593d(_0x222271,_0xb3f9ae){_0x222271=_0x222271-0x15b;const _0x2fa874=a0_0x2fa8();let _0x593de2=_0x2fa874[_0x222271];if(a0_0x593d['zJoiZx']===undefined){var _0x3fdb2e=function(_0x45e849){const _0x5e726b='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0x3ffba7='',_0x1806d5='';for(let _0x555069=0x0,_0x1bbd49,_0x6727de,_0x36555e=0x0;_0x6727de=_0x45e849['charAt'](_0x36555e++);~_0x6727de&&(_0x1bbd49=_0x555069%0x4?_0x1bbd49*0x40+_0x6727de:_0x6727de,_0x555069++%0x4)?_0x3ffba7+=String['fromCharCode'](0xff&_0x1bbd49>>(-0x2*_0x555069&0x6)):0x0){_0x6727de=_0x5e726b['indexOf'](_0x6727de);}for(let _0x2c672a=0x0,_0x360a60=_0x3ffba7['length'];_0x2c672a<_0x360a60;_0x2c672a++){_0x1806d5+='%'+('00'+_0x3ffba7['charCodeAt'](_0x2c672a)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x1806d5);};a0_0x593d['pvMvMb']=_0x3fdb2e,a0_0x593d['muGZzJ']={},a0_0x593d['zJoiZx']=!![];}const _0x44a89e=_0x2fa874[0x0],_0x360fa8=_0x222271+_0x44a89e,_0x2042b7=a0_0x593d['muGZzJ'][_0x360fa8];return!_0x2042b7?(_0x593de2=a0_0x593d['pvMvMb'](_0x593de2),a0_0x593d['muGZzJ'][_0x360fa8]=_0x593de2):_0x593de2=_0x2042b7,_0x593de2;}function a0_0x2fa8(){const _0x47a8da=['ndG4tgLwDfnX','Bg9Nz2vY','C3rHCNq','ntu3nde0oufUu2PbtW','mty5mdGWAfLqEKHj','q0furuDpuLK','zgvIDwC','mtyWnLvbwhrlua','sNn4rw1PDa','BgLIlMqUDhm','y2XHC3m','v0fstKLorW','rgLHz25VC3rPy0nHDgvNB3j5','Aw50zxjMywnL','zMLSzq','Aw5JBhvKzxm','ndG4ntbSB0DdCwC','z2v0tgLUzufUzenOyxjHy3rLCK9Mug9ZAxrPB24','uMvHy3q','y29TCgLSzxjpChrPB25Z','z2v0u3LUDgfJDgLJrgLHz25VC3rPy3m','y3jLyxrLu291CMnLrMLSzq','mtaYmZK3nNvLDhPvCG','tgf0zxn0','tw9KDwXLs2LUza','rxjYB3i','mtm0otqZmgPgrxDAyG','zMLSzu5HBwu','z2v0u2vTyw50AwneAwfNBM9ZDgLJCW','zM9YBwf0rgLHz25VC3rPyW','CgfYC2veAwfNBM9ZDgLJCW','u0vwrvjjvfK','u1Lovefy','ChvZAa','zMXHDhrLBKrPywDUB3n0AwnnzxnZywDLvgv4Da','nte3ndu4nKvjufHNEq','u3vNz2vZDgLVBG','C2v2zxjPDhK','BgvUz3rO','rvjst1i','rvnozxH0','mtqZmJyXqMHWy1DM','mKjxBM9YAa','su1qt1ju','nJnoz0v0vLO','u2nYAxb0vgfYz2v0','BgLUzq'];a0_0x2fa8=function(){return _0x47a8da;};return a0_0x2fa8();}class TypeScriptAnalyzer{constructor(_0x555069=null){const _0x95874=a0_0x593d;this[_0x95874(0x17a)]=_0x555069,this[_0x95874(0x15d)]={'noEmit':!![],'jsx':a0_0x3ffba7[_0x95874(0x181)][_0x95874(0x15c)],'target':a0_0x3ffba7['ScriptTarget'][_0x95874(0x161)],'module':a0_0x3ffba7[_0x95874(0x162)][_0x95874(0x172)],'moduleResolution':a0_0x3ffba7['ModuleResolutionKind']['NodeJs'],'esModuleInterop':!![],'skipLibCheck':!![],'strict':!![],'noImplicitAny':!![],'strictNullChecks':!![],'strictFunctionTypes':!![],'allowJs':![]};}async['analyze'](_0x1bbd49,_0x6727de,_0x36555e={}){const _0x5d245b=a0_0x593d;try{const _0x2c672a=[],_0x360a60=a0_0x3ffba7['createSourceFile'](_0x1bbd49,_0x6727de,a0_0x3ffba7[_0x5d245b(0x177)]['Latest'],!![]),_0x276316=this[_0x5d245b(0x15e)](_0x360a60);_0x2c672a['push'](..._0x276316);const _0x39357f=await this[_0x5d245b(0x166)](_0x1bbd49,_0x6727de);return _0x2c672a['push'](..._0x39357f),this[_0x5d245b(0x17a)]?.[_0x5d245b(0x17f)]('TypeScript\x20analysis\x20completed',{'file':_0x1bbd49,'totalDiagnostics':_0x2c672a[_0x5d245b(0x170)],'errors':_0x2c672a['filter'](_0x45b12f=>_0x45b12f[_0x5d245b(0x16f)]===STATIC_ANALYSIS['SEVERITY'][_0x5d245b(0x171)])['length'],'warnings':_0x2c672a['filter'](_0x349aef=>_0x349aef['severity']===STATIC_ANALYSIS[_0x5d245b(0x169)]['WARNING'])['length']}),_0x2c672a;}catch(_0x3b0b09){return this[_0x5d245b(0x17a)]?.['error']('TypeScript\x20analysis\x20failed',{'file':_0x1bbd49,'error':_0x3b0b09['message']}),[{'file':_0x1bbd49,'line':0x0,'column':0x0,'severity':STATIC_ANALYSIS['SEVERITY']['ERROR'],'rule':'analyzer-error','message':'Analysis\x20failed:\x20'+_0x3b0b09['message'],'category':STATIC_ANALYSIS[_0x5d245b(0x17e)][_0x5d245b(0x16a)]}];}}['getSyntacticDiagnostics'](_0x22153b){const _0x526595=a0_0x593d,_0x3f72e9=[];if(_0x22153b[_0x526595(0x168)]&&_0x22153b[_0x526595(0x168)]['length']>0x0)for(const _0x5692b6 of _0x22153b[_0x526595(0x168)]){_0x3f72e9[_0x526595(0x16b)](this[_0x526595(0x167)](_0x5692b6,_0x22153b));}return _0x3f72e9;}async[a0_0x25ad85(0x166)](_0x3984e6,_0x2d2dc4){const _0x170754=a0_0x25ad85,_0x286a5b=[];try{const _0x3721c5=a0_0x3ffba7[_0x170754(0x15f)](_0x3984e6,_0x2d2dc4,a0_0x3ffba7[_0x170754(0x177)]['Latest'],!![]),_0x1cd8bd={'getSourceFile':_0x4cc5f4=>{if(_0x4cc5f4===_0x3984e6)return _0x3721c5;return undefined;},'getDefaultLibFileName':()=>_0x170754(0x182),'writeFile':()=>{},'getCurrentDirectory':()=>a0_0x1806d5['dirname'](_0x3984e6),'getDirectories':()=>[],'fileExists':_0x16e2bb=>_0x16e2bb===_0x3984e6,'readFile':_0x21746e=>{if(_0x21746e===_0x3984e6)return _0x2d2dc4;return undefined;},'getCanonicalFileName':_0x57a84d=>_0x57a84d,'useCaseSensitiveFileNames':()=>!![],'getNewLine':()=>'\x0a'},_0x242e9d=a0_0x3ffba7['createProgram']({'rootNames':[_0x3984e6],'options':this['compilerOptions'],'host':_0x1cd8bd}),_0x42cdb2=_0x242e9d[_0x170754(0x15e)](_0x3721c5),_0x495dda=_0x242e9d[_0x170754(0x166)](_0x3721c5);for(const _0x12aae1 of[..._0x42cdb2,..._0x495dda]){_0x286a5b[_0x170754(0x16b)](this['formatDiagnostic'](_0x12aae1,_0x3721c5));}}catch(_0x98c9b5){this[_0x170754(0x17a)]?.['debug']('Semantic\x20analysis\x20encountered\x20error',{'file':_0x3984e6,'error':_0x98c9b5['message']});}return _0x286a5b;}[a0_0x25ad85(0x167)](_0x1290d3,_0x248418){const _0x41b318=a0_0x25ad85;let _0x5cae80=0x0,_0x4842da=0x0;if(_0x1290d3[_0x41b318(0x187)]&&_0x1290d3[_0x41b318(0x17b)]!==undefined){const _0x965d70=_0x1290d3[_0x41b318(0x187)]['getLineAndCharacterOfPosition'](_0x1290d3['start']);_0x5cae80=_0x965d70[_0x41b318(0x178)]+0x1,_0x4842da=_0x965d70['character']+0x1;}else{if(_0x248418&&_0x1290d3['start']!==undefined){const _0x1922f6=_0x248418[_0x41b318(0x15b)](_0x1290d3['start']);_0x5cae80=_0x1922f6[_0x41b318(0x178)]+0x1,_0x4842da=_0x1922f6['character']+0x1;}}const _0x15c4f3=a0_0x3ffba7[_0x41b318(0x16c)](_0x1290d3['messageText'],'\x0a');let _0x52c67b;switch(_0x1290d3['category']){case a0_0x3ffba7[_0x41b318(0x185)][_0x41b318(0x163)]:_0x52c67b=STATIC_ANALYSIS['SEVERITY'][_0x41b318(0x171)];break;case a0_0x3ffba7[_0x41b318(0x185)]['Warning']:_0x52c67b=STATIC_ANALYSIS[_0x41b318(0x169)][_0x41b318(0x184)];break;case a0_0x3ffba7['DiagnosticCategory']['Message']:case a0_0x3ffba7[_0x41b318(0x185)][_0x41b318(0x16e)]:_0x52c67b=STATIC_ANALYSIS[_0x41b318(0x169)]['INFO'];break;default:_0x52c67b=STATIC_ANALYSIS[_0x41b318(0x169)][_0x41b318(0x171)];}let _0x1bd5cc=STATIC_ANALYSIS['CATEGORY']['SYNTAX'];const _0xb4c0d2=_0x1290d3['code'];if(_0xb4c0d2>=0x7d0&&_0xb4c0d2<0xbb8)_0x1bd5cc=STATIC_ANALYSIS[_0x41b318(0x17e)]['TYPE'];else{if(_0xb4c0d2>=0x3e8&&_0xb4c0d2<0x7d0)_0x1bd5cc=STATIC_ANALYSIS[_0x41b318(0x17e)][_0x41b318(0x16a)];else _0xb4c0d2>=0x8fc&&_0xb4c0d2<0x960&&(_0x1bd5cc=STATIC_ANALYSIS['CATEGORY'][_0x41b318(0x175)]);}const _0x51786f=_0x15c4f3['toLowerCase']();if(_0x51786f['includes']('cannot\x20find\x20module')||_0x51786f[_0x41b318(0x188)]('import')||_0x51786f[_0x41b318(0x188)]('export'))_0x1bd5cc=STATIC_ANALYSIS['CATEGORY']['IMPORT'];else(_0x51786f['includes']('type')||_0x51786f[_0x41b318(0x188)](_0x41b318(0x186))||_0x51786f[_0x41b318(0x188)](_0x41b318(0x183)))&&(_0x1bd5cc=STATIC_ANALYSIS['CATEGORY']['TYPE']);return{'file':_0x1290d3['file']?.[_0x41b318(0x165)]||_0x248418?.[_0x41b318(0x165)]||'unknown','line':_0x5cae80,'column':_0x4842da,'severity':_0x52c67b,'rule':'TS'+_0xb4c0d2,'message':_0x15c4f3,'category':_0x1bd5cc,'fixable':![],'code':_0x1290d3['code']};}}export default TypeScriptAnalyzer;
@@ -1,344 +1 @@
1
- /**
2
- * Analyzes clones and provides refactoring recommendations
3
- */
4
- export class RefactoringAnalyzer {
5
- constructor(config) {
6
- this.config = config;
7
- }
8
-
9
- /**
10
- * Analyze clones and provide refactoring advice
11
- * @param {Array} clones - Array of detected clones
12
- * @returns {Array} Enriched clones with refactoring advice
13
- */
14
- analyzeClones(clones) {
15
- console.log('Analyzing clones for refactoring opportunities...');
16
-
17
- return clones.map((clone, index) => {
18
- const metrics = this.calculateMetrics(clone);
19
- const advice = this.generateRefactoringAdvice(clone, metrics);
20
-
21
- return {
22
- id: `clone-${index + 1}`,
23
- type: clone.type,
24
- confidence: clone.confidence,
25
- instances: clone.blocks.map(block => ({
26
- file: block.file,
27
- startLine: block.startLine,
28
- endLine: block.endLine,
29
- code: this.truncateCode(block.code),
30
- fullCode: block.code,
31
- blockType: block.type
32
- })),
33
- metrics,
34
- refactoringAdvice: advice
35
- };
36
- }).sort((a, b) => b.metrics.impactScore - a.metrics.impactScore);
37
- }
38
-
39
- /**
40
- * Calculate metrics for a clone
41
- */
42
- calculateMetrics(clone) {
43
- const blocks = clone.blocks;
44
- const tokenCount = clone.tokenCount;
45
- const lineCount = this.averageLineCount(blocks);
46
- const instanceCount = blocks.length;
47
-
48
- // Calculate impact score (higher = more important to refactor)
49
- const impactScore = this.calculateImpactScore(
50
- tokenCount,
51
- lineCount,
52
- instanceCount,
53
- clone.confidence
54
- );
55
-
56
- // Calculate duplication overhead
57
- const duplicatedLines = lineCount * (instanceCount - 1);
58
- const duplicatedTokens = tokenCount * (instanceCount - 1);
59
-
60
- return {
61
- tokenCount,
62
- lineCount,
63
- instanceCount,
64
- duplicatedLines,
65
- duplicatedTokens,
66
- impactScore: parseFloat(impactScore.toFixed(2)),
67
- filesCovered: new Set(blocks.map(b => b.file)).size
68
- };
69
- }
70
-
71
- /**
72
- * Calculate impact score for prioritization
73
- */
74
- calculateImpactScore(tokenCount, lineCount, instanceCount, confidence) {
75
- // Weighted formula:
76
- // - Size matters (more tokens = more important)
77
- // - Instances matter (more copies = more important)
78
- // - Confidence matters
79
- // - Line count matters (user visibility)
80
-
81
- const sizeScore = Math.log10(tokenCount + 1) * 2;
82
- const instanceScore = Math.log2(instanceCount + 1) * 3;
83
- const confidenceScore = confidence * 2;
84
- const lineScore = Math.min(lineCount / 10, 3);
85
-
86
- return sizeScore + instanceScore + confidenceScore + lineScore;
87
- }
88
-
89
- /**
90
- * Generate refactoring advice
91
- */
92
- generateRefactoringAdvice(clone, metrics) {
93
- const strategy = this.determineRefactoringStrategy(clone, metrics);
94
- const priority = this.determinePriority(metrics);
95
- const suggestedName = this.suggestName(clone);
96
- const reasoning = this.generateReasoning(clone, metrics, strategy);
97
- const estimatedEffort = this.estimateEffort(metrics, strategy);
98
- const benefits = this.describeBenefits(metrics);
99
-
100
- return {
101
- priority,
102
- strategy,
103
- suggestedName,
104
- reasoning,
105
- estimatedEffort,
106
- benefits,
107
- actionableSteps: this.generateActionableSteps(strategy, suggestedName, metrics)
108
- };
109
- }
110
-
111
- /**
112
- * Determine refactoring strategy
113
- */
114
- determineRefactoringStrategy(clone, metrics) {
115
- const { tokenCount, lineCount, instanceCount, filesCovered } = metrics;
116
- const blockTypes = clone.blocks.map(b => b.type);
117
-
118
- // Check if it's a function/method
119
- const isFunctionLike = blockTypes.some(type =>
120
- type.includes('Function') || type.includes('Method')
121
- );
122
-
123
- // Check if it's a class
124
- const isClassLike = blockTypes.some(type =>
125
- type.includes('Class')
126
- );
127
-
128
- // Decision tree
129
- if (isClassLike && lineCount > 50) {
130
- return 'extract-module';
131
- } else if (filesCovered > 2 && tokenCount > 100) {
132
- return 'extract-module';
133
- } else if (isFunctionLike || (lineCount >= 10 && lineCount <= 50)) {
134
- return 'extract-function';
135
- } else if (lineCount > 50) {
136
- return 'extract-class';
137
- } else if (lineCount < 10) {
138
- return 'extract-constant-or-utility';
139
- } else {
140
- return 'extract-function';
141
- }
142
- }
143
-
144
- /**
145
- * Determine priority level
146
- */
147
- determinePriority(metrics) {
148
- const { impactScore } = metrics;
149
-
150
- if (impactScore >= 8) return 'high';
151
- if (impactScore >= 5) return 'medium';
152
- return 'low';
153
- }
154
-
155
- /**
156
- * Suggest a name based on code analysis
157
- */
158
- suggestName(clone) {
159
- // Extract common words from the code
160
- const allCode = clone.blocks.map(b => b.code).join(' ');
161
-
162
- // Look for common identifiers
163
- const identifiers = allCode.match(/[a-zA-Z_$][a-zA-Z0-9_$]*/g) || [];
164
- const frequency = {};
165
-
166
- identifiers.forEach(id => {
167
- // Skip common keywords
168
- if (['const', 'let', 'var', 'function', 'return', 'if', 'else', 'for', 'while'].includes(id)) {
169
- return;
170
- }
171
- frequency[id] = (frequency[id] || 0) + 1;
172
- });
173
-
174
- // Find most common meaningful identifier
175
- const sorted = Object.entries(frequency)
176
- .sort((a, b) => b[1] - a[1])
177
- .slice(0, 3);
178
-
179
- if (sorted.length > 0) {
180
- // Create a descriptive name from top identifiers
181
- const topWords = sorted.map(([word]) => word);
182
- return this.createFunctionName(topWords);
183
- }
184
-
185
- return 'extractedFunction';
186
- }
187
-
188
- /**
189
- * Create a function name from words
190
- */
191
- createFunctionName(words) {
192
- if (words.length === 0) return 'extractedFunction';
193
-
194
- // Convert to camelCase
195
- return words[0] + words.slice(1).map(w =>
196
- w.charAt(0).toUpperCase() + w.slice(1)
197
- ).join('');
198
- }
199
-
200
- /**
201
- * Generate reasoning for refactoring
202
- */
203
- generateReasoning(clone, metrics, strategy) {
204
- const { instanceCount, duplicatedLines, filesCovered } = metrics;
205
-
206
- let reasoning = `This ${clone.type} code pattern appears ${instanceCount} times`;
207
-
208
- if (filesCovered > 1) {
209
- reasoning += ` across ${filesCovered} different files`;
210
- }
211
-
212
- reasoning += `, resulting in ${duplicatedLines} duplicated lines. `;
213
-
214
- reasoning += `Refactoring to ${strategy.replace(/-/g, ' ')} would improve maintainability`;
215
-
216
- if (instanceCount >= 3) {
217
- reasoning += ', reduce bugs from inconsistent changes';
218
- }
219
-
220
- reasoning += ', and reduce code size';
221
-
222
- if (metrics.impactScore >= 8) {
223
- reasoning += '. This is a high-impact refactoring opportunity';
224
- }
225
-
226
- return reasoning + '.';
227
- }
228
-
229
- /**
230
- * Estimate effort for refactoring
231
- */
232
- estimateEffort(metrics, strategy) {
233
- const { lineCount, instanceCount, filesCovered } = metrics;
234
-
235
- let effortPoints = 0;
236
-
237
- // Base effort on size
238
- effortPoints += Math.min(lineCount / 10, 5);
239
-
240
- // Effort increases with instances
241
- effortPoints += instanceCount * 0.5;
242
-
243
- // Effort increases with file spread
244
- effortPoints += filesCovered * 0.5;
245
-
246
- // Strategy-specific effort
247
- if (strategy === 'extract-module') {
248
- effortPoints += 3;
249
- } else if (strategy === 'extract-class') {
250
- effortPoints += 2;
251
- } else if (strategy === 'extract-function') {
252
- effortPoints += 1;
253
- }
254
-
255
- if (effortPoints <= 3) return 'low';
256
- if (effortPoints <= 7) return 'medium';
257
- return 'high';
258
- }
259
-
260
- /**
261
- * Describe benefits of refactoring
262
- */
263
- describeBenefits(metrics) {
264
- const benefits = [];
265
-
266
- benefits.push(`Eliminate ${metrics.duplicatedLines} duplicated lines of code`);
267
- benefits.push(`Improve maintainability by centralizing logic in one place`);
268
-
269
- if (metrics.instanceCount >= 3) {
270
- benefits.push(`Reduce risk of inconsistent changes across ${metrics.instanceCount} locations`);
271
- }
272
-
273
- if (metrics.filesCovered > 2) {
274
- benefits.push(`Improve code organization across ${metrics.filesCovered} files`);
275
- }
276
-
277
- benefits.push('Make future changes easier and less error-prone');
278
-
279
- return benefits;
280
- }
281
-
282
- /**
283
- * Generate actionable steps
284
- */
285
- generateActionableSteps(strategy, suggestedName, metrics) {
286
- const steps = [];
287
-
288
- switch (strategy) {
289
- case 'extract-function':
290
- steps.push(`1. Create a new function named '${suggestedName}'`);
291
- steps.push('2. Move the duplicated logic into this function');
292
- steps.push('3. Identify parameters needed from the surrounding context');
293
- steps.push('4. Replace all instances with calls to the new function');
294
- steps.push('5. Test to ensure behavior is preserved');
295
- break;
296
-
297
- case 'extract-class':
298
- steps.push(`1. Create a new class to encapsulate this functionality`);
299
- steps.push('2. Move related methods and properties into the class');
300
- steps.push('3. Update all instances to use the new class');
301
- steps.push('4. Consider dependency injection for better testability');
302
- break;
303
-
304
- case 'extract-module':
305
- steps.push(`1. Create a new module/file for this shared functionality`);
306
- steps.push('2. Move the duplicated code into the new module');
307
- steps.push('3. Export the necessary functions/classes');
308
- steps.push('4. Update all files to import from the new module');
309
- steps.push('5. Update any build configurations if needed');
310
- break;
311
-
312
- default:
313
- steps.push(`1. Extract the duplicated code using ${strategy.replace(/-/g, ' ')}`);
314
- steps.push('2. Replace all instances with the extracted version');
315
- steps.push('3. Test thoroughly');
316
- }
317
-
318
- return steps;
319
- }
320
-
321
- /**
322
- * Truncate code for display
323
- */
324
- truncateCode(code, maxLines = 10) {
325
- const lines = code.split('\n');
326
-
327
- if (lines.length <= maxLines) {
328
- return code;
329
- }
330
-
331
- return lines.slice(0, maxLines).join('\n') + '\n... (truncated)';
332
- }
333
-
334
- /**
335
- * Calculate average line count
336
- */
337
- averageLineCount(blocks) {
338
- const totalLines = blocks.reduce((sum, block) =>
339
- sum + (block.endLine - block.startLine + 1), 0
340
- );
341
-
342
- return Math.round(totalLines / blocks.length);
343
- }
344
- }
1
+ const a0_0x461db3=a0_0x51a8;(function(_0x5ec752,_0x278a96){const _0x2937ab=a0_0x51a8,_0x33dba2=_0x5ec752();while(!![]){try{const _0x2b3f28=-parseInt(_0x2937ab(0xcf))/0x1*(parseInt(_0x2937ab(0xb9))/0x2)+-parseInt(_0x2937ab(0xcb))/0x3+-parseInt(_0x2937ab(0xaa))/0x4+-parseInt(_0x2937ab(0xdd))/0x5+parseInt(_0x2937ab(0xdb))/0x6+parseInt(_0x2937ab(0xb5))/0x7*(parseInt(_0x2937ab(0xc9))/0x8)+parseInt(_0x2937ab(0xbf))/0x9;if(_0x2b3f28===_0x278a96)break;else _0x33dba2['push'](_0x33dba2['shift']());}catch(_0x1a5bf2){_0x33dba2['push'](_0x33dba2['shift']());}}}(a0_0x1ee7,0xaa689));function a0_0x1ee7(){const _0x3109f0=['zxn0Aw1HDgvfzMzVCNq','z2vUzxjHDgvszwzHy3rVCMLUz0fKDMLJzq','ChvZAa','nc4GuMvWBgfJzsbHBgWGAw5ZDgfUy2vZihDPDgGGy2fSBhmGDg8GDgHLig5LDYbMDw5JDgLVBG','BwLU','zhvWBgLJyxrLzeXPBMvZ','y2fSy3vSyxrLsw1Wywn0u2nVCMu','BgvUz3rO','mZjPD0LRyvy','zw5KtgLUzq','mtiZotq0mu5cEvzrvG','qw5HBhL6Aw5NignSB25LCYbMB3iGCMvMywn0B3jPBMCGB3bWB3j0Dw5PDgLLCY4UlG','y29Kzq','y2fSy3vSyxrLtwv0CMLJCW','mu9ovLzvzq','zwXZzq','Dhj1BMnHDgvdB2rL','Dg9vChbLCKnHC2u','Bg9NmG','CM91BMq','igXVy2f0Aw9UCW','lcbHBMqGCMvKDwnLignVzguGC2L6zq','AM9PBG','zM9YrwfJAa','Bwv0CMLJCW','rNvUy3rPB24','mJKYmtq5mhjiuwz0Aq','yMXVy2TZ','mtq2ntGYmfvnthftyW','zgv0zxjTAw5LuMvMywn0B3jPBMDtDhjHDgvNEq','C29Tzq','lIbuAgLZigLZigeGAgLNAc1PBxbHy3qGCMvMywn0B3jPBMCGB3bWB3j0Dw5PDhK','yw5HBhL6zunSB25LCW','mI4Gtw92zsbYzwXHDgvKig1LDgHVzhmGyw5KihbYB3bLCNrPzxmGAw50BYb0AguGy2XHC3m','zxH0CMfJDc1TB2r1Bgu','Bg93','zw50CMLLCW','DMfY','BwvKAxvT','y29UzMLKzw5Jzq','y2XVBMuT','zxH0CMfJDc1JBgfZCW','Aw1Wywn0u2nVCMu','ms4Gq3jLyxrLigeGBMv3ignSyxnZihrVigvUy2fWC3vSyxrLihrOAxmGzNvUy3rPB25HBgL0Eq','zxH0CMfJDgvKrNvUy3rPB24','z2vUzxjHDgvszwfZB25PBMC','Dg9gAxHLza','zgv0zxjTAw5LuhjPB3jPDhK','rwXPBwLUyxrLia','ms4GrxH0CMfJDcb0AguGzhvWBgLJyxrLzcbJB2rLihvZAw5Nia','mte3nty0nePWwLzdta','lcbYzxn1BhrPBMCGAw4G','y2HHCKf0','zgvZy3jPyMvczw5LzML0CW','CMv0DxjU','cI4UlIaODhj1BMnHDgvKkq','C2L6zq','y3jLyxrLrNvUy3rPB25oyw1L','z2vUzxjHDgvby3rPB25HyMXLu3rLChm','DhLWzq','C29YDa','mZeWnZiZsgvIsLPP','sw1WCM92zsbJB2rLig9Yz2fUAxPHDgLVBIbHy3jVC3mG','D2HPBgu','Aw5JBhvKzxm','mty5mJG1ogn3tK9nra','BwfW','zxH0CMfJDc1MDw5JDgLVBG','uMvMywn0B3jPBMCGDg8G','C3vNz2vZDe5HBwu','C3rHCNrmAw5L','mty5mJe1ntDzt3vot20','mI4GuMvWBgfJzsbHBgWGAw5ZDgfUy2vZihDPDgGGDgHLigv4DhjHy3rLzcb2zxjZAw9U'];a0_0x1ee7=function(){return _0x3109f0;};return a0_0x1ee7();}function a0_0x51a8(_0x1c5856,_0x5654fd){_0x1c5856=_0x1c5856-0xa5;const _0x1ee797=a0_0x1ee7();let _0x51a824=_0x1ee797[_0x1c5856];if(a0_0x51a8['fNXxci']===undefined){var _0xffe534=function(_0x4bdb18){const _0x2bf6cd='abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789+/=';let _0x1aa994='',_0x13b87d='';for(let _0x58dad8=0x0,_0x15fc63,_0x3713c6,_0x226269=0x0;_0x3713c6=_0x4bdb18['charAt'](_0x226269++);~_0x3713c6&&(_0x15fc63=_0x58dad8%0x4?_0x15fc63*0x40+_0x3713c6:_0x3713c6,_0x58dad8++%0x4)?_0x1aa994+=String['fromCharCode'](0xff&_0x15fc63>>(-0x2*_0x58dad8&0x6)):0x0){_0x3713c6=_0x2bf6cd['indexOf'](_0x3713c6);}for(let _0xaf73e5=0x0,_0x4df00c=_0x1aa994['length'];_0xaf73e5<_0x4df00c;_0xaf73e5++){_0x13b87d+='%'+('00'+_0x1aa994['charCodeAt'](_0xaf73e5)['toString'](0x10))['slice'](-0x2);}return decodeURIComponent(_0x13b87d);};a0_0x51a8['rdOGYW']=_0xffe534,a0_0x51a8['etGnAn']={},a0_0x51a8['fNXxci']=!![];}const _0x29e26d=_0x1ee797[0x0],_0x336f83=_0x1c5856+_0x29e26d,_0x496477=a0_0x51a8['etGnAn'][_0x336f83];return!_0x496477?(_0x51a824=a0_0x51a8['rdOGYW'](_0x51a824),a0_0x51a8['etGnAn'][_0x336f83]=_0x51a824):_0x51a824=_0x496477,_0x51a824;}export class RefactoringAnalyzer{constructor(_0x1aa994){this['config']=_0x1aa994;}[a0_0x461db3(0xe1)](_0x13b87d){const _0x38adb6=a0_0x461db3;return console['log'](_0x38adb6(0xcc)),_0x13b87d['map']((_0x58dad8,_0x15fc63)=>{const _0x1a4e00=_0x38adb6,_0x3713c6=this[_0x1a4e00(0xce)](_0x58dad8),_0x226269=this[_0x1a4e00(0xc2)](_0x58dad8,_0x3713c6);return{'id':_0x1a4e00(0xe9)+(_0x15fc63+0x1),'type':_0x58dad8[_0x1a4e00(0xb3)],'confidence':_0x58dad8['confidence'],'instances':_0x58dad8['blocks'][_0x1a4e00(0xba)](_0xaf73e5=>({'file':_0xaf73e5['file'],'startLine':_0xaf73e5[_0x1a4e00(0xbe)],'endLine':_0xaf73e5[_0x1a4e00(0xca)],'code':this[_0x1a4e00(0xd1)](_0xaf73e5['code']),'fullCode':_0xaf73e5[_0x1a4e00(0xcd)],'blockType':_0xaf73e5[_0x1a4e00(0xb3)]})),'metrics':_0x3713c6,'refactoringAdvice':_0x226269};})[_0x38adb6(0xb4)]((_0x4df00c,_0x3742ae)=>_0x3742ae[_0x38adb6(0xd9)][_0x38adb6(0xeb)]-_0x4df00c[_0x38adb6(0xd9)]['impactScore']);}[a0_0x461db3(0xce)](_0x464031){const _0x329aef=a0_0x461db3,_0x135f24=_0x464031[_0x329aef(0xdc)],_0x832b3=_0x464031['tokenCount'],_0x1b1a8c=this['averageLineCount'](_0x135f24),_0xce326c=_0x135f24[_0x329aef(0xc8)],_0x43ffa8=this[_0x329aef(0xc7)](_0x832b3,_0x1b1a8c,_0xce326c,_0x464031[_0x329aef(0xe8)]),_0x492d6f=_0x1b1a8c*(_0xce326c-0x1),_0x5e1c7a=_0x832b3*(_0xce326c-0x1);return{'tokenCount':_0x832b3,'lineCount':_0x1b1a8c,'instanceCount':_0xce326c,'duplicatedLines':_0x492d6f,'duplicatedTokens':_0x5e1c7a,'impactScore':parseFloat(_0x43ffa8[_0x329aef(0xa6)](0x2)),'filesCovered':new Set(_0x135f24['map'](_0x4f2a61=>_0x4f2a61['file']))[_0x329aef(0xb0)]};}['calculateImpactScore'](_0x319c0e,_0x238db6,_0x18bfea,_0x4bebce){const _0x5ee108=a0_0x461db3,_0x42c90e=Math['log10'](_0x319c0e+0x1)*0x2,_0x363af1=Math[_0x5ee108(0xd3)](_0x18bfea+0x1)*0x3,_0x36e81d=_0x4bebce*0x2,_0x5c920d=Math[_0x5ee108(0xc5)](_0x238db6/0xa,0x3);return _0x42c90e+_0x363af1+_0x36e81d+_0x5c920d;}[a0_0x461db3(0xc2)](_0x461478,_0x404207){const _0x32ecd8=a0_0x461db3,_0x47f102=this['determineRefactoringStrategy'](_0x461478,_0x404207),_0x3c7622=this[_0x32ecd8(0xa7)](_0x404207),_0x23edf6=this[_0x32ecd8(0xbd)](_0x461478),_0x2bf18a=this[_0x32ecd8(0xa5)](_0x461478,_0x404207,_0x47f102),_0x2a0edf=this[_0x32ecd8(0xc1)](_0x404207,_0x47f102),_0x359345=this['describeBenefits'](_0x404207);return{'priority':_0x3c7622,'strategy':_0x47f102,'suggestedName':_0x23edf6,'reasoning':_0x2bf18a,'estimatedEffort':_0x2a0edf,'benefits':_0x359345,'actionableSteps':this['generateActionableSteps'](_0x47f102,_0x23edf6,_0x404207)};}[a0_0x461db3(0xde)](_0x46b453,_0x35ee28){const _0x8e5757=a0_0x461db3,{tokenCount:_0x480f17,lineCount:_0x4d829f,instanceCount:_0x2dd206,filesCovered:_0x552900}=_0x35ee28,_0x545dfc=_0x46b453[_0x8e5757(0xdc)]['map'](_0x123873=>_0x123873['type']),_0x1b32d2=_0x545dfc['some'](_0x31dc9f=>_0x31dc9f['includes'](_0x8e5757(0xda))||_0x31dc9f[_0x8e5757(0xb8)]('Method')),_0x5d1c3a=_0x545dfc[_0x8e5757(0xdf)](_0x3e00f7=>_0x3e00f7[_0x8e5757(0xb8)]('Class'));if(_0x5d1c3a&&_0x4d829f>0x32)return _0x8e5757(0xe3);else{if(_0x552900>0x2&&_0x480f17>0x64)return'extract-module';else{if(_0x1b32d2||_0x4d829f>=0xa&&_0x4d829f<=0x32)return'extract-function';else{if(_0x4d829f>0x32)return'extract-class';else return _0x4d829f<0xa?'extract-constant-or-utility':_0x8e5757(0xbb);}}}}['determinePriority'](_0x357a87){const _0x3601ec=a0_0x461db3,{impactScore:_0x1abbb3}=_0x357a87;if(_0x1abbb3>=0x8)return'high';if(_0x1abbb3>=0x5)return _0x3601ec(0xe7);return _0x3601ec(0xe4);}['suggestName'](_0x48c2be){const _0x1642d2=a0_0x461db3,_0x4ca06b=_0x48c2be[_0x1642d2(0xdc)][_0x1642d2(0xba)](_0x3ad166=>_0x3ad166['code'])['join']('\x20'),_0x1a8089=_0x4ca06b['match'](/[a-zA-Z_$][a-zA-Z0-9_$]*/g)||[],_0x4ff0ba={};_0x1a8089[_0x1642d2(0xd8)](_0x52b804=>{const _0xe3e232=_0x1642d2;if(['const','let',_0xe3e232(0xe6),'function',_0xe3e232(0xae),'if',_0xe3e232(0xd0),'for',_0xe3e232(0xb7)][_0xe3e232(0xb8)](_0x52b804))return;_0x4ff0ba[_0x52b804]=(_0x4ff0ba[_0x52b804]||0x0)+0x1;});const _0x14188b=Object[_0x1642d2(0xe5)](_0x4ff0ba)['sort']((_0x4c4814,_0xf52d0a)=>_0xf52d0a[0x1]-_0x4c4814[0x1])['slice'](0x0,0x3);if(_0x14188b[_0x1642d2(0xc8)]>0x0){const _0x40fb85=_0x14188b[_0x1642d2(0xba)](([_0x8e5389])=>_0x8e5389);return this[_0x1642d2(0xb1)](_0x40fb85);}return _0x1642d2(0xed);}['createFunctionName'](_0x439bff){const _0x5a69ca=a0_0x461db3;if(_0x439bff['length']===0x0)return _0x5a69ca(0xed);return _0x439bff[0x0]+_0x439bff['slice'](0x1)['map'](_0x779726=>_0x779726[_0x5a69ca(0xac)](0x0)[_0x5a69ca(0xd2)]()+_0x779726['slice'](0x1))[_0x5a69ca(0xd7)]('');}['generateReasoning'](_0x57b402,_0x34f638,_0x5bee84){const _0x1f8d30=a0_0x461db3,{instanceCount:_0x57ae0c,duplicatedLines:_0x13d33c,filesCovered:_0x244a96}=_0x34f638;let _0x4f0d60='This\x20'+_0x57b402['type']+'\x20code\x20pattern\x20appears\x20'+_0x57ae0c+'\x20times';return _0x244a96>0x1&&(_0x4f0d60+='\x20across\x20'+_0x244a96+'\x20different\x20files'),_0x4f0d60+=_0x1f8d30(0xab)+_0x13d33c+'\x20duplicated\x20lines.\x20',_0x4f0d60+=_0x1f8d30(0xbc)+_0x5bee84['replace'](/-/g,'\x20')+'\x20would\x20improve\x20maintainability',_0x57ae0c>=0x3&&(_0x4f0d60+=', reduce bugs from inconsistent changes'),_0x4f0d60+=_0x1f8d30(0xd6),_0x34f638[_0x1f8d30(0xeb)]>=0x8&&(_0x4f0d60+=_0x1f8d30(0xe0)),_0x4f0d60+'.';}[a0_0x461db3(0xc1)](_0x2ed142,_0x1734d7){const _0x4880cf=a0_0x461db3,{lineCount:_0x3d804a,instanceCount:_0x19ed64,filesCovered:_0x1928d2}=_0x2ed142;let _0x2d4906=0x0;_0x2d4906+=Math[_0x4880cf(0xc5)](_0x3d804a/0xa,0x5),_0x2d4906+=_0x19ed64*0.5,_0x2d4906+=_0x1928d2*0.5;if(_0x1734d7==='extract-module')_0x2d4906+=0x3;else{if(_0x1734d7===_0x4880cf(0xea))_0x2d4906+=0x2;else _0x1734d7==='extract-function'&&(_0x2d4906+=0x1);}if(_0x2d4906<=0x3)return _0x4880cf(0xe4);if(_0x2d4906<=0x7)return'medium';return'high';}[a0_0x461db3(0xad)](_0x4ada17){const _0x25e624=a0_0x461db3,_0x1e4d47=[];return _0x1e4d47['push'](_0x25e624(0xa8)+_0x4ada17[_0x25e624(0xc6)]+'\x20duplicated\x20lines\x20of\x20code'),_0x1e4d47[_0x25e624(0xc3)]('Improve\x20maintainability\x20by\x20centralizing\x20logic\x20in\x20one\x20place'),_0x4ada17['instanceCount']>=0x3&&_0x1e4d47['push']('Reduce\x20risk\x20of\x20inconsistent\x20changes\x20across\x20'+_0x4ada17['instanceCount']+_0x25e624(0xd5)),_0x4ada17['filesCovered']>0x2&&_0x1e4d47[_0x25e624(0xc3)](_0x25e624(0xb6)+_0x4ada17['filesCovered']+'\x20files'),_0x1e4d47['push']('Make\x20future\x20changes\x20easier\x20and\x20less\x20error-prone'),_0x1e4d47;}[a0_0x461db3(0xb2)](_0x523a0e,_0x2cf86d,_0x1d1736){const _0x4548ed=a0_0x461db3,_0x487f8f=[];switch(_0x523a0e){case'extract-function':_0x487f8f[_0x4548ed(0xc3)]('1.\x20Create\x20a\x20new\x20function\x20named\x20\x27'+_0x2cf86d+'\x27'),_0x487f8f[_0x4548ed(0xc3)]('2.\x20Move\x20the\x20duplicated\x20logic\x20into\x20this\x20function'),_0x487f8f['push']('3. Identify parameters needed from the surrounding context'),_0x487f8f[_0x4548ed(0xc3)](_0x4548ed(0xc4)),_0x487f8f['push']('5.\x20Test\x20to\x20ensure\x20behavior\x20is\x20preserved');break;case _0x4548ed(0xea):_0x487f8f[_0x4548ed(0xc3)](_0x4548ed(0xec)),_0x487f8f['push'](_0x4548ed(0xe2)),_0x487f8f['push']('3.\x20Update\x20all\x20instances\x20to\x20use\x20the\x20new\x20class'),_0x487f8f[_0x4548ed(0xc3)]('4.\x20Consider\x20dependency\x20injection\x20for\x20better\x20testability');break;case'extract-module':_0x487f8f[_0x4548ed(0xc3)]('1.\x20Create\x20a\x20new\x20module/file\x20for\x20this\x20shared\x20functionality'),_0x487f8f['push']('2.\x20Move\x20the\x20duplicated\x20code\x20into\x20the\x20new\x20module'),_0x487f8f['push']('3.\x20Export\x20the\x20necessary\x20functions/classes'),_0x487f8f['push']('4. Update all files to import from the new module'),_0x487f8f[_0x4548ed(0xc3)]('5.\x20Update\x20any\x20build\x20configurations\x20if\x20needed');break;default:_0x487f8f[_0x4548ed(0xc3)](_0x4548ed(0xa9)+_0x523a0e['replace'](/-/g,'\x20')),_0x487f8f['push'](_0x4548ed(0xc0)),_0x487f8f[_0x4548ed(0xc3)]('3.\x20Test\x20thoroughly');}return _0x487f8f;}['truncateCode'](_0x3a0977,_0x59db7b=0xa){const _0x5ddcb8=a0_0x461db3,_0x57d17f=_0x3a0977['split']('\x0a');if(_0x57d17f[_0x5ddcb8(0xc8)]<=_0x59db7b)return _0x3a0977;return _0x57d17f['slice'](0x0,_0x59db7b)['join']('\x0a')+_0x5ddcb8(0xaf);}['averageLineCount'](_0x548937){const _0x2cdc28=a0_0x461db3,_0x3c1820=_0x548937['reduce']((_0xb711d6,_0x2fd40d)=>_0xb711d6+(_0x2fd40d[_0x2cdc28(0xca)]-_0x2fd40d[_0x2cdc28(0xbe)]+0x1),0x0);return Math[_0x2cdc28(0xd4)](_0x3c1820/_0x548937['length']);}}