UNPKG

@dharshansr/gitgenius

Version:

AI-powered commit message generator with enhanced features

152 lines 6.35 kB
import chalk from 'chalk'; import ora from 'ora'; import { AIService } from '../services/AIService.js'; import { GitService } from '../services/GitService.js'; export class GitOperationsHandler { constructor() { this.aiService = new AIService(); this.gitService = new GitService(); } async showLog(options) { try { const count = parseInt(options.number || '10'); const logs = await this.gitService.getLog({ maxCount: count, ...(options.since && { since: options.since }), ...(options.author && { author: options.author }) }); console.log(chalk.blue(`[LOG] Git Log (${count} commits):`)); for (const commit of logs.all.slice(0, count)) { const date = new Date(commit.date).toLocaleDateString(); console.log(`${chalk.yellow(commit.hash.substring(0, 7))} ${chalk.white(commit.message)}`); console.log(` ${chalk.gray(`${commit.author_name}${date}`)}`); if (options.ai && this.aiService.hasApiKey()) { try { const summary = await this.aiService.explainCommit(commit.message, commit.refs); console.log(` ${chalk.green(`[AI] ${summary}`)}`); } catch (error) { console.log(` ${chalk.red('[AI] Summary unavailable')}`); } } console.log(''); } } catch (error) { throw new Error(`Failed to show log: ${error instanceof Error ? error.message : String(error)}`); } } async showDiff(options) { try { let diff = ''; if (options.staged) { diff = await this.gitService.getStagedDiff(); } else if (options.last) { diff = await this.gitService.getLastCommitDiff(); } else if (options.file) { diff = await this.gitService.getFileDiff(options.file); } else { diff = await this.gitService.getDiff(); } if (!diff.trim()) { console.log(chalk.yellow('[WARNING] No differences found')); return; } console.log(chalk.blue('[DIFF] Git Diff:')); console.log(diff); if (options.ai && this.aiService.hasApiKey()) { try { const explanation = await this.aiService.explainCommit(`Explain these code changes:\n${diff.substring(0, 2000)}`, 'code changes'); console.log(chalk.green(`\n[AI] Explanation: ${explanation}`)); } catch (error) { console.log(chalk.red('\n[AI] Explanation unavailable')); } } } catch (error) { throw new Error(`Failed to show diff: ${error instanceof Error ? error.message : String(error)}`); } } async reviewChanges(options) { try { const diff = options.file ? await this.gitService.getFileDiff(options.file) : await this.gitService.getStagedDiff(); if (!diff.trim()) { console.log(chalk.yellow('[WARNING] No changes to review')); return; } if (!this.aiService.hasApiKey()) { console.log(chalk.red('[ERROR] API key required for code review')); return; } console.log(chalk.blue('✨ [REVIEW] AI Code Review:')); const spinner = ora('Analyzing code...').start(); try { const review = await this.aiService.reviewCode(diff); spinner.stop(); console.log(chalk.white(review)); // Format based on requested format if (options.format === 'json') { const reviewData = { timestamp: new Date().toISOString(), severity: options.severity, review: review, file: options.file || 'staged changes' }; console.log('\n' + JSON.stringify(reviewData, null, 2)); } } catch (error) { spinner.fail('Code review failed'); throw error; } } catch (error) { throw new Error(`Failed to review changes: ${error instanceof Error ? error.message : String(error)}`); } } async suggestCommitInfo(options) { try { const diff = await this.gitService.getStagedDiff(); if (!diff.trim()) { console.log(chalk.yellow('[WARNING] No staged changes found')); return; } console.log(chalk.blue('✨ [SUGGEST] AI Suggestions:')); if (!this.aiService.hasApiKey()) { // Provide basic suggestions without AI const basicTypes = ['feat', 'fix', 'docs', 'style', 'refactor', 'test', 'chore']; console.log(chalk.white(`Suggested types: ${basicTypes.join(', ')}`)); return; } const spinner = ora('Generating suggestions...').start(); try { let suggestion = ''; if (options.type) { suggestion = await this.aiService.suggestCommitType(diff); } else if (options.scope) { suggestion = await this.aiService.suggestCommitScope(diff); } else { suggestion = await this.aiService.suggestCommitType(diff); } spinner.stop(); console.log(chalk.green(`[SUGGEST] ${suggestion}`)); } catch (error) { spinner.fail('Failed to generate suggestions'); throw error; } } catch (error) { throw new Error(`Failed to generate suggestions: ${error instanceof Error ? error.message : String(error)}`); } } } //# sourceMappingURL=GitOperationsHandler.js.map