UNPKG

@iservu-inc/adf-cli

Version:

CLI tool for AgentDevFramework - AI-assisted development framework with multi-provider AI support

222 lines (170 loc) 6.74 kB
const fs = require('fs-extra'); const path = require('path'); const { analyzeProject, getProjectSummary, PROJECT_TYPES } = require('../lib/analyzers/project-analyzer'); describe('Project Analyzer', () => { const tempDir = path.join(__dirname, 'temp-test-project'); beforeEach(async () => { await fs.ensureDir(tempDir); }); afterEach(async () => { await fs.remove(tempDir); }); describe('analyzeProject', () => { test('should detect React web app from package.json', async () => { // Create package.json with React const packageJson = { name: 'test-app', version: '1.0.0', description: 'A React web application', dependencies: { react: '^18.0.0', 'react-dom': '^18.0.0' } }; await fs.writeJson(path.join(tempDir, 'package.json'), packageJson); const context = await analyzeProject(tempDir); expect(context.type).toBe(PROJECT_TYPES.WEB_APP); expect(context.frameworks).toContain('React'); expect(context.languages).toContain('JavaScript/TypeScript'); expect(context.confidence).toBeGreaterThan(50); }); test('should detect CLI tool from package.json bin field', async () => { const packageJson = { name: 'test-cli', version: '1.0.0', description: 'A command-line tool', bin: { 'test-cli': 'bin/cli.js' }, dependencies: { commander: '^9.0.0' } }; await fs.writeJson(path.join(tempDir, 'package.json'), packageJson); const context = await analyzeProject(tempDir); expect(context.type).toBe(PROJECT_TYPES.CLI_TOOL); expect(context.confidence).toBeGreaterThan(50); }); test('should detect npm library from package.json main field', async () => { const packageJson = { name: 'test-library', version: '1.0.0', description: 'A utility library', main: 'index.js', private: false }; await fs.writeJson(path.join(tempDir, 'package.json'), packageJson); const context = await analyzeProject(tempDir); expect(context.type).toBe(PROJECT_TYPES.LIBRARY); expect(context.confidence).toBeGreaterThan(30); }); test('should detect API server from dependencies', async () => { const packageJson = { name: 'test-api', version: '1.0.0', description: 'RESTful API server', dependencies: { express: '^4.18.0', cors: '^2.8.5' } }; await fs.writeJson(path.join(tempDir, 'package.json'), packageJson); const context = await analyzeProject(tempDir); expect(context.type).toBe(PROJECT_TYPES.API_SERVER); expect(context.frameworks).toContain('Express'); }); test('should detect fullstack app with React and Express', async () => { const packageJson = { name: 'test-fullstack', version: '1.0.0', dependencies: { react: '^18.0.0', express: '^4.18.0' } }; await fs.writeJson(path.join(tempDir, 'package.json'), packageJson); const context = await analyzeProject(tempDir); expect(context.type).toBe(PROJECT_TYPES.FULLSTACK); expect(context.frameworks).toContain('React'); expect(context.frameworks).toContain('Express'); }); test('should extract description from README', async () => { const readmeContent = `# Test Project This is a test project for demonstrating the analyzer. It has a clear description. ## Features - Feature 1 - Feature 2 `; await fs.writeFile(path.join(tempDir, 'README.md'), readmeContent); const context = await analyzeProject(tempDir); expect(context.description).toBeTruthy(); expect(context.description).toContain('test project'); }); test('should detect test framework presence', async () => { const packageJson = { name: 'test-project', devDependencies: { jest: '^29.0.0' } }; await fs.writeJson(path.join(tempDir, 'package.json'), packageJson); const context = await analyzeProject(tempDir); expect(context.hasTests).toBe(true); }); test('should detect Docker presence', async () => { await fs.writeFile(path.join(tempDir, 'Dockerfile'), 'FROM node:18'); const context = await analyzeProject(tempDir); expect(context.hasDocker).toBe(true); }); test('should handle project with no package.json gracefully', async () => { const context = await analyzeProject(tempDir); expect(context.type).toBe(PROJECT_TYPES.UNKNOWN); expect(context.confidence).toBeLessThan(50); }); }); describe('getProjectSummary', () => { test('should return readable summary for web app', () => { const context = { type: PROJECT_TYPES.WEB_APP, frameworks: ['React', 'Next.js'], languages: ['JavaScript/TypeScript'], confidence: 90 }; const summary = getProjectSummary(context); expect(summary).toContain('Web Application'); expect(summary).toContain('React'); expect(summary).toContain('Next.js'); }); test('should return readable summary for CLI tool', () => { const context = { type: PROJECT_TYPES.CLI_TOOL, frameworks: [], languages: ['JavaScript/TypeScript'], confidence: 85 }; const summary = getProjectSummary(context); expect(summary).toContain('CLI Tool'); }); }); describe('Confidence scoring', () => { test('should have high confidence with complete information', async () => { const packageJson = { name: 'complete-project', version: '1.0.0', description: 'A complete project with all metadata', bin: { cli: 'bin/cli.js' }, dependencies: { commander: '^9.0.0' }, devDependencies: { jest: '^29.0.0' } }; await fs.writeJson(path.join(tempDir, 'package.json'), packageJson); await fs.writeFile(path.join(tempDir, 'README.md'), '# Project\n\nDescription here'); await fs.writeFile(path.join(tempDir, 'Dockerfile'), 'FROM node:18'); const context = await analyzeProject(tempDir); expect(context.confidence).toBeGreaterThanOrEqual(75); }); test('should have low confidence with minimal information', async () => { const context = await analyzeProject(tempDir); expect(context.confidence).toBeLessThan(50); }); }); });