@nolrm/contextkit 0.13.4 → 0.13.7

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.
@@ -13,7 +13,7 @@ class AnalyzeCommand {
13
13
  console.log(chalk.magenta('šŸ” ContextKit Project Analysis\n'));
14
14
 
15
15
  // Check if contextkit is installed
16
- if (!await fs.pathExists('.contextkit/commands/analyze.md')) {
16
+ if (!(await fs.pathExists('.contextkit/commands/analyze.md'))) {
17
17
  console.log(chalk.red('āŒ ContextKit not found.'));
18
18
  console.log(chalk.yellow(' Run: contextkit install'));
19
19
  return;
@@ -24,27 +24,27 @@ class AnalyzeCommand {
24
24
  try {
25
25
  // Detect monorepo structure
26
26
  const monorepoStructure = await this.detectMonorepoStructure();
27
-
27
+
28
28
  // Determine analysis scope
29
29
  let analysisScope;
30
-
30
+
31
31
  // Handle specific package option
32
32
  if (options.package) {
33
33
  const packagePath = path.resolve(options.package);
34
- if (!await fs.pathExists(packagePath)) {
34
+ if (!(await fs.pathExists(packagePath))) {
35
35
  spinner.fail(`Package path not found: ${options.package}`);
36
36
  return;
37
37
  }
38
-
38
+
39
39
  spinner.succeed(`Analyzing specific package: ${options.package}\n`);
40
40
  analysisScope = {
41
41
  scope: 'package',
42
42
  paths: [packagePath],
43
- packages: [{ path: packagePath, name: path.basename(packagePath) }]
43
+ packages: [{ path: packagePath, name: path.basename(packagePath) }],
44
44
  };
45
45
  } else if (monorepoStructure.isMonorepo) {
46
46
  spinner.succeed('Monorepo detected!\n');
47
-
47
+
48
48
  if (options.scope) {
49
49
  // Use provided scope
50
50
  analysisScope = await this.getScopeFromOption(options.scope, monorepoStructure);
@@ -55,7 +55,7 @@ class AnalyzeCommand {
55
55
  // Interactive: prompt user
56
56
  analysisScope = await this.promptAnalysisScope(monorepoStructure);
57
57
  }
58
-
58
+
59
59
  this.displayScopeInfo(analysisScope, monorepoStructure);
60
60
  } else {
61
61
  spinner.succeed('Single package detected\n');
@@ -66,7 +66,7 @@ class AnalyzeCommand {
66
66
  const contextSpinner = ora('Loading project context...').start();
67
67
  const context = await this.loadProjectContext(analysisScope);
68
68
  contextSpinner.succeed('Context loaded successfully\n');
69
-
69
+
70
70
  // Load analyze.md instructions
71
71
  const analyzeInstructions = await fs.readFile('.contextkit/commands/analyze.md', 'utf-8');
72
72
 
@@ -75,14 +75,20 @@ class AnalyzeCommand {
75
75
  console.log('─'.repeat(60));
76
76
  console.log(analyzeInstructions);
77
77
  console.log('─'.repeat(60));
78
-
78
+
79
79
  console.log(chalk.blue('\nšŸ“Š Project Context:\n'));
80
80
  console.log('─'.repeat(60));
81
- console.log(JSON.stringify({
82
- ...context,
83
- analysisScope: analysisScope.scope,
84
- analyzedPaths: analysisScope.paths
85
- }, null, 2));
81
+ console.log(
82
+ JSON.stringify(
83
+ {
84
+ ...context,
85
+ analysisScope: analysisScope.scope,
86
+ analyzedPaths: analysisScope.paths,
87
+ },
88
+ null,
89
+ 2
90
+ )
91
+ );
86
92
  console.log('─'.repeat(60));
87
93
 
88
94
  // Update config.yml with analysis scope
@@ -90,7 +96,6 @@ class AnalyzeCommand {
90
96
 
91
97
  // Show usage instructions
92
98
  this.showUsageInstructions(options, analysisScope);
93
-
94
99
  } catch (error) {
95
100
  spinner.fail('Failed to load context');
96
101
  console.log(chalk.red(error.message));
@@ -101,18 +106,18 @@ class AnalyzeCommand {
101
106
  try {
102
107
  const yaml = require('js-yaml');
103
108
  const configPath = '.contextkit/config.yml';
104
-
105
- if (!await fs.pathExists(configPath)) {
109
+
110
+ if (!(await fs.pathExists(configPath))) {
106
111
  return;
107
112
  }
108
113
 
109
114
  const configContent = await fs.readFile(configPath, 'utf-8');
110
115
  const config = yaml.load(configContent);
111
-
116
+
112
117
  // Update analysis scope info
113
118
  config.analysis_scope = analysisScope.scope;
114
- config.analyzed_packages = analysisScope.packages.map(p => p.relativePath || p.path);
115
-
119
+ config.analyzed_packages = analysisScope.packages.map((p) => p.relativePath || p.path);
120
+
116
121
  // Write back
117
122
  await fs.writeFile(configPath, yaml.dump(config, { lineWidth: 120 }));
118
123
  } catch (error) {
@@ -124,7 +129,7 @@ class AnalyzeCommand {
124
129
  async loadProjectContext(analysisScope = null) {
125
130
  const context = {
126
131
  paths: analysisScope?.paths || [process.cwd()],
127
- scope: analysisScope?.scope || 'current'
132
+ scope: analysisScope?.scope || 'current',
128
133
  };
129
134
 
130
135
  // Load context for each path in scope
@@ -146,7 +151,7 @@ class AnalyzeCommand {
146
151
  const originalCwd = process.cwd();
147
152
  const pathContext = {
148
153
  path: analysisPath,
149
- relativePath: path.relative(originalCwd, analysisPath)
154
+ relativePath: path.relative(originalCwd, analysisPath),
150
155
  };
151
156
 
152
157
  try {
@@ -165,7 +170,7 @@ class AnalyzeCommand {
165
170
  // Detect frameworks and build tools for this path
166
171
  pathContext.frameworks = await this.detectFrameworks();
167
172
  pathContext.buildTools = await this.detectBuildTools();
168
- } catch (error) {
173
+ } catch {
169
174
  // Continue even if one path fails
170
175
  } finally {
171
176
  process.chdir(originalCwd);
@@ -182,7 +187,7 @@ class AnalyzeCommand {
182
187
  apps: [],
183
188
  frontendPackages: [],
184
189
  backendPackages: [],
185
- fullstackPackages: []
190
+ fullstackPackages: [],
186
191
  };
187
192
 
188
193
  // Detect monorepo type
@@ -219,7 +224,7 @@ class AnalyzeCommand {
219
224
  for (const pkg of allPackages) {
220
225
  const pkgType = await this.classifyPackage(pkg.path);
221
226
  pkg.type = pkgType;
222
-
227
+
223
228
  if (pkgType === 'frontend') {
224
229
  structure.frontendPackages.push(pkg);
225
230
  } else if (pkgType === 'backend') {
@@ -239,24 +244,24 @@ class AnalyzeCommand {
239
244
 
240
245
  async scanPackages(dir) {
241
246
  const packages = [];
242
- if (!await fs.pathExists(dir)) return packages;
247
+ if (!(await fs.pathExists(dir))) return packages;
243
248
 
244
249
  const entries = await fs.readdir(dir, { withFileTypes: true });
245
-
250
+
246
251
  for (const entry of entries) {
247
252
  if (entry.isDirectory()) {
248
253
  const packagePath = path.join(dir, entry.name);
249
254
  const packageJsonPath = path.join(packagePath, 'package.json');
250
-
255
+
251
256
  if (await fs.pathExists(packageJsonPath)) {
252
257
  try {
253
258
  const packageJson = await fs.readJson(packageJsonPath);
254
259
  packages.push({
255
260
  name: packageJson.name || entry.name,
256
261
  path: packagePath,
257
- relativePath: path.relative(process.cwd(), packagePath)
262
+ relativePath: path.relative(process.cwd(), packagePath),
258
263
  });
259
- } catch (error) {
264
+ } catch {
260
265
  // Skip invalid package.json
261
266
  }
262
267
  }
@@ -268,86 +273,112 @@ class AnalyzeCommand {
268
273
 
269
274
  async classifyPackage(packagePath) {
270
275
  const packageJsonPath = path.join(packagePath, 'package.json');
271
- if (!await fs.pathExists(packageJsonPath)) return 'unknown';
272
-
276
+ if (!(await fs.pathExists(packageJsonPath))) return 'unknown';
277
+
273
278
  try {
274
279
  const pkg = await fs.readJson(packageJsonPath);
275
280
  const deps = { ...(pkg.dependencies || {}), ...(pkg.devDependencies || {}) };
276
-
281
+
277
282
  // Frontend indicators
278
- const frontendDeps = ['react', 'vue', '@vue', 'angular', '@angular/core', 'next', 'nuxt', 'svelte'];
279
- const hasFrontend = frontendDeps.some(dep => deps[dep]);
280
-
283
+ const frontendDeps = [
284
+ 'react',
285
+ 'vue',
286
+ '@vue',
287
+ 'angular',
288
+ '@angular/core',
289
+ 'next',
290
+ 'nuxt',
291
+ 'svelte',
292
+ ];
293
+ const hasFrontend = frontendDeps.some((dep) => deps[dep]);
294
+
281
295
  // Backend indicators
282
- const backendDeps = ['express', 'fastify', 'koa', '@nestjs/core', 'django', 'flask', 'fastapi'];
283
- const hasBackend = backendDeps.some(dep => deps[dep]);
284
-
296
+ const backendDeps = [
297
+ 'express',
298
+ 'fastify',
299
+ 'koa',
300
+ '@nestjs/core',
301
+ 'django',
302
+ 'flask',
303
+ 'fastapi',
304
+ ];
305
+ let hasBackend = backendDeps.some((dep) => deps[dep]);
306
+
285
307
  // Check for backend file patterns
286
308
  if (!hasBackend) {
287
309
  const serverFiles = ['server.js', 'server.ts', 'index.js', 'index.ts', 'app.js', 'app.ts'];
288
310
  for (const file of serverFiles) {
289
- if (await fs.pathExists(path.join(packagePath, file)) ||
290
- await fs.pathExists(path.join(packagePath, 'src', file))) {
311
+ if (
312
+ (await fs.pathExists(path.join(packagePath, file))) ||
313
+ (await fs.pathExists(path.join(packagePath, 'src', file)))
314
+ ) {
291
315
  hasBackend = true;
292
316
  break;
293
317
  }
294
318
  }
295
319
  }
296
-
320
+
297
321
  if (hasFrontend && hasBackend) return 'fullstack';
298
322
  if (hasFrontend) return 'frontend';
299
323
  if (hasBackend) return 'backend';
300
-
324
+
301
325
  // Check directory structure
302
- if (await fs.pathExists(path.join(packagePath, 'src', 'components')) ||
303
- await fs.pathExists(path.join(packagePath, 'components'))) {
326
+ if (
327
+ (await fs.pathExists(path.join(packagePath, 'src', 'components'))) ||
328
+ (await fs.pathExists(path.join(packagePath, 'components')))
329
+ ) {
304
330
  return 'frontend';
305
331
  }
306
-
307
- if (await fs.pathExists(path.join(packagePath, 'src', 'server')) ||
308
- await fs.pathExists(path.join(packagePath, 'src', 'api'))) {
332
+
333
+ if (
334
+ (await fs.pathExists(path.join(packagePath, 'src', 'server'))) ||
335
+ (await fs.pathExists(path.join(packagePath, 'src', 'api')))
336
+ ) {
309
337
  return 'backend';
310
338
  }
311
-
339
+
312
340
  return 'unknown';
313
- } catch (error) {
341
+ } catch {
314
342
  return 'unknown';
315
343
  }
316
344
  }
317
345
 
318
346
  async promptAnalysisScope(monorepoStructure) {
319
347
  const choices = [];
320
-
348
+
321
349
  if (monorepoStructure.frontendPackages.length > 0) {
322
- const frontendNames = monorepoStructure.frontendPackages.map(p => p.name).join(', ');
350
+ const frontendNames = monorepoStructure.frontendPackages.map((p) => p.name).join(', ');
323
351
  choices.push({
324
352
  name: `Frontend (${monorepoStructure.frontendPackages.length} package(s): ${frontendNames})`,
325
353
  value: 'frontend',
326
- packages: monorepoStructure.frontendPackages
354
+ packages: monorepoStructure.frontendPackages,
327
355
  });
328
356
  }
329
-
357
+
330
358
  if (monorepoStructure.backendPackages.length > 0) {
331
- const backendNames = monorepoStructure.backendPackages.map(p => p.name).join(', ');
359
+ const backendNames = monorepoStructure.backendPackages.map((p) => p.name).join(', ');
332
360
  choices.push({
333
361
  name: `Backend (${monorepoStructure.backendPackages.length} package(s): ${backendNames})`,
334
362
  value: 'backend',
335
- packages: monorepoStructure.backendPackages
363
+ packages: monorepoStructure.backendPackages,
336
364
  });
337
365
  }
338
-
339
- if (monorepoStructure.frontendPackages.length > 0 && monorepoStructure.backendPackages.length > 0) {
366
+
367
+ if (
368
+ monorepoStructure.frontendPackages.length > 0 &&
369
+ monorepoStructure.backendPackages.length > 0
370
+ ) {
340
371
  choices.push({
341
372
  name: 'Both (Frontend + Backend) - Separate standards',
342
373
  value: 'both',
343
- packages: [...monorepoStructure.frontendPackages, ...monorepoStructure.backendPackages]
374
+ packages: [...monorepoStructure.frontendPackages, ...monorepoStructure.backendPackages],
344
375
  });
345
376
  }
346
-
377
+
347
378
  choices.push({
348
379
  name: 'Current directory only',
349
380
  value: 'current',
350
- packages: []
381
+ packages: [],
351
382
  });
352
383
 
353
384
  if (choices.length === 1) {
@@ -360,17 +391,15 @@ class AnalyzeCommand {
360
391
  type: 'list',
361
392
  name: 'scope',
362
393
  message: 'Which part of the monorepo should we analyze?',
363
- choices: choices.map(c => c.name)
364
- }
394
+ choices: choices.map((c) => c.name),
395
+ },
365
396
  ]);
366
397
 
367
- const selected = choices.find(c => c.name === scope);
398
+ const selected = choices.find((c) => c.name === scope);
368
399
  return {
369
400
  scope: selected.value,
370
401
  packages: selected.packages,
371
- paths: selected.packages.length > 0
372
- ? selected.packages.map(p => p.path)
373
- : [process.cwd()]
402
+ paths: selected.packages.length > 0 ? selected.packages.map((p) => p.path) : [process.cwd()],
374
403
  };
375
404
  }
376
405
 
@@ -380,19 +409,21 @@ class AnalyzeCommand {
380
409
  return {
381
410
  scope: 'frontend',
382
411
  packages: monorepoStructure.frontendPackages,
383
- paths: monorepoStructure.frontendPackages.map(p => p.path)
412
+ paths: monorepoStructure.frontendPackages.map((p) => p.path),
384
413
  };
385
414
  case 'backend':
386
415
  return {
387
416
  scope: 'backend',
388
417
  packages: monorepoStructure.backendPackages,
389
- paths: monorepoStructure.backendPackages.map(p => p.path)
418
+ paths: monorepoStructure.backendPackages.map((p) => p.path),
390
419
  };
391
420
  case 'both':
392
421
  return {
393
422
  scope: 'both',
394
423
  packages: [...monorepoStructure.frontendPackages, ...monorepoStructure.backendPackages],
395
- paths: [...monorepoStructure.frontendPackages, ...monorepoStructure.backendPackages].map(p => p.path)
424
+ paths: [...monorepoStructure.frontendPackages, ...monorepoStructure.backendPackages].map(
425
+ (p) => p.path
426
+ ),
396
427
  };
397
428
  default:
398
429
  return { scope: 'current', paths: [process.cwd()], packages: [] };
@@ -404,10 +435,10 @@ class AnalyzeCommand {
404
435
  console.log(chalk.dim(` Type: ${monorepoStructure.type || 'workspace'}`));
405
436
  console.log(chalk.dim(` Frontend packages: ${monorepoStructure.frontendPackages.length}`));
406
437
  console.log(chalk.dim(` Backend packages: ${monorepoStructure.backendPackages.length}`));
407
-
438
+
408
439
  console.log(chalk.blue(`\nšŸŽÆ Analysis Scope: ${analysisScope.scope}\n`));
409
440
  if (analysisScope.packages.length > 0) {
410
- analysisScope.packages.forEach(pkg => {
441
+ analysisScope.packages.forEach((pkg) => {
411
442
  console.log(chalk.dim(` • ${pkg.name} (${pkg.type})`));
412
443
  });
413
444
  }
@@ -419,7 +450,7 @@ class AnalyzeCommand {
419
450
  if (await fs.pathExists('package.json')) {
420
451
  return await fs.readJson('package.json');
421
452
  }
422
- } catch (error) {
453
+ } catch {
423
454
  // Ignore
424
455
  }
425
456
  return {};
@@ -430,7 +461,7 @@ class AnalyzeCommand {
430
461
  hasSrc: await fs.pathExists('src'),
431
462
  hasApp: await fs.pathExists('src/app'),
432
463
  hasComponents: await fs.pathExists('src/components'),
433
- isMonorepo: await fs.pathExists('packages') || await fs.pathExists('apps'),
464
+ isMonorepo: (await fs.pathExists('packages')) || (await fs.pathExists('apps')),
434
465
  frameworks: await this.detectFrameworks(),
435
466
  buildTools: await this.detectBuildTools(),
436
467
  };
@@ -462,13 +493,13 @@ class AnalyzeCommand {
462
493
  async detectBuildTools() {
463
494
  const tools = [];
464
495
 
465
- if (await fs.pathExists('vite.config.js') || await fs.pathExists('vite.config.ts')) {
496
+ if ((await fs.pathExists('vite.config.js')) || (await fs.pathExists('vite.config.ts'))) {
466
497
  tools.push('Vite');
467
498
  }
468
- if (await fs.pathExists('webpack.config.js') || await fs.pathExists('webpack.config.ts')) {
499
+ if ((await fs.pathExists('webpack.config.js')) || (await fs.pathExists('webpack.config.ts'))) {
469
500
  tools.push('Webpack');
470
501
  }
471
- if (await fs.pathExists('rollup.config.js') || await fs.pathExists('rollup.config.ts')) {
502
+ if ((await fs.pathExists('rollup.config.js')) || (await fs.pathExists('rollup.config.ts'))) {
472
503
  tools.push('Rollup');
473
504
  }
474
505
 
@@ -478,25 +509,26 @@ class AnalyzeCommand {
478
509
  async detectAITools() {
479
510
  const ToolDetector = require('../utils/tool-detector');
480
511
  const detector = new ToolDetector();
481
- const tools = await detector.detectAll();
512
+ const _tools = await detector.detectAll();
482
513
  const summary = detector.getSummary();
483
514
 
484
515
  return {
485
516
  detected: summary.all,
486
517
  editors: summary.editors,
487
518
  cli: summary.cli,
488
- count: summary.count
519
+ count: summary.count,
489
520
  };
490
521
  }
491
522
 
492
523
  showUsageInstructions(options, analysisScope = null) {
493
524
  console.log(chalk.blue('\nšŸ’” To execute analysis with AI:\n'));
494
-
525
+
495
526
  console.log(chalk.yellow('1. Using contextkit AI chat:'));
496
- const scopeHint = analysisScope?.scope === 'both'
497
- ? ' (will generate separate frontend/backend standards)'
498
- : '';
499
- console.log(` contextkit ai "read .contextkit/commands/analyze.md and execute analysis${scopeHint}"\n`);
527
+ const scopeHint =
528
+ analysisScope?.scope === 'both' ? ' (will generate separate frontend/backend standards)' : '';
529
+ console.log(
530
+ ` contextkit ai "read .contextkit/commands/analyze.md and execute analysis${scopeHint}"\n`
531
+ );
500
532
 
501
533
  console.log(chalk.yellow('2. Using Aider (if installed):'));
502
534
  console.log(' aider');
@@ -506,14 +538,22 @@ class AnalyzeCommand {
506
538
  console.log(' claude "read .contextkit/commands/analyze.md and execute analysis"\n');
507
539
 
508
540
  console.log(chalk.blue('šŸ“ Next: Use the AI tool of your choice to execute the analysis'));
509
- console.log(chalk.blue('✨ The AI will generate content for your skeleton .contextkit/standards/*.md files'));
510
-
541
+ console.log(
542
+ chalk.blue(
543
+ '✨ The AI will generate content for your skeleton .contextkit/standards/*.md files'
544
+ )
545
+ );
546
+
511
547
  if (analysisScope?.scope === 'both') {
512
- console.log(chalk.blue('šŸ“¦ For monorepo with both frontend and backend, standards will be generated separately:'));
548
+ console.log(
549
+ chalk.blue(
550
+ 'šŸ“¦ For monorepo with both frontend and backend, standards will be generated separately:'
551
+ )
552
+ );
513
553
  console.log(chalk.dim(' • .contextkit/standards/frontend/'));
514
554
  console.log(chalk.dim(' • .contextkit/standards/backend/'));
515
555
  }
516
-
556
+
517
557
  console.log('');
518
558
  console.log(chalk.yellow('šŸ“‹ What AI will generate:'));
519
559
  console.log(' • code-style.md - Extract formatting & conventions from your code');
@@ -526,8 +566,8 @@ class AnalyzeCommand {
526
566
  console.log(chalk.yellow('āš ļø After generation completes:'));
527
567
  console.log(chalk.yellow(' 1. Review generated files in .contextkit/standards/'));
528
568
  console.log(chalk.yellow(' 2. Edit and refine to match YOUR exact needs'));
529
- console.log(chalk.yellow(' 3. Commit them to your repo (they\'re part of your project now)'));
530
-
569
+ console.log(chalk.yellow(" 3. Commit them to your repo (they're part of your project now)"));
570
+
531
571
  if (analysisScope?.scope && analysisScope.scope !== 'current') {
532
572
  console.log('');
533
573
  console.log(chalk.blue('šŸ’” Tip: Run with --scope flag for non-interactive mode:'));
@@ -1,6 +1,5 @@
1
1
  const chalk = require('chalk');
2
2
  const fs = require('fs-extra');
3
- const path = require('path');
4
3
  const yaml = require('js-yaml');
5
4
 
6
5
  class CheckCommand {
@@ -13,7 +12,7 @@ class CheckCommand {
13
12
  async run(options = {}) {
14
13
  console.log(chalk.magenta('šŸ” ContextKit Validation Check\n'));
15
14
 
16
- if (!await fs.pathExists('.contextkit/config.yml')) {
15
+ if (!(await fs.pathExists('.contextkit/config.yml'))) {
17
16
  console.log(chalk.red('āŒ ContextKit not installed'));
18
17
  console.log(chalk.yellow(' Run: contextkit install'));
19
18
  return;
@@ -88,7 +87,7 @@ class CheckCommand {
88
87
 
89
88
  for (const file of config.required) {
90
89
  const filePath = `.contextkit/${file}`;
91
- if (!await fs.pathExists(filePath)) {
90
+ if (!(await fs.pathExists(filePath))) {
92
91
  this.errors.push(`Required file missing: ${file}`);
93
92
  } else {
94
93
  this.info.push(`āœ“ Required file exists: ${file}`);
@@ -103,13 +102,13 @@ class CheckCommand {
103
102
 
104
103
  for (const file of config.optional) {
105
104
  const filePath = `.contextkit/${file}`;
106
- if (!await fs.pathExists(filePath)) {
105
+ if (!(await fs.pathExists(filePath))) {
107
106
  this.warnings.push(`Optional file missing: ${file}`);
108
107
  }
109
108
  }
110
109
  }
111
110
 
112
- async checkStandardsFreshness(config) {
111
+ async checkStandardsFreshness(_config) {
113
112
  // Load policy to get freshness threshold
114
113
  let freshnessDays = 90; // default
115
114
  try {
@@ -120,7 +119,7 @@ class CheckCommand {
120
119
  freshnessDays = policy.enforcement.standards.freshness_days;
121
120
  }
122
121
  }
123
- } catch (error) {
122
+ } catch {
124
123
  // Policy file might not exist or be invalid, use default
125
124
  }
126
125
 
@@ -130,7 +129,7 @@ class CheckCommand {
130
129
  'standards/testing.md',
131
130
  'standards/architecture.md',
132
131
  'standards/ai-guidelines.md',
133
- 'standards/workflows.md'
132
+ 'standards/workflows.md',
134
133
  ];
135
134
 
136
135
  for (const file of standardsFiles) {
@@ -138,7 +137,7 @@ class CheckCommand {
138
137
  if (await fs.pathExists(filePath)) {
139
138
  const stats = await fs.stat(filePath);
140
139
  const daysSinceUpdate = (Date.now() - stats.mtime.getTime()) / (1000 * 60 * 60 * 24);
141
-
140
+
142
141
  if (daysSinceUpdate > freshnessDays) {
143
142
  this.warnings.push(
144
143
  `Standards file outdated: ${file} (last updated ${Math.floor(daysSinceUpdate)} days ago, threshold: ${freshnessDays} days)`
@@ -148,9 +147,9 @@ class CheckCommand {
148
147
  }
149
148
  }
150
149
 
151
- async checkPolicyCompliance(config) {
150
+ async checkPolicyCompliance(_config) {
152
151
  try {
153
- if (!await fs.pathExists('.contextkit/policies/policy.yml')) {
152
+ if (!(await fs.pathExists('.contextkit/policies/policy.yml'))) {
154
153
  this.warnings.push('Policy file missing: policies/policy.yml');
155
154
  return;
156
155
  }
@@ -171,7 +170,9 @@ class CheckCommand {
171
170
  if (await fs.pathExists(testingPath)) {
172
171
  const content = await fs.readFile(testingPath, 'utf-8');
173
172
  if (!content.includes('numbered') && !content.includes('1., 2., 3.')) {
174
- this.errors.push('Testing standards must require numbered test cases (policy: block)');
173
+ this.errors.push(
174
+ 'Testing standards must require numbered test cases (policy: block)'
175
+ );
175
176
  }
176
177
  }
177
178
  }
@@ -212,7 +213,7 @@ class CheckCommand {
212
213
  for (const dep of deprecations) {
213
214
  if (await fs.pathExists(dep.file)) {
214
215
  if (dep.bridge) {
215
- if (!await fs.pathExists(dep.bridge)) {
216
+ if (!(await fs.pathExists(dep.bridge))) {
216
217
  this.warnings.push(dep.message);
217
218
  }
218
219
  } else {
@@ -240,7 +241,9 @@ class CheckCommand {
240
241
  }
241
242
 
242
243
  if (!anyBridge) {
243
- this.warnings.push('No platform bridge files found. Run: ck <platform> (e.g., ck claude, ck cursor)');
244
+ this.warnings.push(
245
+ 'No platform bridge files found. Run: ck <platform> (e.g., ck claude, ck cursor)'
246
+ );
244
247
  }
245
248
  }
246
249
 
@@ -249,21 +252,21 @@ class CheckCommand {
249
252
 
250
253
  if (this.errors.length > 0) {
251
254
  console.log(chalk.red(`\nāŒ Errors (${this.errors.length}):`));
252
- this.errors.forEach(error => {
255
+ this.errors.forEach((error) => {
253
256
  console.log(chalk.red(` • ${error}`));
254
257
  });
255
258
  }
256
259
 
257
260
  if (this.warnings.length > 0) {
258
261
  console.log(chalk.yellow(`\nāš ļø Warnings (${this.warnings.length}):`));
259
- this.warnings.forEach(warning => {
262
+ this.warnings.forEach((warning) => {
260
263
  console.log(chalk.yellow(` • ${warning}`));
261
264
  });
262
265
  }
263
266
 
264
267
  if (this.info.length > 0 && options.verbose) {
265
268
  console.log(chalk.blue(`\nā„¹ļø Info (${this.info.length}):`));
266
- this.info.forEach(info => {
269
+ this.info.forEach((info) => {
267
270
  console.log(chalk.blue(` • ${info}`));
268
271
  });
269
272
  }
@@ -274,7 +277,11 @@ class CheckCommand {
274
277
  if (this.errors.length === 0 && this.warnings.length === 0) {
275
278
  console.log(chalk.green('\nāœ… All checks passed!'));
276
279
  } else if (this.errors.length === 0) {
277
- console.log(chalk.yellow(`\nāš ļø ${this.warnings.length} warning(s) found (use --strict to fail on warnings)`));
280
+ console.log(
281
+ chalk.yellow(
282
+ `\nāš ļø ${this.warnings.length} warning(s) found (use --strict to fail on warnings)`
283
+ )
284
+ );
278
285
  } else {
279
286
  console.log(chalk.red(`\nāŒ ${this.errors.length} error(s) found`));
280
287
  }
@@ -287,4 +294,3 @@ async function check(options) {
287
294
  }
288
295
 
289
296
  module.exports = check;
290
-