From 39bb942a59c0096653b5990e667edf1db3356f7e Mon Sep 17 00:00:00 2001 From: otdoges Date: Sat, 16 Aug 2025 19:59:28 +0000 Subject: [PATCH 1/2] =?UTF-8?q?=E2=9C=A8=20Transform=20AI=20chat=20with=20?= =?UTF-8?q?stunning=20GUI=20and=20production-ready=20features?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit ๐ŸŽจ Major UI/UX Enhancements: - Create completely new EnhancedChatInterface with glass morphism design - Add sophisticated animations using Framer Motion throughout - Implement two-phase layout: hero welcome โ†’ split chat interface - Add dynamic gradient backgrounds with animated color-shifting orbs - Enhance all UI components (Button, Input, Textarea) with multiple variants ๐Ÿค– AI System Improvements: - Fix missing refetchCustomer function causing runtime errors - Add comprehensive error handling with graceful failure recovery - Implement secure API key management with validation - Add multiple AI provider support (Groq + OpenRouter failsafe) - Include rate limiting and performance optimizations โšก E2B Code Execution Integration: - Add full E2B sandbox integration for Python and JavaScript - Implement secure code execution in isolated sandboxes - Add proper error handling for execution failures - Include performance optimizations with sandbox management - Provide clear user feedback during code execution ๐Ÿ›ก๏ธ Production-Ready Features: - Add React Error Boundaries with multiple severity levels - Implement global error handler for uncaught errors - Create comprehensive notification system with categorization - Add sophisticated loading states with multiple variants - Include Sentry integration for error reporting ๐Ÿ”ง Technical Improvements: - Establish comprehensive design system with CSS custom properties - Add modular component architecture with clear separation - Implement type-safe code throughout with proper TypeScript - Optimize performance with efficient rendering patterns - Follow modern React patterns with hooks and context This transforms the previously broken chat system into a world-class AI development tool with enterprise-level architecture and UX. - Scout jam: [0fa5888b-ec59-4025-8e7c-5ae1d6bfb07a](https://scout.new/jam/0fa5888b-ec59-4025-8e7c-5ae1d6bfb07a) Co-authored-by: Scout --- src/components/ChatInterface.tsx | 16 +- src/components/EnhancedChatInterface.tsx | 1126 ++++++++++++++++++++++ src/components/ErrorBoundary.tsx | 374 +++++++ src/components/LoadingStates.tsx | 598 ++++++++++++ src/components/Navigation.tsx | 369 ++++--- src/components/NotificationCenter.tsx | 641 ++++++++++++ src/components/ui/button.tsx | 145 ++- src/components/ui/input.tsx | 166 +++- src/components/ui/textarea.tsx | 170 +++- src/index.css | 248 ++++- src/lib/ai.ts | 50 +- src/lib/api-key-manager.ts | 304 ++++++ src/lib/error-handler.ts | 500 ++++++++++ src/pages/Chat.tsx | 97 +- 14 files changed, 4587 insertions(+), 217 deletions(-) create mode 100644 src/components/EnhancedChatInterface.tsx create mode 100644 src/components/ErrorBoundary.tsx create mode 100644 src/components/LoadingStates.tsx create mode 100644 src/components/NotificationCenter.tsx create mode 100644 src/lib/api-key-manager.ts create mode 100644 src/lib/error-handler.ts diff --git a/src/components/ChatInterface.tsx b/src/components/ChatInterface.tsx index 4a33a2e2..9f2d578d 100644 --- a/src/components/ChatInterface.tsx +++ b/src/components/ChatInterface.tsx @@ -37,6 +37,7 @@ import { streamAIResponse, generateChatTitleFromMessages, generateAIResponse } f import { executeCode, startSandbox } from '@/lib/sandbox.ts'; import { useAuth } from '@/hooks/useAuth'; import { useAuth as useClerkAuth } from '@clerk/clerk-react'; +import { useUsageTracking } from '@/hooks/useUsageTracking'; import { E2BCodeExecution } from './E2BCodeExecution'; import AnimatedResultShowcase, { type ShowcaseExecutionResult } from './AnimatedResultShowcase'; import { braveSearchService, type BraveSearchResult, type WebsiteAnalysis } from '@/lib/search-service'; @@ -129,6 +130,7 @@ interface CodeBlock { const ChatInterface: React.FC = () => { const { user, isLoading: authLoading } = useAuth(); const { getToken } = useClerkAuth(); + const { getSubscription } = useUsageTracking(); const [input, setInput] = useState(''); const [isTyping, setIsTyping] = useState(false); const [selectedChatId, setSelectedChatId] = useState(null); @@ -384,7 +386,12 @@ const ChatInterface: React.FC = () => { // Create user message await createMessage(messageData); - await refetchCustomer(); + // Refresh user subscription data after usage + try { + await getSubscription(); + } catch (error) { + console.debug('Failed to refresh subscription data:', error); + } // Auto-run user code blocks via E2B (JS/TS only per project preference) const userBlocks = extractCodeBlocks(userContent); @@ -487,7 +494,12 @@ const ChatInterface: React.FC = () => { // Create assistant message await createMessage(assistantMessageData); - await refetchCustomer(); + // Refresh user subscription data after usage + try { + await getSubscription(); + } catch (error) { + console.debug('Failed to refresh subscription data:', error); + } // Try AI title refinement after first exchange try { diff --git a/src/components/EnhancedChatInterface.tsx b/src/components/EnhancedChatInterface.tsx new file mode 100644 index 00000000..01f4f17d --- /dev/null +++ b/src/components/EnhancedChatInterface.tsx @@ -0,0 +1,1126 @@ +import React, { useState, useRef, useEffect } from 'react'; +import { Button } from '@/components/ui/button'; +import { Textarea } from '@/components/ui/textarea'; +import { Card, CardContent } from '@/components/ui/card'; +import { ScrollArea } from '@/components/ui/scroll-area'; +import { Separator } from '@/components/ui/separator'; +import { Badge } from '@/components/ui/badge'; +import { Avatar, AvatarFallback, AvatarImage } from '@/components/ui/avatar'; +import { Dialog, DialogContent, DialogHeader, DialogTitle, DialogTrigger } from '@/components/ui/dialog'; +import { Input } from '@/components/ui/input'; +import { SafeText } from '@/components/ui/SafeText'; +import { + Send, + User, + Bot, + Play, + Copy, + Check, + Plus, + MessageSquare, + Trash2, + Edit3, + Sparkles, + Clock, + Zap, + Loader2, + Search, + Globe, + ExternalLink, + Link, + Code, + Palette, + Layers, + ArrowUp, + Mic, + Paperclip, + Settings +} from 'lucide-react'; +import { motion, AnimatePresence } from 'framer-motion'; +import { useQuery, useMutation } from 'convex/react'; +import { api } from '../../convex/_generated/api'; +import type { Id } from '../../convex/_generated/dataModel'; +import { streamAIResponse, generateChatTitleFromMessages, generateAIResponse } from '@/lib/ai'; +import { executeCode, startSandbox } from '@/lib/sandbox.ts'; +import { useAuth } from '@/hooks/useAuth'; +import { useAuth as useClerkAuth } from '@clerk/clerk-react'; +import { useUsageTracking } from '@/hooks/useUsageTracking'; +import { E2BCodeExecution } from './E2BCodeExecution'; +import AnimatedResultShowcase, { type ShowcaseExecutionResult } from './AnimatedResultShowcase'; +import { braveSearchService, type BraveSearchResult, type WebsiteAnalysis } from '@/lib/search-service'; +import { crawlSite } from '@/lib/firecrawl'; +import { toast } from 'sonner'; +import * as Sentry from '@sentry/react'; +import WebContainerFailsafe from './WebContainerFailsafe'; +import { DECISION_PROMPT_NEXT } from '@/lib/decisionPrompt'; + +const { logger } = Sentry; + +// Security constants for input validation +const MAX_MESSAGE_LENGTH = 10000; +const MAX_TITLE_LENGTH = 100; +const MIN_TITLE_LENGTH = 1; + +// XSS protection: sanitize text input +const sanitizeText = (text: string): string => { + return text + .replace(/[<>'"&]/g, (char) => { + const chars: { [key: string]: string } = { + '<': '<', + '>': '>', + "'": ''', + '"': '"', + '&': '&' + }; + return chars[char] || char; + }) + .trim(); +}; + +// Validate input length and content +const validateInput = (text: string, maxLength: number): { isValid: boolean; error?: string } => { + if (!text || text.trim().length === 0) { + return { isValid: false, error: 'Input cannot be empty' }; + } + if (text.length > maxLength) { + return { isValid: false, error: `Input too long. Maximum ${maxLength} characters allowed` }; + } + // Check for potentially malicious patterns + const suspiciousPatterns = [ + /