ccsetup 1.2.0 → 1.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +93 -24
- package/bin/create-project.js +373 -773
- package/lib/templates/README.md +2 -2
- package/lib/templates/metadata/agents.json +1 -1
- package/package.json +3 -2
- package/template/.claude/settings.json +18 -1
- package/template/.claude/skills/codex-review/SKILL.md +139 -0
- package/template/.claude/skills/secops/SKILL.md +259 -0
- package/template/.codex/skills/codex-review/SKILL.md +139 -0
- package/template/.codex/skills/prd/SKILL.md +343 -0
- package/template/.codex/skills/ralph/SKILL.md +339 -0
- package/template/AGENTS.md +43 -0
- package/template/CLAUDE.md +106 -4
- package/template/docs/codex-setup.md +32 -0
- package/template/hooks/codex-review/index.js +105 -0
- package/template/scripts/codex-review/codex-review.sh +266 -0
- package/template/scripts/ralph/CODEX.md +76 -0
- package/template/scripts/ralph/ralph.sh +32 -9
- package/bin/lib/contextGenerator.js +0 -287
- package/bin/lib/scanner/index.js +0 -28
- package/bin/scan.js +0 -367
- package/lib/aiMergeHelper.js +0 -112
- package/lib/contextGenerator.js +0 -574
- package/lib/contextMerger.js +0 -812
- package/lib/progressReporter.js +0 -88
- package/lib/scanConfig.js +0 -200
- package/lib/scanner/fileAnalyzer.js +0 -605
- package/lib/scanner/index.js +0 -164
- package/lib/scanner/patterns.js +0 -277
- package/lib/scanner/projectDetector.js +0 -147
package/lib/contextGenerator.js
DELETED
|
@@ -1,574 +0,0 @@
|
|
|
1
|
-
class ContextGenerator {
|
|
2
|
-
constructor(scanResults) {
|
|
3
|
-
this.scanResults = scanResults;
|
|
4
|
-
}
|
|
5
|
-
|
|
6
|
-
generate() {
|
|
7
|
-
return {
|
|
8
|
-
overview: this.generateOverview(),
|
|
9
|
-
techStack: this.generateTechStack(),
|
|
10
|
-
commands: this.generateCommands(),
|
|
11
|
-
structure: this.generateStructure(),
|
|
12
|
-
context: this.generateImportantContext(),
|
|
13
|
-
patterns: this.generatePatterns()
|
|
14
|
-
};
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
generateStructuredSections() {
|
|
18
|
-
const timestamp = new Date().toISOString();
|
|
19
|
-
const sections = {};
|
|
20
|
-
|
|
21
|
-
sections['Project Overview'] = {
|
|
22
|
-
content: this.generateOverview(),
|
|
23
|
-
metadata: {
|
|
24
|
-
type: 'text',
|
|
25
|
-
source: 'scan',
|
|
26
|
-
mergeable: true,
|
|
27
|
-
mergeStrategy: 'smart',
|
|
28
|
-
timestamp
|
|
29
|
-
}
|
|
30
|
-
};
|
|
31
|
-
|
|
32
|
-
const techStack = this.generateTechStack();
|
|
33
|
-
sections['Tech Stack'] = {
|
|
34
|
-
content: {
|
|
35
|
-
language: techStack.language || [],
|
|
36
|
-
runtime: this.getRuntime(),
|
|
37
|
-
frameworks: techStack.frameworks || [],
|
|
38
|
-
databases: techStack.databases || [],
|
|
39
|
-
tools: techStack.tools || [],
|
|
40
|
-
dependencies: techStack.runtime || []
|
|
41
|
-
},
|
|
42
|
-
metadata: {
|
|
43
|
-
type: 'list',
|
|
44
|
-
source: 'scan',
|
|
45
|
-
mergeable: true,
|
|
46
|
-
mergeStrategy: 'smart',
|
|
47
|
-
timestamp
|
|
48
|
-
}
|
|
49
|
-
};
|
|
50
|
-
|
|
51
|
-
const commands = this.generateCommands();
|
|
52
|
-
sections['Key Commands'] = {
|
|
53
|
-
content: commands,
|
|
54
|
-
metadata: {
|
|
55
|
-
type: 'commands',
|
|
56
|
-
source: 'scan',
|
|
57
|
-
mergeable: true,
|
|
58
|
-
mergeStrategy: 'smart',
|
|
59
|
-
timestamp
|
|
60
|
-
}
|
|
61
|
-
};
|
|
62
|
-
|
|
63
|
-
const structure = this.generateStructure();
|
|
64
|
-
sections['Project Structure'] = {
|
|
65
|
-
content: structure,
|
|
66
|
-
metadata: {
|
|
67
|
-
type: 'list',
|
|
68
|
-
source: 'scan',
|
|
69
|
-
mergeable: true,
|
|
70
|
-
mergeStrategy: 'smart',
|
|
71
|
-
timestamp
|
|
72
|
-
}
|
|
73
|
-
};
|
|
74
|
-
|
|
75
|
-
const patterns = this.generatePatterns();
|
|
76
|
-
if (patterns && Object.keys(patterns).length > 0) {
|
|
77
|
-
sections['Architecture & Patterns'] = {
|
|
78
|
-
content: patterns,
|
|
79
|
-
metadata: {
|
|
80
|
-
type: 'list',
|
|
81
|
-
source: 'scan',
|
|
82
|
-
mergeable: true,
|
|
83
|
-
mergeStrategy: 'smart',
|
|
84
|
-
timestamp
|
|
85
|
-
}
|
|
86
|
-
};
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
const context = this.generateImportantContext();
|
|
90
|
-
if (context && context.length > 0) {
|
|
91
|
-
sections['Important Context'] = {
|
|
92
|
-
content: context,
|
|
93
|
-
metadata: {
|
|
94
|
-
type: 'list',
|
|
95
|
-
source: 'scan',
|
|
96
|
-
mergeable: true,
|
|
97
|
-
mergeStrategy: 'smart',
|
|
98
|
-
timestamp
|
|
99
|
-
}
|
|
100
|
-
};
|
|
101
|
-
}
|
|
102
|
-
|
|
103
|
-
sections['Scan Information'] = {
|
|
104
|
-
content: {
|
|
105
|
-
scanDate: new Date(this.scanResults.scanDate).toLocaleString(),
|
|
106
|
-
duration: `${this.scanResults.scanTimeMs}ms`,
|
|
107
|
-
filesAnalyzed: this.scanResults.structure?.totalFiles || 0
|
|
108
|
-
},
|
|
109
|
-
metadata: {
|
|
110
|
-
type: 'text',
|
|
111
|
-
source: 'scan',
|
|
112
|
-
mergeable: false,
|
|
113
|
-
mergeStrategy: 'smart',
|
|
114
|
-
timestamp
|
|
115
|
-
}
|
|
116
|
-
};
|
|
117
|
-
|
|
118
|
-
return sections;
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
generateOverview() {
|
|
122
|
-
const { projectType, structure } = this.scanResults;
|
|
123
|
-
|
|
124
|
-
if (!projectType || !projectType.primary) {
|
|
125
|
-
return 'This project structure could not be automatically detected.';
|
|
126
|
-
}
|
|
127
|
-
|
|
128
|
-
const primary = projectType.primary;
|
|
129
|
-
const framework = projectType.framework;
|
|
130
|
-
|
|
131
|
-
let overview = `This is a ${primary.type}`;
|
|
132
|
-
|
|
133
|
-
if (framework && framework.name) {
|
|
134
|
-
overview += ` project using ${framework.name}`;
|
|
135
|
-
}
|
|
136
|
-
|
|
137
|
-
if (primary.type === 'nodejs') {
|
|
138
|
-
overview += ' application';
|
|
139
|
-
} else if (primary.type === 'python') {
|
|
140
|
-
overview += ' application';
|
|
141
|
-
} else if (['react', 'vue', 'angular'].includes(primary.type)) {
|
|
142
|
-
overview += ' web application';
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
overview += '.';
|
|
146
|
-
|
|
147
|
-
if (structure && structure.totalFiles) {
|
|
148
|
-
overview += ` The project contains ${structure.totalFiles} files`;
|
|
149
|
-
if (structure.directories && structure.directories.length > 0) {
|
|
150
|
-
overview += ` organized across ${structure.directories.length} directories`;
|
|
151
|
-
}
|
|
152
|
-
overview += '.';
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
return overview;
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
generateTechStack() {
|
|
159
|
-
const techStack = {
|
|
160
|
-
runtime: [],
|
|
161
|
-
language: [],
|
|
162
|
-
frameworks: [],
|
|
163
|
-
databases: [],
|
|
164
|
-
tools: []
|
|
165
|
-
};
|
|
166
|
-
|
|
167
|
-
const { projectType, dependencies } = this.scanResults;
|
|
168
|
-
|
|
169
|
-
if (projectType && projectType.language) {
|
|
170
|
-
techStack.language.push(this.capitalizeFirst(projectType.language));
|
|
171
|
-
}
|
|
172
|
-
|
|
173
|
-
if (projectType && projectType.framework) {
|
|
174
|
-
techStack.frameworks.push(projectType.framework.name);
|
|
175
|
-
}
|
|
176
|
-
|
|
177
|
-
if (dependencies) {
|
|
178
|
-
if (dependencies.frameworks && dependencies.frameworks.length > 0) {
|
|
179
|
-
dependencies.frameworks.forEach(fw => {
|
|
180
|
-
if (!techStack.frameworks.includes(fw.name)) {
|
|
181
|
-
techStack.frameworks.push(fw.name);
|
|
182
|
-
}
|
|
183
|
-
});
|
|
184
|
-
}
|
|
185
|
-
|
|
186
|
-
if (dependencies.runtime && dependencies.runtime.length > 0) {
|
|
187
|
-
const majorDeps = dependencies.runtime
|
|
188
|
-
.filter(dep => this.isMajorDependency(dep.name))
|
|
189
|
-
.slice(0, 8)
|
|
190
|
-
.map(dep => `${dep.name} ${dep.version}`);
|
|
191
|
-
techStack.runtime.push(...majorDeps);
|
|
192
|
-
}
|
|
193
|
-
}
|
|
194
|
-
|
|
195
|
-
const patterns = this.scanResults.patterns;
|
|
196
|
-
if (patterns) {
|
|
197
|
-
if (patterns.database && patterns.database.length > 0) {
|
|
198
|
-
techStack.databases.push(...patterns.database);
|
|
199
|
-
}
|
|
200
|
-
}
|
|
201
|
-
|
|
202
|
-
if (projectType && projectType.buildTools && projectType.buildTools.length > 0) {
|
|
203
|
-
techStack.tools.push(...projectType.buildTools);
|
|
204
|
-
}
|
|
205
|
-
|
|
206
|
-
return techStack;
|
|
207
|
-
}
|
|
208
|
-
|
|
209
|
-
generateCommands() {
|
|
210
|
-
const { commands } = this.scanResults;
|
|
211
|
-
if (!commands) return {};
|
|
212
|
-
|
|
213
|
-
const organizedCommands = {};
|
|
214
|
-
|
|
215
|
-
Object.keys(commands).forEach(category => {
|
|
216
|
-
if (commands[category] && commands[category].length > 0) {
|
|
217
|
-
organizedCommands[category] = commands[category].map(cmd => ({
|
|
218
|
-
command: cmd.name,
|
|
219
|
-
description: cmd.description || cmd.script || 'No description available'
|
|
220
|
-
}));
|
|
221
|
-
}
|
|
222
|
-
});
|
|
223
|
-
|
|
224
|
-
return organizedCommands;
|
|
225
|
-
}
|
|
226
|
-
|
|
227
|
-
generateStructure() {
|
|
228
|
-
const { structure } = this.scanResults;
|
|
229
|
-
if (!structure || !structure.keyFiles) return [];
|
|
230
|
-
|
|
231
|
-
const importantItems = [];
|
|
232
|
-
|
|
233
|
-
structure.keyFiles
|
|
234
|
-
.filter(file => file.importance && file.importance > 5)
|
|
235
|
-
.slice(0, 10)
|
|
236
|
-
.forEach(file => {
|
|
237
|
-
importantItems.push({
|
|
238
|
-
path: file.path,
|
|
239
|
-
type: file.type,
|
|
240
|
-
description: this.describeStructureItem(file)
|
|
241
|
-
});
|
|
242
|
-
});
|
|
243
|
-
|
|
244
|
-
if (structure.directories) {
|
|
245
|
-
const keyDirectories = structure.directories
|
|
246
|
-
.filter(dir => this.isImportantDirectory(dir.name))
|
|
247
|
-
.slice(0, 8);
|
|
248
|
-
|
|
249
|
-
keyDirectories.forEach(dir => {
|
|
250
|
-
if (!importantItems.some(item => item.path === dir.path)) {
|
|
251
|
-
importantItems.push({
|
|
252
|
-
path: dir.path,
|
|
253
|
-
type: 'directory',
|
|
254
|
-
description: this.describeDirectory(dir.name)
|
|
255
|
-
});
|
|
256
|
-
}
|
|
257
|
-
});
|
|
258
|
-
}
|
|
259
|
-
|
|
260
|
-
return importantItems.sort((a, b) => {
|
|
261
|
-
const order = ['directory', 'file'];
|
|
262
|
-
return order.indexOf(a.type) - order.indexOf(b.type);
|
|
263
|
-
});
|
|
264
|
-
}
|
|
265
|
-
|
|
266
|
-
generateImportantContext() {
|
|
267
|
-
const context = [];
|
|
268
|
-
const { projectType, patterns, dependencies, structure } = this.scanResults;
|
|
269
|
-
|
|
270
|
-
if (patterns && patterns.authentication && patterns.authentication.length > 0) {
|
|
271
|
-
context.push(`Authentication: ${patterns.authentication.join(', ')}`);
|
|
272
|
-
}
|
|
273
|
-
|
|
274
|
-
if (patterns && patterns.database && patterns.database.length > 0) {
|
|
275
|
-
context.push(`Database: ${patterns.database.join(', ')}`);
|
|
276
|
-
}
|
|
277
|
-
|
|
278
|
-
if (patterns && patterns.api && patterns.api.length > 0) {
|
|
279
|
-
context.push(`API: ${patterns.api.join(', ')}`);
|
|
280
|
-
}
|
|
281
|
-
|
|
282
|
-
if (patterns && patterns.testing && patterns.testing.length > 0) {
|
|
283
|
-
context.push(`Testing: ${patterns.testing.join(', ')}`);
|
|
284
|
-
}
|
|
285
|
-
|
|
286
|
-
if (patterns && patterns.deployment && patterns.deployment.length > 0) {
|
|
287
|
-
context.push(`Deployment: ${patterns.deployment.join(', ')}`);
|
|
288
|
-
}
|
|
289
|
-
|
|
290
|
-
if (this.hasEnvironmentFiles()) {
|
|
291
|
-
context.push('Environment variables configured (see .env.example or .env.template)');
|
|
292
|
-
}
|
|
293
|
-
|
|
294
|
-
if (dependencies && dependencies.development && dependencies.development.length > 0) {
|
|
295
|
-
const devTools = dependencies.development
|
|
296
|
-
.filter(dep => this.isImportantDevTool(dep.name))
|
|
297
|
-
.map(dep => dep.name)
|
|
298
|
-
.slice(0, 5);
|
|
299
|
-
if (devTools.length > 0) {
|
|
300
|
-
context.push(`Development tools: ${devTools.join(', ')}`);
|
|
301
|
-
}
|
|
302
|
-
}
|
|
303
|
-
|
|
304
|
-
return context;
|
|
305
|
-
}
|
|
306
|
-
|
|
307
|
-
generatePatterns() {
|
|
308
|
-
const { patterns } = this.scanResults;
|
|
309
|
-
if (!patterns) return {};
|
|
310
|
-
|
|
311
|
-
const organizedPatterns = {};
|
|
312
|
-
|
|
313
|
-
Object.keys(patterns).forEach(category => {
|
|
314
|
-
if (patterns[category] && patterns[category].length > 0) {
|
|
315
|
-
organizedPatterns[category] = patterns[category];
|
|
316
|
-
}
|
|
317
|
-
});
|
|
318
|
-
|
|
319
|
-
return organizedPatterns;
|
|
320
|
-
}
|
|
321
|
-
|
|
322
|
-
formatForClaude() {
|
|
323
|
-
try {
|
|
324
|
-
const sections = this.generateStructuredSections();
|
|
325
|
-
let formatted = '\n## Additional Notes\n\n';
|
|
326
|
-
|
|
327
|
-
if (sections['Project Overview'] && sections['Project Overview'].content) {
|
|
328
|
-
formatted += `### Project Overview\n${sections['Project Overview'].content}\n\n`;
|
|
329
|
-
}
|
|
330
|
-
|
|
331
|
-
if (sections['Tech Stack'] && sections['Tech Stack'].content) {
|
|
332
|
-
const techStack = sections['Tech Stack'].content;
|
|
333
|
-
formatted += '### Tech Stack\n';
|
|
334
|
-
|
|
335
|
-
if (techStack.language && techStack.language.length > 0) {
|
|
336
|
-
formatted += `- **Language**: ${techStack.language.join(', ')}\n`;
|
|
337
|
-
}
|
|
338
|
-
|
|
339
|
-
if (techStack.runtime) {
|
|
340
|
-
formatted += `- **Runtime**: ${techStack.runtime}\n`;
|
|
341
|
-
}
|
|
342
|
-
|
|
343
|
-
if (techStack.frameworks && techStack.frameworks.length > 0) {
|
|
344
|
-
formatted += `- **Framework**: ${techStack.frameworks.join(', ')}\n`;
|
|
345
|
-
}
|
|
346
|
-
|
|
347
|
-
if (techStack.databases && techStack.databases.length > 0) {
|
|
348
|
-
formatted += `- **Database**: ${techStack.databases.join(', ')}\n`;
|
|
349
|
-
}
|
|
350
|
-
|
|
351
|
-
if (techStack.tools && techStack.tools.length > 0) {
|
|
352
|
-
formatted += `- **Build Tools**: ${techStack.tools.join(', ')}\n`;
|
|
353
|
-
}
|
|
354
|
-
|
|
355
|
-
if (techStack.dependencies && techStack.dependencies.length > 0) {
|
|
356
|
-
formatted += `- **Key Dependencies**: ${techStack.dependencies.slice(0, 5).join(', ')}\n`;
|
|
357
|
-
}
|
|
358
|
-
|
|
359
|
-
formatted += '\n';
|
|
360
|
-
}
|
|
361
|
-
|
|
362
|
-
if (sections['Key Commands'] && sections['Key Commands'].content && Object.keys(sections['Key Commands'].content).length > 0) {
|
|
363
|
-
const commands = sections['Key Commands'].content;
|
|
364
|
-
formatted += '### Key Commands\n';
|
|
365
|
-
|
|
366
|
-
['dev', 'build', 'test', 'deploy', 'other'].forEach(category => {
|
|
367
|
-
if (commands[category] && commands[category].length > 0) {
|
|
368
|
-
commands[category].forEach(cmd => {
|
|
369
|
-
formatted += `- \`${cmd.command}\` - ${cmd.description}\n`;
|
|
370
|
-
});
|
|
371
|
-
}
|
|
372
|
-
});
|
|
373
|
-
|
|
374
|
-
formatted += '\n';
|
|
375
|
-
}
|
|
376
|
-
|
|
377
|
-
if (sections['Project Structure'] && sections['Project Structure'].content && sections['Project Structure'].content.length > 0) {
|
|
378
|
-
const structure = sections['Project Structure'].content;
|
|
379
|
-
formatted += '### Project Structure\n';
|
|
380
|
-
structure.forEach(item => {
|
|
381
|
-
const prefix = item.type === 'directory' ? '📁' : '📄';
|
|
382
|
-
formatted += `- ${prefix} \`/${item.path}\` - ${item.description}\n`;
|
|
383
|
-
});
|
|
384
|
-
formatted += '\n';
|
|
385
|
-
}
|
|
386
|
-
|
|
387
|
-
if (sections['Architecture & Patterns'] && sections['Architecture & Patterns'].content && Object.keys(sections['Architecture & Patterns'].content).length > 0) {
|
|
388
|
-
const patterns = sections['Architecture & Patterns'].content;
|
|
389
|
-
formatted += '### Architecture & Patterns\n';
|
|
390
|
-
|
|
391
|
-
if (patterns.architecture && patterns.architecture.length > 0) {
|
|
392
|
-
formatted += `- **Architecture**: ${patterns.architecture.join(', ')}\n`;
|
|
393
|
-
}
|
|
394
|
-
|
|
395
|
-
if (patterns.authentication && patterns.authentication.length > 0) {
|
|
396
|
-
formatted += `- **Authentication**: ${patterns.authentication.join(', ')}\n`;
|
|
397
|
-
}
|
|
398
|
-
|
|
399
|
-
if (patterns.api && patterns.api.length > 0) {
|
|
400
|
-
formatted += `- **API Style**: ${patterns.api.join(', ')}\n`;
|
|
401
|
-
}
|
|
402
|
-
|
|
403
|
-
formatted += '\n';
|
|
404
|
-
}
|
|
405
|
-
|
|
406
|
-
if (sections['Important Context'] && sections['Important Context'].content && sections['Important Context'].content.length > 0) {
|
|
407
|
-
const context = sections['Important Context'].content;
|
|
408
|
-
formatted += '### Important Context\n';
|
|
409
|
-
context.forEach(ctx => {
|
|
410
|
-
formatted += `- ${ctx}\n`;
|
|
411
|
-
});
|
|
412
|
-
formatted += '\n';
|
|
413
|
-
}
|
|
414
|
-
|
|
415
|
-
if (sections['Scan Information'] && sections['Scan Information'].content) {
|
|
416
|
-
const scanInfo = sections['Scan Information'].content;
|
|
417
|
-
formatted += `### Scan Information\n`;
|
|
418
|
-
formatted += `- Scanned on: ${scanInfo.scanDate}\n`;
|
|
419
|
-
formatted += `- Scan duration: ${scanInfo.duration}\n`;
|
|
420
|
-
if (scanInfo.filesAnalyzed) {
|
|
421
|
-
formatted += `- Files analyzed: ${scanInfo.filesAnalyzed}\n`;
|
|
422
|
-
}
|
|
423
|
-
}
|
|
424
|
-
|
|
425
|
-
return formatted;
|
|
426
|
-
} catch (error) {
|
|
427
|
-
console.warn(`Warning: Error formatting context for Claude: ${error.message}`);
|
|
428
|
-
// Fallback to basic context generation
|
|
429
|
-
const basicContext = this.generate();
|
|
430
|
-
return `\n## Additional Notes\n\nProject Type: ${basicContext.overview || 'Unknown'}\n\nError occurred during detailed context generation. Please run scan again.\n`;
|
|
431
|
-
}
|
|
432
|
-
}
|
|
433
|
-
|
|
434
|
-
getRuntime() {
|
|
435
|
-
const { projectType } = this.scanResults;
|
|
436
|
-
|
|
437
|
-
if (projectType && projectType.primary) {
|
|
438
|
-
switch (projectType.primary.type) {
|
|
439
|
-
case 'nodejs':
|
|
440
|
-
return 'Node.js';
|
|
441
|
-
case 'python':
|
|
442
|
-
return 'Python';
|
|
443
|
-
case 'go':
|
|
444
|
-
return 'Go';
|
|
445
|
-
case 'rust':
|
|
446
|
-
return 'Rust';
|
|
447
|
-
case 'java':
|
|
448
|
-
return 'Java (JVM)';
|
|
449
|
-
case 'csharp':
|
|
450
|
-
return '.NET';
|
|
451
|
-
case 'php':
|
|
452
|
-
return 'PHP';
|
|
453
|
-
case 'ruby':
|
|
454
|
-
return 'Ruby';
|
|
455
|
-
default:
|
|
456
|
-
return projectType.language || 'Unknown';
|
|
457
|
-
}
|
|
458
|
-
}
|
|
459
|
-
|
|
460
|
-
return 'Unknown';
|
|
461
|
-
}
|
|
462
|
-
|
|
463
|
-
capitalizeFirst(str) {
|
|
464
|
-
return str.charAt(0).toUpperCase() + str.slice(1);
|
|
465
|
-
}
|
|
466
|
-
|
|
467
|
-
isMajorDependency(depName) {
|
|
468
|
-
const majorPackages = [
|
|
469
|
-
'express', 'react', 'vue', 'angular', 'next', 'nuxt',
|
|
470
|
-
'typescript', 'babel', 'webpack', 'vite', 'rollup',
|
|
471
|
-
'eslint', 'prettier', 'jest', 'cypress', 'playwright',
|
|
472
|
-
'tailwindcss', 'sass', 'less', 'styled-components',
|
|
473
|
-
'prisma', 'mongoose', 'sequelize', 'typeorm',
|
|
474
|
-
'graphql', 'apollo', 'socket.io', 'passport',
|
|
475
|
-
'jsonwebtoken', 'bcrypt', 'axios', 'lodash'
|
|
476
|
-
];
|
|
477
|
-
|
|
478
|
-
return majorPackages.some(pkg => depName.includes(pkg)) ||
|
|
479
|
-
depName.startsWith('@types/') ||
|
|
480
|
-
depName.startsWith('@nestjs/') ||
|
|
481
|
-
depName.startsWith('@angular/') ||
|
|
482
|
-
depName.startsWith('@storybook/');
|
|
483
|
-
}
|
|
484
|
-
|
|
485
|
-
isImportantDevTool(depName) {
|
|
486
|
-
const devTools = [
|
|
487
|
-
'typescript', 'babel', 'webpack', 'vite', 'rollup', 'parcel',
|
|
488
|
-
'eslint', 'prettier', 'jest', 'vitest', 'cypress', 'playwright',
|
|
489
|
-
'storybook', 'nodemon', 'concurrently', 'rimraf'
|
|
490
|
-
];
|
|
491
|
-
|
|
492
|
-
return devTools.some(tool => depName.includes(tool));
|
|
493
|
-
}
|
|
494
|
-
|
|
495
|
-
hasEnvironmentFiles() {
|
|
496
|
-
const { structure } = this.scanResults;
|
|
497
|
-
if (!structure || !structure.keyFiles) return false;
|
|
498
|
-
|
|
499
|
-
return structure.keyFiles.some(file => {
|
|
500
|
-
const fileName = file.name || file.path || '';
|
|
501
|
-
return fileName.includes('.env') ||
|
|
502
|
-
fileName.includes('environment') ||
|
|
503
|
-
fileName.includes('config');
|
|
504
|
-
});
|
|
505
|
-
}
|
|
506
|
-
|
|
507
|
-
isImportantDirectory(dirName) {
|
|
508
|
-
const important = [
|
|
509
|
-
'src', 'lib', 'app', 'components', 'pages', 'routes',
|
|
510
|
-
'controllers', 'models', 'views', 'services', 'utils',
|
|
511
|
-
'middleware', 'config', 'public', 'assets', 'static',
|
|
512
|
-
'tests', 'test', '__tests__', 'spec', 'e2e',
|
|
513
|
-
'docs', 'documentation', 'scripts', 'tools'
|
|
514
|
-
];
|
|
515
|
-
|
|
516
|
-
return important.includes(dirName.toLowerCase());
|
|
517
|
-
}
|
|
518
|
-
|
|
519
|
-
describeStructureItem(file) {
|
|
520
|
-
switch (file.type) {
|
|
521
|
-
case 'package-manager':
|
|
522
|
-
return 'Package manager configuration and dependencies';
|
|
523
|
-
case 'containerization':
|
|
524
|
-
return 'Docker configuration for containerized deployment';
|
|
525
|
-
case 'build':
|
|
526
|
-
return 'Build system configuration and scripts';
|
|
527
|
-
case 'documentation':
|
|
528
|
-
return 'Project documentation and guides';
|
|
529
|
-
case 'configuration':
|
|
530
|
-
return 'Application configuration files';
|
|
531
|
-
case 'environment':
|
|
532
|
-
return 'Environment variables and settings';
|
|
533
|
-
case 'testing':
|
|
534
|
-
return 'Test configuration and setup';
|
|
535
|
-
case 'directory':
|
|
536
|
-
return this.describeDirectory(file.name || file.path || 'unknown');
|
|
537
|
-
default:
|
|
538
|
-
return 'Project file';
|
|
539
|
-
}
|
|
540
|
-
}
|
|
541
|
-
|
|
542
|
-
describeDirectory(dirName) {
|
|
543
|
-
const descriptions = {
|
|
544
|
-
src: 'Source code directory',
|
|
545
|
-
lib: 'Library code and utilities',
|
|
546
|
-
app: 'Main application code',
|
|
547
|
-
components: 'Reusable UI components',
|
|
548
|
-
pages: 'Page components and routing',
|
|
549
|
-
routes: 'API routes and handlers',
|
|
550
|
-
controllers: 'Request controllers (MVC pattern)',
|
|
551
|
-
models: 'Data models and schemas',
|
|
552
|
-
views: 'View templates and components',
|
|
553
|
-
services: 'Business logic and services',
|
|
554
|
-
utils: 'Utility functions and helpers',
|
|
555
|
-
middleware: 'Express/API middleware',
|
|
556
|
-
config: 'Configuration files',
|
|
557
|
-
public: 'Static public assets',
|
|
558
|
-
assets: 'Application assets (images, fonts, etc.)',
|
|
559
|
-
static: 'Static files served directly',
|
|
560
|
-
tests: 'Test files and test utilities',
|
|
561
|
-
test: 'Test files and test utilities',
|
|
562
|
-
'__tests__': 'Jest test files',
|
|
563
|
-
spec: 'Specification and test files',
|
|
564
|
-
e2e: 'End-to-end test files',
|
|
565
|
-
docs: 'Documentation files',
|
|
566
|
-
scripts: 'Build and utility scripts',
|
|
567
|
-
tools: 'Development tools and utilities'
|
|
568
|
-
};
|
|
569
|
-
|
|
570
|
-
return descriptions[dirName.toLowerCase()] || `${dirName} directory`;
|
|
571
|
-
}
|
|
572
|
-
}
|
|
573
|
-
|
|
574
|
-
module.exports = ContextGenerator;
|