MCPcopy Create free account
hub / github.com/QodeXcli/QodeX / detectProjectInfo

Function detectProjectInfo

src/context/project-info.ts:56–147  ·  view source on GitHub ↗
(cwd: string)

Source from the content-addressed store, hash-verified

54}
55
56export async function detectProjectInfo(cwd: string): Promise<ProjectInfo> {
57 const info: ProjectInfo = {
58 languages: [],
59 hasGit: await fileExists(path.join(cwd, '.git')),
60 };
61
62 // Detect languages
63 for (const [lang, files] of Object.entries(LANGUAGE_FILES)) {
64 for (const f of files) {
65 if (await fileExists(path.join(cwd, f))) {
66 info.languages.push(lang);
67 break;
68 }
69 }
70 }
71
72 // Node-specific deeper detection
73 const pkgPath = path.join(cwd, 'package.json');
74 if (await fileExists(pkgPath)) {
75 try {
76 const pkg = JSON.parse(await fs.readFile(pkgPath, 'utf-8'));
77 const allDeps = { ...pkg.dependencies, ...pkg.devDependencies };
78
79 // Framework
80 for (const [fw, predicate] of FRAMEWORK_DETECTION) {
81 if (predicate(allDeps)) {
82 info.framework = fw;
83 break;
84 }
85 }
86
87 // Package manager
88 if (await fileExists(path.join(cwd, 'pnpm-lock.yaml'))) info.packageManager = 'pnpm';
89 else if (await fileExists(path.join(cwd, 'yarn.lock'))) info.packageManager = 'yarn';
90 else if (await fileExists(path.join(cwd, 'bun.lockb'))) info.packageManager = 'bun';
91 else if (await fileExists(path.join(cwd, 'package-lock.json'))) info.packageManager = 'npm';
92 else info.packageManager = 'npm';
93
94 // Test runner
95 if ('vitest' in allDeps) info.testRunner = 'vitest';
96 else if ('jest' in allDeps) info.testRunner = 'jest';
97 else if ('mocha' in allDeps) info.testRunner = 'mocha';
98 else if (pkg.scripts?.test) info.testRunner = 'npm test';
99
100 // Linter
101 if ('eslint' in allDeps) info.linter = 'eslint';
102 else if ('biome' in allDeps || '@biomejs/biome' in allDeps) info.linter = 'biome';
103
104 // Type checker
105 if ('typescript' in allDeps) info.typeChecker = 'tsc';
106 } catch (err: any) {
107 // ENOENT (package.json vanished between the exists-check and read) is
108 // benign — just skip deeper detection. A parse error means the file is
109 // present but malformed; log it so the degraded detection is traceable.
110 if (err?.code !== 'ENOENT') {
111 logger.debug(`Failed to parse ${pkgPath}: ${err?.message ?? err}`);
112 }
113 }

Callers 2

index.tsFile · 0.85
buildInitialMessagesMethod · 0.85

Calls 3

fileExistsFunction · 0.85
debugMethod · 0.80
pushMethod · 0.45

Tested by

no test coverage detected