mikemichez/codegenius-explorer
0
1 2document.addEventListener('DOMContentLoaded', function() {3 // Prevent default for any remaining # links4 document.querySelectorAll('a[href="#"]').forEach(link => {5 link.addEventListener('click', e => e.preventDefault());6 });7 8 // Analyze button functionality9const analyzeBtn = document.getElementById('analyze-btn');10 const repoUrlInput = document.getElementById('repo-url');11 12 analyzeBtn.addEventListener('click', function() {13 const repoUrl = repoUrlInput.value.trim();14 const advancedMode = document.getElementById('advanced').checked;15 16 if (!repoUrl) {17 showAlert('Please enter a GitHub repository URL', 'error');18 return;19 }20 21 if (!isValidGitHubUrl(repoUrl)) {22 showAlert('Please enter a valid GitHub repository URL', 'error');23 return;24 }25 26 // Simulate analysis (in a real app, this would call the API)27 simulateAnalysis(repoUrl, advancedMode);28 });29 30 // Show recent analyses from localStorage31 loadRecentAnalyses();32});33 34function isValidGitHubUrl(url) {35 return /^https?:\/\/(www\.)?github\.com\/[^\/]+\/[^\/]+/.test(url);36}37 38function showAlert(message, type = 'success') {39 const alert = document.createElement('div');40 alert.className = `fixed top-4 right-4 px-6 py-3 rounded-lg shadow-lg z-50 ${41 type === 'error' ? 'bg-red-700' : 'bg-green-700'42 } text-white font-medium`;43 alert.textContent = message;44 45 document.body.appendChild(alert);46 47 setTimeout(() => {48 alert.classList.add('opacity-0', 'transition-opacity', 'duration-300');49 setTimeout(() => alert.remove(), 300);50 }, 3000);51}52function simulateAnalysis(repoUrl, advancedMode) {53 const analyzeBtn = document.getElementById('analyze-btn');54 const originalText = analyzeBtn.innerHTML;55 56 // Disable button and show loading state57 analyzeBtn.disabled = true;58 analyzeBtn.innerHTML = `59 <div class="flex items-center gap-2">60 <div class="w-4 h-4 border-2 border-white border-t-transparent rounded-full animate-spin"></div>61 Analyzing...62 </div>63 `;64 65 // Simulate API call delay66 setTimeout(() => {67 // Save to recent analyses with additional data68 const analysis = {69 url: repoUrl,70 name: extractRepoName(repoUrl),71 timestamp: new Date().toISOString(),72 status: 'completed',73 advanced: advancedMode74 };75 76 let analyses = JSON.parse(localStorage.getItem('recentAnalyses') || '[]');77 analyses.unshift(analysis);78 analyses = analyses.slice(0, 5);79 localStorage.setItem('recentAnalyses', JSON.stringify(analyses));80 81 // Update UI82 loadRecentAnalyses();83 84 // Show success85 showAlert(`Analysis complete! Repository "${analysis.name}" has been documented.`);86 87 // Reset button88 analyzeBtn.disabled = false;89 analyzeBtn.innerHTML = originalText;90 feather.replace();91 }, 3000);92}93function extractRepoName(url) {94 const parts = url.split('/');95 return `${parts[parts.length - 2]}/${parts[parts.length - 1]}`;96}97 98function saveRecentAnalysis(repoUrl) {99 let analyses = JSON.parse(localStorage.getItem('recentAnalyses') || '[]');100 analyses.unshift({101 url: repoUrl,102 name: extractRepoName(repoUrl),103 timestamp: new Date().toISOString()104 });105 106 // Keep only last 5 analyses107 analyses = analyses.slice(0, 5);108 localStorage.setItem('recentAnalyses', JSON.stringify(analyses));109 110 // Update UI111 loadRecentAnalyses();112}113function loadRecentAnalyses() {114 const analyses = JSON.parse(localStorage.getItem('recentAnalyses') || '[]');115 const container = document.querySelector('.bg-gray-700.rounded-lg.p-4');116 117 if (!container) return;118 119 if (analyses.length === 0) {120 container.innerHTML = `121 <div class="text-center py-6 text-gray-400">122 <i data-feather="folder" class="w-8 h-8 mx-auto mb-2"></i>123 <p>No recent analyses</p>124 </div>125 `;126 feather.replace();127 return;128 }129 130 let html = '<div class="space-y-3">';131 132 analyses.forEach((analysis, index) => {133 const timeAgo = getTimeAgo(new Date(analysis.timestamp));134 135 html += `136 <div class="bg-gray-800 rounded-lg p-3 flex justify-between items-center">137 <div>138 <h3 class="font-medium">${analysis.name}</h3>139 <p class="text-sm text-gray-400">Completed ${timeAgo}</p>140 </div>141 <button class="p-2 hover:bg-gray-700 rounded-full download-btn" data-index="${index}">142 <i data-feather="download" class="w-4 h-4"></i>143 </button>144 </div>145 `;146 });147 148 html += '</div>';149 container.innerHTML = html;150 feather.replace();151 152 // Add download event listeners153 document.querySelectorAll('.download-btn').forEach(btn => {154 btn.addEventListener('click', function() {155 const index = this.getAttribute('data-index');156 const analyses = JSON.parse(localStorage.getItem('recentAnalyses') || '[]');157 const analysis = analyses[index];158 159 if (analysis) {160 downloadAnalysis(analysis);161 }162 });163 });164}165function showDocumentationModal(analysis) {166 const content = generateDocumentationContent(analysis);167 168 // Create modal169 const modal = document.createElement('div');170 modal.className = 'fixed inset-0 z-50 flex items-center justify-center bg-black bg-opacity-70';171 modal.innerHTML = `172 <div class="bg-gray-800 rounded-xl max-w-4xl w-full max-h-[90vh] flex flex-col border border-gray-700">173 <div class="p-4 border-b border-gray-700 flex justify-between items-center">174 <h3 class="text-xl font-semibold">Documentation for ${analysis.name}</h3>175 <button id="close-modal" class="p-2 hover:bg-gray-700 rounded-full">176 <i data-feather="x" class="w-5 h-5"></i>177 </button>178 </div>179 <div class="p-4 overflow-auto flex-1">180 <pre class="whitespace-pre-wrap font-mono text-gray-300">${content}</pre>181 </div>182 <div class="p-4 border-t border-gray-700 flex justify-end gap-4">183 <button id="copy-doc" class="px-4 py-2 bg-gray-700 hover:bg-gray-600 rounded-lg flex items-center gap-2">184 <i data-feather="copy" class="w-4 h-4"></i> Copy185 </button>186 <button id="download-doc" class="px-4 py-2 bg-gradient-to-r from-purple-600 to-blue-600 hover:from-purple-700 hover:to-blue-700 text-white rounded-lg flex items-center gap-2">187 <i data-feather="download" class="w-4 h-4"></i> Download188 </button>189 </div>190 </div>191 `;192 193 document.body.appendChild(modal);194 feather.replace();195 196 // Add event listeners197 document.getElementById('close-modal').addEventListener('click', () => modal.remove());198 199 document.getElementById('copy-doc').addEventListener('click', () => {200 navigator.clipboard.writeText(content)201 .then(() => showAlert('Documentation copied to clipboard!', 'success'))202 .catch(() => showAlert('Failed to copy documentation', 'error'));203 });204 205 document.getElementById('download-doc').addEventListener('click', () => {206 downloadDocumentation(analysis, content);207 modal.remove();208 });209}210 211function generateDocumentationContent(analysis) {212 return `# CodeGenius Documentation for ${analysis.name}\n\n` +213 `## Repository Analysis Report\n\n` +214 `- **Repository URL**: ${analysis.url}\n` +215 `- **Analyzed On**: ${new Date(analysis.timestamp).toLocaleString()}\n` +216 `- **Advanced Analysis**: ${analysis.advanced ? 'Yes' : 'No'}\n\n` +217 `## Summary\n\n` +218 `This documentation was generated by CodeGenius Explorer for the repository:\n\n` +219 `### ${analysis.name}\n\n` +220 `### Code Structure Analysis\n` +221 `- Main language detected: JavaScript\n` +222 `- Total files analyzed: 42\n` +223 `- Key files identified:\n` +224 ` - src/index.js (Main entry point)\n` +225 ` - src/utils/calculations.js (Core logic)\n` +226 ` - tests/unit/\n\n` +227 `### API Documentation\n` +228 `- Primary exports:\n` +229 ` - calculateEmissions()\n` +230 ` - validateInput()\n` +231 ` - generateReport()\n\n` +232 `### Dependencies\n` +233 `- Express.js\n` +234 `- Axios\n` +235 `- Chart.js\n\n` +236 `_This documentation was automatically generated by CodeGenius Explorer_`;237}238 239function downloadDocumentation(analysis, content) {240 try {241 const blob = new Blob([content], { type: 'text/markdown;charset=utf-8' });242 const url = URL.createObjectURL(blob);243 const a = document.createElement('a');244 a.href = url;245 a.download = `codegenius-${analysis.name.replace('/', '-')}-documentation.md`;246 document.body.appendChild(a);247 a.click();248 document.body.removeChild(a);249 URL.revokeObjectURL(url);250 251 showAlert(`Documentation for ${analysis.name} is being downloaded`, 'success');252 } catch (error) {253 console.error('Download failed:', error);254 showAlert(`Failed to download documentation for ${analysis.name}`, 'error');255 }256}257 258function downloadAnalysis(analysis) {259 showDocumentationModal(analysis);260}261function getTimeAgo(date) {262 const seconds = Math.floor((new Date() - date) / 1000);263 264 let interval = Math.floor(seconds / 31536000);265 if (interval >= 1) return `${interval} year${interval === 1 ? '' : 's'} ago`;266 267 interval = Math.floor(seconds / 2592000);268 if (interval >= 1) return `${interval} month${interval === 1 ? '' : 's'} ago`;269 270 interval = Math.floor(seconds / 86400);271 if (interval >= 1) return `${interval} day${interval === 1 ? '' : 's'} ago`;272 273 interval = Math.floor(seconds / 3600);274 if (interval >= 1) return `${interval} hour${interval === 1 ? '' : 's'} ago`;275 276 interval = Math.floor(seconds / 60);277 if (interval >= 1) return `${interval} minute${interval === 1 ? '' : 's'} ago`;278 279 return `${Math.floor(seconds)} second${seconds === 1 ? '' : 's'} ago`;280}