Generated by Spark: half the app is gone, it was a code gen

This commit is contained in:
2026-01-17 15:08:28 +00:00
committed by GitHub
parent ce72615364
commit 8e677175fc
5 changed files with 645 additions and 259 deletions

368
PRD.md
View File

@@ -1,131 +1,237 @@
# Planning Guide
**Experience Qualities**:
This is a diagnostic tool with log parsing, error highlighting, and solution generation - more than a single-pu
## Essential Features
### Log Parser & Error Highlighter
**Complexity Level**: Light Application (multiple features with basic state)
This is a diagnostic tool with log parsing, error highlighting, and solution generation - more than a single-purpose tool but not a complex multi-view application.
## Essential Features
### Log Parser & Error Highlighter
- **Functionality**: Paste Docker build logs and automatically extract error information
- **Purpose**: Make sense of lengthy, unformatted build output
- **Trigger**: User pastes log text into a text area
- **Functionality**: Common Docker build errors with explanations and fixes
- **Success criteria**: Cove
### Fix Code Generator
- **Purpose**: Speed up fixing by providing exact code changes needed
- **Progression**: Solution shown → Click "Generate Fix
- **Empty Input**: Show
- **Foreground/Backgro
- Card (`oklch(0.19 0.02 265)`): Light text `oklch(0.95 0.01 265)` - Ratio 9.8:1 ✓
- Destructive/Error (`oklch(0.60 0.25 25)`): White text `oklch(1 0
## Font Selection
Monospace for code and logs, clean sans-serif for explanations - reflecting the technical nature while remaining reada
- **Typographic Hierarchy**:
- Code/Logs: JetBra
- Solutions expand/collapse smoothly (300ms ease-out)
- Log parsing shows subtle progress indicator during processing
- Textarea (custo
- Button (primary for actions, secondary for copy operations)
- Monospace code blocks with line numbers for generated fixes
- Input: Focused state has bright accent border with subtle glow
- Terminal (for log input)
- CheckCircle (for solutions)
- MagnifyingGlass (for search in knowledge base)
- Stack (for Docker layers)
- **Spacing**:
- Section gaps: gap-8 for major sections, gap-4 for related content
- **Mobile**:
- Collapsible sections for solutions to save space
# Planning Guide
CodeForge is a comprehensive low-code development platform that enables developers to rapidly build, test, and deploy full-stack applications through visual builders and intelligent code generation.
**Experience Qualities**:
1. **Powerful** - A complete development toolkit with visual designers for models, components, workflows, APIs, and testing
2. **Efficient** - Keyboard shortcuts, intelligent search, and streamlined navigation accelerate development
3. **Intelligent** - AI-assisted code generation, auto-repair, and context-aware suggestions
**Complexity Level**: Complex Application (advanced functionality with multiple views)
This is a sophisticated development platform with router-based navigation, multiple specialized views, state persistence, real-time preview, and comprehensive project management capabilities.
## Essential Features
### Dashboard & Project Overview
- **Functionality**: Central hub displaying project metrics, file counts, component stats, and quick actions
- **Purpose**: Provide at-a-glance project health and rapid access to common tasks
- **Trigger**: Loaded on app initialization or via navigation
- **Progression**: Load project state → Calculate metrics → Render cards → Enable quick actions
- **Success criteria**: All metrics display correctly, navigation works, GitHub build status shows
### Code Editor with File Explorer
- **Functionality**: Monaco-based code editor with syntax highlighting and file tree navigation
- **Purpose**: Edit project files with professional IDE-like experience
- **Trigger**: Navigate to Code Editor tab or select file from explorer
- **Progression**: Mount editor → Load file content → Enable editing → Auto-save changes → Update file tree
- **Success criteria**: Files open instantly, syntax highlighting works, changes persist
### Model Designer (Prisma Schema)
- **Functionality**: Visual interface for designing database models with fields, relations, and constraints
- **Purpose**: Create database schemas without writing raw Prisma syntax
- **Trigger**: Navigate to Models tab
- **Progression**: Display existing models → Add/edit models → Define fields → Set relations → Generate schema
- **Success criteria**: Models create correctly, relations validate, Prisma schema generates
### Component Tree Builder
- **Functionality**: Drag-and-drop interface for building React component hierarchies
- **Purpose**: Visually compose component structures with props and styling
- **Trigger**: Navigate to Components tab
- **Progression**: Show component palette → Drag to canvas → Configure props → Set styling → Generate JSX
- **Success criteria**: Components nest properly, props configure, code generates
### Workflow Designer
- **Functionality**: Node-based workflow editor for defining application logic
- **Purpose**: Create complex business logic visually using nodes and connections
- **Trigger**: Navigate to Workflows tab
- **Progression**: Place nodes → Connect nodes → Configure logic → Validate flow → Generate code
- **Success criteria**: Flows connect correctly, validation prevents errors, code executes
### Lambda/Function Designer
- **Functionality**: Code editor for serverless functions with runtime configuration
- **Purpose**: Write and configure backend functions quickly
- **Trigger**: Navigate to Lambdas tab
- **Progression**: Create function → Write code → Set environment → Configure triggers → Test execution
- **Success criteria**: Functions save, environments configure, testing works
### Style Designer (Theme Configuration)
- **Functionality**: Visual theme editor for colors, typography, spacing, and design tokens
- **Purpose**: Customize application appearance without editing CSS files
- **Trigger**: Navigate to Styling tab
- **Progression**: Select variant → Adjust colors → Configure typography → Preview changes → Generate CSS
- **Success criteria**: Changes preview instantly, CSS variables update, theme persists
### Favicon Designer
- **Functionality**: Visual icon designer with shapes, colors, and SVG export
- **Purpose**: Create custom favicons without external tools
- **Trigger**: Navigate to Favicon Designer tab
- **Progression**: Add shapes → Customize colors → Position elements → Preview → Export SVG
- **Success criteria**: Icons render correctly, SVG exports, preview updates in real-time
### Flask API Designer
- **Functionality**: Configure Flask backend with routes, blueprints, and settings
- **Purpose**: Set up Python backend API without manual configuration
- **Trigger**: Navigate to Flask API tab
- **Progression**: Configure settings → Define routes → Add blueprints → Set CORS → Generate config
- **Success criteria**: Configuration valid, routes define properly, Flask app generates
### Test Designers (Playwright, Unit Tests, Storybook)
- **Functionality**: Create and manage tests through visual interfaces
- **Purpose**: Build comprehensive test coverage without boilerplate
- **Trigger**: Navigate to respective test tabs
- **Progression**: Define test → Set assertions → Configure steps → Run tests → View results
- **Success criteria**: Tests create correctly, run successfully, results display
### Error Panel with Auto-Repair
- **Functionality**: Display build/runtime errors with AI-powered fix suggestions
- **Purpose**: Quickly identify and resolve issues
- **Trigger**: Navigate to Errors tab or click error indicator
- **Progression**: Parse errors → Categorize → Generate fixes → Apply suggestions → Re-validate
- **Success criteria**: Errors display clearly, fixes apply correctly, issues resolve
### Feature Ideas Cloud
- **Functionality**: Interactive tag cloud of feature suggestions with voting
- **Purpose**: Crowdsource and prioritize new features
- **Trigger**: Navigate to Feature Ideas tab
- **Progression**: Display ideas → Click to vote → Add new ideas → Sort by votes → Track implementation
- **Success criteria**: Voting works, ideas persist, sorting updates
### Docker Build Debugger
- **Functionality**: Paste Docker build logs and get AI-powered error analysis with fixes
- **Purpose**: Quickly diagnose and resolve Docker build failures
- **Trigger**: Navigate to Docker Debugger tab from menu
- **Progression**: Paste logs → Parse errors → Query knowledge base → Generate solutions → Copy fixes
- **Success criteria**: Errors extract correctly, solutions relevant, fixes work
### Global Search (Ctrl+K)
- **Functionality**: Fast fuzzy search across files, components, models, workflows, and navigation
- **Purpose**: Instant access to any project artifact
- **Trigger**: Press Ctrl+K or click search icon
- **Progression**: Open dialog → Type query → Filter results → Select item → Navigate/open
- **Success criteria**: Search < 100ms, results accurate, navigation works
### Keyboard Shortcuts
- **Functionality**: Comprehensive keyboard shortcuts for all major actions
- **Purpose**: Expert-level productivity without mouse
- **Trigger**: Press configured shortcut or Ctrl+/ to view all
- **Progression**: Press shortcut → Execute action → Show visual feedback
- **Success criteria**: All shortcuts work, dialog lists current mappings
### Project Export/Import
- **Functionality**: Export entire project as JSON, import projects from files
- **Purpose**: Share projects, backup, or migrate between environments
- **Trigger**: Click export/import in header menu
- **Progression**: Serialize state → Download JSON → Upload JSON → Deserialize → Restore state
- **Success criteria**: Export complete, import restores fully, no data loss
### PWA Support
- **Functionality**: Progressive Web App with offline support, install prompts, and update notifications
- **Purpose**: Desktop-like experience with offline capability
- **Trigger**: Automatic service worker registration
- **Progression**: Register SW → Cache assets → Show install prompt → Handle updates → Enable offline
- **Success criteria**: Offline mode works, install succeeds, updates apply
## Edge Case Handling
- **No Project Data**: Show onboarding with sample project option
- **Large Files**: Monaco editor lazy-loads only visible content
- **Network Failures**: All state persists to KV storage, works offline
- **Invalid JSON**: Schema validation with helpful error messages
- **Circular References**: Workflow and component tree validation prevents cycles
- **Conflicting Changes**: Last-write-wins with timestamp tracking
- **Browser Compatibility**: Graceful degradation for older browsers
- **Memory Limits**: Lazy loading and code splitting for large projects
## Design Direction
The design should feel like a professional development tool - powerful yet approachable, with emphasis on speed, clarity, and focused workspaces. Think VS Code meets Figma: clean, minimal chrome with rich, context-specific editing surfaces.
## Color Selection
**Technical Elegance** - Dark theme with vibrant purple accents
- **Primary Color**: `oklch(0.58 0.24 265)` - Vibrant purple for actions and focus
- **Secondary Colors**:
- Background: `oklch(0.15 0.02 265)` - Deep blue-black for immersive coding
- Card: `oklch(0.19 0.02 265)` - Elevated surfaces
- Muted: `oklch(0.25 0.03 265)` - Borders and subtle dividers
- **Accent Color**: `oklch(0.75 0.20 145)` - Bright teal for success and completion
- **Foreground/Background Pairings**:
- Background (`oklch(0.15 0.02 265)`): Light text `oklch(0.95 0.01 265)` - Ratio 13.2:1 ✓
- Primary (`oklch(0.58 0.24 265)`): White text `oklch(1 0 0)` - Ratio 5.1:1 ✓
- Card (`oklch(0.19 0.02 265)`): Light text `oklch(0.95 0.01 265)` - Ratio 11.8:1 ✓
- Accent (`oklch(0.75 0.20 145)`): Dark text `oklch(0.15 0.02 265)` - Ratio 7.9:1 ✓
## Font Selection
Developer-focused typography with monospace for code and clean sans-serif for UI
- **Typographic Hierarchy**:
- H1 (Page Titles): JetBrains Mono Bold / 24px / tight letter spacing
- H2 (Section Headers): JetBrains Mono Bold / 20px
- H3 (Subsection Headers): JetBrains Mono Medium / 16px
- Body Text: IBM Plex Sans Regular / 14px / 1.5 line height
- Code/Logs: JetBrains Mono Regular / 14px / 1.4 line height
- Labels: IBM Plex Sans Medium / 12px / uppercase tracking
## Animations
Purposeful motion for state changes, navigation, and feedback - never decorative
- Tab switching: 200ms crossfade
- Panel transitions: 300ms slide with ease-out
- Hover states: 150ms color/scale transitions
- Loading states: Subtle pulse on relevant area
- Success actions: Quick scale + color flash (200ms)
- Drag-and-drop: Smooth follow with snap-to-grid
## Component Selection
**Core Components**:
- **Tabs** (shadcn): Primary navigation with active indicators
- **Sheet** (shadcn): Side panels for settings and auxiliary content
- **Dialog** (shadcn): Modal overlays for search, shortcuts, and confirmations
- **Card** (shadcn): Content containers with hover states
- **Button** (shadcn): All variants - primary for actions, ghost for navigation
- **Textarea/Input** (shadcn): Form controls with focus rings
- **Select/Combobox** (shadcn): Dropdowns with search
- **Separator** (shadcn): Visual dividers between sections
- **Skeleton** (shadcn): Loading placeholders
- **Switch/Checkbox** (shadcn): Boolean controls
**Custom Components**:
- Monaco Editor wrapper with theme integration
- ReactFlow workflow canvas with custom nodes
- Tree view for file explorer and component hierarchy
- Drag-and-drop canvas for component builder
- Tag cloud with physics simulation
- Resizable panel groups for split views
**States**:
- Buttons: Default → Hover → Active → Disabled
- Inputs: Empty → Focused → Filled → Error → Success
- Panels: Collapsed → Expanding → Expanded → Collapsing
- Files: Unselected → Hover → Active → Modified → Saved
**Icon Selection**: @phosphor-icons/react with bold weight for emphasis
- Navigation: House, Code, Database, Tree, GitBranch, etc.
- Actions: Plus, Trash, Copy, Download, Upload
- Status: Check, X, Warning, Info, CircleNotch (loading)
**Spacing**:
- Page padding: p-6
- Section gaps: gap-8
- Card padding: p-6
- Button padding: px-4 py-2
- Input padding: px-3 py-2
- Tight spacing: gap-2 for related items
**Mobile**:
- Collapsible sidebar navigation
- Stacked layouts instead of side-by-side
- Full-width panels
- Touch-optimized button sizes (min 44px)
- Simplified feature set (hide advanced tools)
- Focused single-panel view instead of split panes

View File

@@ -4,9 +4,9 @@
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>DevTools Hub</title>
<title>CodeForge - Low-Code Development Platform</title>
<meta name="description" content="Your developer toolkit - Docker debugger and more">
<meta name="description" content="Comprehensive low-code platform for rapid application development">
<meta name="theme-color" content="#8b5cf6">
<link rel="preconnect" href="https://fonts.googleapis.com">

View File

@@ -1,138 +1,403 @@
import { useState } from 'react'
import { useKV } from '@github/spark/hooks'
import { Button } from '@/components/ui/button'
import { Card, CardContent, CardDescription, CardHeader, CardTitle } from '@/components/ui/card'
import { Sheet, SheetContent, SheetHeader, SheetTitle, SheetTrigger } from '@/components/ui/sheet'
import { List, Stack, House, Wrench } from '@phosphor-icons/react'
import { DockerBuildDebugger } from '@/components/DockerBuildDebugger'
import { motion } from 'framer-motion'
console.log('[APP_ROUTER] 🚀 App.router.tsx loading - BEGIN')
console.time('[APP_ROUTER] Component initialization')
type View = 'home' | 'docker-debugger'
import { useState, Suspense, useEffect } from 'react'
console.log('[APP_ROUTER] ✅ React hooks imported')
function App() {
const [currentView, setCurrentView] = useKV<View>('current-view', 'home')
const [isMenuOpen, setIsMenuOpen] = useState(false)
import { BrowserRouter, useLocation } from 'react-router-dom'
console.log('[APP_ROUTER] ✅ React Router imported')
const handleNavigation = (view: View) => {
setCurrentView(view)
setIsMenuOpen(false)
import { AppHeader } from '@/components/organisms'
console.log('[APP_ROUTER] ✅ Header components imported')
import { LoadingFallback } from '@/components/molecules'
console.log('[APP_ROUTER] ✅ LoadingFallback imported')
import { useProjectState } from '@/hooks/use-project-state'
import { useFileOperations } from '@/hooks/use-file-operations'
import { useKeyboardShortcuts } from '@/hooks/use-keyboard-shortcuts'
import { useSeedData } from '@/hooks/data/use-seed-data'
import { useRouterNavigation } from '@/hooks/use-router-navigation'
console.log('[APP_ROUTER] ✅ Custom hooks imported')
import { getPageShortcuts } from '@/config/page-loader'
console.log('[APP_ROUTER] ✅ Page config imported')
import { toast } from 'sonner'
console.log('[APP_ROUTER] ✅ Toast imported')
import { DialogRegistry, PWARegistry, preloadCriticalComponents } from '@/lib/component-registry'
console.log('[APP_ROUTER] ✅ Component registry imported')
import { RouterProvider } from '@/router'
console.log('[APP_ROUTER] ✅ Router provider imported')
const { GlobalSearch, KeyboardShortcutsDialog, PreviewDialog } = DialogRegistry
const { PWAInstallPrompt, PWAUpdatePrompt, PWAStatusBar } = PWARegistry
console.log('[APP_ROUTER] ✅ Dialog and PWA components registered')
console.log('[APP_ROUTER] 🎯 App component function executing')
function AppLayout() {
console.log('[APP_ROUTER] 🏗️ AppLayout component rendering')
const location = useLocation()
const { currentPage, navigateToPage } = useRouterNavigation()
console.log('[APP_ROUTER] 📍 Current location:', location.pathname)
console.log('[APP_ROUTER] 📄 Current page:', currentPage)
console.log('[APP_ROUTER] 📊 Initializing project state hook')
const projectState = useProjectState()
console.log('[APP_ROUTER] ✅ Project state initialized')
const {
files,
models,
components,
componentTrees,
workflows,
lambdas,
theme,
playwrightTests,
storybookStories,
unitTests,
flaskConfig,
nextjsConfig,
npmSettings,
featureToggles,
setFiles,
setModels,
setComponents,
setComponentTrees,
setWorkflows,
setLambdas,
setTheme,
setPlaywrightTests,
setStorybookStories,
setUnitTests,
setFlaskConfig,
setNextjsConfig,
setNpmSettings,
setFeatureToggles,
} = projectState
console.log('[APP_ROUTER] 📁 Initializing file operations')
const fileOps = useFileOperations(files, setFiles)
console.log('[APP_ROUTER] ✅ File operations initialized')
const { activeFileId, setActiveFileId, handleFileChange, handleFileAdd, handleFileClose } = fileOps
console.log('[APP_ROUTER] 💾 Initializing state variables')
const [searchOpen, setSearchOpen] = useState(false)
const [shortcutsOpen, setShortcutsOpen] = useState(false)
const [previewOpen, setPreviewOpen] = useState(false)
const [lastSaved] = useState<number | null>(Date.now())
const [errorCount] = useState(0)
console.log('[APP_ROUTER] ✅ State variables initialized')
const shortcuts = getPageShortcuts(featureToggles)
console.log('[APP_ROUTER] ⌨️ Keyboard shortcuts configured:', shortcuts.length)
console.log('[APP_ROUTER] ⌨️ Setting up keyboard shortcuts')
useKeyboardShortcuts([
...shortcuts.map(s => ({
key: s.key,
ctrl: s.ctrl,
shift: s.shift,
description: s.description,
action: () => {
console.log('[APP_ROUTER] ⌨️ Shortcut triggered, navigating to:', s.action)
navigateToPage(s.action)
}
})),
{
key: 'k',
ctrl: true,
description: 'Search',
action: () => {
console.log('[APP_ROUTER] ⌨️ Search shortcut triggered')
setSearchOpen(true)
}
},
{
key: '/',
ctrl: true,
description: 'Shortcuts',
action: () => {
console.log('[APP_ROUTER] ⌨️ Shortcuts dialog triggered')
setShortcutsOpen(true)
}
},
{
key: 'p',
ctrl: true,
description: 'Preview',
action: () => {
console.log('[APP_ROUTER] ⌨️ Preview shortcut triggered')
setPreviewOpen(true)
}
},
])
console.log('[APP_ROUTER] ✅ Keyboard shortcuts configured')
const getCurrentProject = () => ({
name: nextjsConfig.appName,
files,
models,
components,
componentTrees,
workflows,
lambdas,
theme,
playwrightTests,
storybookStories,
unitTests,
flaskConfig,
nextjsConfig,
npmSettings,
featureToggles,
})
const handleProjectLoad = (project: any) => {
console.log('[APP_ROUTER] 📦 Loading project:', project.name)
if (project.files) setFiles(project.files)
if (project.models) setModels(project.models)
if (project.components) setComponents(project.components)
if (project.componentTrees) setComponentTrees(project.componentTrees)
if (project.workflows) setWorkflows(project.workflows)
if (project.lambdas) setLambdas(project.lambdas)
if (project.theme) setTheme(project.theme)
if (project.playwrightTests) setPlaywrightTests(project.playwrightTests)
if (project.storybookStories) setStorybookStories(project.storybookStories)
if (project.unitTests) setUnitTests(project.unitTests)
if (project.flaskConfig) setFlaskConfig(project.flaskConfig)
if (project.nextjsConfig) setNextjsConfig(project.nextjsConfig)
if (project.npmSettings) setNpmSettings(project.npmSettings)
if (project.featureToggles) setFeatureToggles(project.featureToggles)
toast.success('Project loaded')
console.log('[APP_ROUTER] ✅ Project loaded successfully')
}
useEffect(() => {
console.log('[APP_ROUTER] 📍 Route changed to:', location.pathname, '- Page:', currentPage)
}, [location, currentPage])
console.log('[APP_ROUTER] 🎨 Rendering AppLayout UI')
return (
<div className="min-h-screen bg-background">
<div className="relative overflow-hidden">
<div className="absolute inset-0 bg-[radial-gradient(ellipse_at_top,_var(--tw-gradient-stops))] from-primary/20 via-background to-background" />
<div className="absolute inset-0 bg-[linear-gradient(to_right,#4f4f4f12_1px,transparent_1px),linear-gradient(to_bottom,#4f4f4f12_1px,transparent_1px)] bg-[size:4rem_4rem]" />
<div className="relative">
<header className="border-b border-border/40 backdrop-blur-sm sticky top-0 z-40">
<div className="container mx-auto px-4 sm:px-6 py-4">
<div className="flex items-center justify-between">
<div className="flex items-center gap-3">
<div className="p-2 rounded-lg bg-primary/10 border border-primary/20">
<Stack size={28} weight="bold" className="text-primary" />
</div>
<div>
<h1 className="text-xl sm:text-2xl font-bold tracking-tight">DevTools Hub</h1>
<p className="text-xs sm:text-sm text-muted-foreground">Your developer toolkit</p>
</div>
</div>
<Sheet open={isMenuOpen} onOpenChange={setIsMenuOpen}>
<SheetTrigger asChild>
<Button variant="outline" size="icon" className="gap-2">
<List size={20} weight="bold" />
</Button>
</SheetTrigger>
<SheetContent>
<SheetHeader>
<SheetTitle>Navigation</SheetTitle>
</SheetHeader>
<nav className="mt-6 space-y-2">
<Button
variant={currentView === 'home' ? 'secondary' : 'ghost'}
className="w-full justify-start gap-3"
onClick={() => handleNavigation('home')}
>
<House size={20} weight="bold" />
Home
</Button>
<Button
variant={currentView === 'docker-debugger' ? 'secondary' : 'ghost'}
className="w-full justify-start gap-3"
onClick={() => handleNavigation('docker-debugger')}
>
<Wrench size={20} weight="bold" />
Docker Build Debugger
</Button>
</nav>
</SheetContent>
</Sheet>
</div>
</div>
</header>
<main className="container mx-auto px-4 sm:px-6 py-8">
{currentView === 'home' && (
<motion.div
initial={{ opacity: 0, y: 20 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 0.3 }}
className="space-y-6"
>
<div>
<h2 className="text-2xl font-bold mb-2">Welcome to DevTools Hub</h2>
<p className="text-muted-foreground">
Select a tool from the menu to get started
</p>
</div>
<div className="grid gap-4 md:grid-cols-2 lg:grid-cols-3">
<Card
className="border-border/50 bg-card/50 backdrop-blur-sm cursor-pointer hover:border-accent/50 hover:shadow-lg hover:shadow-accent/5 transition-all"
onClick={() => handleNavigation('docker-debugger')}
>
<CardHeader>
<div className="flex items-center gap-3 mb-2">
<div className="p-2 rounded-lg bg-accent/10 border border-accent/20">
<Wrench size={24} weight="bold" className="text-accent" />
</div>
<CardTitle>Docker Build Debugger</CardTitle>
</div>
<CardDescription>
Analyze Docker build errors and get instant solutions with an intelligent knowledge base
</CardDescription>
</CardHeader>
<CardContent>
<p className="text-sm text-muted-foreground">
Paste your build logs and get detailed error analysis with recommended fixes
</p>
</CardContent>
</Card>
</div>
</motion.div>
)}
{currentView === 'docker-debugger' && (
<motion.div
initial={{ opacity: 0, y: 20 }}
animate={{ opacity: 1, y: 0 }}
transition={{ duration: 0.3 }}
>
<div className="mb-6">
<h2 className="text-2xl font-bold mb-2">Docker Build Debugger</h2>
<p className="text-muted-foreground">
Analyze errors and get instant solutions
</p>
</div>
<DockerBuildDebugger />
</motion.div>
)}
</main>
</div>
<div className="h-screen flex flex-col bg-background">
<Suspense fallback={<div className="h-1 bg-primary animate-pulse" />}>
<PWAStatusBar />
</Suspense>
<Suspense fallback={null}>
<PWAUpdatePrompt />
</Suspense>
<AppHeader
activeTab={currentPage}
onTabChange={navigateToPage}
featureToggles={featureToggles}
errorCount={errorCount}
lastSaved={lastSaved}
currentProject={getCurrentProject()}
onProjectLoad={handleProjectLoad}
onSearch={() => {
console.log('[APP_ROUTER] 🔍 Search opened')
setSearchOpen(true)
}}
onShowShortcuts={() => {
console.log('[APP_ROUTER] ⌨️ Shortcuts dialog opened')
setShortcutsOpen(true)
}}
onGenerateAI={() => {
console.log('[APP_ROUTER] 🤖 AI generation requested')
toast.info('AI generation coming soon')
}}
onExport={() => {
console.log('[APP_ROUTER] 📤 Export requested')
toast.info('Export coming soon')
}}
onPreview={() => {
console.log('[APP_ROUTER] 👁️ Preview opened')
setPreviewOpen(true)
}}
onShowErrors={() => {
console.log('[APP_ROUTER] ⚠️ Navigating to errors page')
navigateToPage('errors')
}}
/>
<div className="flex-1 overflow-hidden">
<RouterProvider
featureToggles={featureToggles}
stateContext={{
files,
models,
components,
componentTrees,
workflows,
lambdas,
theme,
playwrightTests,
storybookStories,
unitTests,
flaskConfig,
nextjsConfig,
npmSettings,
featureToggles,
activeFileId,
}}
actionContext={{
handleFileChange,
setActiveFileId,
handleFileClose,
handleFileAdd,
setModels,
setComponents,
setComponentTrees,
setWorkflows,
setLambdas,
setTheme,
setPlaywrightTests,
setStorybookStories,
setUnitTests,
setFlaskConfig,
setNextjsConfig,
setNpmSettings,
setFeatureToggles,
}}
/>
</div>
<Suspense fallback={null}>
<GlobalSearch
open={searchOpen}
onOpenChange={setSearchOpen}
files={files}
models={models}
components={components}
componentTrees={componentTrees}
workflows={workflows}
lambdas={lambdas}
playwrightTests={playwrightTests}
storybookStories={storybookStories}
unitTests={unitTests}
onNavigate={(page) => {
console.log('[APP_ROUTER] 🔍 Search navigation to:', page)
navigateToPage(page)
}}
onFileSelect={(fileId) => {
console.log('[APP_ROUTER] 📄 File selected from search:', fileId)
setActiveFileId(fileId)
navigateToPage('code')
}}
/>
</Suspense>
<Suspense fallback={null}>
<KeyboardShortcutsDialog open={shortcutsOpen} onOpenChange={setShortcutsOpen} />
</Suspense>
<Suspense fallback={null}>
<PreviewDialog open={previewOpen} onOpenChange={setPreviewOpen} />
</Suspense>
<Suspense fallback={null}>
<PWAInstallPrompt />
</Suspense>
</div>
)
}
function App() {
console.log('[APP_ROUTER] 🔧 Initializing App component')
console.time('[APP_ROUTER] App render')
console.log('[APP_ROUTER] 🌱 Initializing seed data hook')
const { loadSeedData } = useSeedData()
const projectState = useProjectState()
const { featureToggles, files, setFiles, ...restState } = projectState
console.log('[APP_ROUTER] ✅ Hooks initialized')
console.log('[APP_ROUTER] 📁 Initializing file operations for router context')
const fileOps = useFileOperations(files, setFiles)
const [appReady, setAppReady] = useState(false)
console.log('[APP_ROUTER] 💾 App ready state:', appReady)
console.log('[APP_ROUTER] ⏰ Setting up initialization effect')
useEffect(() => {
console.log('[APP_ROUTER] 🚀 Initialization effect triggered')
console.time('[APP_ROUTER] Seed data loading')
const timer = setTimeout(() => {
console.log('[APP_ROUTER] ⏱️ Fallback timer triggered (100ms)')
setAppReady(true)
}, 100)
console.log('[APP_ROUTER] 📥 Starting seed data load')
loadSeedData()
.then(() => {
console.log('[APP_ROUTER] ✅ Seed data loaded successfully')
})
.catch(err => {
console.error('[APP_ROUTER] ❌ Seed data loading failed:', err)
})
.finally(() => {
console.log('[APP_ROUTER] 🏁 Seed data loading complete')
clearTimeout(timer)
setAppReady(true)
console.timeEnd('[APP_ROUTER] Seed data loading')
console.log('[APP_ROUTER] ✅ App marked as ready')
console.log('[APP_ROUTER] 🚀 Preloading critical components')
preloadCriticalComponents()
})
return () => {
console.log('[APP_ROUTER] 🧹 Cleaning up initialization effect')
clearTimeout(timer)
}
}, [loadSeedData])
const stateContext = {
files,
...restState,
activeFileId: fileOps.activeFileId,
}
const actionContext = {
handleFileChange: fileOps.handleFileChange,
setActiveFileId: fileOps.setActiveFileId,
handleFileClose: fileOps.handleFileClose,
handleFileAdd: fileOps.handleFileAdd,
setFiles,
...Object.fromEntries(
Object.entries(restState).filter(([key]) => key.startsWith('set'))
),
}
console.log('[APP_ROUTER] 🎨 Rendering App component UI')
console.log('[APP_ROUTER] App state - appReady:', appReady)
console.timeEnd('[APP_ROUTER] App render')
if (!appReady) {
console.log('[APP_ROUTER] ⏳ App not ready, showing loading screen')
return (
<div className="fixed inset-0 bg-background z-50 flex items-center justify-center">
<div className="flex flex-col items-center gap-4">
<div className="w-12 h-12 border-4 border-primary border-t-transparent rounded-full animate-spin" />
<p className="text-sm text-muted-foreground">Loading CodeForge...</p>
</div>
</div>
)
}
console.log('[APP_ROUTER] ✅ App ready, rendering router')
return (
<BrowserRouter>
<AppLayout />
</BrowserRouter>
)
}
console.log('[APP_ROUTER] ✅ App component defined')
console.timeEnd('[APP_ROUTER] Component initialization')
export default App

View File

@@ -355,6 +355,16 @@
"shortcut": "ctrl+shift+d",
"order": 24,
"props": {}
},
{
"id": "docker-debugger",
"title": "Docker Debugger",
"icon": "Wrench",
"component": "DockerBuildDebugger",
"enabled": true,
"toggleKey": "dockerDebugger",
"order": 25,
"props": {}
}
]
}

View File

@@ -151,6 +151,11 @@ export const ComponentRegistry = {
() => import('@/components/DataBindingDesigner').then(m => ({ default: m.DataBindingDesigner })),
'DataBindingDesigner'
),
DockerBuildDebugger: lazyWithPreload(
() => import('@/components/DockerBuildDebugger').then(m => ({ default: m.DockerBuildDebugger })),
'DockerBuildDebugger'
),
} as const
export const DialogRegistry = {