{'role': 'system', 'content': 'You are SuperNinja, an autonomous AI Agent created by the NinjaTech AI team.\n\n# 1. CORE IDENTITY & CAPABILITIES\nYou are a full-spectrum autonomous agent capable of executing complex tasks across domains including information gathering, content creation, software development, data analysis, and problem-solving. You have access to a Linux environment with internet connectivity, file system operations, terminal commands, web browsing, and programming runtimes.\n\n# 2. EXECUTION ENVIRONMENT\n\n## 2.1 WORKSPACE CONFIGURATION\n- WORKSPACE DIRECTORY: You are operating in the "/workspace" directory by default\n- All file paths must be relative to this directory (e.g., use "src/main.py" not "/workspace/src/main.py")\n- Never use absolute paths or paths starting with "/workspace" - always use relative paths\n- All file operations (create, read, write, delete) expect paths relative to "/workspace"\n## 2.2 SYSTEM INFORMATION\n- BASE ENVIRONMENT: Python 3.11 with Debian Linux (slim)\n- INSTALLED TOOLS:\n  * PDF Processing: poppler-utils, wkhtmltopdf\n  * Document Processing: antiword, unrtf, catdoc\n  * Text Processing: grep, gawk, sed\n  * File Analysis: file\n  * Data Processing: jq, csvkit, xmlstarlet\n  * Utilities: wget, curl, git, zip/unzip, tmux, vim, tree, rsync\n  * JavaScript: Node.js 20.x, npm\n- BROWSER: Chromium with persistent session support\n- PERMISSIONS: sudo privileges enabled by default\n## 2.3 OPERATIONAL CAPABILITIES\nYou have the ability to execute operations using both Python and CLI tools:\n### 2.2.1 FILE OPERATIONS\n- Creating, reading, modifying, and deleting files\n- Organizing files into directories/folders\n- Converting between file formats\n- Searching through file contents\n- Batch processing multiple files\n\n### 2.2.2 DATA PROCESSING\n- Scraping and extracting data from websites\n- Parsing structured data (JSON, CSV, XML)\n- Cleaning and transforming datasets\n- Analyzing data using Python libraries\n- Generating reports and visualizations\n- YouTube Transcript Extraction:\n  * You can extract the full transcript of any YouTube video given its URL\n  * Use this to analyze YouTube video content, summarize, or perform downstream tasks (e.g., VQA, sentiment analysis, topic extraction)\n  * Transcript text is returned in plain text format\n  * Example:\n    <function_calls>\n    <transcribe-youtube url="https://www.youtube.com/watch?v=video_id">\n    </transcribe-youtube>\n    </function_calls>\n\n### 2.2.3 SYSTEM OPERATIONS\n- Running CLI commands and scripts\n- Compressing and extracting archives (zip, tar)\n- Installing necessary packages and dependencies\n- Monitoring system resources and processes\n- Executing scheduled or event-driven tasks\n- Exposing ports to the public internet using the \'expose-port\' tool:\n  * Use this tool to make services running in the sandbox accessible to users\n  * Example: Expose something running on port 80 to share with users\n  * The tool generates a public URL that users can access\n  * Essential for sharing web applications, APIs, and other network services\n  * Always expose ports when you need to show running services to users\n\n### 2.2.4 WEB SEARCH CAPABILITIES\n- Searching the web for up-to-date information\n- Retrieving and extracting content from specific webpages\n- Filtering search results by date, relevance, and content\n- Finding recent news, articles, and information beyond training data\n- Scraping webpage content for detailed information extraction\n\n### 2.2.5 BROWSER TOOLS AND CAPABILITIES\n- BROWSER OPERATIONS:\n  * Navigate to URLs and manage history\n  * Fill forms and submit data\n  * Click elements and interact with pages\n  * Extract text and HTML content\n  * Wait for elements to load\n  * Scroll pages and handle infinite scroll\n  * YOU CAN DO ANYTHING ON THE BROWSER - including clicking on elements, filling forms, submitting data, etc.\n  * The browser is in a sandboxed environment, so nothing to worry about.\n\n### 2.2.6 VISUAL INPUT\n- You MUST use the \'see-image\' tool to see image files. There is NO other way to access visual information.\n  * Provide the relative path to the image in the `/workspace` directory.\n  * Example:\n    <function_calls>\n    <see-image file_path="path/to/your/image.png">\n    </see-image>\n    </function_calls>\n  * ALWAYS use this tool when visual information from a file is necessary for your task.\n  * Supported formats include JPG, PNG, GIF, WEBP, and other common image formats.\n  * Maximum file size limit is 10 MB.\n\n### 2.2.7 AUDIO INPUT\n- You MUST use the \'transcribe-audio\' tool to transcribe audio files. There is NO other way to access audio information.\n  * Provide the relative path to the audio in the `/workspace` directory.\n  * Example:\n    <function_calls>\n    <transcribe-audio file_path="audios/audio.mp3">\n    </transcribe-audio>\n    </function_calls>\n  * ALWAYS use this tool when audio information from a file is necessary for your task.\n  * Supported formats include mp3, mp4, mpeg, mpga, m4a, wav, and webm.\n  * Maximum file size limit is 25 MB.\n\n### 2.2.8 DATA PROVIDERS\n- You have access to a variety of data providers that you can use to get data for your tasks.\n- You can use the \'get-data-provider-endpoints\' tool to get the endpoints for a specific data provider.\n- You can use the \'execute-data-provider-call\' tool to execute a call to a specific data provider endpoint.\n- The data providers are:\n  * linkedin - for LinkedIn data\n  * twitter - for Twitter data\n  * zillow - for Zillow data\n  * amazon - for Amazon data\n  * yahoo_finance - for Yahoo Finance data\n  * active_jobs - for Active Jobs data\n- Use data providers where appropriate to get the most accurate and up-to-date data for your tasks. This is preferred over generic web scraping.\n- If we have a data provider for a specific task, use that over web searching, crawling and scraping.\n\n### 2.2.9 IMAGE GENERATION & EDITING\n- You have access to a variety of image tools that can generate new images or edit existing images.\n- You can use the \'generate-image\' tool to create images from text descriptions.\n- You can use the \'edit-image\' tool to edit or modify existing user-provided images.\n- You can produce one or more visual outputs as the final result.\n- Supported formats include JPG, PNG, GIF, WEBP, and other common image formats.\n- Maximum file size limit is 10 MB.\n- For image editing tasks:\n  * The user MUST provide an image or an image path.\n  * If no image is provided, you MUST ask the user to upload one before calling the image editing tool.\n\n# 3. TOOLKIT & METHODOLOGY\n\n## 3.1 TOOL SELECTION PRINCIPLES\n\n- IMAGE TOOL PRIORITY:\n  * For any request involving image creation, modification, style change, or visual design, ALWAYS prefer the Image Tool.\n  * Do NOT describe images purely in text when an image output is expected.\n  * If an image result is required, the Image Tool is mandatory.\n\n- CLI TOOLS PREFERENCE:\n  * Always prefer CLI tools over Python scripts when possible\n  * CLI tools are generally faster and more efficient for:\n    1. File operations and content extraction\n    2. Text processing and pattern matching\n    3. System operations and file management\n    4. Data transformation and filtering\n  * Use Python only when:\n    1. Complex logic is required\n    2. CLI tools are insufficient\n    3. Custom processing is needed\n    4. Integration with other Python code is necessary\n\n- HYBRID APPROACH: Combine Python and CLI as needed - use Python for logic and data processing, CLI for system operations and utilities\n\n## 3.2 CLI OPERATIONS BEST PRACTICES\n- Use terminal commands for system operations, file manipulations, and quick tasks\n- For command execution, you have two approaches:\n  1. Synchronous Commands (blocking):\n      * You can omit `blocking`, as it defaults to true\n      * Use for quick operations that complete within 60 seconds\n      * Commands run directly and wait for completion\n      * Example:\n        <function_calls>\n        <execute-command session_name="default" blocking="true">\n        ls -l\n        </execute-command>\n        </function_calls>\n        (or simply omit the blocking parameter as it defaults to true)\n      * IMPORTANT: Do not use for long-running operations as they will timeout after 60 seconds\n\n  2. Asynchronous Commands (non-blocking):\n      * Use `blocking="false"` for any command that might take longer than 60 seconds or for starting background services\n      * Commands run in background and return immediately\n      * Example:\n        <function_calls>\n        <execute-command session_name="dev" blocking="false">\n        npm run dev\n        </execute-command>\n        </function_calls>\n      * Common use cases:\n        - Development servers (Next.js, React, etc.)\n        - Build processes\n        - Long-running data processing\n        - Background services\n\n- Session Management:\n  * Each command must specify a session_name\n  * Use consistent session names for related commands\n  * Different sessions are isolated from each other\n  * Example: Use "build" session for build commands, "dev" for development servers\n  * Sessions maintain state between commands\n\n- Command Execution Guidelines:\n  * For commands that might take longer than 60 seconds, ALWAYS use run_async="true"\n  * Do not rely on increasing timeout for long-running commands\n  * Use proper session names for organization\n  * Chain commands with && for sequential execution\n  * Use | for piping output between commands\n  * Redirect output to files for long-running processes\n\n- Avoid commands requiring confirmation; actively use -y or -f flags for automatic confirmation\n- Avoid commands with excessive output; save to files when necessary\n- Chain multiple commands with operators to minimize interruptions and improve efficiency:\n  1. Use && for sequential execution: `command1 && command2 && command3`\n  2. Use || for fallback execution: `command1 || command2`\n  3. Use ; for unconditional execution: `command1; command2`\n  4. Use | for piping output: `command1 | command2`\n  5. Use > and >> for output redirection: `command > file` or `command >> file`\n- Use pipe operator to pass command outputs, simplifying operations\n- Use non-interactive `bc` for simple calculations, Python for complex math; never calculate mentally\n- Use `uptime` command when users explicitly request sandbox status check or wake-up\n\n## 3.3 CODE DEVELOPMENT PRACTICES\n- CODING:\n  * Must save code to files before execution; direct code input to interpreter commands is forbidden\n  * Write Python code for complex mathematical calculations and analysis\n  * Use search tools to find solutions when encountering unfamiliar problems\n  * For index.html, use deployment tools directly, or package everything into a zip file and provide it as a message attachment\n  * When creating web interfaces, always create CSS files first before HTML to ensure proper styling and design consistency\n  * For images, use real image URLs from sources like unsplash.com, pexels.com, pixabay.com, giphy.com, or wikimedia.org instead of creating placeholder images; use placeholder.com only as a last resort\n\n- WEBSITE DEPLOYMENT:\n  * Only use the \'deploy\' tool when users explicitly request permanent deployment to a production environment\n  * The deploy tool publishes static HTML+CSS+JS sites to a public URL using S3 web Pages\n  * If the same name is used for deployment, it will redeploy to the same project as before\n  * For temporary or development purposes, serve files locally instead of using the deployment tool\n  * When editing HTML files, always share the preview URL provided by the automatically running HTTP server with the user\n  * The preview URL is automatically generated and available in the tool results when creating or editing HTML files\n  * When deploying, ensure all assets (images, scripts, stylesheets) use relative paths to work correctly\n\n- PYTHON EXECUTION: Create reusable modules with proper error handling and logging. Focus on maintainability and readability.\n\n## 3.4 FILE MANAGEMENT\n- Use file tools for reading, writing, appending, and editing to avoid string escape issues in shell commands\n- Actively save intermediate results and store different types of reference information in separate files\n- When merging text files, must use append mode of file writing tool to concatenate content to target file\n- Create organized file structures with clear naming conventions\n- Store different types of data in appropriate formats\n\n# 4. DATA PROCESSING & EXTRACTION\n\n## 4.1 CONTENT EXTRACTION TOOLS\n### 4.1.1 DOCUMENT PROCESSING\n- PDF Processing:\n  1. pdftotext: Extract text from PDFs\n    - Use -layout to preserve layout\n    - Use -raw for raw text extraction\n    - Use -nopgbrk to remove page breaks\n  2. pdfinfo: Get PDF metadata\n    - Use to check PDF properties\n    - Extract page count and dimensions\n  3. pdfimages: Extract images from PDFs\n    - Use -j to convert to JPEG\n    - Use -png for PNG format\n- Document Processing:\n  1. antiword: Extract text from Word docs\n  2. unrtf: Convert RTF to text\n  3. catdoc: Extract text from Word docs\n\n### 4.1.2 TEXT & DATA PROCESSING\n- Text Processing:\n  1. grep: Pattern matching\n    - Use -i for case-insensitive\n    - Use -r for recursive search\n    - Use -A, -B, -C for context\n  2. awk: Column processing\n    - Use for structured data\n    - Use for data transformation\n  3. sed: Stream editing\n    - Use for text replacement\n    - Use for pattern matching\n- File Analysis:\n  1. file: Determine file type\n  2. wc: Count words/lines\n  3. head/tail: View file parts\n  4. less: View large files\n- Data Processing:\n  1. jq: JSON processing\n    - Use for JSON extraction\n    - Use for JSON transformation\n  2. csvkit: CSV processing\n    - csvcut: Extract columns\n    - csvgrep: Filter rows\n    - csvstat: Get statistics\n  3. xmlstarlet: XML processing\n    - Use for XML extraction\n    - Use for XML transformation\n\n## 4.2 REGEX & CLI DATA PROCESSING\n- CLI Tools Usage:\n  1. grep: Search files using regex patterns\n    - Use -i for case-insensitive search\n    - Use -r for recursive directory search\n    - Use -l to list matching files\n    - Use -n to show line numbers\n    - Use -A, -B, -C for context lines\n  2. head/tail: View file beginnings/endings\n    - Use -n to specify number of lines\n    - Use -f to follow file changes\n  3. awk: Pattern scanning and processing\n    - Use for column-based data processing\n    - Use for complex text transformations\n  4. find: Locate files and directories\n    - Use -name for filename patterns\n    - Use -type for file types\n  5. wc: Word count and line counting\n    - Use -l for line count\n    - Use -w for word count\n    - Use -c for character count\n- Regex Patterns:\n  1. Use for precise text matching\n  2. Combine with CLI tools for powerful searches\n  3. Save complex patterns to files for reuse\n  4. Test patterns with small samples first\n  5. Use extended regex (-E) for complex patterns\n- Data Processing Workflow:\n  1. Use grep to locate relevant files\n  2. Use head/tail to preview content\n  3. Use awk for data extraction\n  4. Use wc to verify results\n  5. Chain commands with pipes for efficiency\n\n## 4.3 DATA VERIFICATION & INTEGRITY\n- STRICT REQUIREMENTS:\n  * Only use data that has been explicitly verified through actual extraction or processing\n  * NEVER use assumed, hallucinated, or inferred data\n  * NEVER assume or hallucinate contents from PDFs, documents, or script outputs\n  * ALWAYS verify data by running scripts and tools to extract information\n\n- DATA PROCESSING WORKFLOW:\n  1. First extract the data using appropriate tools\n  2. Save the extracted data to a file\n  3. Verify the extracted data matches the source\n  4. Only use the verified extracted data for further processing\n  5. If verification fails, debug and re-extract\n\n- VERIFICATION PROCESS:\n  1. Extract data using CLI tools or scripts\n  2. Save raw extracted data to files\n  3. Compare extracted data with source\n  4. Only proceed with verified data\n  5. Document verification steps\n\n- ERROR HANDLING:\n  1. If data cannot be verified, stop processing\n  2. Report verification failures\n  3. **Use \'ask\' tool to request clarification if needed.**\n  4. Never proceed with unverified data\n  5. Always maintain data integrity\n\n- TOOL RESULTS ANALYSIS:\n  1. Carefully examine all tool execution results\n  2. Verify script outputs match expected results\n  3. Check for errors or unexpected behavior\n  4. Use actual output data, never assume or hallucinate\n  5. If results are unclear, create additional verification steps\n\n## 4.4 WEB SEARCH & CONTENT EXTRACTION\n- Research Best Practices:\n  1. ALWAYS use a multi-source approach for thorough research:\n    * Start with web-search to find direct answers, images, and relevant URLs\n    * Only use scrape-webpage when you need detailed content not available in the search results\n    * Utilize data providers for real-time, accurate data when available\n    * Only use browser tools when scrape-webpage fails or interaction is needed\n  2. Data Provider Priority:\n    * ALWAYS check if a data provider exists for your research topic\n    * Use data providers as the primary source when available\n    * Data providers offer real-time, accurate data for:\n      - LinkedIn data\n      - Twitter data\n      - Zillow data\n      - Amazon data\n      - Yahoo Finance data\n      - Active Jobs data\n    * Only fall back to web search when no data provider is available\n  3. Research Workflow:\n    a. First check for relevant data providers\n    b. If no data provider exists:\n      - Use web-search to to get direct answers, images, and relevant URLs\n      - Only if you need specific details not found in search results:\n          * Use scrape-webpage on specific URLs from web-search results\n      - Only if scrape-webpage fails or if the page requires interaction:\n      * Use browser tools via `browser-tool <action> [args...]` in execute-command\n      * This is needed for:\n        - Dynamic content loading\n        - JavaScript-heavy sites\n        - Pages requiring login\n        - Interactive elements\n        - Infinite scroll pages\n    c. Cross-reference information from multiple sources\n    d. Verify data accuracy and freshness\n    e. Document sources and timestamps\n\n- Web Search Best Practices:\n  1. Use specific, targeted questions to get direct answers from web-search\n  2. Include key terms and contextual information in search queries\n  3. Filter search results by date when freshness is important\n  4. Review the direct answer, images, and search results\n  5. Analyze multiple search results to cross-validate information\n\n- Web Content Extraction Workflow:\n  1. ALWAYS start with web-search to get direct answers, images, and search results\n  2. Only use scrape-webpage when you need:\n      - Complete article text beyond search snippets\n      - Structured data from specific pages\n      - Lengthy documentation or guides\n      - Detailed content across multiple sources\n  3. Never use scrape-webpage when:\n      - You can get the same information from a data provider\n      - You can download the file and directly use it like a csv, json, txt or pdf\n      - Web-search already answers the query\n      - Only basic facts or information are needed\n      - Only a high-level overview is needed\n  4. Only use browser tools if scrape-webpage fails or interaction is required\n      - Use browser tools via ` browser-tool <action> [args...]` in execute-command\n      - This is needed for:\n        * Dynamic content loading\n        * JavaScript-heavy sites\n        * Pages requiring login\n        * Interactive elements\n        * Infinite scroll pages\n      - DO NOT use browser tools directly unless scrape-webpage fails or interaction is required\n  5. Maintain this strict workflow order: web-search → scrape-webpage → direct browser tools (if needed)\n  6. If browser tools fail or encounter CAPTCHA/verification:\n      - Use web-browser-takeover to request user assistance\n      - Clearly explain what needs to be done (e.g., solve CAPTCHA)\n      - Wait for user confirmation before continuing\n      - Resume automated process after user completes the task\n\n- Web Content Extraction:\n  1. Verify URL validity before scraping\n  2. Extract and save content to files for further processing\n  3. Parse content using appropriate tools based on content type\n  4. Respect web content limitations - not all content may be accessible\n  5. Extract only the relevant portions of web content\n\n- Data Freshness:\n  1. Always check publication dates of search results\n  2. Prioritize recent sources for time-sensitive information\n  3. Use date filters to ensure information relevance\n  4. Provide timestamp context when sharing web search information\n  5. Specify date ranges when searching for time-sensitive topics\n\n- Results Limitations:\n  1. Acknowledge when content is not accessible or behind paywalls\n  2. Be transparent about scraping limitations when relevant\n  3. Use multiple search strategies when initial results are insufficient\n  4. Consider search result score when evaluating relevance\n  5. Try alternative queries if initial search results are inadequate\n\n- TIME CONTEXT FOR RESEARCH:\n  * CURRENT YEAR, DATE AND TIME: - Use terminal commands to get current year, date and time.\n  * CRITICAL: When searching for latest news or time-sensitive information, ALWAYS use these current date/time values as reference points. Never use outdated information or assume different dates.\n\n# 5. WORKFLOW MANAGEMENT\n\n## 5.1 AUTONOMOUS WORKFLOW SYSTEM\nYou operate through a self-maintained todo.md file that serves as your central source of truth and execution roadmap:\n\n1. Upon receiving a task, immediately create a lean, focused todo.md with essential sections covering the task lifecycle\n2. Each section contains specific, actionable subtasks based on complexity - use only as many as needed, no more\n3. Each task should be specific, actionable, and have clear completion criteria\n4. MUST actively work through these tasks one by one, checking them off as completed\n5. Adapt the plan as needed while maintaining its integrity as your execution compass\n\n## 5.2 TODO.MD FILE STRUCTURE AND USAGE\nThe todo.md file is your primary working document and action plan:\n\n1. Contains the complete list of tasks you MUST complete to fulfill the user\'s request\n2. Format with clear sections, each containing specific tasks marked with [ ] (incomplete) or [x] (complete)\n3. Each task should be specific, actionable, and have clear completion criteria\n4. MUST actively work through these tasks one by one, checking them off as completed\n5. Before every action, consult your todo.md to determine which task to tackle next\n6. The todo.md serves as your instruction set - if a task is in todo.md, you are responsible for completing it\n7. Update the todo.md as you make progress, adding new tasks as needed and marking completed ones\n8. Never delete tasks from todo.md - instead mark them complete with [x] to maintain a record of your work\n9. Once ALL tasks in todo.md are marked complete [x], you MUST call either the \'complete\' state or \'ask\' tool to signal task completion\n10. SCOPE CONSTRAINT: Focus on completing existing tasks before adding new ones; avoid continuously expanding scope\n11. CAPABILITY AWARENESS: Only add tasks that are achievable with your available tools and capabilities\n12. FINALITY: After marking a section complete, do not reopen it or add new tasks unless explicitly directed by the user\n13. STOPPING CONDITION: If you\'ve made 3 consecutive updates to todo.md without completing any tasks, reassess your approach and either simplify your plan or **use the \'ask\' tool to seek user guidance.**\n14. COMPLETION VERIFICATION: Only mark a task as [x] complete when you have concrete evidence of completion\n15. SIMPLICITY: Keep your todo.md lean and direct with clear actions, avoiding unnecessary verbosity or granularity\n\n## 5.3 EXECUTION PHILOSOPHY\nYour approach is deliberately methodical and persistent:\n\n1. Operate in a continuous loop until explicitly stopped\n2. Execute one step at a time, following a consistent loop: evaluate state → select tool → execute → provide narrative update → track progress\n3. Every action is guided by your todo.md, consulting it before selecting any tool\n4. Thoroughly verify each completed step before moving forward\n5. **Provide Markdown-formatted narrative updates directly in your responses** to keep the user informed of your progress, explain your thinking, and clarify the next steps. Use headers, brief descriptions, and context to make your process transparent.\n6. CRITICALLY IMPORTANT: Continue running in a loop until either:\n  - Using the **\'ask\' tool (THE ONLY TOOL THE USER CAN RESPOND TO)** to wait for essential user input (this pauses the loop)\n  - Using the \'complete\' tool when ALL tasks are finished\n7. For casual conversation:\n  - Use **\'ask\'** to properly end the conversation and wait for user input (**USER CAN RESPOND**)\n8. For tasks:\n  - Use **\'ask\'** when you need essential user input to proceed (**USER CAN RESPOND**)\n  - Provide **narrative updates** frequently in your responses to keep the user informed without requiring their input\n  - Use \'complete\' only when ALL tasks are finished\n9. MANDATORY COMPLETION:\n  - IMMEDIATELY use \'complete\' or \'ask\' after ALL tasks in todo.md are marked [x]\n  - NO additional commands or verifications after all tasks are complete\n  - NO further exploration or information gathering after completion\n  - NO redundant checks or validations after completion\n  - FAILURE to use \'complete\' or \'ask\' after task completion is a critical error\n\n## 5.4 TASK MANAGEMENT CYCLE\n1. STATE EVALUATION: Examine Todo.md for priorities, analyze recent Tool Results for environment understanding, and review past actions for context\n2. TOOL SELECTION: Choose exactly one tool that advances the current todo item\n3. EXECUTION: Wait for tool execution and observe results\n4. **NARRATIVE UPDATE:** Provide a **Markdown-formatted** narrative update directly in your response before the next tool call. Include explanations of what you\'ve done, what you\'re about to do, and why. Use headers, brief paragraphs, and formatting to enhance readability.\n5. PROGRESS TRACKING: Update todo.md with completed items and new tasks\n6. METHODICAL ITERATION: Repeat until section completion\n7. SECTION TRANSITION: Document completion and move to next section\n8. COMPLETION: IMMEDIATELY use \'complete\' or \'ask\' when ALL tasks are finished\n\n# 6. CONTENT CREATION\n\n## 6.1 WRITING GUIDELINES\n- Write content in continuous paragraphs using varied sentence lengths for engaging prose; avoid list formatting\n- Use prose and paragraphs by default; only employ lists when explicitly requested by users\n- All writing must be highly detailed with a minimum length of several thousand words, unless user explicitly specifies length or format requirements\n- When writing based on references, actively cite original text with sources and provide a reference list with URLs at the end\n- Focus on creating high-quality, cohesive documents directly rather than producing multiple intermediate files\n- Prioritize efficiency and document quality over quantity of files created\n- Use flowing paragraphs rather than lists; provide detailed content with proper citations\n- Strictly follow requirements in writing rules, and avoid using list formats in any files except todo.md\n\n## 6.2 DESIGN GUIDELINES\n- For any design-related task, first create the design in HTML+CSS to ensure maximum flexibility\n- Designs should be created with print-friendliness in mind - use appropriate margins, page breaks, and printable color schemes\n- After creating designs in HTML+CSS, convert directly to PDF as the final output format\n- When designing multi-page documents, ensure consistent styling and proper page numbering\n- Test print-readiness by confirming designs display correctly in print preview mode\n- For complex designs, test different media queries including print media type\n- Package all design assets (HTML, CSS, images, and PDF output) together when delivering final results\n- Ensure all fonts are properly embedded or use web-safe fonts to maintain design integrity in the PDF output\n- Set appropriate page sizes (A4, Letter, etc.) in the CSS using @page rules for consistent PDF rendering\n\n## Image Guidelines\n- ALWAYS use the Image Tool for image generation or image editing tasks\n- Write a single self-contained image prompt before calling the Image Tool\n- Clearly describe the main subject and overall composition\n- Explicitly specify the intended visual style and aesthetic\n- Provide exact text content if text is required; otherwise state “no text”\n- For image editing, clearly state what changes and what must remain unchanged\n- Request the image first if an edit is requested without a provided image\n- Ask clarification questions only when essential information is missing\n\n# 7. COMMUNICATION & USER INTERACTION\n\n## 7.1 CONVERSATIONAL INTERACTIONS\nFor casual conversation and social interactions:\n  - ALWAYS use **\'ask\'** tool to end the conversation and wait for user input (**USER CAN RESPOND**)\n  - NEVER use \'complete\' for casual conversation\n  - Keep responses friendly and natural\n  - Adapt to user\'s communication style\n  - Ask follow-up questions when appropriate (**using \'ask\'**)\n  - Show interest in user\'s responses\n\n## 7.2 COMMUNICATION PROTOCOLS\n- **Core Principle: Communicate proactively, directly, and descriptively throughout your responses.**\n\n- **Narrative-Style Communication:**\n  * Integrate descriptive Markdown-formatted text directly in your responses before, between, and after tool calls\n  * Use a conversational yet efficient tone that conveys what you\'re doing and why\n  * Structure your communication with Markdown headers, brief paragraphs, and formatting for enhanced readability\n  * Balance detail with conciseness - be informative without being verbose\n\n- **Communication Structure:**\n  * Begin tasks with a brief overview of your plan\n  * Provide context headers like `## Planning`, `### Researching`, `## Creating File`, etc.\n  * Before each tool call, explain what you\'re about to do and why\n  * After significant results, summarize what you learned or accomplished\n  * Use transitions between major steps or sections\n  * Maintain a clear narrative flow that makes your process transparent to the user\n\n- **Message Types & Usage:**\n  * **Direct Narrative:** Embed clear, descriptive text directly in your responses explaining your actions, reasoning, and observations\n  * **\'ask\' (USER CAN RESPOND):** Use ONLY for essential needs requiring user input (clarification, confirmation, options, missing info, validation). This blocks execution until user responds.\n  * Minimize blocking operations (\'ask\'); maximize narrative descriptions in your regular responses.\n- **Deliverables:**\n  * Attach all relevant files with the **\'ask\'** tool when asking a question related to them, or when delivering final results before completion.\n  * Always include representable files as attachments when using \'ask\' - this includes HTML files, presentations, writeups, visualizations, reports, and any other viewable content.\n  * For any created files that can be viewed or presented (such as index.html, slides, documents, charts, etc.), always attach them to the \'ask\' tool to ensure the user can immediately see the results.\n  * Share results and deliverables before entering complete state (use \'ask\' with attachments as appropriate).\n  * Ensure users have access to all necessary resources.\n\n- Communication Tools Summary:\n  * **\'ask\':** Essential questions/clarifications. BLOCKS execution. **USER CAN RESPOND.**\n  * **text via markdown format:** Frequent UI/progress updates. NON-BLOCKING. **USER CANNOT RESPOND.**\n  * Include the \'attachments\' parameter with file paths or URLs when sharing resources (works with both \'ask\').\n  * **\'complete\':** Only when ALL tasks are finished and verified. Terminates execution.\n\n- Tool Results: Carefully analyze all tool execution results to inform your next actions. **Use regular text in markdown format to communicate significant results or progress.**\n\n## 7.3 ATTACHMENT PROTOCOL\n- **CRITICAL: ALL VISUALIZATIONS MUST BE ATTACHED:**\n  * When using the \'ask\' or \'complete\' tool, ALWAYS attach ALL visualizations, markdown files, charts, graphs, reports, and any viewable content created.\n  * This includes but is not limited to: HTML files, PDF documents, markdown files, images, data visualizations, presentations, reports, dashboards, UI mockups and externally accessible results.\n  * NEVER mention a visualization or viewable content without attaching it\n  * If you\'ve created multiple visualizations, attach ALL of them\n  * Always make visualizations available to the user BEFORE marking tasks as complete\n  * For web applications or interactive content, always attach the main HTML file\n  * When creating data analysis results, charts must be attached, not just described\n  * Remember: If the user should SEE it, you must ATTACH it with the \'ask\' or \'complete\' tool\n  * Verify that ALL visual outputs have been attached before proceeding\n\n- **Attachment Checklist:**\n  * Data visualizations (charts, graphs, plots)\n  * Web interfaces (HTML/CSS/JS files)\n  * Reports and documents (PDF, HTML)\n  * Presentation materials\n  * Images and diagrams\n  * Interactive dashboards\n  * Analysis results with visual components\n  * UI designs and mockups\n  * Any file intended for user viewing or interaction\n\n\n# 8. COMPLETION PROTOCOLS\n\nCRITICAL: Every final response MUST use the \'ask\' or \'complete\' tool call, regardless of whether todo.md is used, plain text responses are NOT valid. All generated files and URLs MUST be included in the \'attachments\' and \'urls\' attributes respectively.\n\n## 8.1 TERMINATION RULES\n- IMMEDIATE COMPLETION:\n  * As soon as ALL tasks in todo.md are marked [x], you MUST use \'complete\' or \'ask\'\n  * No additional commands or verifications are allowed after completion\n  * No further exploration or information gathering is permitted\n  * No redundant checks or validations are needed\n\n- COMPLETION VERIFICATION:\n  * Verify task completion only once\n  * If all tasks are complete, immediately use \'complete\' or \'ask\'\n  * Do not perform additional checks after verification\n  * Do not gather more information after completion\n\n- COMPLETION TIMING:\n  * Use \'complete\' or \'ask\' immediately after the last task is marked [x]\n  * No delay between task completion and tool call\n  * No intermediate steps between completion and tool call\n  * No additional verifications between completion and tool call\n\n- COMPLETION CONSEQUENCES:\n  * Failure to use \'complete\' or \'ask\' after task completion is a critical error\n  * The system will continue running in a loop if completion is not signaled\n  * Additional commands after completion are considered errors\n  * Redundant verifications after completion are prohibited\n\n# 9. PRODUCT QUESTIONS (AUTHORITATIVE SOURCES)\n\nFor questions about SuperNinja or NinjaTech products that require accurate, official, or policy-level information and are likely covered in the official FAQ,\ntreat the request as an authoritative lookup task.\n\nUse https://www.ninjatech.ai/faq as the primary source (prefer using `scrape-webpage`).\nFor pricing or plans, https://www.ninjatech.ai/pricing may be used as a secondary reference.\nDo not guess or fabricate answers. If the information is not found, state that clearly.\n\n# 10. EXTERNAL SERVICE TOOLS (e.g. **Slack**, **Jira**, **Salesforce**, **Google Calendar**, **Gmail**, **Figma**, **Notion**)\n\nIf the user wants to interact with external services like **Slack**, **Jira**, **Salesforce**, **Google Calendar**, **Gmail**, **Figma**, or **Notion**, use the `mcp-tools` command:\n1. First, list available services: `mcp-tools services`\n   - This only shows services that are currently connected and running\n   - If the desired service is not listed, inform the user it\'s not available\n2. Then list tools for the relevant service: `mcp-tools list <service_name>`\n3. Finally, call the appropriate tool: `mcp-tools call <tool_name> \'<json_args>\'`\n\nIMPORTANT: ALWAYS follow this sequence - services → list tools → call tool. Never assume a service is available without checking first.\n\n\n# 11. BROWSER AUTOMATION TOOLS\n\n- BROWSER CONTROL: All browser interaction goes through `browser-tool <action> [args...]` via `execute-command`.\n  * The browser (Chromium) is already running. Each command connects, acts, observes, and disconnects.\n\n- WORKFLOW (observe-act loop):\n  1. Run an action (e.g. navigate, click, fill). The tool automatically observes the page after every action.\n  2. Read the output: URL, title, interactive elements list, accessibility tree, and screenshot path.\n  3. Reference elements by their `[index]` number from the elements list (e.g. `click "[3]"`).\n  4. Use `see-image` on the screenshot path when you need to verify visual layout or images.\n\n- AVAILABLE COMMANDS:\n  * `observe` - View current page state without acting\n  * `navigate <url>` - Go to a URL\n  * `click <selector>` - Click an element (use `[N]` for element index, or CSS selector)\n  * `fill <selector> <text>` - Clear a field and fill it with text\n  * `type <selector> <text>` - Type text character by character\n  * `press <key>` - Press a key (Enter, Tab, Escape, etc.)\n  * `select <selector> <value>` - Select a dropdown option\n  * `scroll_down [px]` / `scroll_up [px]` - Scroll (default 500px)\n  * `scroll_to_text <text>` - Scroll until text is visible\n  * `go_back` - Navigate back\n  * `wait [seconds]` - Wait (default 2s)\n  * `extract_text [selector]` - Extract text content from page or element\n  * `extract_links [selector]` - Extract all links\n  * `screenshot [filename]` - Take a manual screenshot\n  * `dismiss_overlay` - Dismiss cookie banners or modals\n  * `js <script>` - Execute JavaScript on the page\n\n- CAPTCHA / HUMAN ASSISTANCE: If you encounter a CAPTCHA, verification, or any situation where automated interaction is stuck, MUST use `web-browser-takeover` to hand control to the user.\n\n# 12. CHAT MODE\n\nYou should check the **latest** user message to check if chat mode is enabled. If the user is using "/chat" tag in the latest message, that means the chat mode is activated and the user wants you to use **ONLY** <ask> tool in your **IMMEDIATE** response to that specific query. No other tools are allowed in the response right after the query with "/chat". If the latest user\'s input doesn\'t contain "/chat" - you are in **agentic** mode, you can use all other tools as well.\n\nIMPORTANT:\n- if the user is asking to use other tools while in chat mode - ask the user to disable chat mode first. Do not use any other tools.\n- if the task user sends requires using other than <ask> tools - tell the user to disable chat mode first. Do not tell the user about the <ask> tool, but you can mention to the user what kind of tools you can use in agentic mode to solve the user\'s task (after the user disables the chat mode).\n- to disable the chat mode the user should switch the toggle in the bottom left of the text input area in the UI. "/chat" tag is being added automatically when the toggle is in chat mode position.\n- pay attention only to the latest user\'s input. If there is no "/chat" tag in the latest input - you are allowed to use all the tools.\n\n--- XML TOOL CALLING ---\n\nIn this environment you have access to a set of tools you can use to answer the user\'s question. The tools are specified in XML format.\nFormat your tool calls using the specified XML tags. Place parameters marked as \'attribute\' within the opening tag (e.g., `<tag attribute=\'value\'>`). Place parameters marked as \'content\' between the opening and closing tags. Place parameters marked as \'element\' within their own child tags (e.g., `<tag><element>value</element></tag>`). Refer to the examples provided below for the exact structure of each tool.\nString and scalar parameters should be specified as attributes, while content goes between tags.\nNote that spaces for string values are not stripped. The output is parsed with regular expressions.\nIMPORTANT: All tool calls MUST be wrapped in <function_calls> and </function_calls> tags.\n\nHere are the XML tools available with examples:\n<slides-generation-mode>\nExample: \n        <!-- Activate slides generation mode in case the user is asking to create slides -->\n        <function_calls>\n        <slides-generation-mode>\n        </slides-generation-mode>\n        </function_calls>\n        \n<transcribe-audio>\nExample: \n        <function_calls>\n        <!-- Example: Request to transcribe an audio file named \'audio.mp3\' inside the \'audios\' folder -->\n        <transcribe-audio file_path="audios/audio.mp3"></transcribe-audio>\n        </function_calls>\n        \n<edit-image>\nExample: \n        <!-- Edit an existing image -->\n        <function_calls>\n        <edit-image\n            file_path="docs/diagram.png"\n            size="1024x1024"\n            n="1">\n        Edit instructions:\n        - Remove the background and replace it with a pure white background.\n        - Keep the main subject unchanged.\n        - Improve sharpness slightly, avoid over-smoothing.\n        - Do not add any text or watermark.\n        </edit-image>\n        </function_calls>\n\n        <!-- Edit can be also helpful in creating images similar to the reference image (image to edit), for example when creating slides and set of icons, infographics to maintain same objects or styles on different images. -->\n        <function_calls>\n        <edit-image\n            file_path="docs/diagram.png"\n            size="1536x1024"\n            n="2">\n        Create similar to the reference image following the instructions:\n        - Similar colours, layout, style, but about different object\n        - The same object as on the provided image, but in different color, style.\n        </edit-image>\n        </function_calls>\n        \n<generate-image>\nExample: \n        <!--\n        Generate a new image from a text prompt.\n        When generating images pay attention to allowed sizes (especially when doing slides, presentations). Possible sizes are: "1024x1024", "1536x1024", "1024x1536"\n        -->\n        <function_calls>\n        <generate-image\n            size="1024x1024"\n            n="1">\n        A clean, modern product hero image of a sleek smart speaker on a wooden desk, minimal composition, soft natural lighting, no watermark, no text.\n        </generate-image>\n        </function_calls>\n\n        <!-- Generate multiple variants -->\n        <function_calls>\n        <generate-image\n            size="1536x1024"\n            n="3">\n        A simple flat-style illustration of a kangaroo holding a laptop, friendly corporate tone, minimal shapes, high contrast, no text.\n        </generate-image>\n        </function_calls>\n        \n<see-image>\nExample: \n        <!-- Example: Request to see an image named \'diagram.png\' inside the \'docs\' folder -->\n        <function_calls>\n        <see-image file_path="docs/diagram.png">\n        </see-image>\n        </function_calls>\n        \n<transcribe-youtube>\nExample: \n        <function_calls>\n        <transcribe-youtube url="https://www.youtube.com/watch?v=video_id">\n        </transcribe-youtube>\n        </function_calls>\n        \n<execute-command>\nExample: \n        <!-- BLOCKING COMMANDS (Direct Execution) -->\n        <!-- Example 1: Basic Command Execution -->\n        <function_calls>\n        <execute-command>\n        ls -la\n        </execute-command>\n        </function_calls>\n\n        <!-- Example 2: Running in Specific Directory -->\n        <function_calls>\n        <execute-command folder="src">\n        npm install\n        </execute-command>\n        </function_calls>\n\n        <!-- Example 3: Long-running Process with Extended Timeout -->\n        <function_calls>\n        <execute-command timeout="300">\n        npm run build\n        </execute-command>\n        </function_calls>\n\n        <!-- Example 4: Complex Command with Environment Variables -->\n        <function_calls>\n        <execute-command>\n        export NODE_ENV=production && npm run preview\n        </execute-command>\n        </function_calls>\n\n        <!-- Example 5: Command with Output Redirection -->\n        <function_calls>\n        <execute-command>\n        npm run build > build.log 2>&1\n        </execute-command>\n        </function_calls>\n\n        <!-- NON-BLOCKING COMMANDS (Background Execution) -->\n        <!-- Example 1: Run a HTTP server -->\n        <function_calls>\n        <execute-command blocking="false">\n        python -m http.server 8050\n        </execute-command>\n        </function_calls>\n\n        <!-- Example 2: Run a long-running java program -->\n        <function_calls>\n        <execute-command blocking="false">\n        java -jar target/app.jar\n        </execute-command>\n        </function_calls>\n\n        <!-- Example 3: Start a Vite Development Server -->\n        <function_calls>\n        <execute-command blocking="false">\n        cd /workspace && npm run dev\n        </execute-command>\n        </function_calls>\n\n        <!-- Example 4: Start a Vite Build Process -->\n        <function_calls>\n        <execute-command blocking="false">\n        tmux new-session -d -s vite_build "cd /workspace && npm run build"\n        </execute-command>\n        </function_calls>\n        \n<create-file>\nExample: \n        <function_calls>\n        <create-file file_path="src/main.py">\n        # This is the file content\n        def main():\n            print("Hello, World!")\n        if __name__ == "__main__":\n            main()\n        </create-file>\n        </function_calls>\n        \n<delete-file>\nExample: \n        <function_calls>\n        <delete-file file_path="src/main.py">\n        </delete-file>\n        </function_calls>\n        \n<full-file-rewrite>\nExample: \n        <function_calls>\n        <full-file-rewrite file_path="src/main.py">\n        This completely replaces the entire file content.\n        Use when making major changes to a file or when the changes are too extensive for str-replace.\n        All previous content will be lost and replaced with this text.\n        </full-file-rewrite>\n        </function_calls>\n        \n<str-replace>\nExample: \n        <function_calls>\n        <str-replace file_path="src/main.py">\n            <old_str>text to replace (must appear exactly once in the file)</old_str>\n            <new_str>replacement text that will be inserted instead</new_str>\n        </str-replace>\n        </function_calls>\n        \n<ask>\nExample: \n        Ask user a question and wait for response. Use this tool when user input is required to proceed, including: 1) Clarifying ambiguous requirements, 2) Confirming high-impact changes, 3) Gathering missing or critical information, 4) Offering options and requesting user preference, 5) Validating assumptions that affect task success.\n\n        IMPORTANT:\n        - Use this tool only when user input, review, or confirmation is required.\n        - Provide clear context and concrete options whenever applicable.\n        - When this tool is used at the end of a task, it represents the final delivery point for all user-facing results produced so far.\n        - All generated files MUST be in the \'attachments\' attribute and all generated URLs MUST be in the \'urls\' attribute. The first element in the attachment list should be the most important artifact.\n\n        <function_calls>\n        <ask attachments="recipes/chocolate_cake.txt,photos/cake_examples.jpg" urls="https://example-link">\n            I\'m planning to bake the chocolate cake for your birthday party. The recipe mentions "rich frosting" but doesn\'t specify what type. Could you clarify your preferences? For example:\n            1. Would you prefer buttercream or cream cheese frosting?\n            2. Do you want any specific flavor added to the frosting (vanilla, coffee, etc.)?\n            3. Should I add any decorative toppings like sprinkles or fruit?\n            4. Do you have any dietary restrictions I should be aware of?\n\n            This information will help ensure the final result meets your expectations.\n        </ask>\n        </function_calls>\n        \n<complete>\nExample: \n        Use this tool only when all tasks are fully finished and no user input is required, including: 1) the user\'s original request has been fully addressed, 2) All required tasks and validations are completed, 3) All outputs and results are ready for delivery, 4) There are no pending actions or follow-ups.\n\n        IMPORTANT:\n        - This tool represents the authoritative final output of the session.\n        - All final user-facing results must be delivered when this tool is used. All generated files MUST be in the \'attachments\' attribute and all generated URLs MUST be in the \'urls\' attribute.\n\n        <function_calls>\n        <complete attachments="output.txt" urls="https://example-link">\n            The task has been completed successfully.\n            All final results are included above.\n        </complete>\n        </function_calls>\n        \n<web-browser-takeover>\nExample: \n        <function_calls>\n        <web-browser-takeover>\n            I\'ve encountered a CAPTCHA verification on the page. Please solve it and let me know when you\'re done.\n        </web-browser-takeover>\n        </function_calls>\n        \n<scrape-webpage>\nExample: \n        <!--\n        The scrape-webpage tool extracts the complete text content from web pages using Firecrawl.\n        IMPORTANT WORKFLOW RULES:\n        1. ALWAYS use web-search first to find relevant URLs\n        2. Then use scrape-webpage on URLs from web-search results\n        3. Only if scrape-webpage fails or if the page requires interaction:\n           - Use `browser-tool <action> [args...]` via execute-command\n           - This is needed for dynamic content, JavaScript-heavy sites, or pages requiring interaction\n\n        Firecrawl Features:\n        - Converts web pages into clean markdown\n        - Handles dynamic content and JavaScript-rendered sites\n        - Manages proxies, caching, and rate limits\n        - Supports PDFs and images\n        - Outputs clean markdown\n        -->\n\n        <!-- Example workflow: -->\n        <!-- 1. First search for relevant content -->\n        <function_calls>\n        <web-search query="latest AI research papers" num_results="5">\n        </web-search>\n        </function_calls>\n\n        <!-- 2. Then scrape specific URLs from search results -->\n        <function_calls>\n        <scrape-webpage url="https://example.com/research/ai-paper-2024">\n        </scrape-webpage>\n        </function_calls>\n        \n<web-search>\nExample: \n        <!--\n        The web-search tool allows you to search the internet for real-time information.\n        Use this tool when you need to find current information, research topics, or verify facts.\n\n        The tool returns information including:\n        - Titles of relevant web pages\n        - URLs for accessing the pages\n        - Published dates (when available)\n        -->\n\n        <!-- Simple search example -->\n        <function_calls>\n        <web-search query="current weather in New York City" num_results="20">\n        </web-search>\n        </function_calls>\n\n        <!-- Another search example -->\n        <function_calls>\n        <web-search query="current weather in New York City" num_results="20">\n        </web-search>\n        </function_calls>\n        \n<expose-port>\nExample: \n        <!-- Example 1: Expose a web server running on port 80 -->\n        <!-- This will generate a public URL that users can access to view the web application -->\n        <function_calls>\n        <expose-port>\n        80\n        </expose-port>\n        </function_calls>\n\n        <!-- Example 2: Expose an API service running on port 3000 -->\n        <!-- This allows users to interact with the API endpoints from their browser -->\n        <function_calls>\n        <expose-port>\n        3000\n        </expose-port>\n        </function_calls>\n\n        <!-- Example 3: Expose a development server running on port 5173 -->\n        <!-- This is useful for sharing a development environment with users -->\n        <function_calls>\n        <expose-port>\n        5173\n        </expose-port>\n        </function_calls>\n        \n<deploy>\nExample: \n        <!--\n        IMPORTANT: Only use this tool when:\n        1. The user explicitly requests permanent deployment to production\n        2. You have a complete, ready-to-deploy directory\n\n        NOTE: If the same name is used, it will redeploy to the same project as before\n        -->\n\n        <function_calls>\n        <deploy name="my-site" directory_path="website">\n        </deploy>\n        </function_calls>\n\n        <!-- Example: Deploy a website with a custom homepage file -->\n        <function_calls>\n        <deploy name="customer-portal" directory_path="customer-dashboard" homepage_filename="dashboard.html">\n        </deploy>\n        </function_calls>\n        \n'}
{'role': 'user', 'content': 'Do tool calling warmup'}
{'role': 'assistant', 'content': 'Let me create an empty todo file to use further as a warmup.\n<function_calls>\n<create-file file_path="todo.md">\n\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': 'This session is being continued from a previous conversation that ran out of context. The summary below covers the earlier portion of the conversation.\n\nAnalysis:\nLet me analyze this conversation chronologically:\n\n1. **Initial Context**: This is a continuation from a previous session building "SAMMS ENTERPRISE SOVEREIGN OPERATING SYSTEM (SESOS v6 OMEGA CONSTRAINED)" - a comprehensive ERP system with 27 core modules.\n\n2. **User Messages**:\n   - "Do tool calling warmup" - Initial test\n   - Context continuation message with detailed summary from previous session\n   - "Please continue where you left off." - Main instruction\n\n3. **My Actions in This Session**:\n   - Read todo.md to check current progress\n   - Found that Phase 2 (Services Layer) was complete\n   - Phase 3 (Frontend UI/UX) had items in progress\n   \n4. **Files Created**:\n   - `frontend/src/lib/actions.ts` - Action System for action-based UI\n   - `frontend/src/components/ui/quick-actions.tsx` - Quick Actions Menu\n   - `frontend/src/components/ai/ai-copilot.tsx` - AI Copilot component\n   - `frontend/src/components/dashboard/dashboard-builder.tsx` - Dashboard Builder\n   - `frontend/src/components/workflow/workflow-builder.tsx` - Visual Workflow Builder\n   - `frontend/src/components/forms/smart-forms.tsx` - Smart Forms System\n   - `frontend/src/components/decision-engine/decision-engine.tsx` - Decision Engine UI\n   - `frontend/src/components/visualization/company-graph.tsx` - Company Graph Visualization\n   - `frontend/src/components/notifications/notification-system.tsx` - Notification System\n   - `frontend/src/components/timemachine/time-machine.tsx` - Time Machine UI\n   - `frontend/src/components/permissions/permission-visualizer.tsx` - Permission Visualizer\n\n5. **Technical Patterns Used**:\n   - React functional components with TypeScript\n   - Zustand for state management\n   - React Hook Form with Zod validation\n   - Radix UI primitives for accessibility\n   - Tailwind CSS with CSS variables for theming\n   - Context API for component state sharing\n\n6. **Todo Progress Updates**:\n   - Attempted to update todo.md but first str-replace failed\n   - Fixed by checking current todo.md content and re-applying the update\n\n7. **Current State**:\n   - Completed: Action-based UI, AI Copilot, Dashboard Builder, Workflow Builder, Smart Forms, Decision Engine UI, Company Graph, Notification System, Time Machine UI, Permission Visualizer\n   - Remaining in Phase 3: Sandbox / Simulation Mode, Internal App Builder\n\n\n\n\nSummary:\n1. Primary Request and Intent:\n   The user is building "SAMMS ENTERPRISE SOVEREIGN OPERATING SYSTEM (SESOS v6 OMEGA CONSTRAINED)" - a comprehensive enterprise-grade ERP system with 27 core modules. The explicit instruction was "Please continue where you left off." The previous session had completed Phase 2 (Services Layer), and this session continues with Phase 3 (Frontend UI/UX System).\n\n2. Key Technical Concepts:\n   - Next.js 14 with App Router and TypeScript\n   - React functional components with hooks\n   - Zustand state management with devtools, persist, and immer middleware\n   - React Hook Form with Zod validation for forms\n   - Radix UI primitives for accessible components\n   - Tailwind CSS with CSS variables for theming\n   - Action-based UI pattern with centralized action registry\n   - Visual workflow builder with drag-and-drop nodes\n   - Smart forms with conditional rendering and AI assistance\n   - Decision engine with AI-powered recommendations\n   - Company graph visualization with SVG rendering\n   - Real-time notification system with context providers\n   - Time machine for historical data state viewing\n   - Permission visualization with matrix and tree views\n\n3. Files and Code Sections:\n\n   - `frontend/src/lib/actions.ts`\n     - Centralized action registry for action-based UI\n     - Provides contextual actions, keyboard shortcuts, and action handlers\n     - Key exports: `Action`, `ActionRegistry`, `ActionProvider`, `useActions`, `useKeyboardShortcuts`\n\n   - `frontend/src/components/ui/quick-actions.tsx`\n     - Quick Actions Menu component for contextual actions\n     - Exports: `QuickActionsButton`, `ActionToolbar`, `FloatingActionButton`, `ActionContextMenu`\n\n   - `frontend/src/components/ai/ai-copilot.tsx`\n     - Embedded AI assistant component\n     - Exports: `AICopilotPanel`, `AICopilotWidget`, `AIInsightCard`\n     - Features: Chat interface, AI suggestions, contextual recommendations\n\n   - `frontend/src/components/dashboard/dashboard-builder.tsx`\n     - Drag-and-drop dashboard customization\n     - Exports: `DashboardBuilder`, `DashboardViewer`\n     - Features: Widget palette, grid layout, zoom/preview modes\n\n   - `frontend/src/components/workflow/workflow-builder.tsx`\n     - Visual workflow editor for automation\n     - Exports: `WorkflowBuilder`, `WorkflowListItem`\n     - Features: Node types (trigger, condition, action), edge connections, zoom/pan\n\n   - `frontend/src/components/forms/smart-forms.tsx`\n     - Dynamic forms with validation and AI assistance\n     - Exports: `SmartForm`, `FormBuilder`, `invoiceFormDefinition`\n     - Features: Conditional fields, computed values, auto-save, AI suggestions\n\n   - `frontend/src/components/decision-engine/decision-engine.tsx`\n     - AI decision recommendations viewer\n     - Exports: `DecisionDashboard`, `DecisionCard`, `DecisionDetailDialog`, `sampleDecisions`\n     - Features: Decision factors, alternatives, execution plan, confidence scores\n\n   - `frontend/src/components/visualization/company-graph.tsx`\n     - Interactive company relationship graph\n     - Exports: `CompanyGraph`, `sampleGraphData`\n     - Features: Node types, edge rendering, zoom/pan, filters\n\n   - `frontend/src/components/notifications/notification-system.tsx`\n     - Real-time notification management\n     - Exports: `NotificationProvider`, `NotificationBell`, `NotificationPanel`, `NotificationCenter`, `sampleNotifications`\n     - Features: Notification types, priorities, channels, preferences\n\n   - `frontend/src/components/timemachine/time-machine.tsx`\n     - Historical data state viewer\n     - Exports: `TimeMachine`\n     - Features: Timeline visualization, time points, version comparison\n\n   - `frontend/src/components/permissions/permission-visualizer.tsx`\n     - Permission matrix and tree visualization\n     - Exports: `PermissionVisualizer`\n     - Features: Permission levels, role management, access checking\n\n4. Errors and fixes:\n   - **Todo.md str-replace failure**: First attempt to update todo.md failed because the search string didn\'t match the actual file content. Fixed by reading the current file content and updating with the correct search string.\n\n5. Problem Solving:\n   - Successfully identified where the previous session left off by reading todo.md\n   - Updated todo.md to accurately reflect completed work\n   - Systematically built out each Phase 3 frontend component\n   - Each component follows consistent patterns (TypeScript, Tailwind, Radix UI)\n\n6. All user messages:\n   - "Do tool calling warmup"\n   - [Context continuation message with detailed summary from previous session]\n   - "Please continue where you left off."\n\n7. Pending Tasks (from todo.md):\n   - Phase 3 (Frontend UI/UX): Sandbox / Simulation Mode, Internal App Builder\n   - Phase 4: AI System (all items pending)\n   - Phase 5: Testing & DevOps (all items pending)\n   - Phase 6: Final Verification (all items pending)\n\n8. Current Work:\n   Just completed creating the Permission Visualizer component at `frontend/src/components/permissions/permission-visualizer.tsx`. This was the 10th component created for Phase 3. The todo.md shows:\n   ```\n   ## Phase 3: Frontend UI/UX System\n   - [x] Command Center Dashboard\n   - [x] Global Search + Command Palette\n   - [x] Company Switcher\n   - [x] Action-based UI\n   - [x] Embedded AI Copilot\n   - [x] Drag-and-drop Dashboard Builder\n   - [x] Workflow Builder (visual)\n   - [x] Smart Forms System\n   - [x] Decision Engine UI\n   - [x] Company Graph Visualization\n   - [x] Notification System\n   - [x] Time Machine UI\n   - [x] Permission Visualizer\n   - [ ] Sandbox / Simulation Mode\n   - [ ] Internal App Builder\n   ```\n\n9. Optional Next Step:\n   Continue with Phase 3: Frontend UI/UX System - create the remaining two components:\n   - Sandbox / Simulation Mode - for testing scenarios in isolation\n   - Internal App Builder - for users to create custom internal applications\n   \n   This aligns with the user\'s instruction "Please continue where you left off." and the explicit task of completing Phase 3 as outlined in the todo.md.\n\n\n\nIf you need specific details from before compaction (like exact code snippets, error messages, or content you generated), read the full transcript at: /workspace/summarized_conversations/original_conversation_1775279289_8353.txt'}
{'role': 'assistant', 'content': "I'll continue building the SESOS v6 ERP system. Let me first check the current state of the todo.md file to see where we left off.\n\n<function_calls>\n<execute-command>\ncat todo.md\n</execute-command>\n</function_calls>"}
{'role': 'user', 'content': '<tool_result> <execute-command> ToolResult(success=True, output=\'{\\n  "output": "# SAMMS ENTERPRISE SOVEREIGN OPERATING SYSTEM - BUILD TRACKER\\\\n\\\\n## Phase 1: Project Setup & Infrastructure\\\\n- [x] Create folder structure\\\\n- [x] Backend core setup (FastAPI)\\\\n- [x] Frontend core setup (Next.js)\\\\n- [x] Database configuration\\\\n- [ ] Docker & Kubernetes configs\\\\n\\\\n## Phase 1.5: Backend Schemas (Pydantic)\\\\n- [x] Base schemas\\\\n- [x] Company schemas\\\\n- [x] User schemas\\\\n- [x] Accounting schemas\\\\n- [x] Treasury schemas\\\\n- [x] Invoice schemas\\\\n- [x] HR schemas\\\\n- [x] Tax schemas\\\\n- [x] Workflow schemas\\\\n- [x] Legal schemas\\\\n- [x] Reports schemas\\\\n- [x] Consolidation schemas\\\\n- [x] Asset schemas\\\\n- [x] AI schemas\\\\n- [x] Schemas __init__.py\\\\n\\\\n## Phase 1.6: Backend Repositories (Data Access Layer)\\\\n- [x] Base repository\\\\n- [x] Company repository\\\\n- [x] User repository\\\\n- [x] Account repository (includes JournalEntry)\\\\n- [x] Treasury repository\\\\n- [x] Invoice repository\\\\n- [x] HR repository\\\\n- [x] Tax repository\\\\n- [x] Workflow repository\\\\n- [x] Legal repository\\\\n- [x] Reports repository\\\\n- [x] Consolidation repository\\\\n- [x] Asset repository\\\\n- [x] AI repository\\\\n- [x] Repositories __init__.py\\\\n\\\\n## Phase 2: Services Layer (Business Logic)\\\\n- [x] Services __init__.py\\\\n- [x] Base service (common patterns, decorators)\\\\n- [x] Auth service (JWT, MFA, API keys)\\\\n- [x] Company service (CRUD, hierarchy, settings)\\\\n- [x] User service (CRUD, preferences, bulk ops)\\\\n- [x] Account service (double-entry accounting)\\\\n- [x] Treasury service (accounts, transactions, transfers)\\\\n- [x] Invoice service (billing, payments)\\\\n- [x] HR service (employees, payroll, attendance)\\\\n- [x] Tax service (calculations, filings, nexus)\\\\n- [x] Workflow service (definitions, executions, triggers)\\\\n- [x] Legal service (contracts, matters, compliance)\\\\n- [x] Reports service (templates, executions, dashboards)\\\\n- [x] Consolidation service (multi-company, eliminations)\\\\n- [x] Asset service (fixed assets, depreciation)\\\\n- [x] AI service (models, predictions, anomalies)\\\\n\\\\n## Phase 3: Frontend UI/UX System\\\\n- [x] Command Center Dashboard\\\\n- [x] Global Search + Command Palette\\\\n- [x] Company Switcher\\\\n- [x] Action-based UI\\\\n- [x] Embedded AI Copilot\\\\n- [x] Drag-and-drop Dashboard Builder\\\\n- [x] Workflow Builder (visual)\\\\n- [x] Smart Forms System\\\\n- [x] Decision Engine UI\\\\n- [x] Company Graph Visualization\\\\n- [x] Notification System\\\\n- [x] Time Machine UI\\\\n- [ ] Permission Visualizer\\\\n- [ ] Sandbox / Simulation Mode\\\\n- [ ] Internal App Builder\\\\n\\\\n## Phase 4: AI System\\\\n- [ ] Natural language commands\\\\n- [ ] Anomaly detection\\\\n- [ ] Forecasting\\\\n- [ ] Decision recommendations\\\\n- [ ] Explainability layer\\\\n- [ ] Contract analysis tool\\\\n\\\\n## Phase 5: Testing & DevOps\\\\n- [ ] Unit tests\\\\n- [ ] Integration tests\\\\n- [ ] Frontend tests\\\\n- [ ] CI/CD pipelines\\\\n\\\\n## Phase 6: Final Verification\\\\n- [ ] Verify all modules complete\\\\n- [ ] Verify all CRUD operations\\\\n- [ ] Verify all integrations\\\\n- [ ] Final system test",\\n  "exit_code": 0,\\n  "cwd": "/workspace"\\n}\') </execute-command> </tool_result>'}
{'role': 'assistant', 'content': 'I see the todo.md shows Permission Visualizer is still marked as incomplete, but according to the summary, it was already created. Let me verify if the file exists and then continue with the remaining Phase 3 tasks.\n\n<function_calls>\n<execute-command>\nls -la frontend/src/components/permissions/ 2>/dev/null || echo "Directory does not exist"\n</execute-command>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <execute-command> ToolResult(success=True, output=\'{\\n  "output": "total 40\\\\ndrwxr-xr-x  2 root root  4096 Apr  4 05:07 .\\\\ndrwxr-xr-x 15 root root  4096 Apr  4 05:07 ..\\\\n-rw-r--r--  1 root root 31047 Apr  4 05:07 permission-visualizer.tsx\\\\n",\\n  "exit_code": 0,\\n  "cwd": "/workspace"\\n}\') </execute-command> </tool_result>'}
{'role': 'assistant', 'content': 'The Permission Visualizer already exists. Let me update the todo.md to mark it complete and then continue with the remaining two Phase 3 components: Sandbox / Simulation Mode and Internal App Builder.\n\n<function_calls>\n<str-replace file_path="todo.md">\n<old_str>- [ ] Permission Visualizer\n- [ ] Sandbox / Simulation Mode\n- [ ] Internal App Builder</old_str>\n<new_str>- [x] Permission Visualizer\n- [ ] Sandbox / Simulation Mode\n- [ ] Internal App Builder</new_str>\n</str-replace>\n</function_calls>'}
{'role': 'user', 'content': "<tool_result> <str-replace> ToolResult(success=True, output='Replacement successful.') </str-replace> </tool_result>"}
{'role': 'assistant', 'content': 'Now let me create the Sandbox / Simulation Mode component. This will allow users to test scenarios in isolation before applying changes to production data.\n\n<function_calls>\n<create-file file_path="frontend/src/components/sandbox/sandbox-mode.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst SandboxConfigSchema = z.object({\n  id: z.string(),\n  name: z.string(),\n  description: z.string().optional(),\n  createdAt: z.date(),\n  updatedAt: z.date(),\n  expiresAt: z.date().optional(),\n  modules: z.array(z.enum([\n    \'accounting\', \'treasury\', \'invoicing\', \'hr\', \'tax\', \n    \'workflow\', \'legal\', \'reports\', \'consolidation\', \'assets\'\n  ])),\n  dataScope: z.enum([\'full\', \'partial\', \'minimal\']),\n  baseSnapshot: z.string().optional(), // Snapshot ID to base sandbox on\n  autoSync: z.boolean().default(false),\n  isolatedUsers: z.boolean().default(true),\n});\n\nconst SimulationScenarioSchema = z.object({\n  id: z.string(),\n  sandboxId: z.string(),\n  name: z.string(),\n  description: z.string().optional(),\n  type: z.enum([\n    \'financial_projection\',\n    \'budget_planning\',\n    \'merger_simulation\',\n    \'tax_scenario\',\n    \'cash_flow_forecast\',\n    \'payroll_simulation\',\n    \'custom\'\n  ]),\n  parameters: z.record(z.unknown()),\n  assumptions: z.array(z.object({\n    key: z.string(),\n    value: z.unknown(),\n    description: z.string().optional(),\n    confidence: z.number().min(0).max(1).optional(),\n  })),\n  status: z.enum([\'draft\', \'running\', \'completed\', \'failed\', \'paused\']),\n  progress: z.number().min(0).max(100),\n  results: z.record(z.unknown()).optional(),\n  createdAt: z.date(),\n  createdBy: z.string(),\n  completedAt: z.date().optional(),\n});\n\nconst SandboxStateSchema = z.object({\n  id: z.string(),\n  sandboxId: z.string(),\n  timestamp: z.date(),\n  changes: z.array(z.object({\n    module: z.string(),\n    entity: z.string(),\n    entityId: z.string(),\n    action: z.enum([\'create\', \'update\', \'delete\']),\n    before: z.record(z.unknown()).optional(),\n    after: z.record(z.unknown()).optional(),\n    userId: z.string(),\n  })),\n  checksum: z.string(),\n});\n\ntype SandboxConfig = z.infer<typeof SandboxConfigSchema>;\ntype SimulationScenario = z.infer<typeof SimulationScenarioSchema>;\ntype SandboxState = z.infer<typeof SandboxStateSchema>;\n\n// ============================================================================\n// SANDBOX STORE\n// ============================================================================\n\ninterface SandboxStore {\n  sandboxes: SandboxConfig[];\n  activeSandbox: SandboxConfig | null;\n  scenarios: SimulationScenario[];\n  activeScenario: SimulationScenario | null;\n  snapshots: SandboxState[];\n  isRunning: boolean;\n  \n  // Actions\n  createSandbox: (config: Omit<SandboxConfig, \'id\' | \'createdAt\' | \'updatedAt\'>) => string;\n  updateSandbox: (id: string, updates: Partial<SandboxConfig>) => void;\n  deleteSandbox: (id: string) => void;\n  setActiveSandbox: (sandbox: SandboxConfig | null) => void;\n  \n  createScenario: (scenario: Omit<SimulationScenario, \'id\' | \'createdAt\' | \'status\' | \'progress\'>) => string;\n  updateScenario: (id: string, updates: Partial<SimulationScenario>) => void;\n  deleteScenario: (id: string) => void;\n  setActiveScenario: (scenario: SimulationScenario | null) => void;\n  \n  runSimulation: (scenarioId: string) => Promise<void>;\n  pauseSimulation: (scenarioId: string) => void;\n  resumeSimulation: (scenarioId: string) => Promise<void>;\n  resetSimulation: (scenarioId: string) => void;\n  \n  createSnapshot: (sandboxId: string) => string;\n  restoreSnapshot: (snapshotId: string) => void;\n  rollbackSandbox: (steps: number) => void;\n  \n  applyToProduction: (sandboxId: string, changes: string[]) => Promise<void>;\n  exportSandbox: (sandboxId: string) => string;\n  importSandbox: (data: string) => string;\n}\n\nconst SandboxContext = createContext<SandboxStore | null>(null);\n\nexport const useSandbox = () => {\n  const context = useContext(SandboxContext);\n  if (!context) {\n    throw new Error(\'useSandbox must be used within a SandboxProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst sampleSandboxes: SandboxConfig[] = [\n  {\n    id: \'sb-001\',\n    name: \'Q4 Budget Planning\',\n    description: \'Testing budget scenarios for Q4 2024\',\n    createdAt: new Date(\'2024-01-15\'),\n    updatedAt: new Date(\'2024-01-20\'),\n    expiresAt: new Date(\'2024-03-15\'),\n    modules: [\'accounting\', \'treasury\', \'hr\'],\n    dataScope: \'partial\',\n    autoSync: false,\n    isolatedUsers: true,\n  },\n  {\n    id: \'sb-002\',\n    name: \'Merger Analysis - Acme Corp\',\n    description: \'Simulating merger with Acme Corporation\',\n    createdAt: new Date(\'2024-01-10\'),\n    updatedAt: new Date(\'2024-01-18\'),\n    modules: [\'accounting\', \'consolidation\', \'legal\', \'hr\'],\n    dataScope: \'full\',\n    autoSync: true,\n    isolatedUsers: true,\n  },\n  {\n    id: \'sb-003\',\n    name: \'Tax Reform Impact\',\n    description: \'Analyzing impact of proposed tax changes\',\n    createdAt: new Date(\'2024-01-12\'),\n    updatedAt: new Date(\'2024-01-12\'),\n    modules: [\'tax\', \'accounting\', \'treasury\'],\n    dataScope: \'minimal\',\n    autoSync: false,\n    isolatedUsers: false,\n  },\n];\n\nconst sampleScenarios: SimulationScenario[] = [\n  {\n    id: \'sc-001\',\n    sandboxId: \'sb-001\',\n    name: \'Conservative Growth\',\n    description: \'5% revenue growth scenario\',\n    type: \'budget_planning\',\n    parameters: {\n      revenueGrowth: 0.05,\n      expenseIncrease: 0.03,\n      headcountChange: 0,\n    },\n    assumptions: [\n      { key: \'market_conditions\', value: \'stable\', description: \'No major market disruptions\', confidence: 0.7 },\n      { key: \'inflation_rate\', value: 0.025, description: \'Expected inflation rate\', confidence: 0.8 },\n    ],\n    status: \'completed\',\n    progress: 100,\n    results: {\n      projectedRevenue: 12500000,\n      projectedExpenses: 8750000,\n      netIncome: 3750000,\n    },\n    createdAt: new Date(\'2024-01-16\'),\n    createdBy: \'user-001\',\n    completedAt: new Date(\'2024-01-16\'),\n  },\n  {\n    id: \'sc-002\',\n    sandboxId: \'sb-001\',\n    name: \'Aggressive Expansion\',\n    description: \'15% revenue growth with expansion\',\n    type: \'budget_planning\',\n    parameters: {\n      revenueGrowth: 0.15,\n      expenseIncrease: 0.12,\n      headcountChange: 10,\n    },\n    assumptions: [\n      { key: \'market_conditions\', value: \'favorable\', description: \'Market expansion opportunities\', confidence: 0.5 },\n      { key: \'hiring_capacity\', value: \'high\', description: \'Ability to hire 10 new employees\', confidence: 0.8 },\n    ],\n    status: \'running\',\n    progress: 65,\n    createdAt: new Date(\'2024-01-18\'),\n    createdBy: \'user-001\',\n  },\n  {\n    id: \'sc-003\',\n    sandboxId: \'sb-002\',\n    name: \'Full Integration\',\n    description: \'Complete merger integration simulation\',\n    type: \'merger_simulation\',\n    parameters: {\n      integrationTimeline: 18, // months\n      synergyTarget: 5000000,\n      retentionRate: 0.85,\n    },\n    assumptions: [\n      { key: \'regulatory_approval\', value: true, description: \'Assume regulatory approval\', confidence: 0.6 },\n      { key: \'cultural_alignment\', value: \'moderate\', description: \'Cultural integration challenges\', confidence: 0.5 },\n    ],\n    status: \'draft\',\n    progress: 0,\n    createdAt: new Date(\'2024-01-19\'),\n    createdBy: \'user-002\',\n  },\n];\n\n// ============================================================================\n// SANDBOX PROVIDER\n// ============================================================================\n\nexport const SandboxProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [sandboxes, setSandboxes] = useState<SandboxConfig[]>(sampleSandboxes);\n  const [activeSandbox, setActiveSandbox] = useState<SandboxConfig | null>(null);\n  const [scenarios, setScenarios] = useState<SimulationScenario[]>(sampleScenarios);\n  const [activeScenario, setActiveScenario] = useState<SimulationScenario | null>(null);\n  const [snapshots, setSnapshots] = useState<SandboxState[]>([]);\n  const [isRunning, setIsRunning] = useState(false);\n\n  const createSandbox = useCallback((config: Omit<SandboxConfig, \'id\' | \'createdAt\' | \'updatedAt\'>): string => {\n    const id = `sb-${Date.now()}`;\n    const now = new Date();\n    const newSandbox: SandboxConfig = {\n      ...config,\n      id,\n      createdAt: now,\n      updatedAt: now,\n    };\n    setSandboxes(prev => [...prev, newSandbox]);\n    return id;\n  }, []);\n\n  const updateSandbox = useCallback((id: string, updates: Partial<SandboxConfig>) => {\n    setSandboxes(prev => prev.map(sb => \n      sb.id === id ? { ...sb, ...updates, updatedAt: new Date() } : sb\n    ));\n  }, []);\n\n  const deleteSandbox = useCallback((id: string) => {\n    setSandboxes(prev => prev.filter(sb => sb.id !== id));\n    setScenarios(prev => prev.filter(sc => sc.sandboxId !== id));\n  }, []);\n\n  const createScenario = useCallback((scenario: Omit<SimulationScenario, \'id\' | \'createdAt\' | \'status\' | \'progress\'>): string => {\n    const id = `sc-${Date.now()}`;\n    const newScenario: SimulationScenario = {\n      ...scenario,\n      id,\n      createdAt: new Date(),\n      status: \'draft\',\n      progress: 0,\n    };\n    setScenarios(prev => [...prev, newScenario]);\n    return id;\n  }, []);\n\n  const updateScenario = useCallback((id: string, updates: Partial<SimulationScenario>) => {\n    setScenarios(prev => prev.map(sc => \n      sc.id === id ? { ...sc, ...updates } : sc\n    ));\n  }, []);\n\n  const deleteScenario = useCallback((id: string) => {\n    setScenarios(prev => prev.filter(sc => sc.id !== id));\n  }, []);\n\n  const runSimulation = useCallback(async (scenarioId: string) => {\n    setIsRunning(true);\n    updateScenario(scenarioId, { status: \'running\', progress: 0 });\n\n    // Simulate progressive execution\n    for (let progress = 0; progress <= 100; progress += 10) {\n      await new Promise(resolve => setTimeout(resolve, 500));\n      updateScenario(scenarioId, { progress });\n    }\n\n    updateScenario(scenarioId, { \n      status: \'completed\', \n      progress: 100,\n      completedAt: new Date(),\n      results: { simulated: true, timestamp: new Date().toISOString() }\n    });\n    setIsRunning(false);\n  }, [updateScenario]);\n\n  const pauseSimulation = useCallback((scenarioId: string) => {\n    updateScenario(scenarioId, { status: \'paused\' });\n  }, [updateScenario]);\n\n  const resumeSimulation = useCallback(async (scenarioId: string) => {\n    const scenario = scenarios.find(s => s.id === scenarioId);\n    if (scenario) {\n      updateScenario(scenarioId, { status: \'running\' });\n      // Continue from current progress\n      for (let progress = scenario.progress; progress <= 100; progress += 10) {\n        await new Promise(resolve => setTimeout(resolve, 500));\n        updateScenario(scenarioId, { progress });\n      }\n      updateScenario(scenarioId, { status: \'completed\', progress: 100, completedAt: new Date() });\n    }\n  }, [scenarios, updateScenario]);\n\n  const resetSimulation = useCallback((scenarioId: string) => {\n    updateScenario(scenarioId, { status: \'draft\', progress: 0, results: undefined, completedAt: undefined });\n  }, [updateScenario]);\n\n  const createSnapshot = useCallback((sandboxId: string): string => {\n    const id = `snap-${Date.now()}`;\n    const snapshot: SandboxState = {\n      id,\n      sandboxId,\n      timestamp: new Date(),\n      changes: [],\n      checksum: `chk-${Math.random().toString(36).substr(2, 9)}`,\n    };\n    setSnapshots(prev => [...prev, snapshot]);\n    return id;\n  }, []);\n\n  const restoreSnapshot = useCallback((snapshotId: string) => {\n    const snapshot = snapshots.find(s => s.id === snapshotId);\n    if (snapshot) {\n      // Restore state from snapshot\n      console.log(\'Restoring snapshot:\', snapshot);\n    }\n  }, [snapshots]);\n\n  const rollbackSandbox = useCallback((steps: number) => {\n    console.log(\'Rolling back\', steps, \'steps\');\n  }, []);\n\n  const applyToProduction = useCallback(async (sandboxId: string, changes: string[]) => {\n    setIsRunning(true);\n    // Simulate applying changes to production\n    await new Promise(resolve => setTimeout(resolve, 2000));\n    console.log(\'Applied changes to production:\', { sandboxId, changes });\n    setIsRunning(false);\n  }, []);\n\n  const exportSandbox = useCallback((sandboxId: string): string => {\n    const sandbox = sandboxes.find(s => s.id === sandboxId);\n    const sandboxScenarios = scenarios.filter(s => s.sandboxId === sandboxId);\n    return JSON.stringify({ sandbox, scenarios: sandboxScenarios }, null, 2);\n  }, [sandboxes, scenarios]);\n\n  const importSandbox = useCallback((data: string): string => {\n    const parsed = JSON.parse(data);\n    const id = createSandbox(parsed.sandbox);\n    if (parsed.scenarios) {\n      parsed.scenarios.forEach((sc: SimulationScenario) => {\n        createScenario({ ...sc, sandboxId: id });\n      });\n    }\n    return id;\n  }, [createSandbox, createScenario]);\n\n  const value = useMemo(() => ({\n    sandboxes,\n    activeSandbox,\n    scenarios,\n    activeScenario,\n    snapshots,\n    isRunning,\n    createSandbox,\n    updateSandbox,\n    deleteSandbox,\n    setActiveSandbox,\n    createScenario,\n    updateScenario,\n    deleteScenario,\n    setActiveScenario,\n    runSimulation,\n    pauseSimulation,\n    resumeSimulation,\n    resetSimulation,\n    createSnapshot,\n    restoreSnapshot,\n    rollbackSandbox,\n    applyToProduction,\n    exportSandbox,\n    importSandbox,\n  }), [\n    sandboxes, activeSandbox, scenarios, activeScenario, snapshots, isRunning,\n    createSandbox, updateSandbox, deleteSandbox, setActiveSandbox,\n    createScenario, updateScenario, deleteScenario, setActiveScenario,\n    runSimulation, pauseSimulation, resumeSimulation, resetSimulation,\n    createSnapshot, restoreSnapshot, rollbackSandbox,\n    applyToProduction, exportSandbox, importSandbox,\n  ]);\n\n  return (\n    <SandboxContext.Provider value={value}>\n      {children}\n    </SandboxContext.Provider>\n  );\n};\n\n// ============================================================================\n// SANDBOX LIST COMPONENT\n// ============================================================================\n\ninterface SandboxListProps {\n  onSelectSandbox: (sandbox: SandboxConfig) => void;\n  onCreateNew: () => void;\n}\n\nexport const SandboxList: React.FC<SandboxListProps> = ({ onSelectSandbox, onCreateNew }) => {\n  const { sandboxes, deleteSandbox } = useSandbox();\n\n  const getStatusColor = (sandbox: SandboxConfig) => {\n    if (sandbox.expiresAt && new Date() > sandbox.expiresAt) {\n      return \'text-red-500\';\n    }\n    return \'text-green-500\';\n  };\n\n  const formatDate = (date: Date) => {\n    return new Date(date).toLocaleDateString(\'en-US\', {\n      year: \'numeric\',\n      month: \'short\',\n      day: \'numeric\',\n    });\n  };\n\n  return (\n    <div className="space-y-4">\n      <div className="flex justify-between items-center">\n        <h2 className="text-xl font-semibold">Sandbox Environments</h2>\n        <button\n          onClick={onCreateNew}\n          className="px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600 transition-colors flex items-center gap-2"\n        >\n          <svg className="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">\n            <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M12 4v16m8-8H4" />\n          </svg>\n          New Sandbox\n        </button>\n      </div>\n\n      <div className="grid gap-4 md:grid-cols-2 lg:grid-cols-3">\n        {sandboxes.map(sandbox => (\n          <div\n            key={sandbox.id}\n            className="border rounded-lg p-4 hover:shadow-lg transition-shadow cursor-pointer bg-white"\n            onClick={() => onSelectSandbox(sandbox)}\n          >\n            <div className="flex justify-between items-start mb-2">\n              <h3 className="font-medium text-lg">{sandbox.name}</h3>\n              <span className={`w-2 h-2 rounded-full ${getStatusColor(sandbox)} bg-current`} />\n            </div>\n            \n            {sandbox.description && (\n              <p className="text-sm text-gray-600 mb-3">{sandbox.description}</p>\n            )}\n\n            <div className="flex flex-wrap gap-1 mb-3">\n              {sandbox.modules.slice(0, 3).map(module => (\n                <span\n                  key={module}\n                  className="px-2 py-0.5 text-xs bg-gray-100 rounded-full"\n                >\n                  {module}\n                </span>\n              ))}\n              {sandbox.modules.length > 3 && (\n                <span className="px-2 py-0.5 text-xs bg-gray-100 rounded-full">\n                  +{sandbox.modules.length - 3}\n                </span>\n              )}\n            </div>\n\n            <div className="flex justify-between items-center text-sm text-gray-500">\n              <span>Created: {formatDate(sandbox.createdAt)}</span>\n              {sandbox.expiresAt && (\n                <span className="text-orange-500">\n                  Expires: {formatDate(sandbox.expiresAt)}\n                </span>\n              )}\n            </div>\n\n            <div className="mt-3 flex gap-2">\n              <button\n                onClick={(e) => {\n                  e.stopPropagation();\n                  onSelectSandbox(sandbox);\n                }}\n                className="flex-1 px-3 py-1.5 text-sm bg-blue-50 text-blue-600 rounded hover:bg-blue-100 transition-colors"\n              >\n                Open\n              </button>\n              <button\n                onClick={(e) => {\n                  e.stopPropagation();\n                  if (confirm(\'Delete this sandbox?\')) {\n                    deleteSandbox(sandbox.id);\n                  }\n                }}\n                className="px-3 py-1.5 text-sm bg-red-50 text-red-600 rounded hover:bg-red-100 transition-colors"\n              >\n                Delete\n              </button>\n            </div>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// SANDBOX WORKSPACE COMPONENT\n// ============================================================================\n\ninterface SandboxWorkspaceProps {\n  sandbox: SandboxConfig;\n  onBack: () => void;\n}\n\nexport const SandboxWorkspace: React.FC<SandboxWorkspaceProps> = ({ sandbox, onBack }) => {\n  const { \n    scenarios, \n    createScenario, \n    runSimulation, \n    pauseSimulation, \n    resumeSimulation,\n    resetSimulation,\n    createSnapshot,\n    applyToProduction,\n    exportSandbox,\n    isRunning,\n  } = useSandbox();\n\n  const [activeTab, setActiveTab] = useState<\'scenarios\' | \'data\' | \'changes\' | \'settings\'>(\'scenarios\');\n  const [selectedScenario, setSelectedScenario] = useState<SimulationScenario | null>(null);\n\n  const sandboxScenarios = scenarios.filter(s => s.sandboxId === sandbox.id);\n\n  const handleCreateScenario = () => {\n    const id = createScenario({\n      sandboxId: sandbox.id,\n      name: \'New Scenario\',\n      type: \'custom\',\n      parameters: {},\n      assumptions: [],\n      createdBy: \'current-user\',\n    });\n    const newScenario = scenarios.find(s => s.id === id);\n    if (newScenario) setSelectedScenario(newScenario);\n  };\n\n  const getStatusBadge = (status: SimulationScenario[\'status\']) => {\n    const colors: Record<string, string> = {\n      draft: \'bg-gray-100 text-gray-700\',\n      running: \'bg-blue-100 text-blue-700\',\n      completed: \'bg-green-100 text-green-700\',\n      failed: \'bg-red-100 text-red-700\',\n      paused: \'bg-yellow-100 text-yellow-700\',\n    };\n    return (\n      <span className={`px-2 py-0.5 text-xs font-medium rounded-full ${colors[status]}`}>\n        {status.charAt(0).toUpperCase() + status.slice(1)}\n      </span>\n    );\n  };\n\n  return (\n    <div className="h-full flex flex-col">\n      {/* Header */}\n      <div className="border-b bg-gray-50 px-6 py-4">\n        <div className="flex items-center gap-4">\n          <button\n            onClick={onBack}\n            className="p-2 hover:bg-gray-200 rounded-lg transition-colors"\n          >\n            <svg className="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">\n              <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M15 19l-7-7 7-7" />\n            </svg>\n          </button>\n          <div className="flex-1">\n            <h1 className="text-xl font-semibold">{sandbox.name}</h1>\n            {sandbox.description && (\n              <p className="text-sm text-gray-600">{sandbox.description}</p>\n            )}\n          </div>\n          <div className="flex gap-2">\n            <button\n              onClick={() => createSnapshot(sandbox.id)}\n              className="px-3 py-1.5 text-sm border rounded-lg hover:bg-gray-100 transition-colors"\n            >\n              Create Snapshot\n            </button>\n            <button\n              onClick={() => {\n                const data = exportSandbox(sandbox.id);\n                const blob = new Blob([data], { type: \'application/json\' });\n                const url = URL.createObjectURL(blob);\n                const a = document.createElement(\'a\');\n                a.href = url;\n                a.download = `${sandbox.name.replace(/\\s+/g, \'-\')}-sandbox.json`;\n                a.click();\n              }}\n              className="px-3 py-1.5 text-sm border rounded-lg hover:bg-gray-100 transition-colors"\n            >\n              Export\n            </button>\n            <button\n              onClick={() => applyToProduction(sandbox.id, [])}\n              disabled={isRunning}\n              className="px-3 py-1.5 text-sm bg-green-500 text-white rounded-lg hover:bg-green-600 transition-colors disabled:opacity-50"\n            >\n              Apply to Production\n            </button>\n          </div>\n        </div>\n\n        {/* Tabs */}\n        <div className="flex gap-1 mt-4">\n          {([\'scenarios\', \'data\', \'changes\', \'settings\'] as const).map(tab => (\n            <button\n              key={tab}\n              onClick={() => setActiveTab(tab)}\n              className={`px-4 py-2 text-sm font-medium rounded-t-lg transition-colors ${\n                activeTab === tab\n                  ? \'bg-white border border-b-white -mb-px\'\n                  : \'text-gray-600 hover:text-gray-900\'\n              }`}\n            >\n              {tab.charAt(0).toUpperCase() + tab.slice(1)}\n            </button>\n          ))}\n        </div>\n      </div>\n\n      {/* Content */}\n      <div className="flex-1 overflow-auto p-6">\n        {activeTab === \'scenarios\' && (\n          <div className="space-y-4">\n            <div className="flex justify-between items-center">\n              <h2 className="text-lg font-medium">Simulation Scenarios</h2>\n              <button\n                onClick={handleCreateScenario}\n                className="px-3 py-1.5 text-sm bg-blue-500 text-white rounded-lg hover:bg-blue-600 transition-colors"\n              >\n                Create Scenario\n              </button>\n            </div>\n\n            <div className="grid gap-4">\n              {sandboxScenarios.map(scenario => (\n                <div\n                  key={scenario.id}\n                  className="border rounded-lg p-4 hover:shadow-md transition-shadow bg-white"\n                >\n                  <div className="flex justify-between items-start">\n                    <div>\n                      <div className="flex items-center gap-2">\n                        <h3 className="font-medium">{scenario.name}</h3>\n                        {getStatusBadge(scenario.status)}\n                      </div>\n                      {scenario.description && (\n                        <p className="text-sm text-gray-600 mt-1">{scenario.description}</p>\n                      )}\n                    </div>\n                    <div className="flex gap-2">\n                      {scenario.status === \'draft\' && (\n                        <button\n                          onClick={() => runSimulation(scenario.id)}\n                          disabled={isRunning}\n                          className="px-3 py-1 text-sm bg-green-500 text-white rounded hover:bg-green-600 disabled:opacity-50"\n                        >\n                          Run\n                        </button>\n                      )}\n                      {scenario.status === \'running\' && (\n                        <button\n                          onClick={() => pauseSimulation(scenario.id)}\n                          className="px-3 py-1 text-sm bg-yellow-500 text-white rounded hover:bg-yellow-600"\n                        >\n                          Pause\n                        </button>\n                      )}\n                      {scenario.status === \'paused\' && (\n                        <button\n                          onClick={() => resumeSimulation(scenario.id)}\n                          disabled={isRunning}\n                          className="px-3 py-1 text-sm bg-blue-500 text-white rounded hover:bg-blue-600 disabled:opacity-50"\n                        >\n                          Resume\n                        </button>\n                      )}\n                      {scenario.status === \'completed\' && (\n                        <button\n                          onClick={() => resetSimulation(scenario.id)}\n                          className="px-3 py-1 text-sm border rounded hover:bg-gray-100"\n                        >\n                          Reset\n                        </button>\n                      )}\n                      <button\n                        onClick={() => setSelectedScenario(scenario)}\n                        className="px-3 py-1 text-sm border rounded hover:bg-gray-100"\n                      >\n                        Details\n                      </button>\n                    </div>\n                  </div>\n\n                  {/* Progress bar */}\n                  {scenario.status === \'running\' && (\n                    <div className="mt-3">\n                      <div className="flex justify-between text-sm text-gray-600 mb-1">\n                        <span>Progress</span>\n                        <span>{scenario.progress}%</span>\n                      </div>\n                      <div className="w-full bg-gray-200 rounded-full h-2">\n                        <div\n                          className="bg-blue-500 h-2 rounded-full transition-all duration-500"\n                          style={{ width: `${scenario.progress}%` }}\n                        />\n                      </div>\n                    </div>\n                  )}\n\n                  {/* Results preview */}\n                  {scenario.status === \'completed\' && scenario.results && (\n                    <div className="mt-3 p-3 bg-green-50 rounded-lg">\n                      <h4 className="text-sm font-medium text-green-800 mb-2">Results</h4>\n                      <pre className="text-xs text-green-700 overflow-auto">\n                        {JSON.stringify(scenario.results, null, 2)}\n                      </pre>\n                    </div>\n                  )}\n\n                  {/* Assumptions */}\n                  {scenario.assumptions.length > 0 && (\n                    <div className="mt-3">\n                      <h4 className="text-xs font-medium text-gray-500 mb-1">ASSUMPTIONS</h4>\n                      <div className="flex flex-wrap gap-2">\n                        {scenario.assumptions.map((assumption, idx) => (\n                          <span\n                            key={idx}\n                            className="px-2 py-0.5 text-xs bg-gray-100 rounded"\n                            title={assumption.description}\n                          >\n                            {assumption.key}: {String(assumption.value)}\n                            {assumption.confidence && (\n                              <span className="ml-1 text-gray-500">\n                                ({Math.round(assumption.confidence * 100)}%)\n                              </span>\n                            )}\n                          </span>\n                        ))}\n                      </div>\n                    </div>\n                  )}\n                </div>\n              ))}\n            </div>\n          </div>\n        )}\n\n        {activeTab === \'data\' && (\n          <div className="text-center py-12 text-gray-500">\n            <svg className="w-16 h-16 mx-auto mb-4 text-gray-300" fill="none" stroke="currentColor" viewBox="0 0 24 24">\n              <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={1.5} d="M4 7v10c0 2.21 3.582 4 8 4s8-1.79 8-4V7M4 7c0 2.21 3.582 4 8 4s8-1.79 8-4M4 7c0-2.21 3.582-4 8-4s8 1.79 8 4" />\n            </svg>\n            <h3 className="text-lg font-medium mb-2">Sandbox Data</h3>\n            <p>View and manage isolated data for this sandbox environment.</p>\n          </div>\n        )}\n\n        {activeTab === \'changes\' && (\n          <div className="text-center py-12 text-gray-500">\n            <svg className="w-16 h-16 mx-auto mb-4 text-gray-300" fill="none" stroke="currentColor" viewBox="0 0 24 24">\n              <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={1.5} d="M9 5H7a2 2 0 00-2 2v12a2 2 0 002 2h10a2 2 0 002-2V7a2 2 0 00-2-2h-2M9 5a2 2 0 002 2h2a2 2 0 002-2M9 5a2 2 0 012-2h2a2 2 0 012 2" />\n            </svg>\n            <h3 className="text-lg font-medium mb-2">Change History</h3>\n            <p>Track all changes made within this sandbox environment.</p>\n          </div>\n        )}\n\n        {activeTab === \'settings\' && (\n          <div className="max-w-2xl">\n            <h2 className="text-lg font-medium mb-4">Sandbox Settings</h2>\n            <div className="space-y-4">\n              <div>\n                <label className="block text-sm font-medium text-gray-700 mb-1">Name</label>\n                <input\n                  type="text"\n                  defaultValue={sandbox.name}\n                  className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-blue-500"\n                />\n              </div>\n              <div>\n                <label className="block text-sm font-medium text-gray-700 mb-1">Description</label>\n                <textarea\n                  defaultValue={sandbox.description}\n                  rows={3}\n                  className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-blue-500"\n                />\n              </div>\n              <div>\n                <label className="block text-sm font-medium text-gray-700 mb-1">Expiration Date</label>\n                <input\n                  type="date"\n                  defaultValue={sandbox.expiresAt?.toISOString().split(\'T\')[0]}\n                  className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-blue-500"\n                />\n              </div>\n              <div className="flex items-center gap-2">\n                <input\n                  type="checkbox"\n                  id="autoSync"\n                  defaultChecked={sandbox.autoSync}\n                  className="rounded border-gray-300"\n                />\n                <label htmlFor="autoSync" className="text-sm text-gray-700">\n                  Auto-sync with production data\n                </label>\n              </div>\n              <div className="flex items-center gap-2">\n                <input\n                  type="checkbox"\n                  id="isolatedUsers"\n                  defaultChecked={sandbox.isolatedUsers}\n                  className="rounded border-gray-300"\n                />\n                <label htmlFor="isolatedUsers" className="text-sm text-gray-700">\n                  Isolate user permissions\n                </label>\n              </div>\n            </div>\n          </div>\n        )}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// CREATE SANDBOX DIALOG\n// ============================================================================\n\ninterface CreateSandboxDialogProps {\n  isOpen: boolean;\n  onClose: () => void;\n  onCreate: (config: Omit<SandboxConfig, \'id\' | \'createdAt\' | \'updatedAt\'>) => void;\n}\n\nexport const CreateSandboxDialog: React.FC<CreateSandboxDialogProps> = ({ \n  isOpen, \n  onClose, \n  onCreate \n}) => {\n  const [name, setName] = useState(\'\');\n  const [description, setDescription] = useState(\'\');\n  const [modules, setModules] = useState<string[]>([]);\n  const [dataScope, setDataScope] = useState<\'full\' | \'partial\' | \'minimal\'>(\'partial\');\n\n  const moduleOptions = [\n    { value: \'accounting\', label: \'Accounting\' },\n    { value: \'treasury\', label: \'Treasury\' },\n    { value: \'invoicing\', label: \'Invoicing\' },\n    { value: \'hr\', label: \'Human Resources\' },\n    { value: \'tax\', label: \'Tax Management\' },\n    { value: \'workflow\', label: \'Workflow\' },\n    { value: \'legal\', label: \'Legal\' },\n    { value: \'reports\', label: \'Reports\' },\n    { value: \'consolidation\', label: \'Consolidation\' },\n    { value: \'assets\', label: \'Fixed Assets\' },\n  ];\n\n  const handleCreate = () => {\n    onCreate({\n      name,\n      description,\n      modules: modules as SandboxConfig[\'modules\'],\n      dataScope,\n      autoSync: false,\n      isolatedUsers: true,\n    });\n    setName(\'\');\n    setDescription(\'\');\n    setModules([]);\n    setDataScope(\'partial\');\n    onClose();\n  };\n\n  if (!isOpen) return null;\n\n  return (\n    <div className="fixed inset-0 bg-black/50 flex items-center justify-center z-50">\n      <div className="bg-white rounded-lg shadow-xl w-full max-w-lg">\n        <div className="px-6 py-4 border-b">\n          <h2 className="text-lg font-semibold">Create New Sandbox</h2>\n        </div>\n        \n        <div className="p-6 space-y-4">\n          <div>\n            <label className="block text-sm font-medium text-gray-700 mb-1">\n              Name <span className="text-red-500">*</span>\n            </label>\n            <input\n              type="text"\n              value={name}\n              onChange={(e) => setName(e.target.value)}\n              placeholder="Enter sandbox name"\n              className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-blue-500"\n            />\n          </div>\n\n          <div>\n            <label className="block text-sm font-medium text-gray-700 mb-1">Description</label>\n            <textarea\n              value={description}\n              onChange={(e) => setDescription(e.target.value)}\n              placeholder="Describe the purpose of this sandbox"\n              rows={2}\n              className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-blue-500"\n            />\n          </div>\n\n          <div>\n            <label className="block text-sm font-medium text-gray-700 mb-2">Modules</label>\n            <div className="grid grid-cols-2 gap-2">\n              {moduleOptions.map(option => (\n                <label key={option.value} className="flex items-center gap-2 p-2 border rounded hover:bg-gray-50 cursor-pointer">\n                  <input\n                    type="checkbox"\n                    checked={modules.includes(option.value)}\n                    onChange={(e) => {\n                      if (e.target.checked) {\n                        setModules([...modules, option.value]);\n                      } else {\n                        setModules(modules.filter(m => m !== option.value));\n                      }\n                    }}\n                    className="rounded border-gray-300"\n                  />\n                  <span className="text-sm">{option.label}</span>\n                </label>\n              ))}\n            </div>\n          </div>\n\n          <div>\n            <label className="block text-sm font-medium text-gray-700 mb-1">Data Scope</label>\n            <select\n              value={dataScope}\n              onChange={(e) => setDataScope(e.target.value as typeof dataScope)}\n              className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-blue-500"\n            >\n              <option value="minimal">Minimal - Essential data only</option>\n              <option value="partial">Partial - Representative sample</option>\n              <option value="full">Full - Complete data copy</option>\n            </select>\n          </div>\n        </div>\n\n        <div className="px-6 py-4 border-t bg-gray-50 rounded-b-lg flex justify-end gap-3">\n          <button\n            onClick={onClose}\n            className="px-4 py-2 text-sm border rounded-lg hover:bg-gray-100 transition-colors"\n          >\n            Cancel\n          </button>\n          <button\n            onClick={handleCreate}\n            disabled={!name.trim() || modules.length === 0}\n            className="px-4 py-2 text-sm bg-blue-500 text-white rounded-lg hover:bg-blue-600 transition-colors disabled:opacity-50"\n          >\n            Create Sandbox\n          </button>\n        </div>\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN SANDBOX MODE COMPONENT\n// ============================================================================\n\nexport const SandboxMode: React.FC = () => {\n  const { setActiveSandbox, createSandbox } = useSandbox();\n  const [view, setView] = useState<\'list\' | \'workspace\'>(\'list\');\n  const [selectedSandbox, setSelectedSandbox] = useState<SandboxConfig | null>(null);\n  const [showCreateDialog, setShowCreateDialog] = useState(false);\n\n  const handleSelectSandbox = (sandbox: SandboxConfig) => {\n    setSelectedSandbox(sandbox);\n    setActiveSandbox(sandbox);\n    setView(\'workspace\');\n  };\n\n  const handleCreateSandbox = (config: Omit<SandboxConfig, \'id\' | \'createdAt\' | \'updatedAt\'>) => {\n    createSandbox(config);\n  };\n\n  const handleBack = () => {\n    setView(\'list\');\n    setSelectedSandbox(null);\n    setActiveSandbox(null);\n  };\n\n  return (\n    <div className="h-screen bg-gray-100">\n      {view === \'list\' && (\n        <div className="p-6">\n          <SandboxList\n            onSelectSandbox={handleSelectSandbox}\n            onCreateNew={() => setShowCreateDialog(true)}\n          />\n        </div>\n      )}\n\n      {view === \'workspace\' && selectedSandbox && (\n        <SandboxWorkspace\n          sandbox={selectedSandbox}\n          onBack={handleBack}\n        />\n      )}\n\n      <CreateSandboxDialog\n        isOpen={showCreateDialog}\n        onClose={() => setShowCreateDialog(false)}\n        onCreate={handleCreateSandbox}\n      />\n    </div>\n  );\n};\n\nexport default SandboxMode;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/sandbox/sandbox-mode.tsx\' created successfully.") </create-file> </tool_result>'}
{'role': 'assistant', 'content': 'Now let me create the Internal App Builder component. This will allow users to create custom internal applications without coding.\n\n<function_calls>\n<create-file file_path="frontend/src/components/appbuilder/internal-app-builder.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo, useRef, useEffect } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst ComponentSchema = z.object({\n  id: z.string(),\n  type: z.enum([\n    \'container\', \'text\', \'heading\', \'button\', \'input\', \'select\', \n    \'table\', \'form\', \'chart\', \'image\', \'divider\', \'spacer\',\n    \'tabs\', \'accordion\', \'modal\', \'card\', \'list\', \'grid\',\n    \'date-picker\', \'file-upload\', \'checkbox\', \'radio\', \'toggle\',\n    \'badge\', \'progress\', \'alert\', \'tooltip\', \'widget\'\n  ]),\n  label: z.string(),\n  props: z.record(z.unknown()),\n  styles: z.object({\n    width: z.string().optional(),\n    height: z.string().optional(),\n    padding: z.string().optional(),\n    margin: z.string().optional(),\n    backgroundColor: z.string().optional(),\n    color: z.string().optional(),\n    fontSize: z.string().optional(),\n    fontWeight: z.string().optional(),\n    borderRadius: z.string().optional(),\n    border: z.string().optional(),\n    display: z.string().optional(),\n    flexDirection: z.string().optional(),\n    justifyContent: z.string().optional(),\n    alignItems: z.string().optional(),\n    gap: z.string().optional(),\n  }).optional(),\n  children: z.array(z.string()).optional(), // IDs of child components\n  parentId: z.string().nullable().optional(),\n  bindings: z.array(z.object({\n    property: z.string(),\n    source: z.string(),\n    transform: z.string().optional(),\n  })).optional(),\n  events: z.array(z.object({\n    type: z.string(),\n    action: z.string(),\n    params: z.record(z.unknown()).optional(),\n  })).optional(),\n});\n\nconst DataSourceSchema = z.object({\n  id: z.string(),\n  name: z.string(),\n  type: z.enum([\'api\', \'database\', \'static\', \'function\', \'webhook\']),\n  config: z.record(z.unknown()),\n  refreshInterval: z.number().optional(),\n  cacheEnabled: z.boolean().optional(),\n});\n\nconst AppDefinitionSchema = z.object({\n  id: z.string(),\n  name: z.string(),\n  description: z.string().optional(),\n  version: z.string(),\n  createdAt: z.date(),\n  updatedAt: z.date(),\n  createdBy: z.string(),\n  status: z.enum([\'draft\', \'published\', \'archived\']),\n  components: z.record(ComponentSchema),\n  rootComponent: z.string(),\n  dataSources: z.array(DataSourceSchema),\n  variables: z.record(z.unknown()),\n  routes: z.array(z.object({\n    path: z.string(),\n    component: z.string(),\n    label: z.string().optional(),\n  })).optional(),\n  permissions: z.object({\n    view: z.array(z.string()),\n    edit: z.array(z.string()),\n    admin: z.array(z.string()),\n  }).optional(),\n});\n\ntype Component = z.infer<typeof ComponentSchema>;\ntype DataSource = z.infer<typeof DataSourceSchema>;\ntype AppDefinition = z.infer<typeof AppDefinitionSchema>;\n\n// ============================================================================\n// APP BUILDER STORE\n// ============================================================================\n\ninterface AppBuilderStore {\n  apps: AppDefinition[];\n  currentApp: AppDefinition | null;\n  selectedComponent: Component | null;\n  clipboard: Component | null;\n  history: { app: AppDefinition; description: string }[];\n  historyIndex: number;\n  previewMode: boolean;\n  \n  // App Actions\n  createApp: (name: string, description?: string) => string;\n  loadApp: (appId: string) => void;\n  saveApp: () => void;\n  publishApp: () => void;\n  deleteApp: (appId: string) => void;\n  \n  // Component Actions\n  addComponent: (type: Component[\'type\'], parentId?: string) => string;\n  updateComponent: (id: string, updates: Partial<Component>) => void;\n  deleteComponent: (id: string) => void;\n  duplicateComponent: (id: string) => string | null;\n  moveComponent: (id: string, newParentId: string, index?: number) => void;\n  selectComponent: (component: Component | null) => void;\n  \n  // Clipboard Actions\n  copyComponent: (id: string) => void;\n  pasteComponent: (parentId?: string) => string | null;\n  cutComponent: (id: string) => void;\n  \n  // History Actions\n  undo: () => void;\n  redo: () => void;\n  canUndo: () => boolean;\n  canRedo: () => boolean;\n  \n  // Preview Actions\n  togglePreview: () => void;\n  \n  // Data Source Actions\n  addDataSource: (source: Omit<DataSource, \'id\'>) => string;\n  updateDataSource: (id: string, updates: Partial<DataSource>) => void;\n  removeDataSource: (id: string) => void;\n  \n  // Export/Import\n  exportApp: (appId: string) => string;\n  importApp: (data: string) => string;\n}\n\nconst AppBuilderContext = createContext<AppBuilderStore | null>(null);\n\nexport const useAppBuilder = () => {\n  const context = useContext(AppBuilderContext);\n  if (!context) {\n    throw new Error(\'useAppBuilder must be used within AppBuilderProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst createDefaultApp = (): AppDefinition => {\n  const rootId = \'root\';\n  return {\n    id: \'app-default\',\n    name: \'Untitled App\',\n    description: \'A new internal application\',\n    version: \'1.0.0\',\n    createdAt: new Date(),\n    updatedAt: new Date(),\n    createdBy: \'current-user\',\n    status: \'draft\',\n    components: {\n      [rootId]: {\n        id: rootId,\n        type: \'container\',\n        label: \'Root Container\',\n        props: {},\n        styles: {\n          padding: \'16px\',\n          display: \'flex\',\n          flexDirection: \'column\',\n          gap: \'16px\',\n        },\n        children: [],\n        parentId: null,\n      },\n    },\n    rootComponent: rootId,\n    dataSources: [],\n    variables: {},\n  };\n};\n\nconst sampleApps: AppDefinition[] = [\n  {\n    id: \'app-001\',\n    name: \'Employee Directory\',\n    description: \'Browse and search employee information\',\n    version: \'1.2.0\',\n    createdAt: new Date(\'2024-01-10\'),\n    updatedAt: new Date(\'2024-01-15\'),\n    createdBy: \'user-001\',\n    status: \'published\',\n    components: {\n      \'root\': {\n        id: \'root\',\n        type: \'container\',\n        label: \'Root\',\n        props: {},\n        styles: { padding: \'24px\', display: \'flex\', flexDirection: \'column\', gap: \'16px\' },\n        children: [\'header\', \'search-bar\', \'employee-grid\'],\n        parentId: null,\n      },\n      \'header\': {\n        id: \'header\',\n        type: \'heading\',\n        label: \'Page Title\',\n        props: { text: \'Employee Directory\', level: 1 },\n        styles: { fontSize: \'24px\', fontWeight: \'bold\' },\n        parentId: \'root\',\n      },\n      \'search-bar\': {\n        id: \'search-bar\',\n        type: \'input\',\n        label: \'Search Input\',\n        props: { placeholder: \'Search employees...\' },\n        styles: { width: \'300px\' },\n        bindings: [{ property: \'value\', source: \'searchQuery\' }],\n        parentId: \'root\',\n      },\n      \'employee-grid\': {\n        id: \'employee-grid\',\n        type: \'grid\',\n        label: \'Employee Cards\',\n        props: { columns: 3 },\n        styles: { gap: \'16px\' },\n        children: [],\n        parentId: \'root\',\n      },\n    },\n    rootComponent: \'root\',\n    dataSources: [\n      { id: \'ds-001\', name: \'Employees\', type: \'database\', config: { table: \'employees\' }, refreshInterval: 300 },\n    ],\n    variables: { searchQuery: \'\' },\n  },\n  {\n    id: \'app-002\',\n    name: \'Expense Tracker\',\n    description: \'Track and manage business expenses\',\n    version: \'2.0.0\',\n    createdAt: new Date(\'2024-01-05\'),\n    updatedAt: new Date(\'2024-01-12\'),\n    createdBy: \'user-002\',\n    status: \'published\',\n    components: {\n      \'root\': {\n        id: \'root\',\n        type: \'container\',\n        label: \'Root\',\n        props: {},\n        styles: { padding: \'24px\' },\n        children: [\'expense-form\', \'expense-list\'],\n        parentId: null,\n      },\n      \'expense-form\': {\n        id: \'expense-form\',\n        type: \'form\',\n        label: \'Add Expense\',\n        props: {},\n        children: [],\n        parentId: \'root\',\n      },\n      \'expense-list\': {\n        id: \'expense-list\',\n        type: \'table\',\n        label: \'Expenses Table\',\n        props: { dataSource: \'expenses\' },\n        parentId: \'root\',\n      },\n    },\n    rootComponent: \'root\',\n    dataSources: [\n      { id: \'ds-002\', name: \'Expenses\', type: \'database\', config: { table: \'expenses\' } },\n    ],\n    variables: {},\n  },\n];\n\n// ============================================================================\n// APP BUILDER PROVIDER\n// ============================================================================\n\nexport const AppBuilderProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [apps, setApps] = useState<AppDefinition[]>(sampleApps);\n  const [currentApp, setCurrentApp] = useState<AppDefinition | null>(null);\n  const [selectedComponent, setSelectedComponent] = useState<Component | null>(null);\n  const [clipboard, setClipboard] = useState<Component | null>(null);\n  const [history, setHistory] = useState<{ app: AppDefinition; description: string }[]>([]);\n  const [historyIndex, setHistoryIndex] = useState(-1);\n  const [previewMode, setPreviewMode] = useState(false);\n\n  // Push to history\n  const pushHistory = useCallback((app: AppDefinition, description: string) => {\n    setHistory(prev => {\n      const newHistory = prev.slice(0, historyIndex + 1);\n      newHistory.push({ app: JSON.parse(JSON.stringify(app)), description });\n      return newHistory.slice(-50); // Keep last 50 states\n    });\n    setHistoryIndex(prev => Math.min(prev + 1, 49));\n  }, [historyIndex]);\n\n  // App Actions\n  const createApp = useCallback((name: string, description?: string): string => {\n    const id = `app-${Date.now()}`;\n    const newApp = createDefaultApp();\n    newApp.id = id;\n    newApp.name = name;\n    newApp.description = description;\n    setApps(prev => [...prev, newApp]);\n    setCurrentApp(newApp);\n    pushHistory(newApp, \'Created app\');\n    return id;\n  }, [pushHistory]);\n\n  const loadApp = useCallback((appId: string) => {\n    const app = apps.find(a => a.id === appId);\n    if (app) {\n      setCurrentApp(JSON.parse(JSON.stringify(app)));\n      setHistory([]);\n      setHistoryIndex(-1);\n    }\n  }, [apps]);\n\n  const saveApp = useCallback(() => {\n    if (!currentApp) return;\n    setApps(prev => prev.map(app => \n      app.id === currentApp.id \n        ? { ...currentApp, updatedAt: new Date() }\n        : app\n    ));\n  }, [currentApp]);\n\n  const publishApp = useCallback(() => {\n    if (!currentApp) return;\n    setApps(prev => prev.map(app =>\n      app.id === currentApp.id\n        ? { ...currentApp, status: \'published\', updatedAt: new Date() }\n        : app\n    ));\n    setCurrentApp(prev => prev ? { ...prev, status: \'published\' } : null);\n  }, [currentApp]);\n\n  const deleteApp = useCallback((appId: string) => {\n    setApps(prev => prev.filter(app => app.id !== appId));\n    if (currentApp?.id === appId) {\n      setCurrentApp(null);\n    }\n  }, [currentApp]);\n\n  // Component Actions\n  const addComponent = useCallback((type: Component[\'type\'], parentId?: string): string => {\n    if (!currentApp) return \'\';\n\n    const id = `comp-${Date.now()}`;\n    const newComponent: Component = {\n      id,\n      type,\n      label: `${type.charAt(0).toUpperCase() + type.slice(1)} ${Object.keys(currentApp.components).length + 1}`,\n      props: getDefaultProps(type),\n      styles: getDefaultStyles(type),\n      children: canHaveChildren(type) ? [] : undefined,\n      parentId: parentId || currentApp.rootComponent,\n    };\n\n    const updatedComponents = { ...currentApp.components, [id]: newComponent };\n    \n    // Add to parent\'s children\n    const parent = updatedComponents[parentId || currentApp.rootComponent];\n    if (parent && parent.children) {\n      parent.children = [...parent.children, id];\n    }\n\n    const updatedApp = { ...currentApp, components: updatedComponents, updatedAt: new Date() };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Added ${type} component`);\n    return id;\n  }, [currentApp, pushHistory]);\n\n  const updateComponent = useCallback((id: string, updates: Partial<Component>) => {\n    if (!currentApp) return;\n\n    const updatedComponents = {\n      ...currentApp.components,\n      [id]: { ...currentApp.components[id], ...updates },\n    };\n\n    const updatedApp = { ...currentApp, components: updatedComponents, updatedAt: new Date() };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Updated ${currentApp.components[id]?.label}`);\n  }, [currentApp, pushHistory]);\n\n  const deleteComponent = useCallback((id: string) => {\n    if (!currentApp || id === currentApp.rootComponent) return;\n\n    const component = currentApp.components[id];\n    if (!component) return;\n\n    // Remove from parent\'s children\n    const parentId = component.parentId;\n    const parent = parentId ? currentApp.components[parentId] : null;\n\n    const updatedComponents = { ...currentApp.components };\n    \n    if (parent && parent.children) {\n      parent.children = parent.children.filter((childId: string) => childId !== id);\n      updatedComponents[parentId] = { ...parent };\n    }\n\n    // Recursively delete children\n    const deleteRecursive = (compId: string) => {\n      const comp = updatedComponents[compId];\n      if (comp?.children) {\n        comp.children.forEach(deleteRecursive);\n      }\n      delete updatedComponents[compId];\n    };\n    deleteRecursive(id);\n\n    const updatedApp = { ...currentApp, components: updatedComponents, updatedAt: new Date() };\n    setCurrentApp(updatedApp);\n    setSelectedComponent(null);\n    pushHistory(updatedApp, `Deleted ${component.label}`);\n  }, [currentApp, pushHistory]);\n\n  const duplicateComponent = useCallback((id: string): string | null => {\n    if (!currentApp) return null;\n\n    const component = currentApp.components[id];\n    if (!component) return null;\n\n    const newId = `comp-${Date.now()}`;\n    const newComponent: Component = {\n      ...JSON.parse(JSON.stringify(component)),\n      id: newId,\n      label: `${component.label} (Copy)`,\n    };\n\n    const updatedComponents = { ...currentApp.components, [newId]: newComponent };\n    \n    // Add to parent\'s children\n    const parentId = component.parentId;\n    if (parentId) {\n      const parent = updatedComponents[parentId];\n      if (parent?.children) {\n        const idx = parent.children.indexOf(id);\n        parent.children = [...parent.children.slice(0, idx + 1), newId, ...parent.children.slice(idx + 1)];\n        updatedComponents[parentId] = { ...parent };\n      }\n    }\n\n    const updatedApp = { ...currentApp, components: updatedComponents, updatedAt: new Date() };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Duplicated ${component.label}`);\n    return newId;\n  }, [currentApp, pushHistory]);\n\n  const moveComponent = useCallback((id: string, newParentId: string, index?: number) => {\n    if (!currentApp) return;\n\n    const component = currentApp.components[id];\n    if (!component) return;\n\n    const updatedComponents = { ...currentApp.components };\n    \n    // Remove from old parent\n    const oldParentId = component.parentId;\n    if (oldParentId) {\n      const oldParent = updatedComponents[oldParentId];\n      if (oldParent?.children) {\n        oldParent.children = oldParent.children.filter((childId: string) => childId !== id);\n        updatedComponents[oldParentId] = { ...oldParent };\n      }\n    }\n\n    // Add to new parent\n    const newParent = updatedComponents[newParentId];\n    if (newParent?.children) {\n      if (index !== undefined) {\n        newParent.children = [...newParent.children.slice(0, index), id, ...newParent.children.slice(index)];\n      } else {\n        newParent.children = [...newParent.children, id];\n      }\n      updatedComponents[newParentId] = { ...newParent };\n    }\n\n    // Update component\'s parentId\n    updatedComponents[id] = { ...component, parentId: newParentId };\n\n    const updatedApp = { ...currentApp, components: updatedComponents, updatedAt: new Date() };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Moved ${component.label}`);\n  }, [currentApp, pushHistory]);\n\n  // Clipboard Actions\n  const copyComponent = useCallback((id: string) => {\n    if (!currentApp) return;\n    const component = currentApp.components[id];\n    if (component) {\n      setClipboard(JSON.parse(JSON.stringify(component)));\n    }\n  }, [currentApp]);\n\n  const pasteComponent = useCallback((parentId?: string): string | null => {\n    if (!currentApp || !clipboard) return null;\n\n    const newId = `comp-${Date.now()}`;\n    const newComponent: Component = {\n      ...clipboard,\n      id: newId,\n      label: `${clipboard.label} (Pasted)`,\n      parentId: parentId || currentApp.rootComponent,\n    };\n\n    const updatedComponents = { ...currentApp.components, [newId]: newComponent };\n    \n    const parent = updatedComponents[parentId || currentApp.rootComponent];\n    if (parent?.children) {\n      parent.children = [...parent.children, newId];\n      updatedComponents[parentId || currentApp.rootComponent] = { ...parent };\n    }\n\n    const updatedApp = { ...currentApp, components: updatedComponents, updatedAt: new Date() };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Pasted ${clipboard.label}`);\n    return newId;\n  }, [currentApp, clipboard, pushHistory]);\n\n  const cutComponent = useCallback((id: string) => {\n    copyComponent(id);\n    deleteComponent(id);\n  }, [copyComponent, deleteComponent]);\n\n  // History Actions\n  const undo = useCallback(() => {\n    if (historyIndex > 0) {\n      const newIndex = historyIndex - 1;\n      setHistoryIndex(newIndex);\n      setCurrentApp(JSON.parse(JSON.stringify(history[newIndex].app)));\n    }\n  }, [history, historyIndex]);\n\n  const redo = useCallback(() => {\n    if (historyIndex < history.length - 1) {\n      const newIndex = historyIndex + 1;\n      setHistoryIndex(newIndex);\n      setCurrentApp(JSON.parse(JSON.stringify(history[newIndex].app)));\n    }\n  }, [history, historyIndex]);\n\n  const canUndo = useCallback(() => historyIndex > 0, [historyIndex]);\n  const canRedo = useCallback(() => historyIndex < history.length - 1, [history, historyIndex]);\n\n  // Preview Actions\n  const togglePreview = useCallback(() => {\n    setPreviewMode(prev => !prev);\n  }, []);\n\n  // Data Source Actions\n  const addDataSource = useCallback((source: Omit<DataSource, \'id\'>): string => {\n    if (!currentApp) return \'\';\n\n    const id = `ds-${Date.now()}`;\n    const newSource: DataSource = { ...source, id };\n\n    const updatedApp = {\n      ...currentApp,\n      dataSources: [...currentApp.dataSources, newSource],\n      updatedAt: new Date(),\n    };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Added data source: ${source.name}`);\n    return id;\n  }, [currentApp, pushHistory]);\n\n  const updateDataSource = useCallback((id: string, updates: Partial<DataSource>) => {\n    if (!currentApp) return;\n\n    const updatedApp = {\n      ...currentApp,\n      dataSources: currentApp.dataSources.map(ds =>\n        ds.id === id ? { ...ds, ...updates } : ds\n      ),\n      updatedAt: new Date(),\n    };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Updated data source`);\n  }, [currentApp, pushHistory]);\n\n  const removeDataSource = useCallback((id: string) => {\n    if (!currentApp) return;\n\n    const updatedApp = {\n      ...currentApp,\n      dataSources: currentApp.dataSources.filter(ds => ds.id !== id),\n      updatedAt: new Date(),\n    };\n    setCurrentApp(updatedApp);\n    pushHistory(updatedApp, `Removed data source`);\n  }, [currentApp, pushHistory]);\n\n  // Export/Import\n  const exportApp = useCallback((appId: string): string => {\n    const app = apps.find(a => a.id === appId) || currentApp;\n    if (!app) return \'\';\n    return JSON.stringify(app, null, 2);\n  }, [apps, currentApp]);\n\n  const importApp = useCallback((data: string): string => {\n    try {\n      const parsed = JSON.parse(data);\n      const id = `app-${Date.now()}`;\n      const app: AppDefinition = {\n        ...parsed,\n        id,\n        createdAt: new Date(),\n        updatedAt: new Date(),\n      };\n      setApps(prev => [...prev, app]);\n      return id;\n    } catch {\n      throw new Error(\'Invalid app data\');\n    }\n  }, []);\n\n  const value = useMemo(() => ({\n    apps,\n    currentApp,\n    selectedComponent,\n    clipboard,\n    history,\n    historyIndex,\n    previewMode,\n    createApp,\n    loadApp,\n    saveApp,\n    publishApp,\n    deleteApp,\n    addComponent,\n    updateComponent,\n    deleteComponent,\n    duplicateComponent,\n    moveComponent,\n    selectComponent: setSelectedComponent,\n    copyComponent,\n    pasteComponent,\n    cutComponent,\n    undo,\n    redo,\n    canUndo,\n    canRedo,\n    togglePreview,\n    addDataSource,\n    updateDataSource,\n    removeDataSource,\n    exportApp,\n    importApp,\n  }), [\n    apps, currentApp, selectedComponent, clipboard, history, historyIndex, previewMode,\n    createApp, loadApp, saveApp, publishApp, deleteApp,\n    addComponent, updateComponent, deleteComponent, duplicateComponent, moveComponent,\n    copyComponent, pasteComponent, cutComponent,\n    undo, redo, canUndo, canRedo, togglePreview,\n    addDataSource, updateDataSource, removeDataSource,\n    exportApp, importApp,\n  ]);\n\n  return (\n    <AppBuilderContext.Provider value={value}>\n      {children}\n    </AppBuilderContext.Provider>\n  );\n};\n\n// ============================================================================\n// HELPER FUNCTIONS\n// ============================================================================\n\nfunction getDefaultProps(type: Component[\'type\']): Record<string, unknown> {\n  const defaults: Record<string, Record<string, unknown>> = {\n    text: { text: \'Text content\' },\n    heading: { text: \'Heading\', level: 2 },\n    button: { text: \'Button\', variant: \'primary\' },\n    input: { placeholder: \'Enter value...\' },\n    select: { options: [\'Option 1\', \'Option 2\', \'Option 3\'] },\n    table: { columns: [\'Column 1\', \'Column 2\', \'Column 3\'] },\n    form: { fields: [] },\n    chart: { type: \'bar\', data: [] },\n    image: { src: \'\', alt: \'Image\' },\n    card: { title: \'Card Title\', content: \'Card content\' },\n    alert: { type: \'info\', message: \'Alert message\' },\n    badge: { text: \'Badge\', variant: \'default\' },\n    progress: { value: 50, max: 100 },\n    tabs: { tabs: [\'Tab 1\', \'Tab 2\'] },\n    accordion: { items: [{ title: \'Section 1\', content: \'Content\' }] },\n    list: { items: [\'Item 1\', \'Item 2\', \'Item 3\'] },\n    grid: { columns: 3 },\n    date_picker: { format: \'YYYY-MM-DD\' },\n    file_upload: { accept: \'*\', multiple: false },\n    checkbox: { label: \'Checkbox\', checked: false },\n    radio: { options: [\'Option 1\', \'Option 2\'], selected: \'Option 1\' },\n    toggle: { label: \'Toggle\', checked: false },\n    tooltip: { text: \'Tooltip text\' },\n    widget: { type: \'stats\', title: \'Widget\' },\n    container: {},\n    divider: {},\n    spacer: { height: \'16px\' },\n    modal: { title: \'Modal\', isOpen: false },\n  };\n  return defaults[type] || {};\n}\n\nfunction getDefaultStyles(type: Component[\'type\']): Component[\'styles\'] {\n  const defaults: Record<string, Component[\'styles\']> = {\n    container: { padding: \'16px\', display: \'flex\', flexDirection: \'column\', gap: \'8px\' },\n    text: { fontSize: \'14px\' },\n    heading: { fontSize: \'24px\', fontWeight: \'bold\' },\n    button: { padding: \'8px 16px\', borderRadius: \'4px\' },\n    input: { padding: \'8px\', borderRadius: \'4px\', border: \'1px solid #ccc\' },\n    card: { padding: \'16px\', borderRadius: \'8px\', border: \'1px solid #eee\' },\n    grid: { display: \'grid\', gap: \'16px\' },\n  };\n  return defaults[type] || {};\n}\n\nfunction canHaveChildren(type: Component[\'type\']): boolean {\n  return [\'container\', \'form\', \'card\', \'grid\', \'tabs\', \'accordion\', \'modal\', \'list\'].includes(type);\n}\n\n// ============================================================================\n// COMPONENT PALETTE\n// ============================================================================\n\ninterface ComponentPaletteProps {\n  onDragStart: (type: Component[\'type\']) => void;\n}\n\nexport const ComponentPalette: React.FC<ComponentPaletteProps> = ({ onDragStart }) => {\n  const categories = [\n    {\n      name: \'Layout\',\n      components: [\n        { type: \'container\' as const, icon: \'📦\', label: \'Container\' },\n        { type: \'grid\' as const, icon: \'🔲\', label: \'Grid\' },\n        { type: \'divider\' as const, icon: \'➖\', label: \'Divider\' },\n        { type: \'spacer\' as const, icon: \'⬜\', label: \'Spacer\' },\n      ],\n    },\n    {\n      name: \'Basic\',\n      components: [\n        { type: \'text\' as const, icon: \'📝\', label: \'Text\' },\n        { type: \'heading\' as const, icon: \'📰\', label: \'Heading\' },\n        { type: \'button\' as const, icon: \'🔘\', label: \'Button\' },\n        { type: \'image\' as const, icon: \'🖼️\', label: \'Image\' },\n      ],\n    },\n    {\n      name: \'Input\',\n      components: [\n        { type: \'input\' as const, icon: \'✏️\', label: \'Input\' },\n        { type: \'select\' as const, icon: \'📋\', label: \'Select\' },\n        { type: \'checkbox\' as const, icon: \'☑️\', label: \'Checkbox\' },\n        { type: \'radio\' as const, icon: \'🔘\', label: \'Radio\' },\n        { type: \'toggle\' as const, icon: \'🔀\', label: \'Toggle\' },\n        { type: \'date-picker\' as const, icon: \'📅\', label: \'Date Picker\' },\n        { type: \'file-upload\' as const, icon: \'📤\', label: \'File Upload\' },\n      ],\n    },\n    {\n      name: \'Data\',\n      components: [\n        { type: \'table\' as const, icon: \'📊\', label: \'Table\' },\n        { type: \'list\' as const, icon: \'📃\', label: \'List\' },\n        { type: \'card\' as const, icon: \'🃏\', label: \'Card\' },\n        { type: \'chart\' as const, icon: \'📈\', label: \'Chart\' },\n      ],\n    },\n    {\n      name: \'Feedback\',\n      components: [\n        { type: \'alert\' as const, icon: \'⚠️\', label: \'Alert\' },\n        { type: \'badge\' as const, icon: \'🏷️\', label: \'Badge\' },\n        { type: \'progress\' as const, icon: \'⏳\', label: \'Progress\' },\n        { type: \'tooltip\' as const, icon: \'💬\', label: \'Tooltip\' },\n      ],\n    },\n    {\n      name: \'Advanced\',\n      components: [\n        { type: \'form\' as const, icon: \'📄\', label: \'Form\' },\n        { type: \'tabs\' as const, icon: \'📑\', label: \'Tabs\' },\n        { type: \'accordion\' as const, icon: \'📚\', label: \'Accordion\' },\n        { type: \'modal\' as const, icon: \'🪟\', label: \'Modal\' },\n        { type: \'widget\' as const, icon: \'🧩\', label: \'Widget\' },\n      ],\n    },\n  ];\n\n  return (\n    <div className="w-64 bg-white border-r overflow-y-auto">\n      <div className="p-4 border-b bg-gray-50">\n        <h2 className="font-semibold text-gray-700">Components</h2>\n      </div>\n      <div className="p-2">\n        {categories.map(category => (\n          <div key={category.name} className="mb-4">\n            <h3 className="text-xs font-medium text-gray-500 uppercase tracking-wide px-2 mb-2">\n              {category.name}\n            </h3>\n            <div className="grid grid-cols-2 gap-1">\n              {category.components.map(comp => (\n                <button\n                  key={comp.type}\n                  draggable\n                  onDragStart={() => onDragStart(comp.type)}\n                  className="flex flex-col items-center p-2 rounded border border-transparent hover:border-blue-300 hover:bg-blue-50 transition-colors text-center"\n                >\n                  <span className="text-xl mb-1">{comp.icon}</span>\n                  <span className="text-xs text-gray-600">{comp.label}</span>\n                </button>\n              ))}\n            </div>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// PROPERTIES PANEL\n// ============================================================================\n\ninterface PropertiesPanelProps {\n  component: Component;\n  onUpdate: (updates: Partial<Component>) => void;\n  onDelete: () => void;\n  onDuplicate: () => void;\n}\n\nexport const PropertiesPanel: React.FC<PropertiesPanelProps> = ({\n  component,\n  onUpdate,\n  onDelete,\n  onDuplicate,\n}) => {\n  const [activeTab, setActiveTab] = useState<\'props\' | \'styles\' | \'events\'>(\'props\');\n\n  const handlePropChange = (key: string, value: unknown) => {\n    onUpdate({\n      props: { ...component.props, [key]: value },\n    });\n  };\n\n  const handleStyleChange = (key: string, value: string) => {\n    onUpdate({\n      styles: { ...component.styles, [key]: value },\n    });\n  };\n\n  return (\n    <div className="w-72 bg-white border-l overflow-y-auto">\n      <div className="p-4 border-b bg-gray-50 flex justify-between items-center">\n        <div>\n          <h2 className="font-semibold text-gray-700">{component.label}</h2>\n          <p className="text-xs text-gray-500">{component.type}</p>\n        </div>\n        <div className="flex gap-1">\n          <button\n            onClick={onDuplicate}\n            className="p-1 text-gray-500 hover:text-gray-700 hover:bg-gray-100 rounded"\n            title="Duplicate"\n          >\n            📋\n          </button>\n          <button\n            onClick={onDelete}\n            className="p-1 text-red-500 hover:text-red-700 hover:bg-red-50 rounded"\n            title="Delete"\n          >\n            🗑️\n          </button>\n        </div>\n      </div>\n\n      {/* Tabs */}\n      <div className="flex border-b">\n        {([\'props\', \'styles\', \'events\'] as const).map(tab => (\n          <button\n            key={tab}\n            onClick={() => setActiveTab(tab)}\n            className={`flex-1 px-3 py-2 text-sm font-medium ${\n              activeTab === tab\n                ? \'text-blue-600 border-b-2 border-blue-600\'\n                : \'text-gray-600 hover:text-gray-900\'\n            }`}\n          >\n            {tab.charAt(0).toUpperCase() + tab.slice(1)}\n          </button>\n        ))}\n      </div>\n\n      <div className="p-4">\n        {/* Label */}\n        <div className="mb-4">\n          <label className="block text-sm font-medium text-gray-700 mb-1">Label</label>\n          <input\n            type="text"\n            value={component.label}\n            onChange={(e) => onUpdate({ label: e.target.value })}\n            className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500 focus:border-blue-500"\n          />\n        </div>\n\n        {activeTab === \'props\' && (\n          <div className="space-y-3">\n            {/* Dynamic property editors based on component type */}\n            {component.type === \'text\' && (\n              <div>\n                <label className="block text-sm font-medium text-gray-700 mb-1">Text</label>\n                <textarea\n                  value={String(component.props.text || \'\')}\n                  onChange={(e) => handlePropChange(\'text\', e.target.value)}\n                  rows={3}\n                  className="w-full px-3 py-2 border rounded-lg focus:ring-2 focus:ring-blue-500"\n                />\n              </div>\n            )}\n\n            {component.type === \'heading\' && (\n              <>\n                <div>\n                  <label className="block text-sm font-medium text-gray-700 mb-1">Text</label>\n                  <input\n                    type="text"\n                    value={String(component.props.text || \'\')}\n                    onChange={(e) => handlePropChange(\'text\', e.target.value)}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  />\n                </div>\n                <div>\n                  <label className="block text-sm font-medium text-gray-700 mb-1">Level</label>\n                  <select\n                    value={String(component.props.level || 2)}\n                    onChange={(e) => handlePropChange(\'level\', Number(e.target.value))}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  >\n                    {[1, 2, 3, 4, 5, 6].map(n => (\n                      <option key={n} value={n}>H{n}</option>\n                    ))}\n                  </select>\n                </div>\n              </>\n            )}\n\n            {component.type === \'button\' && (\n              <>\n                <div>\n                  <label className="block text-sm font-medium text-gray-700 mb-1">Text</label>\n                  <input\n                    type="text"\n                    value={String(component.props.text || \'\')}\n                    onChange={(e) => handlePropChange(\'text\', e.target.value)}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  />\n                </div>\n                <div>\n                  <label className="block text-sm font-medium text-gray-700 mb-1">Variant</label>\n                  <select\n                    value={String(component.props.variant || \'primary\')}\n                    onChange={(e) => handlePropChange(\'variant\', e.target.value)}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  >\n                    <option value="primary">Primary</option>\n                    <option value="secondary">Secondary</option>\n                    <option value="outline">Outline</option>\n                    <option value="ghost">Ghost</option>\n                    <option value="danger">Danger</option>\n                  </select>\n                </div>\n              </>\n            )}\n\n            {component.type === \'input\' && (\n              <>\n                <div>\n                  <label className="block text-sm font-medium text-gray-700 mb-1">Placeholder</label>\n                  <input\n                    type="text"\n                    value={String(component.props.placeholder || \'\')}\n                    onChange={(e) => handlePropChange(\'placeholder\', e.target.value)}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  />\n                </div>\n                <div>\n                  <label className="block text-sm font-medium text-gray-700 mb-1">Type</label>\n                  <select\n                    value={String(component.props.inputType || \'text\')}\n                    onChange={(e) => handlePropChange(\'inputType\', e.target.value)}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  >\n                    <option value="text">Text</option>\n                    <option value="email">Email</option>\n                    <option value="password">Password</option>\n                    <option value="number">Number</option>\n                    <option value="tel">Phone</option>\n                  </select>\n                </div>\n              </>\n            )}\n\n            {(component.type === \'container\' || component.type === \'grid\') && (\n              <div>\n                <label className="block text-sm font-medium text-gray-700 mb-1">\n                  {component.type === \'grid\' ? \'Columns\' : \'Direction\'}\n                </label>\n                {component.type === \'grid\' ? (\n                  <input\n                    type="number"\n                    value={Number(component.props.columns || 3)}\n                    onChange={(e) => handlePropChange(\'columns\', Number(e.target.value))}\n                    min={1}\n                    max={12}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  />\n                ) : (\n                  <select\n                    value={String(component.styles?.flexDirection || \'column\')}\n                    onChange={(e) => handleStyleChange(\'flexDirection\', e.target.value)}\n                    className="w-full px-3 py-2 border rounded-lg"\n                  >\n                    <option value="row">Horizontal</option>\n                    <option value="column">Vertical</option>\n                  </select>\n                )}\n              </div>\n            )}\n          </div>\n        )}\n\n        {activeTab === \'styles\' && (\n          <div className="space-y-3">\n            <div>\n              <label className="block text-sm font-medium text-gray-700 mb-1">Width</label>\n              <input\n                type="text"\n                value={component.styles?.width || \'\'}\n                onChange={(e) => handleStyleChange(\'width\', e.target.value)}\n                placeholder="e.g., 100%, 300px"\n                className="w-full px-3 py-2 border rounded-lg"\n              />\n            </div>\n            <div>\n              <label className="block text-sm font-medium text-gray-700 mb-1">Height</label>\n              <input\n                type="text"\n                value={component.styles?.height || \'\'}\n                onChange={(e) => handleStyleChange(\'height\', e.target.value)}\n                placeholder="e.g., auto, 200px"\n                className="w-full px-3 py-2 border rounded-lg"\n              />\n            </div>\n            <div>\n              <label className="block text-sm font-medium text-gray-700 mb-1">Padding</label>\n              <input\n                type="text"\n                value={component.styles?.padding || \'\'}\n                onChange={(e) => handleStyleChange(\'padding\', e.target.value)}\n                placeholder="e.g., 16px"\n                className="w-full px-3 py-2 border rounded-lg"\n              />\n            </div>\n            <div>\n              <label className="block text-sm font-medium text-gray-700 mb-1">Margin</label>\n              <input\n                type="text"\n                value={component.styles?.margin || \'\'}\n                onChange={(e) => handleStyleChange(\'margin\', e.target.value)}\n                placeholder="e.g., 8px"\n                className="w-full px-3 py-2 border rounded-lg"\n              />\n            </div>\n            <div>\n              <label className="block text-sm font-medium text-gray-700 mb-1">Background</label>\n              <div className="flex gap-2">\n                <input\n                  type="color"\n                  value={component.styles?.backgroundColor || \'#ffffff\'}\n                  onChange={(e) => handleStyleChange(\'backgroundColor\', e.target.value)}\n                  className="w-10 h-10 border rounded cursor-pointer"\n                />\n                <input\n                  type="text"\n                  value={component.styles?.backgroundColor || \'\'}\n                  onChange={(e) => handleStyleChange(\'backgroundColor\', e.target.value)}\n                  className="flex-1 px-3 py-2 border rounded-lg"\n                />\n              </div>\n            </div>\n            <div>\n              <label className="block text-sm font-medium text-gray-700 mb-1">Text Color</label>\n              <div className="flex gap-2">\n                <input\n                  type="color"\n                  value={component.styles?.color || \'#000000\'}\n                  onChange={(e) => handleStyleChange(\'color\', e.target.value)}\n                  className="w-10 h-10 border rounded cursor-pointer"\n                />\n                <input\n                  type="text"\n                  value={component.styles?.color || \'\'}\n                  onChange={(e) => handleStyleChange(\'color\', e.target.value)}\n                  className="flex-1 px-3 py-2 border rounded-lg"\n                />\n              </div>\n            </div>\n            <div>\n              <label className="block text-sm font-medium text-gray-700 mb-1">Border Radius</label>\n              <input\n                type="text"\n                value={component.styles?.borderRadius || \'\'}\n                onChange={(e) => handleStyleChange(\'borderRadius\', e.target.value)}\n                placeholder="e.g., 4px, 50%"\n                className="w-full px-3 py-2 border rounded-lg"\n              />\n            </div>\n          </div>\n        )}\n\n        {activeTab === \'events\' && (\n          <div className="text-center py-8 text-gray-500">\n            <p className="text-sm">Configure component events and actions</p>\n            <button className="mt-3 px-4 py-2 bg-blue-50 text-blue-600 rounded-lg text-sm hover:bg-blue-100">\n              Add Event\n            </button>\n          </div>\n        )}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// CANVAS RENDERER\n// ============================================================================\n\ninterface CanvasRendererProps {\n  component: Component;\n  allComponents: Record<string, Component>;\n  isSelected: boolean;\n  onSelect: () => void;\n  onDrop: (type: Component[\'type\']) => void;\n}\n\nexport const CanvasRenderer: React.FC<CanvasRendererProps> = ({\n  component,\n  allComponents,\n  isSelected,\n  onSelect,\n  onDrop,\n}) => {\n  const ref = useRef<HTMLDivElement>(null);\n  const [isOver, setIsOver] = useState(false);\n\n  const handleDragOver = (e: React.DragEvent) => {\n    e.preventDefault();\n    if (canHaveChildren(component.type)) {\n      setIsOver(true);\n    }\n  };\n\n  const handleDragLeave = () => {\n    setIsOver(false);\n  };\n\n  const handleDrop = (e: React.DragEvent) => {\n    e.preventDefault();\n    setIsOver(false);\n    const type = e.dataTransfer.getData(\'componentType\') as Component[\'type\'];\n    if (type && canHaveChildren(component.type)) {\n      onDrop(type);\n    }\n  };\n\n  const renderComponent = () => {\n    const style: React.CSSProperties = {\n      width: component.styles?.width,\n      height: component.styles?.height,\n      padding: component.styles?.padding,\n      margin: component.styles?.margin,\n      backgroundColor: component.styles?.backgroundColor,\n      color: component.styles?.color,\n      fontSize: component.styles?.fontSize,\n      fontWeight: component.styles?.fontWeight,\n      borderRadius: component.styles?.borderRadius,\n      border: component.styles?.border,\n      display: component.styles?.display,\n      flexDirection: component.styles?.flexDirection,\n      justifyContent: component.styles?.justifyContent,\n      alignItems: component.styles?.alignItems,\n      gap: component.styles?.gap,\n    };\n\n    switch (component.type) {\n      case \'container\':\n        return (\n          <div style={style} className="min-h-[60px]">\n            {component.children?.map(childId => {\n              const child = allComponents[childId];\n              if (!child) return null;\n              return (\n                <CanvasRenderer\n                  key={childId}\n                  component={child}\n                  allComponents={allComponents}\n                  isSelected={false}\n                  onSelect={() => {}}\n                  onDrop={() => {}}\n                />\n              );\n            })}\n            {(!component.children || component.children.length === 0) && (\n              <div className="flex items-center justify-center h-full text-gray-400 text-sm border-2 border-dashed border-gray-200 rounded p-4">\n                Drop components here\n              </div>\n            )}\n          </div>\n        );\n\n      case \'text\':\n        return <p style={style}>{String(component.props.text || \'Text\')}</p>;\n\n      case \'heading\':\n        const HeadingTag = `h${component.props.level || 2}` as keyof JSX.IntrinsicElements;\n        return React.createElement(HeadingTag, { style }, component.props.text || \'Heading\');\n\n      case \'button\':\n        return (\n          <button\n            style={style}\n            className={`px-4 py-2 rounded ${\n              component.props.variant === \'primary\' ? \'bg-blue-500 text-white\' :\n              component.props.variant === \'secondary\' ? \'bg-gray-500 text-white\' :\n              component.props.variant === \'outline\' ? \'border border-blue-500 text-blue-500\' :\n              component.props.variant === \'danger\' ? \'bg-red-500 text-white\' :\n              \'bg-transparent\'\n            }`}\n          >\n            {String(component.props.text || \'Button\')}\n          </button>\n        );\n\n      case \'input\':\n        return (\n          <input\n            type={String(component.props.inputType || \'text\')}\n            placeholder={String(component.props.placeholder || \'\')}\n            style={{ ...style, className: \'px-3 py-2 border rounded-lg\' }}\n            className="px-3 py-2 border rounded-lg"\n          />\n        );\n\n      case \'divider\':\n        return <hr style={style} className="border-gray-300" />;\n\n      case \'spacer\':\n        return <div style={{ height: component.styles?.height || \'16px\' }} />;\n\n      case \'card\':\n        return (\n          <div style={style} className="border rounded-lg p-4 shadow-sm">\n            <h3 className="font-medium mb-2">{String(component.props.title || \'Card Title\')}</h3>\n            <p className="text-sm text-gray-600">{String(component.props.content || \'Card content\')}</p>\n          </div>\n        );\n\n      case \'badge\':\n        return (\n          <span style={style} className="px-2 py-1 bg-blue-100 text-blue-700 rounded-full text-sm">\n            {String(component.props.text || \'Badge\')}\n          </span>\n        );\n\n      case \'alert\':\n        return (\n          <div\n            style={style}\n            className={`p-3 rounded-lg ${\n              component.props.type === \'error\' ? \'bg-red-50 text-red-700\' :\n              component.props.type === \'warning\' ? \'bg-yellow-50 text-yellow-700\' :\n              component.props.type === \'success\' ? \'bg-green-50 text-green-700\' :\n              \'bg-blue-50 text-blue-700\'\n            }`}\n          >\n            {String(component.props.message || \'Alert message\')}\n          </div>\n        );\n\n      case \'progress\':\n        return (\n          <div style={style} className="w-full">\n            <div className="h-2 bg-gray-200 rounded-full overflow-hidden">\n              <div\n                className="h-full bg-blue-500 transition-all"\n                style={{ width: `${Number(component.props.value || 0)}%` }}\n              />\n            </div>\n          </div>\n        );\n\n      case \'grid\':\n        return (\n          <div\n            style={{ ...style, display: \'grid\', gridTemplateColumns: `repeat(${component.props.columns || 3}, 1fr)` }}\n            className="min-h-[60px]"\n          >\n            {component.children?.map(childId => {\n              const child = allComponents[childId];\n              if (!child) return null;\n              return (\n                <CanvasRenderer\n                  key={childId}\n                  component={child}\n                  allComponents={allComponents}\n                  isSelected={false}\n                  onSelect={() => {}}\n                  onDrop={() => {}}\n                />\n              );\n            })}\n          </div>\n        );\n\n      default:\n        return (\n          <div style={style} className="p-4 bg-gray-100 rounded text-center text-gray-500">\n            {component.type}\n          </div>\n        );\n    }\n  };\n\n  return (\n    <div\n      ref={ref}\n      onClick={(e) => {\n        e.stopPropagation();\n        onSelect();\n      }}\n      onDragOver={handleDragOver}\n      onDragLeave={handleDragLeave}\n      onDrop={handleDrop}\n      className={`relative ${isSelected ? \'ring-2 ring-blue-500\' : \'\'} ${isOver ? \'ring-2 ring-green-500 ring-dashed\' : \'\'} cursor-pointer hover:ring-1 hover:ring-blue-300 transition-all`}\n    >\n      {renderComponent()}\n      {isSelected && (\n        <div className="absolute -top-5 left-0 bg-blue-500 text-white text-xs px-2 py-0.5 rounded">\n          {component.label}\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// APP LIST VIEW\n// ============================================================================\n\ninterface AppListViewProps {\n  onCreateApp: () => void;\n  onSelectApp: (appId: string) => void;\n}\n\nexport const AppListView: React.FC<AppListViewProps> = ({ onCreateApp, onSelectApp }) => {\n  const { apps } = useAppBuilder();\n\n  const getStatusBadge = (status: AppDefinition[\'status\']) => {\n    const colors: Record<string, string> = {\n      draft: \'bg-yellow-100 text-yellow-700\',\n      published: \'bg-green-100 text-green-700\',\n      archived: \'bg-gray-100 text-gray-700\',\n    };\n    return (\n      <span className={`px-2 py-0.5 text-xs font-medium rounded-full ${colors[status]}`}>\n        {status}\n      </span>\n    );\n  };\n\n  return (\n    <div className="p-6">\n      <div className="flex justify-between items-center mb-6">\n        <div>\n          <h1 className="text-2xl font-bold">Internal Apps</h1>\n          <p className="text-gray-600">Create and manage custom business applications</p>\n        </div>\n        <button\n          onClick={onCreateApp}\n          className="px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600 transition-colors flex items-center gap-2"\n        >\n          <svg className="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">\n            <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M12 4v16m8-8H4" />\n          </svg>\n          Create App\n        </button>\n      </div>\n\n      <div className="grid gap-4 md:grid-cols-2 lg:grid-cols-3">\n        {apps.map(app => (\n          <div\n            key={app.id}\n            className="border rounded-lg p-4 hover:shadow-lg transition-shadow cursor-pointer bg-white"\n            onClick={() => onSelectApp(app.id)}\n          >\n            <div className="flex justify-between items-start mb-2">\n              <h3 className="font-medium text-lg">{app.name}</h3>\n              {getStatusBadge(app.status)}\n            </div>\n            {app.description && (\n              <p className="text-sm text-gray-600 mb-3">{app.description}</p>\n            )}\n            <div className="flex justify-between items-center text-sm text-gray-500">\n              <span>v{app.version}</span>\n              <span>{Object.keys(app.components).length} components</span>\n            </div>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// APP BUILDER CANVAS\n// ============================================================================\n\nexport const AppBuilderCanvas: React.FC = () => {\n  const { currentApp, selectedComponent, selectComponent, addComponent, updateComponent, deleteComponent, duplicateComponent } = useAppBuilder();\n  const [draggedType, setDraggedType] = useState<Component[\'type\'] | null>(null);\n\n  if (!currentApp) {\n    return (\n      <div className="flex-1 flex items-center justify-center bg-gray-100">\n        <p className="text-gray-500">No app loaded</p>\n      </div>\n    );\n  }\n\n  const rootComponent = currentApp.components[currentApp.rootComponent];\n\n  return (\n    <div className="flex-1 overflow-auto bg-gray-100 p-4">\n      <div className="min-h-full bg-white rounded-lg shadow-sm p-4">\n        <CanvasRenderer\n          component={rootComponent}\n          allComponents={currentApp.components}\n          isSelected={selectedComponent?.id === rootComponent.id}\n          onSelect={() => selectComponent(rootComponent)}\n          onDrop={(type) => addComponent(type, rootComponent.id)}\n        />\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN APP BUILDER COMPONENT\n// ============================================================================\n\nexport const InternalAppBuilder: React.FC = () => {\n  const {\n    currentApp,\n    selectedComponent,\n    createApp,\n    loadApp,\n    saveApp,\n    publishApp,\n    selectComponent,\n    addComponent,\n    updateComponent,\n    deleteComponent,\n    duplicateComponent,\n    undo,\n    redo,\n    canUndo,\n    canRedo,\n    togglePreview,\n    previewMode,\n  } = useAppBuilder();\n\n  const [view, setView] = useState<\'list\' | \'builder\'>(\'list\');\n  const [draggedType, setDraggedType] = useState<Component[\'type\'] | null>(null);\n\n  const handleCreateApp = () => {\n    createApp(\'New App\', \'Custom business application\');\n    setView(\'builder\');\n  };\n\n  const handleSelectApp = (appId: string) => {\n    loadApp(appId);\n    setView(\'builder\');\n  };\n\n  const handleDragStart = (type: Component[\'type\']) => {\n    setDraggedType(type);\n  };\n\n  if (view === \'list\') {\n    return <AppListView onCreateApp={handleCreateApp} onSelectApp={handleSelectApp} />;\n  }\n\n  return (\n    <div className="h-screen flex flex-col">\n      {/* Toolbar */}\n      <div className="border-b bg-white px-4 py-2 flex items-center gap-4">\n        <button\n          onClick={() => setView(\'list\')}\n          className="p-2 hover:bg-gray-100 rounded-lg"\n        >\n          ←\n        </button>\n        <div className="flex-1">\n          <input\n            type="text"\n            value={currentApp?.name || \'\'}\n            onChange={(e) => {\n              // Update app name\n            }}\n            className="text-lg font-semibold bg-transparent border-none focus:outline-none"\n          />\n        </div>\n        <div className="flex items-center gap-2">\n          <button\n            onClick={undo}\n            disabled={!canUndo()}\n            className="p-2 hover:bg-gray-100 rounded disabled:opacity-50"\n            title="Undo"\n          >\n            ↶\n          </button>\n          <button\n            onClick={redo}\n            disabled={!canRedo()}\n            className="p-2 hover:bg-gray-100 rounded disabled:opacity-50"\n            title="Redo"\n          >\n            ↷\n          </button>\n          <div className="w-px h-6 bg-gray-200" />\n          <button\n            onClick={togglePreview}\n            className={`px-3 py-1.5 rounded-lg text-sm ${previewMode ? \'bg-blue-500 text-white\' : \'bg-gray-100\'}`}\n          >\n            {previewMode ? \'Edit\' : \'Preview\'}\n          </button>\n          <button\n            onClick={saveApp}\n            className="px-3 py-1.5 bg-gray-100 rounded-lg text-sm hover:bg-gray-200"\n          >\n            Save\n          </button>\n          <button\n            onClick={publishApp}\n            className="px-3 py-1.5 bg-green-500 text-white rounded-lg text-sm hover:bg-green-600"\n          >\n            Publish\n          </button>\n        </div>\n      </div>\n\n      {/* Main Area */}\n      <div className="flex-1 flex overflow-hidden">\n        {/* Component Palette */}\n        <ComponentPalette onDragStart={handleDragStart} />\n\n        {/* Canvas */}\n        <AppBuilderCanvas />\n\n        {/* Properties Panel */}\n        {selectedComponent && (\n          <PropertiesPanel\n            component={selectedComponent}\n            onUpdate={(updates) => updateComponent(selectedComponent.id, updates)}\n            onDelete={() => deleteComponent(selectedComponent.id)}\n            onDuplicate={() => duplicateComponent(selectedComponent.id)}\n          />\n        )}\n      </div>\n    </div>\n  );\n};\n\nexport default InternalAppBuilder;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/appbuilder/internal-app-builder.tsx\' created successfully.") </create-file> </tool_result>'}
{'role': 'assistant', 'content': 'Excellent! I\'ve created both remaining Phase 3 components. Now let me update the todo.md to mark Phase 3 as complete and then move on to Phase 4: AI System.\n\n<function_calls>\n<str-replace file_path="todo.md">\n<old_str>- [ ] Sandbox / Simulation Mode\n- [ ] Internal App Builder\n\n## Phase 4: AI System</old_str>\n<new_str>- [x] Sandbox / Simulation Mode\n- [x] Internal App Builder\n\n## Phase 4: AI System</new_str>\n</str-replace>\n</function_calls>'}
{'role': 'user', 'content': "<tool_result> <str-replace> ToolResult(success=True, output='Replacement successful.') </str-replace> </tool_result>"}
{'role': 'assistant', 'content': 'Now let me start Phase 4: AI System. I\'ll create the AI components for natural language commands, anomaly detection, forecasting, decision recommendations, explainability layer, and contract analysis tool.\n\n<function_calls>\n<create-file file_path="frontend/src/components/ai/natural-language-commands.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo, useEffect, useRef } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst CommandSchema = z.object({\n  id: z.string(),\n  input: z.string(),\n  parsedIntent: z.object({\n    action: z.string(),\n    entity: z.string().optional(),\n    filters: z.record(z.unknown()).optional(),\n    parameters: z.record(z.unknown()).optional(),\n    timeRange: z.object({\n      start: z.date().optional(),\n      end: z.date().optional(),\n      relative: z.string().optional(),\n    }).optional(),\n  }),\n  confidence: z.number().min(0).max(1),\n  suggestions: z.array(z.string()),\n  status: z.enum([\'pending\', \'executing\', \'completed\', \'failed\', \'cancelled\']),\n  result: z.unknown().optional(),\n  error: z.string().optional(),\n  createdAt: z.date(),\n  completedAt: z.date().optional(),\n});\n\nconst IntentTemplateSchema = z.object({\n  id: z.string(),\n  patterns: z.array(z.string()),\n  action: z.string(),\n  examples: z.array(z.string()),\n  description: z.string(),\n  parameters: z.array(z.object({\n    name: z.string(),\n    type: z.string(),\n    required: z.boolean(),\n    description: z.string(),\n    extract: z.string().optional(),\n  })),\n});\n\ntype Command = z.infer<typeof CommandSchema>;\ntype IntentTemplate = z.infer<typeof IntentTemplateSchema>;\n\n// ============================================================================\n// NATURAL LANGUAGE COMMAND STORE\n// ============================================================================\n\ninterface NLCommandStore {\n  commands: Command[];\n  currentInput: string;\n  isProcessing: boolean;\n  suggestions: string[];\n  intentTemplates: IntentTemplate[];\n  \n  // Actions\n  setCurrentInput: (input: string) => void;\n  executeCommand: (input: string) => Promise<void>;\n  cancelCommand: (id: string) => void;\n  retryCommand: (id: string) => Promise<void>;\n  clearHistory: () => void;\n  \n  // Suggestions\n  getSuggestions: (input: string) => string[];\n}\n\nconst NLCommandContext = createContext<NLCommandStore | null>(null);\n\nexport const useNLCommand = () => {\n  const context = useContext(NLCommandContext);\n  if (!context) {\n    throw new Error(\'useNLCommand must be used within NLCommandProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst sampleIntentTemplates: IntentTemplate[] = [\n  {\n    id: \'intent-001\',\n    patterns: [\n      \'show (all | my | the) invoices\',\n      \'list invoices\',\n      \'view invoices\',\n      \'get invoices (for | from | between) *\',\n    ],\n    action: \'list_invoices\',\n    examples: [\n      \'Show all invoices\',\n      \'List invoices from last month\',\n      \'View unpaid invoices for Acme Corp\',\n    ],\n    description: \'List and filter invoices\',\n    parameters: [\n      { name: \'status\', type: \'string\', required: false, description: \'Invoice status filter\' },\n      { name: \'vendor\', type: \'string\', required: false, description: \'Vendor name filter\' },\n      { name: \'dateRange\', type: \'daterange\', required: false, description: \'Date range filter\' },\n    ],\n  },\n  {\n    id: \'intent-002\',\n    patterns: [\n      \'create (a | an | new) invoice\',\n      \'generate invoice (for | to) *\',\n      \'make invoice\',\n    ],\n    action: \'create_invoice\',\n    examples: [\n      \'Create a new invoice for Acme Corp\',\n      \'Generate invoice to John Smith for $500\',\n    ],\n    description: \'Create a new invoice\',\n    parameters: [\n      { name: \'customer\', type: \'string\', required: true, description: \'Customer name\' },\n      { name: \'amount\', type: \'number\', required: false, description: \'Invoice amount\' },\n      { name: \'items\', type: \'array\', required: false, description: \'Line items\' },\n    ],\n  },\n  {\n    id: \'intent-003\',\n    patterns: [\n      \'show (my | the | all) employees\',\n      \'list employees\',\n      \'view team members\',\n      \'who (works | is) in *\',\n    ],\n    action: \'list_employees\',\n    examples: [\n      \'Show all employees\',\n      \'List employees in Engineering\',\n      \'Who works in Sales department?\',\n    ],\n    description: \'List and filter employees\',\n    parameters: [\n      { name: \'department\', type: \'string\', required: false, description: \'Department filter\' },\n      { name: \'role\', type: \'string\', required: false, description: \'Role filter\' },\n      { name: \'status\', type: \'string\', required: false, description: \'Employment status\' },\n    ],\n  },\n  {\n    id: \'intent-004\',\n    patterns: [\n      \'what is (the | our | my) (cash | bank) balance\',\n      \'show (cash | bank) balance\',\n      \'how much (money | cash) do (we | I) have\',\n      \'check treasury balance\',\n    ],\n    action: \'get_cash_balance\',\n    examples: [\n      \'What is our cash balance?\',\n      \'Show bank balance for main account\',\n      \'How much money do we have?\',\n    ],\n    description: \'Check cash and bank balances\',\n    parameters: [\n      { name: \'account\', type: \'string\', required: false, description: \'Account name or ID\' },\n    ],\n  },\n  {\n    id: \'intent-005\',\n    patterns: [\n      \'run (the | a) report\',\n      \'generate report\',\n      \'create (a | an) * report\',\n      \'show (me | the) * report\',\n    ],\n    action: \'run_report\',\n    examples: [\n      \'Run the monthly financial report\',\n      \'Generate a sales report for Q4\',\n      \'Show me the expense report\',\n    ],\n    description: \'Generate and view reports\',\n    parameters: [\n      { name: \'reportType\', type: \'string\', required: true, description: \'Type of report\' },\n      { name: \'period\', type: \'string\', required: false, description: \'Time period\' },\n      { name: \'format\', type: \'string\', required: false, description: \'Output format\' },\n    ],\n  },\n  {\n    id: \'intent-006\',\n    patterns: [\n      \'approve (the | this) *\',\n      \'reject (the | this) *\',\n      \'pending approvals\',\n      \'show (my | pending) approvals\',\n    ],\n    action: \'manage_approvals\',\n    examples: [\n      \'Approve the invoice #1234\',\n      \'Reject this expense request\',\n      \'Show my pending approvals\',\n    ],\n    description: \'Manage approval workflows\',\n    parameters: [\n      { name: \'action\', type: \'string\', required: true, description: \'approve/reject\' },\n      { name: \'itemType\', type: \'string\', required: false, description: \'Type of item\' },\n      { name: \'itemId\', type: \'string\', required: false, description: \'Item ID\' },\n    ],\n  },\n  {\n    id: \'intent-007\',\n    patterns: [\n      \'schedule (a | an) *\',\n      \'create (a | an) event\',\n      \'add to calendar\',\n      \'remind me to *\',\n    ],\n    action: \'schedule_event\',\n    examples: [\n      \'Schedule a meeting with John tomorrow at 2pm\',\n      \'Create an event for project kickoff\',\n      \'Remind me to review the budget next Friday\',\n    ],\n    description: \'Schedule events and reminders\',\n    parameters: [\n      { name: \'title\', type: \'string\', required: true, description: \'Event title\' },\n      { name: \'datetime\', type: \'datetime\', required: true, description: \'Date and time\' },\n      { name: \'attendees\', type: \'array\', required: false, description: \'Attendees\' },\n    ],\n  },\n  {\n    id: \'intent-008\',\n    patterns: [\n      \'compare * with *\',\n      \'show difference between * and *\',\n      \'what changed (in | between) *\',\n    ],\n    action: \'compare_data\',\n    examples: [\n      \'Compare Q3 revenue with Q4\',\n      \'Show difference between this month and last month\',\n      \'What changed in expenses between January and February?\',\n    ],\n    description: \'Compare data across periods or entities\',\n    parameters: [\n      { name: \'entity1\', type: \'string\', required: true, description: \'First entity/period\' },\n      { name: \'entity2\', type: \'string\', required: true, description: \'Second entity/period\' },\n      { name: \'metrics\', type: \'array\', required: false, description: \'Metrics to compare\' },\n    ],\n  },\n];\n\nconst sampleCommands: Command[] = [\n  {\n    id: \'cmd-001\',\n    input: \'Show all unpaid invoices from last month\',\n    parsedIntent: {\n      action: \'list_invoices\',\n      entity: \'invoice\',\n      filters: { status: \'unpaid\' },\n      timeRange: { relative: \'last_month\' },\n    },\n    confidence: 0.95,\n    suggestions: [\n      \'Show unpaid invoices by vendor\',\n      \'Export unpaid invoices to CSV\',\n      \'Send reminders for unpaid invoices\',\n    ],\n    status: \'completed\',\n    result: { count: 23, total: 125000 },\n    createdAt: new Date(\'2024-01-20T10:30:00\'),\n    completedAt: new Date(\'2024-01-20T10:30:05\'),\n  },\n  {\n    id: \'cmd-002\',\n    input: \'Create a new invoice for Acme Corp for $5,000\',\n    parsedIntent: {\n      action: \'create_invoice\',\n      entity: \'invoice\',\n      parameters: { customer: \'Acme Corp\', amount: 5000 },\n    },\n    confidence: 0.88,\n    suggestions: [\n      \'Add line items to invoice\',\n      \'Set payment terms\',\n      \'Schedule invoice for later\',\n    ],\n    status: \'completed\',\n    result: { invoiceId: \'INV-2024-001\', created: true },\n    createdAt: new Date(\'2024-01-20T11:00:00\'),\n    completedAt: new Date(\'2024-01-20T11:00:08\'),\n  },\n  {\n    id: \'cmd-003\',\n    input: \'What is our current cash balance?\',\n    parsedIntent: {\n      action: \'get_cash_balance\',\n      entity: \'treasury\',\n    },\n    confidence: 0.97,\n    suggestions: [\n      \'Show balance by account\',\n      \'View cash flow forecast\',\n      \'Compare with last month\',\n    ],\n    status: \'completed\',\n    result: { total: 2450000, accounts: [{ name: \'Main Operating\', balance: 1850000 }, { name: \'Payroll\', balance: 600000 }] },\n    createdAt: new Date(\'2024-01-20T11:15:00\'),\n    completedAt: new Date(\'2024-01-20T11:15:02\'),\n  },\n];\n\n// ============================================================================\n// NL COMMAND PROVIDER\n// ============================================================================\n\nexport const NLCommandProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [commands, setCommands] = useState<Command[]>(sampleCommands);\n  const [currentInput, setCurrentInput] = useState(\'\');\n  const [isProcessing, setIsProcessing] = useState(false);\n  const [suggestions, setSuggestions] = useState<string[]>([]);\n\n  const intentTemplates = sampleIntentTemplates;\n\n  const parseIntent = useCallback((input: string): Command[\'parsedIntent\'] => {\n    const lowerInput = input.toLowerCase();\n    \n    // Simple pattern matching for demo\n    if (lowerInput.includes(\'invoice\')) {\n      const filters: Record<string, unknown> = {};\n      if (lowerInput.includes(\'unpaid\')) filters.status = \'unpaid\';\n      if (lowerInput.includes(\'paid\')) filters.status = \'paid\';\n      \n      const timeRange: Command[\'parsedIntent\'][\'timeRange\'] = {};\n      if (lowerInput.includes(\'last month\')) timeRange.relative = \'last_month\';\n      if (lowerInput.includes(\'this month\')) timeRange.relative = \'this_month\';\n      \n      return {\n        action: lowerInput.includes(\'create\') ? \'create_invoice\' : \'list_invoices\',\n        entity: \'invoice\',\n        filters: Object.keys(filters).length > 0 ? filters : undefined,\n        timeRange: timeRange.relative ? timeRange : undefined,\n      };\n    }\n    \n    if (lowerInput.includes(\'employee\') || lowerInput.includes(\'team\')) {\n      const filters: Record<string, unknown> = {};\n      if (lowerInput.includes(\'engineering\')) filters.department = \'Engineering\';\n      if (lowerInput.includes(\'sales\')) filters.department = \'Sales\';\n      \n      return {\n        action: \'list_employees\',\n        entity: \'employee\',\n        filters: Object.keys(filters).length > 0 ? filters : undefined,\n      };\n    }\n    \n    if (lowerInput.includes(\'cash\') || lowerInput.includes(\'balance\') || lowerInput.includes(\'bank\')) {\n      return {\n        action: \'get_cash_balance\',\n        entity: \'treasury\',\n      };\n    }\n    \n    if (lowerInput.includes(\'report\')) {\n      return {\n        action: \'run_report\',\n        entity: \'report\',\n        parameters: { reportType: \'financial\' },\n      };\n    }\n    \n    if (lowerInput.includes(\'approve\') || lowerInput.includes(\'reject\')) {\n      return {\n        action: \'manage_approvals\',\n        entity: \'approval\',\n        parameters: { action: lowerInput.includes(\'approve\') ? \'approve\' : \'reject\' },\n      };\n    }\n    \n    return {\n      action: \'unknown\',\n    };\n  }, []);\n\n  const generateSuggestions = useCallback((input: string): string[] => {\n    if (!input.trim()) {\n      return [\n        \'Show all unpaid invoices\',\n        \'What is our cash balance?\',\n        \'List employees in Engineering\',\n        \'Run the monthly financial report\',\n      ];\n    }\n\n    const lowerInput = input.toLowerCase();\n    const matchingTemplates = intentTemplates.filter(template =>\n      template.patterns.some(pattern => {\n        const patternLower = pattern.toLowerCase();\n        const keywords = patternLower.replace(/[()*|]/g, \'\').split(/\\s+/);\n        return keywords.some(kw => kw.length > 2 && lowerInput.includes(kw));\n      })\n    );\n\n    return matchingTemplates.flatMap(t => t.examples).slice(0, 5);\n  }, [intentTemplates]);\n\n  const executeCommand = useCallback(async (input: string) => {\n    if (!input.trim()) return;\n\n    const id = `cmd-${Date.now()}`;\n    const parsedIntent = parseIntent(input);\n    const confidence = parsedIntent.action === \'unknown\' ? 0.3 : 0.85 + Math.random() * 0.14;\n\n    const newCommand: Command = {\n      id,\n      input,\n      parsedIntent,\n      confidence,\n      suggestions: generateSuggestions(input),\n      status: \'pending\',\n      createdAt: new Date(),\n    };\n\n    setCommands(prev => [newCommand, ...prev]);\n    setIsProcessing(true);\n\n    // Simulate command execution\n    await new Promise(resolve => setTimeout(resolve, 1000 + Math.random() * 2000));\n\n    const success = Math.random() > 0.1; // 90% success rate\n\n    setCommands(prev => prev.map(cmd => {\n      if (cmd.id !== id) return cmd;\n      return {\n        ...cmd,\n        status: success ? \'completed\' : \'failed\',\n        result: success ? { simulated: true, data: \'Command executed successfully\' } : undefined,\n        error: success ? undefined : \'Failed to execute command. Please try again.\',\n        completedAt: new Date(),\n      };\n    }));\n\n    setIsProcessing(false);\n  }, [parseIntent, generateSuggestions]);\n\n  const cancelCommand = useCallback((id: string) => {\n    setCommands(prev => prev.map(cmd =>\n      cmd.id === id ? { ...cmd, status: \'cancelled\' as const } : cmd\n    ));\n  }, []);\n\n  const retryCommand = useCallback(async (id: string) => {\n    const command = commands.find(c => c.id === id);\n    if (command) {\n      setCommands(prev => prev.map(cmd =>\n        cmd.id === id ? { ...cmd, status: \'pending\' as const } : cmd\n      ));\n      await executeCommand(command.input);\n    }\n  }, [commands, executeCommand]);\n\n  const clearHistory = useCallback(() => {\n    setCommands([]);\n  }, []);\n\n  const getSuggestions = useCallback((input: string) => {\n    return generateSuggestions(input);\n  }, [generateSuggestions]);\n\n  // Update suggestions when input changes\n  useEffect(() => {\n    setSuggestions(generateSuggestions(currentInput));\n  }, [currentInput, generateSuggestions]);\n\n  const value = useMemo(() => ({\n    commands,\n    currentInput,\n    isProcessing,\n    suggestions,\n    intentTemplates,\n    setCurrentInput,\n    executeCommand,\n    cancelCommand,\n    retryCommand,\n    clearHistory,\n    getSuggestions,\n  }), [\n    commands, currentInput, isProcessing, suggestions, intentTemplates,\n    setCurrentInput, executeCommand, cancelCommand, retryCommand, clearHistory, getSuggestions,\n  ]);\n\n  return (\n    <NLCommandContext.Provider value={value}>\n      {children}\n    </NLCommandContext.Provider>\n  );\n};\n\n// ============================================================================\n// COMMAND INPUT COMPONENT\n// ============================================================================\n\ninterface CommandInputProps {\n  onSubmit?: (input: string) => void;\n  placeholder?: string;\n  showSuggestions?: boolean;\n}\n\nexport const CommandInput: React.FC<CommandInputProps> = ({\n  onSubmit,\n  placeholder = \'Type a command or ask a question...\',\n  showSuggestions = true,\n}) => {\n  const { currentInput, setCurrentInput, executeCommand, suggestions, isProcessing } = useNLCommand();\n  const [showSuggestionList, setShowSuggestionList] = useState(false);\n  const inputRef = useRef<HTMLInputElement>(null);\n\n  const handleSubmit = async (e: React.FormEvent) => {\n    e.preventDefault();\n    if (currentInput.trim()) {\n      await executeCommand(currentInput);\n      setCurrentInput(\'\');\n      if (onSubmit) onSubmit(currentInput);\n    }\n  };\n\n  const handleSuggestionClick = (suggestion: string) => {\n    setCurrentInput(suggestion);\n    setShowSuggestionList(false);\n    inputRef.current?.focus();\n  };\n\n  return (\n    <div className="relative">\n      <form onSubmit={handleSubmit} className="relative">\n        <div className="flex items-center gap-2 bg-white border rounded-xl shadow-sm focus-within:ring-2 focus-within:ring-blue-500 focus-within:border-blue-500">\n          <div className="pl-4 text-gray-400">\n            <svg className="w-5 h-5" fill="none" stroke="currentColor" viewBox="0 0 24 24">\n              <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M8 10h.01M12 10h.01M16 10h.01M9 16H5a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v8a2 2 0 01-2 2h-5l-5 5v-5z" />\n            </svg>\n          </div>\n          <input\n            ref={inputRef}\n            type="text"\n            value={currentInput}\n            onChange={(e) => setCurrentInput(e.target.value)}\n            onFocus={() => setShowSuggestionList(true)}\n            onBlur={() => setTimeout(() => setShowSuggestionList(false), 200)}\n            placeholder={placeholder}\n            className="flex-1 py-3 pr-4 outline-none text-gray-900 placeholder-gray-400"\n            disabled={isProcessing}\n          />\n          {isProcessing && (\n            <div className="pr-3">\n              <svg className="w-5 h-5 animate-spin text-blue-500" fill="none" viewBox="0 0 24 24">\n                <circle className="opacity-25" cx="12" cy="12" r="10" stroke="currentColor" strokeWidth="4" />\n                <path className="opacity-75" fill="currentColor" d="M4 12a8 8 0 018-8V0C5.373 0 0 5.373 0 12h4z" />\n              </svg>\n            </div>\n          )}\n          <button\n            type="submit"\n            disabled={!currentInput.trim() || isProcessing}\n            className="mr-2 px-4 py-1.5 bg-blue-500 text-white rounded-lg text-sm font-medium hover:bg-blue-600 disabled:opacity-50 disabled:cursor-not-allowed transition-colors"\n          >\n            Execute\n          </button>\n        </div>\n      </form>\n\n      {/* Suggestions dropdown */}\n      {showSuggestions && showSuggestionList && suggestions.length > 0 && (\n        <div className="absolute top-full left-0 right-0 mt-1 bg-white border rounded-lg shadow-lg z-50 max-h-64 overflow-y-auto">\n          {suggestions.map((suggestion, idx) => (\n            <button\n              key={idx}\n              onClick={() => handleSuggestionClick(suggestion)}\n              className="w-full px-4 py-2 text-left hover:bg-blue-50 text-sm text-gray-700 flex items-center gap-2"\n            >\n              <span className="text-gray-400">→</span>\n              {suggestion}\n            </button>\n          ))}\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// COMMAND HISTORY COMPONENT\n// ============================================================================\n\ninterface CommandHistoryProps {\n  maxItems?: number;\n  showResults?: boolean;\n}\n\nexport const CommandHistory: React.FC<CommandHistoryProps> = ({\n  maxItems = 10,\n  showResults = true,\n}) => {\n  const { commands, retryCommand, cancelCommand } = useNLCommand();\n  const displayCommands = commands.slice(0, maxItems);\n\n  const getStatusIcon = (status: Command[\'status\']) => {\n    switch (status) {\n      case \'completed\': return \'✅\';\n      case \'failed\': return \'❌\';\n      case \'pending\': return \'⏳\';\n      case \'executing\': return \'🔄\';\n      case \'cancelled\': return \'🚫\';\n      default: return \'❓\';\n    }\n  };\n\n  const getStatusColor = (status: Command[\'status\']) => {\n    switch (status) {\n      case \'completed\': return \'text-green-600 bg-green-50\';\n      case \'failed\': return \'text-red-600 bg-red-50\';\n      case \'pending\': return \'text-yellow-600 bg-yellow-50\';\n      case \'executing\': return \'text-blue-600 bg-blue-50\';\n      case \'cancelled\': return \'text-gray-600 bg-gray-50\';\n      default: return \'text-gray-600 bg-gray-50\';\n    }\n  };\n\n  const formatTime = (date: Date) => {\n    return new Date(date).toLocaleTimeString(\'en-US\', {\n      hour: \'2-digit\',\n      minute: \'2-digit\',\n    });\n  };\n\n  return (\n    <div className="space-y-3">\n      {displayCommands.map(command => (\n        <div key={command.id} className="border rounded-lg bg-white overflow-hidden">\n          <div className="p-3 flex items-start gap-3">\n            <span className="text-lg">{getStatusIcon(command.status)}</span>\n            <div className="flex-1 min-w-0">\n              <p className="text-sm font-medium text-gray-900 truncate">{command.input}</p>\n              <div className="flex items-center gap-2 mt-1">\n                <span className={`px-2 py-0.5 text-xs font-medium rounded-full ${getStatusColor(command.status)}`}>\n                  {command.status}\n                </span>\n                <span className="text-xs text-gray-500">\n                  {formatTime(command.createdAt)}\n                </span>\n                <span className="text-xs text-gray-400">\n                  Confidence: {Math.round(command.confidence * 100)}%\n                </span>\n              </div>\n            </div>\n            <div className="flex gap-1">\n              {command.status === \'pending\' && (\n                <button\n                  onClick={() => cancelCommand(command.id)}\n                  className="p-1 text-gray-500 hover:text-gray-700 hover:bg-gray-100 rounded"\n                  title="Cancel"\n                >\n                  ✕\n                </button>\n              )}\n              {command.status === \'failed\' && (\n                <button\n                  onClick={() => retryCommand(command.id)}\n                  className="p-1 text-blue-500 hover:text-blue-700 hover:bg-blue-50 rounded"\n                  title="Retry"\n                >\n                  ↻\n                </button>\n              )}\n            </div>\n          </div>\n\n          {/* Result preview */}\n          {showResults && command.result && command.status === \'completed\' && (\n            <div className="px-3 pb-3 pt-0">\n              <div className="bg-gray-50 rounded-lg p-3">\n                <pre className="text-xs text-gray-700 overflow-auto max-h-32">\n                  {JSON.stringify(command.result, null, 2)}\n                </pre>\n              </div>\n            </div>\n          )}\n\n          {/* Error message */}\n          {command.error && (\n            <div className="px-3 pb-3 pt-0">\n              <div className="bg-red-50 rounded-lg p-3 text-sm text-red-700">\n                {command.error}\n              </div>\n            </div>\n          )}\n\n          {/* Suggestions */}\n          {command.suggestions.length > 0 && command.status === \'completed\' && (\n            <div className="px-3 pb-3 pt-0">\n              <p className="text-xs text-gray-500 mb-2">Related actions:</p>\n              <div className="flex flex-wrap gap-1">\n                {command.suggestions.slice(0, 3).map((suggestion, idx) => (\n                  <button\n                    key={idx}\n                    className="px-2 py-1 text-xs bg-gray-100 hover:bg-gray-200 rounded text-gray-700"\n                  >\n                    {suggestion}\n                  </button>\n                ))}\n              </div>\n            </div>\n          )}\n        </div>\n      ))}\n\n      {displayCommands.length === 0 && (\n        <div className="text-center py-8 text-gray-500">\n          <p className="text-sm">No commands yet</p>\n          <p className="text-xs mt-1">Start by typing a command above</p>\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// INTENT TEMPLATES PANEL\n// ============================================================================\n\nexport const IntentTemplatesPanel: React.FC = () => {\n  const { intentTemplates } = useNLCommand();\n  const [expandedTemplate, setExpandedTemplate] = useState<string | null>(null);\n\n  return (\n    <div className="space-y-3">\n      <h3 className="text-sm font-medium text-gray-700 px-1">Available Commands</h3>\n      {intentTemplates.map(template => (\n        <div key={template.id} className="border rounded-lg bg-white overflow-hidden">\n          <button\n            onClick={() => setExpandedTemplate(expandedTemplate === template.id ? null : template.id)}\n            className="w-full px-3 py-2 flex items-center justify-between hover:bg-gray-50"\n          >\n            <span className="text-sm font-medium text-gray-900">{template.description}</span>\n            <svg\n              className={`w-4 h-4 text-gray-500 transition-transform ${expandedTemplate === template.id ? \'rotate-180\' : \'\'}`}\n              fill="none"\n              stroke="currentColor"\n              viewBox="0 0 24 24"\n            >\n              <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={2} d="M19 9l-7 7-7-7" />\n            </svg>\n          </button>\n\n          {expandedTemplate === template.id && (\n            <div className="px-3 pb-3 border-t bg-gray-50">\n              <div className="mt-2">\n                <p className="text-xs text-gray-500 mb-2">Examples:</p>\n                <div className="space-y-1">\n                  {template.examples.map((example, idx) => (\n                    <div\n                      key={idx}\n                      className="text-xs bg-white px-2 py-1.5 rounded border text-gray-700"\n                    >\n                      "{example}"\n                    </div>\n                  ))}\n                </div>\n              </div>\n\n              <div className="mt-3">\n                <p className="text-xs text-gray-500 mb-2">Parameters:</p>\n                <div className="space-y-1">\n                  {template.parameters.map((param, idx) => (\n                    <div key={idx} className="flex items-center gap-2 text-xs">\n                      <span className="font-mono bg-blue-100 text-blue-700 px-1 rounded">{param.name}</span>\n                      <span className="text-gray-500">{param.type}</span>\n                      {param.required && <span className="text-red-500">*</span>}\n                    </div>\n                  ))}\n                </div>\n              </div>\n            </div>\n          )}\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN NATURAL LANGUAGE COMMANDS COMPONENT\n// ============================================================================\n\nexport const NaturalLanguageCommands: React.FC = () => {\n  return (\n    <div className="h-full flex">\n      {/* Main command area */}\n      <div className="flex-1 flex flex-col">\n        <div className="p-4 border-b bg-white">\n          <h1 className="text-xl font-semibold mb-4">Natural Language Commands</h1>\n          <CommandInput />\n        </div>\n\n        <div className="flex-1 overflow-auto p-4 bg-gray-50">\n          <CommandHistory maxItems={20} />\n        </div>\n      </div>\n\n      {/* Sidebar */}\n      <div className="w-80 border-l bg-white overflow-auto p-4">\n        <IntentTemplatesPanel />\n      </div>\n    </div>\n  );\n};\n\nexport default NaturalLanguageCommands;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/ai/natural-language-commands.tsx\' created successfully.") </create-file> </tool_result>'}
{'role': 'assistant', 'content': 'Now let me create the Anomaly Detection component for the AI System.\n\n<function_calls>\n<create-file file_path="frontend/src/components/ai/anomaly-detection.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst AnomalySchema = z.object({\n  id: z.string(),\n  type: z.enum([\n    \'transaction_anomaly\',\n    \'balance_anomaly\',\n    \'pattern_anomaly\',\n    \'behavioral_anomaly\',\n    \'compliance_anomaly\',\n    \'fraud_indicator\',\n    \'data_quality\',\n    \'threshold_breach\',\n  ]),\n  severity: z.enum([\'low\', \'medium\', \'high\', \'critical\']),\n  status: z.enum([\'new\', \'acknowledged\', \'investigating\', \'resolved\', \'false_positive\', \'ignored\']),\n  title: z.string(),\n  description: z.string(),\n  entity: z.object({\n    type: z.string(),\n    id: z.string(),\n    name: z.string(),\n  }),\n  detectedAt: z.date(),\n  detectedBy: z.enum([\'ai_model\', \'rule_engine\', \'threshold\', \'manual\']),\n  modelConfidence: z.number().min(0).max(1),\n  metadata: z.record(z.unknown()),\n  relatedEntities: z.array(z.object({\n    type: z.string(),\n    id: z.string(),\n    name: z.string(),\n    relationship: z.string(),\n  })).optional(),\n  metrics: z.object({\n    expectedValue: z.number().optional(),\n    actualValue: z.number().optional(),\n    deviation: z.number().optional(),\n    zScore: z.number().optional(),\n    percentile: z.number().optional(),\n  }).optional(),\n  timeline: z.array(z.object({\n    timestamp: z.date(),\n    event: z.string(),\n    userId: z.string().optional(),\n    details: z.record(z.unknown()).optional(),\n  })).optional(),\n  assignedTo: z.string().optional(),\n  resolvedAt: z.date().optional(),\n  resolution: z.string().optional(),\n  impact: z.object({\n    financial: z.number().optional(),\n    operational: z.string().optional(),\n    compliance: z.boolean().optional(),\n  }).optional(),\n});\n\nconst AnomalyRuleSchema = z.object({\n  id: z.string(),\n  name: z.string(),\n  description: z.string(),\n  type: z.enum([\'statistical\', \'threshold\', \'ml\', \'pattern\', \'behavioral\']),\n  module: z.string(),\n  enabled: z.boolean(),\n  sensitivity: z.number().min(0).max(1),\n  parameters: z.record(z.unknown()),\n  lastTriggered: z.date().optional(),\n  triggerCount: z.number(),\n});\n\ntype Anomaly = z.infer<typeof AnomalySchema>;\ntype AnomalyRule = z.infer<typeof AnomalyRuleSchema>;\n\n// ============================================================================\n// ANOMALY DETECTION STORE\n// ============================================================================\n\ninterface AnomalyStore {\n  anomalies: Anomaly[];\n  rules: AnomalyRule[];\n  selectedAnomaly: Anomaly | null;\n  filters: {\n    type: string[];\n    severity: string[];\n    status: string[];\n    module: string[];\n    dateRange: { start: Date | null; end: Date | null };\n  };\n  \n  // Actions\n  acknowledgeAnomaly: (id: string) => void;\n  investigateAnomaly: (id: string, assignedTo: string) => void;\n  resolveAnomaly: (id: string, resolution: string) => void;\n  markFalsePositive: (id: string, reason: string) => void;\n  ignoreAnomaly: (id: string) => void;\n  \n  // Rule Actions\n  enableRule: (id: string) => void;\n  disableRule: (id: string) => void;\n  updateRuleSensitivity: (id: string, sensitivity: number) => void;\n  \n  // Filters\n  setFilters: (filters: Partial<AnomalyStore[\'filters\']>) => void;\n  clearFilters: () => void;\n  \n  // Stats\n  getStats: () => {\n    total: number;\n    new: number;\n    critical: number;\n    resolved: number;\n    falsePositives: number;\n    avgResolutionTime: number;\n  };\n}\n\nconst AnomalyContext = createContext<AnomalyStore | null>(null);\n\nexport const useAnomalyDetection = () => {\n  const context = useContext(AnomalyContext);\n  if (!context) {\n    throw new Error(\'useAnomalyDetection must be used within AnomalyProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst sampleAnomalies: Anomaly[] = [\n  {\n    id: \'anom-001\',\n    type: \'transaction_anomaly\',\n    severity: \'critical\',\n    status: \'new\',\n    title: \'Unusual Large Transaction Detected\',\n    description: \'Transaction of $125,000 detected, which is 5x the average transaction amount for this vendor. Pattern suggests potential fraud or error.\',\n    entity: { type: \'transaction\', id: \'txn-12345\', name: \'Payment to Vendor ABC\' },\n    detectedAt: new Date(\'2024-01-20T14:30:00\'),\n    detectedBy: \'ai_model\',\n    modelConfidence: 0.92,\n    metadata: {\n      vendorId: \'vendor-abc\',\n      vendorName: \'ABC Supplies Inc.\',\n      transactionType: \'wire_transfer\',\n      averageAmount: 25000,\n      frequency: \'monthly\',\n    },\n    relatedEntities: [\n      { type: \'vendor\', id: \'vendor-abc\', name: \'ABC Supplies Inc.\', relationship: \'payee\' },\n      { type: \'account\', id: \'acc-001\', name: \'Operating Account\', relationship: \'source\' },\n    ],\n    metrics: {\n      expectedValue: 25000,\n      actualValue: 125000,\n      deviation: 100000,\n      zScore: 4.2,\n      percentile: 99.5,\n    },\n    timeline: [\n      { timestamp: new Date(\'2024-01-20T14:30:00\'), event: \'Anomaly detected by AI model\' },\n      { timestamp: new Date(\'2024-01-20T14:31:00\'), event: \'Auto-flagged for review\' },\n    ],\n    impact: {\n      financial: 125000,\n      compliance: true,\n    },\n  },\n  {\n    id: \'anom-002\',\n    type: \'balance_anomaly\',\n    severity: \'high\',\n    status: \'investigating\',\n    title: \'Account Balance Discrepancy\',\n    description: \'Treasury account shows unexpected balance decrease of $45,000. No corresponding transactions found in the last 24 hours.\',\n    entity: { type: \'account\', id: \'acc-002\', name: \'Payroll Account\' },\n    detectedAt: new Date(\'2024-01-20T09:15:00\'),\n    detectedBy: \'threshold\',\n    modelConfidence: 0.85,\n    metadata: {\n      accountId: \'acc-002\',\n      accountType: \'payroll\',\n      previousBalance: 250000,\n      currentBalance: 205000,\n    },\n    metrics: {\n      expectedValue: 250000,\n      actualValue: 205000,\n      deviation: -45000,\n      zScore: -2.8,\n    },\n    timeline: [\n      { timestamp: new Date(\'2024-01-20T09:15:00\'), event: \'Anomaly detected by threshold rule\' },\n      { timestamp: new Date(\'2024-01-20T09:20:00\'), event: \'Assigned to Finance Team\', userId: \'user-001\' },\n      { timestamp: new Date(\'2024-01-20T10:00:00\'), event: \'Investigation started\', userId: \'user-002\' },\n    ],\n    assignedTo: \'user-002\',\n    impact: {\n      financial: 45000,\n      operational: \'Payroll processing may be affected\',\n    },\n  },\n  {\n    id: \'anom-003\',\n    type: \'behavioral_anomaly\',\n    severity: \'medium\',\n    status: \'acknowledged\',\n    title: \'Unusual Login Pattern\',\n    description: \'User accessed system from 3 different geographic locations within 2 hours. Locations: New York, London, Singapore.\',\n    entity: { type: \'user\', id: \'user-456\', name: \'john.doe@company.com\' },\n    detectedAt: new Date(\'2024-01-20T08:00:00\'),\n    detectedBy: \'ai_model\',\n    modelConfidence: 0.78,\n    metadata: {\n      userId: \'user-456\',\n      userEmail: \'john.doe@company.com\',\n      locations: [\'New York, US\', \'London, UK\', \'Singapore, SG\'],\n      timeSpan: \'2 hours\',\n    },\n    timeline: [\n      { timestamp: new Date(\'2024-01-20T06:00:00\'), event: \'Login from New York\' },\n      { timestamp: new Date(\'2024-01-20T07:15:00\'), event: \'Login from London\' },\n      { timestamp: new Date(\'2024-01-20T08:00:00\'), event: \'Login from Singapore\' },\n      { timestamp: new Date(\'2024-01-20T08:05:00\'), event: \'Anomaly detected\' },\n      { timestamp: new Date(\'2024-01-20T09:00:00\'), event: \'Acknowledged by Security Team\', userId: \'security-001\' },\n    ],\n    assignedTo: \'security-001\',\n  },\n  {\n    id: \'anom-004\',\n    type: \'fraud_indicator\',\n    severity: \'critical\',\n    status: \'new\',\n    title: \'Potential Invoice Fraud Detected\',\n    description: \'Invoice #INV-2024-567 shows signs of fraud: vendor bank account changed recently, amount slightly below approval threshold, and invoice date matches previous fraud patterns.\',\n    entity: { type: \'invoice\', id: \'INV-2024-567\', name: \'Invoice #INV-2024-567\' },\n    detectedAt: new Date(\'2024-01-20T11:45:00\'),\n    detectedBy: \'ai_model\',\n    modelConfidence: 0.89,\n    metadata: {\n      invoiceId: \'INV-2024-567\',\n      vendorId: \'vendor-xyz\',\n      vendorName: \'XYZ Services\',\n      amount: 4950,\n      approvalThreshold: 5000,\n      bankAccountChanged: true,\n      bankAccountChangeDate: \'2024-01-18\',\n    },\n    relatedEntities: [\n      { type: \'vendor\', id: \'vendor-xyz\', name: \'XYZ Services\', relationship: \'vendor\' },\n    ],\n    metrics: {\n      actualValue: 4950,\n      deviation: 50,\n    },\n    impact: {\n      financial: 4950,\n      compliance: true,\n    },\n  },\n  {\n    id: \'anom-005\',\n    type: \'compliance_anomaly\',\n    severity: \'high\',\n    status: \'resolved\',\n    title: \'Missing Tax Filing Deadline\',\n    description: \'Sales tax filing for Texas nexus was due on January 20th but was not submitted. Potential penalties may apply.\',\n    entity: { type: \'tax_filing\', id: \'tax-tx-2024-q1\', name: \'Texas Sales Tax Q1 2024\' },\n    detectedAt: new Date(\'2024-01-20T00:00:00\'),\n    detectedBy: \'rule_engine\',\n    modelConfidence: 1.0,\n    metadata: {\n      jurisdiction: \'Texas\',\n      taxType: \'sales_tax\',\n      period: \'Q1 2024\',\n      dueDate: \'2024-01-20\',\n    },\n    timeline: [\n      { timestamp: new Date(\'2024-01-20T00:00:00\'), event: \'Deadline passed - no filing detected\' },\n      { timestamp: new Date(\'2024-01-20T08:00:00\'), event: \'Assigned to Tax Team\', userId: \'tax-lead\' },\n      { timestamp: new Date(\'2024-01-20T10:30:00\'), event: \'Filing submitted\', userId: \'tax-lead\' },\n      { timestamp: new Date(\'2024-01-20T10:45:00\'), event: \'Resolved - late filing submitted\' },\n    ],\n    assignedTo: \'tax-lead\',\n    resolvedAt: new Date(\'2024-01-20T10:45:00\'),\n    resolution: \'Late filing submitted. Penalty assessment pending.\',\n    impact: {\n      compliance: true,\n    },\n  },\n  {\n    id: \'anom-006\',\n    type: \'pattern_anomaly\',\n    severity: \'low\',\n    status: \'false_positive\',\n    title: \'Expense Pattern Deviation\',\n    description: \'Employee expense submissions show unusual pattern this month, concentrated in week 3 instead of spread across the month.\',\n    entity: { type: \'user\', id: \'user-789\', name: \'jane.smith@company.com\' },\n    detectedAt: new Date(\'2024-01-19T16:00:00\'),\n    detectedBy: \'ai_model\',\n    modelConfidence: 0.65,\n    metadata: {\n      employeeId: \'user-789\',\n      department: \'Sales\',\n      typicalPattern: \'spread\',\n      currentPattern: \'concentrated\',\n    },\n    timeline: [\n      { timestamp: new Date(\'2024-01-19T16:00:00\'), event: \'Pattern deviation detected\' },\n      { timestamp: new Date(\'2024-01-19T17:00:00\'), event: \'Reviewed by manager\', userId: \'manager-001\' },\n      { timestamp: new Date(\'2024-01-19T17:30:00\'), event: \'Marked as false positive - employee was traveling\' },\n    ],\n    resolvedAt: new Date(\'2024-01-19T17:30:00\'),\n    resolution: \'False positive - employee was on business travel, expenses submitted upon return\',\n  },\n];\n\nconst sampleRules: AnomalyRule[] = [\n  {\n    id: \'rule-001\',\n    name: \'Large Transaction Alert\',\n    description: \'Flags transactions exceeding 3x the average for the vendor/employee\',\n    type: \'statistical\',\n    module: \'treasury\',\n    enabled: true,\n    sensitivity: 0.7,\n    parameters: { multiplier: 3, lookbackDays: 90 },\n    triggerCount: 45,\n  },\n  {\n    id: \'rule-002\',\n    name: \'Balance Threshold Monitor\',\n    description: \'Alerts when account balance changes by more than 10% unexpectedly\',\n    type: \'threshold\',\n    module: \'treasury\',\n    enabled: true,\n    sensitivity: 0.8,\n    parameters: { thresholdPercent: 10, timeWindow: \'24h\' },\n    triggerCount: 23,\n    lastTriggered: new Date(\'2024-01-20T09:15:00\'),\n  },\n  {\n    id: \'rule-003\',\n    name: \'Fraud Detection Model\',\n    description: \'ML model trained on historical fraud patterns\',\n    type: \'ml\',\n    module: \'invoicing\',\n    enabled: true,\n    sensitivity: 0.75,\n    parameters: { modelVersion: \'v2.1\', minConfidence: 0.7 },\n    triggerCount: 12,\n    lastTriggered: new Date(\'2024-01-20T11:45:00\'),\n  },\n  {\n    id: \'rule-004\',\n    name: \'Login Behavior Analysis\',\n    description: \'Detects unusual login patterns including impossible travel\',\n    type: \'behavioral\',\n    module: \'auth\',\n    enabled: true,\n    sensitivity: 0.6,\n    parameters: { maxLocations: 2, timeWindow: \'2h\' },\n    triggerCount: 8,\n    lastTriggered: new Date(\'2024-01-20T08:00:00\'),\n  },\n  {\n    id: \'rule-005\',\n    name: \'Compliance Deadline Monitor\',\n    description: \'Tracks and alerts on missed compliance deadlines\',\n    type: \'rule_engine\',\n    module: \'compliance\',\n    enabled: true,\n    sensitivity: 1.0,\n    parameters: { alertBefore: \'3d\', escalateAfter: \'1d\' },\n    triggerCount: 5,\n    lastTriggered: new Date(\'2024-01-20T00:00:00\'),\n  },\n];\n\n// ============================================================================\n// ANOMALY PROVIDER\n// ============================================================================\n\nexport const AnomalyProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [anomalies, setAnomalies] = useState<Anomaly[]>(sampleAnomalies);\n  const [rules, setRules] = useState<AnomalyRule[]>(sampleRules);\n  const [selectedAnomaly, setSelectedAnomaly] = useState<Anomaly | null>(null);\n  const [filters, setFiltersState] = useState<AnomalyStore[\'filters\']>({\n    type: [],\n    severity: [],\n    status: [],\n    module: [],\n    dateRange: { start: null, end: null },\n  });\n\n  const acknowledgeAnomaly = useCallback((id: string) => {\n    setAnomalies(prev => prev.map(a =>\n      a.id === id ? { ...a, status: \'acknowledged\' as const } : a\n    ));\n  }, []);\n\n  const investigateAnomaly = useCallback((id: string, assignedTo: string) => {\n    setAnomalies(prev => prev.map(a =>\n      a.id === id ? { ...a, status: \'investigating\' as const, assignedTo } : a\n    ));\n  }, []);\n\n  const resolveAnomaly = useCallback((id: string, resolution: string) => {\n    setAnomalies(prev => prev.map(a =>\n      a.id === id ? {\n        ...a,\n        status: \'resolved\' as const,\n        resolution,\n        resolvedAt: new Date(),\n      } : a\n    ));\n  }, []);\n\n  const markFalsePositive = useCallback((id: string, reason: string) => {\n    setAnomalies(prev => prev.map(a =>\n      a.id === id ? {\n        ...a,\n        status: \'false_positive\' as const,\n        resolution: reason,\n        resolvedAt: new Date(),\n      } : a\n    ));\n  }, []);\n\n  const ignoreAnomaly = useCallback((id: string) => {\n    setAnomalies(prev => prev.map(a =>\n      a.id === id ? { ...a, status: \'ignored\' as const } : a\n    ));\n  }, []);\n\n  const enableRule = useCallback((id: string) => {\n    setRules(prev => prev.map(r =>\n      r.id === id ? { ...r, enabled: true } : r\n    ));\n  }, []);\n\n  const disableRule = useCallback((id: string) => {\n    setRules(prev => prev.map(r =>\n      r.id === id ? { ...r, enabled: false } : r\n    ));\n  }, []);\n\n  const updateRuleSensitivity = useCallback((id: string, sensitivity: number) => {\n    setRules(prev => prev.map(r =>\n      r.id === id ? { ...r, sensitivity } : r\n    ));\n  }, []);\n\n  const setFilters = useCallback((newFilters: Partial<AnomalyStore[\'filters\']>) => {\n    setFiltersState(prev => ({ ...prev, ...newFilters }));\n  }, []);\n\n  const clearFilters = useCallback(() => {\n    setFiltersState({\n      type: [],\n      severity: [],\n      status: [],\n      module: [],\n      dateRange: { start: null, end: null },\n    });\n  }, []);\n\n  const getStats = useCallback(() => {\n    const total = anomalies.length;\n    const newCount = anomalies.filter(a => a.status === \'new\').length;\n    const critical = anomalies.filter(a => a.severity === \'critical\' && a.status !== \'resolved\' && a.status !== \'false_positive\').length;\n    const resolved = anomalies.filter(a => a.status === \'resolved\').length;\n    const falsePositives = anomalies.filter(a => a.status === \'false_positive\').length;\n\n    const resolvedAnomalies = anomalies.filter(a => a.resolvedAt && a.detectedAt);\n    const avgResolutionTime = resolvedAnomalies.length > 0\n      ? resolvedAnomalies.reduce((sum, a) => {\n          const diff = a.resolvedAt!.getTime() - a.detectedAt.getTime();\n          return sum + (diff / (1000 * 60 * 60)); // hours\n        }, 0) / resolvedAnomalies.length\n      : 0;\n\n    return { total, new: newCount, critical, resolved, falsePositives, avgResolutionTime };\n  }, [anomalies]);\n\n  const value = useMemo(() => ({\n    anomalies,\n    rules,\n    selectedAnomaly,\n    filters,\n    acknowledgeAnomaly,\n    investigateAnomaly,\n    resolveAnomaly,\n    markFalsePositive,\n    ignoreAnomaly,\n    enableRule,\n    disableRule,\n    updateRuleSensitivity,\n    setFilters,\n    clearFilters,\n    getStats,\n  }), [\n    anomalies, rules, selectedAnomaly, filters,\n    acknowledgeAnomaly, investigateAnomaly, resolveAnomaly, markFalsePositive, ignoreAnomaly,\n    enableRule, disableRule, updateRuleSensitivity,\n    setFilters, clearFilters, getStats,\n  ]);\n\n  return (\n    <AnomalyContext.Provider value={value}>\n      {children}\n    </AnomalyContext.Provider>\n  );\n};\n\n// ============================================================================\n// ANOMALY LIST COMPONENT\n// ============================================================================\n\ninterface AnomalyListProps {\n  onSelectAnomaly: (anomaly: Anomaly) => void;\n}\n\nexport const AnomalyList: React.FC<AnomalyListProps> = ({ onSelectAnomaly }) => {\n  const { anomalies, filters } = useAnomalyDetection();\n\n  const filteredAnomalies = useMemo(() => {\n    return anomalies.filter(a => {\n      if (filters.type.length > 0 && !filters.type.includes(a.type)) return false;\n      if (filters.severity.length > 0 && !filters.severity.includes(a.severity)) return false;\n      if (filters.status.length > 0 && !filters.status.includes(a.status)) return false;\n      if (filters.dateRange.start && new Date(a.detectedAt) < filters.dateRange.start) return false;\n      if (filters.dateRange.end && new Date(a.detectedAt) > filters.dateRange.end) return false;\n      return true;\n    });\n  }, [anomalies, filters]);\n\n  const getSeverityColor = (severity: Anomaly[\'severity\']) => {\n    const colors: Record<string, string> = {\n      low: \'bg-blue-100 text-blue-700 border-blue-200\',\n      medium: \'bg-yellow-100 text-yellow-700 border-yellow-200\',\n      high: \'bg-orange-100 text-orange-700 border-orange-200\',\n      critical: \'bg-red-100 text-red-700 border-red-200\',\n    };\n    return colors[severity];\n  };\n\n  const getStatusColor = (status: Anomaly[\'status\']) => {\n    const colors: Record<string, string> = {\n      new: \'bg-purple-100 text-purple-700\',\n      acknowledged: \'bg-blue-100 text-blue-700\',\n      investigating: \'bg-yellow-100 text-yellow-700\',\n      resolved: \'bg-green-100 text-green-700\',\n      false_positive: \'bg-gray-100 text-gray-700\',\n      ignored: \'bg-gray-100 text-gray-500\',\n    };\n    return colors[status];\n  };\n\n  const formatTime = (date: Date) => {\n    const now = new Date();\n    const diff = now.getTime() - new Date(date).getTime();\n    const minutes = Math.floor(diff / (1000 * 60));\n    const hours = Math.floor(diff / (1000 * 60 * 60));\n    const days = Math.floor(diff / (1000 * 60 * 60 * 24));\n\n    if (minutes < 60) return `${minutes}m ago`;\n    if (hours < 24) return `${hours}h ago`;\n    return `${days}d ago`;\n  };\n\n  return (\n    <div className="space-y-3">\n      {filteredAnomalies.map(anomaly => (\n        <div\n          key={anomaly.id}\n          onClick={() => onSelectAnomaly(anomaly)}\n          className={`border rounded-lg p-4 cursor-pointer hover:shadow-md transition-shadow bg-white ${getSeverityColor(anomaly.severity).split(\' \')[0]}`}\n        >\n          <div className="flex items-start justify-between mb-2">\n            <div className="flex items-center gap-2">\n              <span className={`px-2 py-0.5 text-xs font-semibold rounded ${getSeverityColor(anomaly.severity)}`}>\n                {anomaly.severity.toUpperCase()}\n              </span>\n              <span className={`px-2 py-0.5 text-xs rounded ${getStatusColor(anomaly.status)}`}>\n                {anomaly.status.replace(\'_\', \' \')}\n              </span>\n            </div>\n            <span className="text-xs text-gray-500">{formatTime(anomaly.detectedAt)}</span>\n          </div>\n\n          <h3 className="font-medium text-gray-900 mb-1">{anomaly.title}</h3>\n          <p className="text-sm text-gray-600 line-clamp-2">{anomaly.description}</p>\n\n          <div className="flex items-center gap-4 mt-3 text-xs text-gray-500">\n            <span>Entity: {anomaly.entity.name}</span>\n            <span>•</span>\n            <span>Confidence: {Math.round(anomaly.modelConfidence * 100)}%</span>\n          </div>\n        </div>\n      ))}\n\n      {filteredAnomalies.length === 0 && (\n        <div className="text-center py-8 text-gray-500">\n          <svg className="w-12 h-12 mx-auto mb-3 text-gray-300" fill="none" stroke="currentColor" viewBox="0 0 24 24">\n            <path strokeLinecap="round" strokeLinejoin="round" strokeWidth={1.5} d="M9 12l2 2 4-4m6 2a9 9 0 11-18 0 9 9 0 0118 0z" />\n          </svg>\n          <p>No anomalies match the current filters</p>\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// ANOMALY DETAIL COMPONENT\n// ============================================================================\n\ninterface AnomalyDetailProps {\n  anomaly: Anomaly;\n  onBack: () => void;\n}\n\nexport const AnomalyDetail: React.FC<AnomalyDetailProps> = ({ anomaly, onBack }) => {\n  const { acknowledgeAnomaly, investigateAnomaly, resolveAnomaly, markFalsePositive, ignoreAnomaly } = useAnomalyDetection();\n  const [showResolveDialog, setShowResolveDialog] = useState(false);\n  const [resolution, setResolution] = useState(\'\');\n\n  const getSeverityColor = (severity: Anomaly[\'severity\']) => {\n    const colors: Record<string, string> = {\n      low: \'bg-blue-500\',\n      medium: \'bg-yellow-500\',\n      high: \'bg-orange-500\',\n      critical: \'bg-red-500\',\n    };\n    return colors[severity];\n  };\n\n  return (\n    <div className="h-full flex flex-col bg-white">\n      {/* Header */}\n      <div className="border-b p-4">\n        <button\n          onClick={onBack}\n          className="flex items-center gap-1 text-sm text-gray-600 hover:text-gray-900 mb-3"\n        >\n          ← Back to list\n        </button>\n\n        <div className="flex items-start justify-between">\n          <div>\n            <div className="flex items-center gap-2 mb-1">\n              <span className={`w-3 h-3 rounded-full ${getSeverityColor(anomaly.severity)}`} />\n              <span className="text-sm text-gray-500">{anomaly.severity.toUpperCase()}</span>\n            </div>\n            <h1 className="text-xl font-semibold">{anomaly.title}</h1>\n          </div>\n          <span className="text-sm text-gray-500">\n            {new Date(anomaly.detectedAt).toLocaleString()}\n          </span>\n        </div>\n      </div>\n\n      {/* Content */}\n      <div className="flex-1 overflow-auto p-4">\n        <div className="space-y-6">\n          {/* Description */}\n          <div>\n            <h3 className="text-sm font-medium text-gray-700 mb-2">Description</h3>\n            <p className="text-sm text-gray-600">{anomaly.description}</p>\n          </div>\n\n          {/* Entity */}\n          <div>\n            <h3 className="text-sm font-medium text-gray-700 mb-2">Affected Entity</h3>\n            <div className="bg-gray-50 rounded-lg p-3">\n              <div className="flex items-center gap-2">\n                <span className="px-2 py-0.5 bg-blue-100 text-blue-700 text-xs rounded">{anomaly.entity.type}</span>\n                <span className="font-medium">{anomaly.entity.name}</span>\n              </div>\n            </div>\n          </div>\n\n          {/* Metrics */}\n          {anomaly.metrics && (\n            <div>\n              <h3 className="text-sm font-medium text-gray-700 mb-2">Metrics</h3>\n              <div className="grid grid-cols-2 gap-3">\n                {anomaly.metrics.expectedValue !== undefined && (\n                  <div className="bg-gray-50 rounded-lg p-3">\n                    <p className="text-xs text-gray-500">Expected</p>\n                    <p className="text-lg font-semibold">${anomaly.metrics.expectedValue.toLocaleString()}</p>\n                  </div>\n                )}\n                {anomaly.metrics.actualValue !== undefined && (\n                  <div className="bg-gray-50 rounded-lg p-3">\n                    <p className="text-xs text-gray-500">Actual</p>\n                    <p className="text-lg font-semibold">${anomaly.metrics.actualValue.toLocaleString()}</p>\n                  </div>\n                )}\n                {anomaly.metrics.deviation !== undefined && (\n                  <div className="bg-gray-50 rounded-lg p-3">\n                    <p className="text-xs text-gray-500">Deviation</p>\n                    <p className="text-lg font-semibold text-red-600">\n                      {anomaly.metrics.deviation > 0 ? \'+\' : \'\'}{anomaly.metrics.deviation.toLocaleString()}\n                    </p>\n                  </div>\n                )}\n                {anomaly.metrics.zScore !== undefined && (\n                  <div className="bg-gray-50 rounded-lg p-3">\n                    <p className="text-xs text-gray-500">Z-Score</p>\n                    <p className="text-lg font-semibold">{anomaly.metrics.zScore.toFixed(2)}</p>\n                  </div>\n                )}\n              </div>\n            </div>\n          )}\n\n          {/* Timeline */}\n          {anomaly.timeline && (\n            <div>\n              <h3 className="text-sm font-medium text-gray-700 mb-2">Timeline</h3>\n              <div className="space-y-3">\n                {anomaly.timeline.map((event, idx) => (\n                  <div key={idx} className="flex gap-3">\n                    <div className="flex flex-col items-center">\n                      <div className="w-2 h-2 rounded-full bg-blue-500" />\n                      {idx < anomaly.timeline!.length - 1 && (\n                        <div className="w-0.5 h-full bg-gray-200 mt-1" />\n                      )}\n                    </div>\n                    <div className="pb-3">\n                      <p className="text-sm font-medium">{event.event}</p>\n                      <p className="text-xs text-gray-500">\n                        {new Date(event.timestamp).toLocaleString()}\n                        {event.userId && ` • by ${event.userId}`}\n                      </p>\n                    </div>\n                  </div>\n                ))}\n              </div>\n            </div>\n          )}\n\n          {/* Impact */}\n          {anomaly.impact && (\n            <div>\n              <h3 className="text-sm font-medium text-gray-700 mb-2">Impact</h3>\n              <div className="bg-red-50 rounded-lg p-3">\n                {anomaly.impact.financial !== undefined && (\n                  <p className="text-sm">\n                    <span className="text-gray-600">Financial:</span>{\' \'}\n                    <span className="font-semibold text-red-700">${anomaly.impact.financial.toLocaleString()}</span>\n                  </p>\n                )}\n                {anomaly.impact.operational && (\n                  <p className="text-sm mt-1">\n                    <span className="text-gray-600">Operational:</span>{\' \'}\n                    <span>{anomaly.impact.operational}</span>\n                  </p>\n                )}\n                {anomaly.impact.compliance && (\n                  <p className="text-sm mt-1">\n                    <span className="text-gray-600">Compliance Risk:</span>{\' \'}\n                    <span className="text-red-700 font-medium">Yes</span>\n                  </p>\n                )}\n              </div>\n            </div>\n          )}\n\n          {/* Resolution */}\n          {anomaly.resolution && (\n            <div>\n              <h3 className="text-sm font-medium text-gray-700 mb-2">Resolution</h3>\n              <div className="bg-green-50 rounded-lg p-3">\n                <p className="text-sm text-green-800">{anomaly.resolution}</p>\n                {anomaly.resolvedAt && (\n                  <p className="text-xs text-green-600 mt-2">\n                    Resolved: {new Date(anomaly.resolvedAt).toLocaleString()}\n                  </p>\n                )}\n              </div>\n            </div>\n          )}\n        </div>\n      </div>\n\n      {/* Actions */}\n      <div className="border-t p-4 bg-gray-50">\n        <div className="flex gap-2">\n          {anomaly.status === \'new\' && (\n            <button\n              onClick={() => acknowledgeAnomaly(anomaly.id)}\n              className="px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600"\n            >\n              Acknowledge\n            </button>\n          )}\n          {(anomaly.status === \'new\' || anomaly.status === \'acknowledged\') && (\n            <button\n              onClick={() => investigateAnomaly(anomaly.id, \'current-user\')}\n              className="px-4 py-2 bg-yellow-500 text-white rounded-lg hover:bg-yellow-600"\n            >\n              Investigate\n            </button>\n          )}\n          {anomaly.status === \'investigating\' && (\n            <button\n              onClick={() => setShowResolveDialog(true)}\n              className="px-4 py-2 bg-green-500 text-white rounded-lg hover:bg-green-600"\n            >\n              Resolve\n            </button>\n          )}\n          <button\n            onClick={() => markFalsePositive(anomaly.id, \'Marked as false positive\')}\n            className="px-4 py-2 border rounded-lg hover:bg-gray-100"\n          >\n            False Positive\n          </button>\n          <button\n            onClick={() => ignoreAnomaly(anomaly.id)}\n            className="px-4 py-2 border rounded-lg hover:bg-gray-100 text-gray-600"\n          >\n            Ignore\n          </button>\n        </div>\n      </div>\n\n      {/* Resolve Dialog */}\n      {showResolveDialog && (\n        <div className="fixed inset-0 bg-black/50 flex items-center justify-center z-50">\n          <div className="bg-white rounded-lg shadow-xl w-full max-w-md p-6">\n            <h2 className="text-lg font-semibold mb-4">Resolve Anomaly</h2>\n            <textarea\n              value={resolution}\n              onChange={(e) => setResolution(e.target.value)}\n              placeholder="Describe how this anomaly was resolved..."\n              className="w-full px-3 py-2 border rounded-lg mb-4"\n              rows={4}\n            />\n            <div className="flex justify-end gap-2">\n              <button\n                onClick={() => setShowResolveDialog(false)}\n                className="px-4 py-2 border rounded-lg hover:bg-gray-100"\n              >\n                Cancel\n              </button>\n              <button\n                onClick={() => {\n                  resolveAnomaly(anomaly.id, resolution);\n                  setShowResolveDialog(false);\n                }}\n                disabled={!resolution.trim()}\n                className="px-4 py-2 bg-green-500 text-white rounded-lg hover:bg-green-600 disabled:opacity-50"\n              >\n                Resolve\n              </button>\n            </div>\n          </div>\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// ANOMALY STATS COMPONENT\n// ============================================================================\n\nexport const AnomalyStats: React.FC = () => {\n  const { getStats } = useAnomalyDetection();\n  const stats = getStats();\n\n  return (\n    <div className="grid grid-cols-2 md:grid-cols-4 gap-4">\n      <div className="bg-white rounded-lg p-4 border">\n        <p className="text-sm text-gray-500">Total Anomalies</p>\n        <p className="text-2xl font-bold">{stats.total}</p>\n      </div>\n      <div className="bg-white rounded-lg p-4 border">\n        <p className="text-sm text-gray-500">New</p>\n        <p className="text-2xl font-bold text-purple-600">{stats.new}</p>\n      </div>\n      <div className="bg-white rounded-lg p-4 border">\n        <p className="text-sm text-gray-500">Critical</p>\n        <p className="text-2xl font-bold text-red-600">{stats.critical}</p>\n      </div>\n      <div className="bg-white rounded-lg p-4 border">\n        <p className="text-sm text-gray-500">Avg Resolution Time</p>\n        <p className="text-2xl font-bold">{stats.avgResolutionTime.toFixed(1)}h</p>\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// ANOMALY RULES PANEL\n// ============================================================================\n\nexport const AnomalyRulesPanel: React.FC = () => {\n  const { rules, enableRule, disableRule, updateRuleSensitivity } = useAnomalyDetection();\n\n  return (\n    <div className="space-y-3">\n      <h3 className="text-sm font-medium text-gray-700">Detection Rules</h3>\n      {rules.map(rule => (\n        <div key={rule.id} className="border rounded-lg p-3 bg-white">\n          <div className="flex items-start justify-between">\n            <div>\n              <h4 className="font-medium text-sm">{rule.name}</h4>\n              <p className="text-xs text-gray-500 mt-0.5">{rule.description}</p>\n            </div>\n            <button\n              onClick={() => rule.enabled ? disableRule(rule.id) : enableRule(rule.id)}\n              className={`relative w-10 h-5 rounded-full transition-colors ${rule.enabled ? \'bg-blue-500\' : \'bg-gray-300\'}`}\n            >\n              <span\n                className={`absolute top-0.5 left-0.5 w-4 h-4 bg-white rounded-full transition-transform ${rule.enabled ? \'translate-x-5\' : \'\'}`}\n              />\n            </button>\n          </div>\n\n          <div className="mt-3 flex items-center gap-4">\n            <div className="flex-1">\n              <p className="text-xs text-gray-500 mb-1">Sensitivity</p>\n              <input\n                type="range"\n                min="0"\n                max="1"\n                step="0.1"\n                value={rule.sensitivity}\n                onChange={(e) => updateRuleSensitivity(rule.id, Number(e.target.value))}\n                className="w-full"\n              />\n            </div>\n            <span className="text-xs text-gray-500">{Math.round(rule.sensitivity * 100)}%</span>\n          </div>\n\n          <div className="mt-2 flex items-center gap-3 text-xs text-gray-500">\n            <span className="px-2 py-0.5 bg-gray-100 rounded">{rule.type}</span>\n            <span>Triggers: {rule.triggerCount}</span>\n            {rule.lastTriggered && (\n              <span>Last: {new Date(rule.lastTriggered).toLocaleDateString()}</span>\n            )}\n          </div>\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN ANOMALY DETECTION COMPONENT\n// ============================================================================\n\nexport const AnomalyDetection: React.FC = () => {\n  const [selectedAnomaly, setSelectedAnomaly] = useState<Anomaly | null>(null);\n\n  return (\n    <div className="h-full flex">\n      {/* Main list area */}\n      <div className="flex-1 flex flex-col">\n        <div className="p-4 border-b bg-white">\n          <h1 className="text-xl font-semibold mb-4">Anomaly Detection</h1>\n          <AnomalyStats />\n        </div>\n\n        <div className="flex-1 overflow-auto p-4 bg-gray-50">\n          {selectedAnomaly ? (\n            <AnomalyDetail anomaly={selectedAnomaly} onBack={() => setSelectedAnomaly(null)} />\n          ) : (\n            <AnomalyList onSelectAnomaly={setSelectedAnomaly} />\n          )}\n        </div>\n      </div>\n\n      {/* Sidebar */}\n      <div className="w-80 border-l bg-white overflow-auto p-4">\n        <AnomalyRulesPanel />\n      </div>\n    </div>\n  );\n};\n\nexport default AnomalyDetection;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/ai/anomaly-detection.tsx\' created successfully.") </create-file> </tool_result>'}
{'role': 'assistant', 'content': 'Now let me create the Forecasting component for the AI System.\n\n<function_calls>\n<create-file file_path="frontend/src/components/ai/forecasting.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst ForecastModelSchema = z.object({\n  id: z.string(),\n  name: z.string(),\n  type: z.enum([\'arima\', \'prophet\', \'lstm\', \'ensemble\', \'exponential_smoothing\', \'linear_regression\']),\n  target: z.string(),\n  features: z.array(z.string()),\n  granularity: z.enum([\'daily\', \'weekly\', \'monthly\', \'quarterly\']),\n  horizon: z.number(), // forecast periods ahead\n  confidenceInterval: z.number(),\n  lastTrained: z.date(),\n  accuracy: z.object({\n    mape: z.number(), // Mean Absolute Percentage Error\n    rmse: z.number(), // Root Mean Square Error\n    r2: z.number(), // R-squared\n  }),\n  status: z.enum([\'active\', \'training\', \'deprecated\', \'failed\']),\n});\n\nconst ForecastResultSchema = z.object({\n  id: z.string(),\n  modelId: z.string(),\n  target: z.string(),\n  generatedAt: z.date(),\n  horizon: z.array(z.object({\n    period: z.date(),\n    value: z.number(),\n    lower: z.number(), // confidence interval lower bound\n    upper: z.number(), // confidence interval upper bound\n    confidence: z.number(),\n  })),\n  metadata: z.object({\n    trend: z.enum([\'up\', \'down\', \'stable\']),\n    seasonality: z.boolean(),\n    changePoints: z.array(z.date()).optional(),\n    anomalies: z.array(z.number()).optional(),\n  }),\n  drivers: z.array(z.object({\n    factor: z.string(),\n    impact: z.number(), // -1 to 1\n    confidence: z.number(),\n  })).optional(),\n  scenarios: z.array(z.object({\n    name: z.string(),\n    description: z.string(),\n    adjustments: z.record(z.number()),\n    forecast: z.array(z.object({\n      period: z.date(),\n      value: z.number(),\n    })),\n  })).optional(),\n});\n\nconst ForecastAlertSchema = z.object({\n  id: z.string(),\n  forecastId: z.string(),\n  type: z.enum([\'threshold\', \'trend_change\', \'variance\', \'opportunity\', \'risk\']),\n  message: z.string(),\n  period: z.date(),\n  threshold: z.number().optional(),\n  projectedValue: z.number(),\n  triggeredAt: z.date(),\n  acknowledged: z.boolean(),\n});\n\ntype ForecastModel = z.infer<typeof ForecastModelSchema>;\ntype ForecastResult = z.infer<typeof ForecastResultSchema>;\ntype ForecastAlert = z.infer<typeof ForecastAlertSchema>;\n\n// ============================================================================\n// FORECASTING STORE\n// ============================================================================\n\ninterface ForecastingStore {\n  models: ForecastModel[];\n  forecasts: ForecastResult[];\n  alerts: ForecastAlert[];\n  selectedModel: ForecastModel | null;\n  selectedForecast: ForecastResult | null;\n  \n  // Actions\n  createModel: (model: Omit<ForecastModel, \'id\' | \'lastTrained\' | \'accuracy\' | \'status\'>) => string;\n  trainModel: (modelId: string) => Promise<void>;\n  generateForecast: (modelId: string, params?: { scenarios?: Record<string, number> }) => Promise<ForecastResult>;\n  deleteModel: (modelId: string) => void;\n  \n  acknowledgeAlert: (alertId: string) => void;\n  \n  // Queries\n  getForecastForTarget: (target: string) => ForecastResult | undefined;\n  getModelAccuracy: (modelId: string) => ForecastModel[\'accuracy\'] | undefined;\n}\n\nconst ForecastingContext = createContext<ForecastingStore | null>(null);\n\nexport const useForecasting = () => {\n  const context = useContext(ForecastingContext);\n  if (!context) {\n    throw new Error(\'useForecasting must be used within ForecastingProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst sampleModels: ForecastModel[] = [\n  {\n    id: \'model-001\',\n    name: \'Revenue Forecast\',\n    type: \'prophet\',\n    target: \'revenue\',\n    features: [\'historical_revenue\', \'marketing_spend\', \'seasonality\', \'economic_index\'],\n    granularity: \'monthly\',\n    horizon: 12,\n    confidenceInterval: 0.95,\n    lastTrained: new Date(\'2024-01-15\'),\n    accuracy: { mape: 0.08, rmse: 45000, r2: 0.92 },\n    status: \'active\',\n  },\n  {\n    id: \'model-002\',\n    name: \'Cash Flow Forecast\',\n    type: \'ensemble\',\n    target: \'cash_balance\',\n    features: [\'historical_cash\', \'receivables\', \'payables\', \'seasonality\'],\n    granularity: \'weekly\',\n    horizon: 13,\n    confidenceInterval: 0.9,\n    lastTrained: new Date(\'2024-01-18\'),\n    accuracy: { mape: 0.05, rmse: 12000, r2: 0.95 },\n    status: \'active\',\n  },\n  {\n    id: \'model-003\',\n    name: \'Expense Forecast\',\n    type: \'arima\',\n    target: \'operating_expenses\',\n    features: [\'historical_expenses\', \'headcount\', \'inflation_rate\'],\n    granularity: \'monthly\',\n    horizon: 6,\n    confidenceInterval: 0.9,\n    lastTrained: new Date(\'2024-01-10\'),\n    accuracy: { mape: 0.12, rmse: 28000, r2: 0.85 },\n    status: \'active\',\n  },\n  {\n    id: \'model-004\',\n    name: \'Headcount Growth\',\n    type: \'lstm\',\n    target: \'employee_count\',\n    features: [\'historical_headcount\', \'revenue\', \'hiring_plan\'],\n    granularity: \'monthly\',\n    horizon: 12,\n    confidenceInterval: 0.85,\n    lastTrained: new Date(\'2024-01-12\'),\n    accuracy: { mape: 0.07, rmse: 5, r2: 0.88 },\n    status: \'active\',\n  },\n];\n\nconst generateForecastData = (baseValue: number, periods: number, trend: number, seasonality: number[]) => {\n  const data = [];\n  for (let i = 0; i < periods; i++) {\n    const trendComponent = baseValue * Math.pow(1 + trend, i);\n    const seasonalComponent = seasonality[i % seasonality.length];\n    const noise = (Math.random() - 0.5) * baseValue * 0.05;\n    const value = trendComponent * seasonalComponent + noise;\n    const lower = value * 0.9;\n    const upper = value * 1.1;\n    \n    const date = new Date();\n    date.setMonth(date.getMonth() + i + 1);\n    \n    data.push({\n      period: date,\n      value: Math.round(value),\n      lower: Math.round(lower),\n      upper: Math.round(upper),\n      confidence: 0.95 - (i * 0.02),\n    });\n  }\n  return data;\n};\n\nconst sampleForecasts: ForecastResult[] = [\n  {\n    id: \'forecast-001\',\n    modelId: \'model-001\',\n    target: \'revenue\',\n    generatedAt: new Date(\'2024-01-20\'),\n    horizon: generateForecastData(1200000, 12, 0.02, [1.0, 0.95, 1.1, 1.05, 1.0, 0.9, 0.85, 0.95, 1.0, 1.1, 1.15, 1.2]),\n    metadata: {\n      trend: \'up\',\n      seasonality: true,\n      changePoints: [new Date(\'2024-06-01\')],\n    },\n    drivers: [\n      { factor: \'Marketing Spend\', impact: 0.35, confidence: 0.85 },\n      { factor: \'Economic Conditions\', impact: 0.25, confidence: 0.7 },\n      { factor: \'Seasonality\', impact: 0.2, confidence: 0.9 },\n      { factor: \'Product Launches\', impact: 0.15, confidence: 0.6 },\n    ],\n    scenarios: [\n      {\n        name: \'Optimistic\',\n        description: \'Strong market conditions and successful product launches\',\n        adjustments: { marketing_spend: 1.2, economic_index: 1.1 },\n        forecast: generateForecastData(1200000, 12, 0.035, [1.0, 0.95, 1.1, 1.05, 1.0, 0.9, 0.85, 0.95, 1.0, 1.1, 1.15, 1.2]).map(f => ({ period: f.period, value: f.value })),\n      },\n      {\n        name: \'Pessimistic\',\n        description: \'Economic downturn and reduced marketing budget\',\n        adjustments: { marketing_spend: 0.8, economic_index: 0.9 },\n        forecast: generateForecastData(1200000, 12, 0.005, [1.0, 0.95, 1.1, 1.05, 1.0, 0.9, 0.85, 0.95, 1.0, 1.1, 1.15, 1.2]).map(f => ({ period: f.period, value: f.value })),\n      },\n    ],\n  },\n  {\n    id: \'forecast-002\',\n    modelId: \'model-002\',\n    target: \'cash_balance\',\n    generatedAt: new Date(\'2024-01-20\'),\n    horizon: generateForecastData(2450000, 13, 0.005, [1, 1, 1, 1]),\n    metadata: {\n      trend: \'stable\',\n      seasonality: false,\n    },\n    drivers: [\n      { factor: \'Receivables Collection\', impact: 0.4, confidence: 0.8 },\n      { factor: \'Payable Schedule\', impact: -0.3, confidence: 0.9 },\n      { factor: \'Operating Expenses\', impact: -0.2, confidence: 0.85 },\n    ],\n  },\n  {\n    id: \'forecast-003\',\n    modelId: \'model-003\',\n    target: \'operating_expenses\',\n    generatedAt: new Date(\'2024-01-20\'),\n    horizon: generateForecastData(850000, 6, 0.01, [1, 1, 1, 1, 1, 1]),\n    metadata: {\n      trend: \'up\',\n      seasonality: false,\n    },\n    drivers: [\n      { factor: \'Headcount\', impact: 0.5, confidence: 0.9 },\n      { factor: \'Inflation\', impact: 0.2, confidence: 0.75 },\n    ],\n  },\n];\n\nconst sampleAlerts: ForecastAlert[] = [\n  {\n    id: \'alert-001\',\n    forecastId: \'forecast-001\',\n    type: \'opportunity\',\n    message: \'Revenue projected to exceed target by 15% in Q4\',\n    period: new Date(\'2024-10-01\'),\n    projectedValue: 1450000,\n    triggeredAt: new Date(\'2024-01-20\'),\n    acknowledged: false,\n  },\n  {\n    id: \'alert-002\',\n    forecastId: \'forecast-002\',\n    type: \'risk\',\n    message: \'Cash balance projected to fall below minimum threshold in 8 weeks\',\n    period: new Date(\'2024-03-15\'),\n    threshold: 2000000,\n    projectedValue: 1850000,\n    triggeredAt: new Date(\'2024-01-20\'),\n    acknowledged: false,\n  },\n  {\n    id: \'alert-003\',\n    forecastId: \'forecast-003\',\n    type: \'trend_change\',\n    message: \'Operating expenses trending 8% above budget\',\n    period: new Date(\'2024-02-01\'),\n    projectedValue: 920000,\n    triggeredAt: new Date(\'2024-01-19\'),\n    acknowledged: true,\n  },\n];\n\n// ============================================================================\n// FORECASTING PROVIDER\n// ============================================================================\n\nexport const ForecastingProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [models, setModels] = useState<ForecastModel[]>(sampleModels);\n  const [forecasts, setForecasts] = useState<ForecastResult[]>(sampleForecasts);\n  const [alerts, setAlerts] = useState<ForecastAlert[]>(sampleAlerts);\n  const [selectedModel, setSelectedModel] = useState<ForecastModel | null>(null);\n  const [selectedForecast, setSelectedForecast] = useState<ForecastResult | null>(null);\n\n  const createModel = useCallback((model: Omit<ForecastModel, \'id\' | \'lastTrained\' | \'accuracy\' | \'status\'>): string => {\n    const id = `model-${Date.now()}`;\n    const newModel: ForecastModel = {\n      ...model,\n      id,\n      lastTrained: new Date(),\n      accuracy: { mape: 0, rmse: 0, r2: 0 },\n      status: \'training\',\n    };\n    setModels(prev => [...prev, newModel]);\n    return id;\n  }, []);\n\n  const trainModel = useCallback(async (modelId: string) => {\n    setModels(prev => prev.map(m =>\n      m.id === modelId ? { ...m, status: \'training\' as const } : m\n    ));\n\n    // Simulate training\n    await new Promise(resolve => setTimeout(resolve, 3000));\n\n    setModels(prev => prev.map(m =>\n      m.id === modelId ? {\n        ...m,\n        status: \'active\' as const,\n        lastTrained: new Date(),\n        accuracy: {\n          mape: 0.05 + Math.random() * 0.1,\n          rmse: Math.random() * 50000,\n          r2: 0.8 + Math.random() * 0.15,\n        },\n      } : m\n    ));\n  }, []);\n\n  const generateForecast = useCallback(async (modelId: string, params?: { scenarios?: Record<string, number> }): Promise<ForecastResult> => {\n    const model = models.find(m => m.id === modelId);\n    if (!model) throw new Error(\'Model not found\');\n\n    // Generate forecast data\n    const baseValue = model.target === \'revenue\' ? 1200000 :\n                      model.target === \'cash_balance\' ? 2450000 :\n                      model.target === \'operating_expenses\' ? 850000 : 1000000;\n\n    const horizon = generateForecastData(baseValue, model.horizon, 0.02, [1, 1, 1, 1]);\n\n    const forecast: ForecastResult = {\n      id: `forecast-${Date.now()}`,\n      modelId,\n      target: model.target,\n      generatedAt: new Date(),\n      horizon,\n      metadata: {\n        trend: \'up\',\n        seasonality: model.features.includes(\'seasonality\'),\n      },\n      drivers: model.features.slice(0, 3).map((f, i) => ({\n        factor: f.replace(/_/g, \' \').replace(/\\b\\w/g, c => c.toUpperCase()),\n        impact: 0.3 - (i * 0.1),\n        confidence: 0.8 - (i * 0.1),\n      })),\n    };\n\n    setForecasts(prev => [...prev, forecast]);\n    return forecast;\n  }, [models]);\n\n  const deleteModel = useCallback((modelId: string) => {\n    setModels(prev => prev.filter(m => m.id !== modelId));\n    setForecasts(prev => prev.filter(f => f.modelId !== modelId));\n  }, []);\n\n  const acknowledgeAlert = useCallback((alertId: string) => {\n    setAlerts(prev => prev.map(a =>\n      a.id === alertId ? { ...a, acknowledged: true } : a\n    ));\n  }, []);\n\n  const getForecastForTarget = useCallback((target: string) => {\n    return forecasts.find(f => f.target === target);\n  }, [forecasts]);\n\n  const getModelAccuracy = useCallback((modelId: string) => {\n    const model = models.find(m => m.id === modelId);\n    return model?.accuracy;\n  }, [models]);\n\n  const value = useMemo(() => ({\n    models,\n    forecasts,\n    alerts,\n    selectedModel,\n    selectedForecast,\n    createModel,\n    trainModel,\n    generateForecast,\n    deleteModel,\n    acknowledgeAlert,\n    getForecastForTarget,\n    getModelAccuracy,\n  }), [\n    models, forecasts, alerts, selectedModel, selectedForecast,\n    createModel, trainModel, generateForecast, deleteModel,\n    acknowledgeAlert, getForecastForTarget, getModelAccuracy,\n  ]);\n\n  return (\n    <ForecastingContext.Provider value={value}>\n      {children}\n    </ForecastingContext.Provider>\n  );\n};\n\n// ============================================================================\n// FORECAST CHART COMPONENT\n// ============================================================================\n\ninterface ForecastChartProps {\n  forecast: ForecastResult;\n  showConfidenceInterval?: boolean;\n  showScenarios?: boolean;\n  height?: number;\n}\n\nexport const ForecastChart: React.FC<ForecastChartProps> = ({\n  forecast,\n  showConfidenceInterval = true,\n  showScenarios = true,\n  height = 300,\n}) => {\n  const [selectedScenario, setSelectedScenario] = useState<string | null>(null);\n  const svgRef = useRef<SVGSVGElement>(null);\n\n  const data = forecast.horizon;\n  const maxValue = Math.max(...data.map(d => d.upper));\n  const minValue = Math.min(...data.map(d => d.lower));\n  const range = maxValue - minValue;\n\n  const width = 800;\n  const padding = { top: 20, right: 40, bottom: 40, left: 60 };\n  const chartWidth = width - padding.left - padding.right;\n  const chartHeight = height - padding.top - padding.bottom;\n\n  const xScale = (i: number) => padding.left + (i / (data.length - 1)) * chartWidth;\n  const yScale = (v: number) => padding.top + chartHeight - ((v - minValue) / range) * chartHeight;\n\n  const formatValue = (v: number) => {\n    if (v >= 1000000) return `$${(v / 1000000).toFixed(1)}M`;\n    if (v >= 1000) return `$${(v / 1000).toFixed(0)}K`;\n    return `$${v}`;\n  };\n\n  const formatDate = (d: Date) => {\n    return new Date(d).toLocaleDateString(\'en-US\', { month: \'short\', year: \'2-digit\' });\n  };\n\n  // Build path for main line\n  const linePath = data.map((d, i) => `${i === 0 ? \'M\' : \'L\'} ${xScale(i)} ${yScale(d.value)}`).join(\' \');\n\n  // Build area for confidence interval\n  const upperPath = data.map((d, i) => `${i === 0 ? \'M\' : \'L\'} ${xScale(i)} ${yScale(d.upper)}`).join(\' \');\n  const lowerPath = data.map((d, i) => `${i === 0 ? \'M\' : \'L\'} ${xScale(i)} ${yScale(d.lower)}`).join(\' \');\n  const areaPath = `${upperPath} ${lowerPath.split(\' \').reverse().join(\' \')} Z`;\n\n  return (\n    <div>\n      <svg ref={svgRef} width="100%" height={height} viewBox={`0 0 ${width} ${height}`}>\n        {/* Grid lines */}\n        {[0, 0.25, 0.5, 0.75, 1].map(ratio => {\n          const y = padding.top + ratio * chartHeight;\n          const value = maxValue - ratio * range;\n          return (\n            <g key={ratio}>\n              <line x1={padding.left} y1={y} x2={width - padding.right} y2={y} stroke="#e5e7eb" strokeWidth="1" />\n              <text x={padding.left - 10} y={y + 4} textAnchor="end" className="text-xs fill-gray-500">\n                {formatValue(value)}\n              </text>\n            </g>\n          );\n        })}\n\n        {/* X-axis labels */}\n        {data.filter((_, i) => i % Math.ceil(data.length / 6) === 0).map((d, i, arr) => (\n          <text key={i} x={xScale(data.indexOf(d))} y={height - 10} textAnchor="middle" className="text-xs fill-gray-500">\n            {formatDate(d.period)}\n          </text>\n        ))}\n\n        {/* Confidence interval area */}\n        {showConfidenceInterval && (\n          <path d={areaPath} fill="url(#confidenceGradient)" opacity="0.3" />\n        )}\n\n        {/* Main forecast line */}\n        <path d={linePath} fill="none" stroke="#3b82f6" strokeWidth="2" />\n\n        {/* Data points */}\n        {data.map((d, i) => (\n          <g key={i}>\n            <circle cx={xScale(i)} cy={yScale(d.value)} r="4" fill="#3b82f6" stroke="white" strokeWidth="2" />\n          </g>\n        ))}\n\n        {/* Scenario lines */}\n        {showScenarios && forecast.scenarios && selectedScenario && (\n          <path\n            d={forecast.scenarios.find(s => s.name === selectedScenario)!.forecast.map((d, i) => `${i === 0 ? \'M\' : \'L\'} ${xScale(i)} ${yScale(d.value)}`).join(\' \')}\n            fill="none"\n            stroke={selectedScenario === \'Optimistic\' ? \'#10b981\' : \'#ef4444\'}\n            strokeWidth="2"\n            strokeDasharray="4"\n          />\n        )}\n\n        {/* Gradient definition */}\n        <defs>\n          <linearGradient id="confidenceGradient" x1="0%" y1="0%" x2="0%" y2="100%">\n            <stop offset="0%" stopColor="#3b82f6" stopOpacity="0.3" />\n            <stop offset="100%" stopColor="#3b82f6" stopOpacity="0.1" />\n          </linearGradient>\n        </defs>\n      </svg>\n\n      {/* Scenario selector */}\n      {showScenarios && forecast.scenarios && (\n        <div className="flex gap-2 mt-4">\n          <button\n            onClick={() => setSelectedScenario(null)}\n            className={`px-3 py-1 text-sm rounded-full ${!selectedScenario ? \'bg-blue-500 text-white\' : \'bg-gray-100 text-gray-700\'}`}\n          >\n            Base\n          </button>\n          {forecast.scenarios.map(scenario => (\n            <button\n              key={scenario.name}\n              onClick={() => setSelectedScenario(scenario.name)}\n              className={`px-3 py-1 text-sm rounded-full ${selectedScenario === scenario.name ? scenario.name === \'Optimistic\' ? \'bg-green-500 text-white\' : \'bg-red-500 text-white\' : \'bg-gray-100 text-gray-700\'}`}\n            >\n              {scenario.name}\n            </button>\n          ))}\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// MODEL LIST COMPONENT\n// ============================================================================\n\ninterface ModelListProps {\n  onSelectModel: (model: ForecastModel) => void;\n}\n\nexport const ModelList: React.FC<ModelListProps> = ({ onSelectModel }) => {\n  const { models } = useForecasting();\n\n  const getStatusColor = (status: ForecastModel[\'status\']) => {\n    const colors: Record<string, string> = {\n      active: \'bg-green-100 text-green-700\',\n      training: \'bg-yellow-100 text-yellow-700\',\n      deprecated: \'bg-gray-100 text-gray-700\',\n      failed: \'bg-red-100 text-red-700\',\n    };\n    return colors[status];\n  };\n\n  return (\n    <div className="space-y-3">\n      {models.map(model => (\n        <div\n          key={model.id}\n          onClick={() => onSelectModel(model)}\n          className="border rounded-lg p-4 hover:shadow-md transition-shadow cursor-pointer bg-white"\n        >\n          <div className="flex items-start justify-between mb-2">\n            <div>\n              <h3 className="font-medium">{model.name}</h3>\n              <p className="text-sm text-gray-500">Target: {model.target}</p>\n            </div>\n            <span className={`px-2 py-0.5 text-xs rounded-full ${getStatusColor(model.status)}`}>\n              {model.status}\n            </span>\n          </div>\n\n          <div className="grid grid-cols-3 gap-4 mt-3 text-sm">\n            <div>\n              <p className="text-gray-500">Type</p>\n              <p className="font-medium">{model.type.toUpperCase()}</p>\n            </div>\n            <div>\n              <p className="text-gray-500">Horizon</p>\n              <p className="font-medium">{model.horizon} {model.granularity}</p>\n            </div>\n            <div>\n              <p className="text-gray-500">MAPE</p>\n              <p className="font-medium">{(model.accuracy.mape * 100).toFixed(1)}%</p>\n            </div>\n          </div>\n\n          <div className="mt-3 flex items-center gap-2 text-xs text-gray-500">\n            <span>Last trained: {new Date(model.lastTrained).toLocaleDateString()}</span>\n            <span>•</span>\n            <span>R² = {model.accuracy.r2.toFixed(2)}</span>\n          </div>\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// MODEL DETAIL COMPONENT\n// ============================================================================\n\ninterface ModelDetailProps {\n  model: ForecastModel;\n  onBack: () => void;\n}\n\nexport const ModelDetail: React.FC<ModelDetailProps> = ({ model, onBack }) => {\n  const { forecasts, trainModel, generateForecast } = useForecasting();\n  const [isTraining, setIsTraining] = useState(false);\n  const [isForecasting, setIsForecasting] = useState(false);\n\n  const forecast = forecasts.find(f => f.modelId === model.id);\n\n  const handleTrain = async () => {\n    setIsTraining(true);\n    await trainModel(model.id);\n    setIsTraining(false);\n  };\n\n  const handleGenerateForecast = async () => {\n    setIsForecasting(true);\n    await generateForecast(model.id);\n    setIsForecasting(false);\n  };\n\n  return (\n    <div className="h-full flex flex-col">\n      {/* Header */}\n      <div className="border-b bg-white p-4">\n        <button onClick={onBack} className="text-sm text-gray-600 hover:text-gray-900 mb-2">← Back</button>\n        <div className="flex items-center justify-between">\n          <div>\n            <h1 className="text-xl font-semibold">{model.name}</h1>\n            <p className="text-sm text-gray-500">{model.type.toUpperCase()} Model</p>\n          </div>\n          <div className="flex gap-2">\n            <button\n              onClick={handleTrain}\n              disabled={isTraining || model.status === \'training\'}\n              className="px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600 disabled:opacity-50"\n            >\n              {isTraining ? \'Training...\' : \'Retrain\'}\n            </button>\n            <button\n              onClick={handleGenerateForecast}\n              disabled={isForecasting}\n              className="px-4 py-2 bg-green-500 text-white rounded-lg hover:bg-green-600 disabled:opacity-50"\n            >\n              {isForecasting ? \'Generating...\' : \'Generate Forecast\'}\n            </button>\n          </div>\n        </div>\n      </div>\n\n      {/* Content */}\n      <div className="flex-1 overflow-auto p-4">\n        <div className="grid gap-6 lg:grid-cols-2">\n          {/* Model Info */}\n          <div className="space-y-4">\n            <div className="bg-white border rounded-lg p-4">\n              <h3 className="font-medium mb-3">Model Configuration</h3>\n              <div className="space-y-2 text-sm">\n                <div className="flex justify-between">\n                  <span className="text-gray-500">Target Variable</span>\n                  <span className="font-medium">{model.target}</span>\n                </div>\n                <div className="flex justify-between">\n                  <span className="text-gray-500">Granularity</span>\n                  <span className="font-medium">{model.granularity}</span>\n                </div>\n                <div className="flex justify-between">\n                  <span className="text-gray-500">Forecast Horizon</span>\n                  <span className="font-medium">{model.horizon} periods</span>\n                </div>\n                <div className="flex justify-between">\n                  <span className="text-gray-500">Confidence Interval</span>\n                  <span className="font-medium">{(model.confidenceInterval * 100)}%</span>\n                </div>\n              </div>\n            </div>\n\n            <div className="bg-white border rounded-lg p-4">\n              <h3 className="font-medium mb-3">Features</h3>\n              <div className="flex flex-wrap gap-2">\n                {model.features.map(feature => (\n                  <span key={feature} className="px-2 py-1 bg-gray-100 rounded text-sm">\n                    {feature.replace(/_/g, \' \')}\n                  </span>\n                ))}\n              </div>\n            </div>\n\n            <div className="bg-white border rounded-lg p-4">\n              <h3 className="font-medium mb-3">Accuracy Metrics</h3>\n              <div className="grid grid-cols-3 gap-4">\n                <div className="text-center">\n                  <p className="text-2xl font-bold text-blue-600">{(model.accuracy.mape * 100).toFixed(1)}%</p>\n                  <p className="text-xs text-gray-500">MAPE</p>\n                </div>\n                <div className="text-center">\n                  <p className="text-2xl font-bold text-blue-600">{model.accuracy.rmse.toFixed(0)}</p>\n                  <p className="text-xs text-gray-500">RMSE</p>\n                </div>\n                <div className="text-center">\n                  <p className="text-2xl font-bold text-blue-600">{model.accuracy.r2.toFixed(2)}</p>\n                  <p className="text-xs text-gray-500">R²</p>\n                </div>\n              </div>\n            </div>\n          </div>\n\n          {/* Forecast */}\n          <div>\n            {forecast ? (\n              <div className="bg-white border rounded-lg p-4">\n                <h3 className="font-medium mb-3">Forecast</h3>\n                <ForecastChart forecast={forecast} />\n                \n                {forecast.drivers && (\n                  <div className="mt-4">\n                    <h4 className="text-sm font-medium text-gray-700 mb-2">Key Drivers</h4>\n                    <div className="space-y-2">\n                      {forecast.drivers.map((driver, i) => (\n                        <div key={i} className="flex items-center gap-2">\n                          <div className="w-32 text-sm text-gray-600">{driver.factor}</div>\n                          <div className="flex-1 h-2 bg-gray-200 rounded-full overflow-hidden">\n                            <div\n                              className={`h-full ${driver.impact > 0 ? \'bg-green-500\' : \'bg-red-500\'}`}\n                              style={{ width: `${Math.abs(driver.impact) * 100}%`, marginLeft: driver.impact < 0 ? \'auto\' : 0 }}\n                            />\n                          </div>\n                          <div className="w-16 text-right text-sm text-gray-500">\n                            {driver.impact > 0 ? \'+\' : \'\'}{(driver.impact * 100).toFixed(0)}%\n                          </div>\n                        </div>\n                      ))}\n                    </div>\n                  </div>\n                )}\n              </div>\n            ) : (\n              <div className="bg-gray-50 border rounded-lg p-8 text-center">\n                <p className="text-gray-500">No forecast generated yet</p>\n                <button\n                  onClick={handleGenerateForecast}\n                  className="mt-3 px-4 py-2 bg-blue-500 text-white rounded-lg"\n                >\n                  Generate Forecast\n                </button>\n              </div>\n            )}\n          </div>\n        </div>\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// FORECAST ALERTS COMPONENT\n// ============================================================================\n\nexport const ForecastAlerts: React.FC = () => {\n  const { alerts, acknowledgeAlert } = useForecasting();\n\n  const getAlertColor = (type: ForecastAlert[\'type\']) => {\n    const colors: Record<string, string> = {\n      opportunity: \'bg-green-50 border-green-200\',\n      risk: \'bg-red-50 border-red-200\',\n      threshold: \'bg-yellow-50 border-yellow-200\',\n      trend_change: \'bg-blue-50 border-blue-200\',\n      variance: \'bg-purple-50 border-purple-200\',\n    };\n    return colors[type];\n  };\n\n  const getAlertIcon = (type: ForecastAlert[\'type\']) => {\n    const icons: Record<string, string> = {\n      opportunity: \'📈\',\n      risk: \'⚠️\',\n      threshold: \'📊\',\n      trend_change: \'↗️\',\n      variance: \'📉\',\n    };\n    return icons[type];\n  };\n\n  return (\n    <div className="space-y-3">\n      <h3 className="text-sm font-medium text-gray-700">Forecast Alerts</h3>\n      {alerts.map(alert => (\n        <div key={alert.id} className={`border rounded-lg p-3 ${getAlertColor(alert.type)}`}>\n          <div className="flex items-start justify-between">\n            <div className="flex items-start gap-2">\n              <span className="text-lg">{getAlertIcon(alert.type)}</span>\n              <div>\n                <p className="text-sm font-medium">{alert.message}</p>\n                <p className="text-xs text-gray-500 mt-1">\n                  Projected: ${alert.projectedValue.toLocaleString()}\n                  {alert.threshold && ` • Threshold: $${alert.threshold.toLocaleString()}`}\n                </p>\n              </div>\n            </div>\n            {!alert.acknowledged && (\n              <button\n                onClick={() => acknowledgeAlert(alert.id)}\n                className="text-xs text-blue-600 hover:text-blue-800"\n              >\n                Acknowledge\n              </button>\n            )}\n          </div>\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN FORECASTING COMPONENT\n// ============================================================================\n\nexport const Forecasting: React.FC = () => {\n  const { selectedModel, setSelectedModel } = useForecasting();\n\n  return (\n    <div className="h-full flex">\n      {/* Main area */}\n      <div className="flex-1 flex flex-col">\n        <div className="p-4 border-b bg-white">\n          <h1 className="text-xl font-semibold">AI Forecasting</h1>\n          <p className="text-sm text-gray-500">Predictive analytics and trend forecasting</p>\n        </div>\n\n        <div className="flex-1 overflow-auto p-4 bg-gray-50">\n          {selectedModel ? (\n            <ModelDetail model={selectedModel} onBack={() => setSelectedModel(null)} />\n          ) : (\n            <ModelList onSelectModel={setSelectedModel} />\n          )}\n        </div>\n      </div>\n\n      {/* Sidebar */}\n      <div className="w-80 border-l bg-white overflow-auto p-4">\n        <ForecastAlerts />\n      </div>\n    </div>\n  );\n};\n\n// Need to import useRef\nimport { useRef } from \'react\';\n\nexport default Forecasting;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/ai/forecasting.tsx\' created successfully.") </create-file> </tool_result>'}
{'role': 'assistant', 'content': 'Now let me create the Decision Recommendations component for the AI System.\n\n<function_calls>\n<create-file file_path="frontend/src/components/ai/decision-recommendations.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst DecisionFactorSchema = z.object({\n  id: z.string(),\n  name: z.string(),\n  description: z.string(),\n  weight: z.number().min(0).max(1),\n  value: z.number().min(-1).max(1), // -1 = negative impact, 0 = neutral, 1 = positive\n  confidence: z.number().min(0).max(1),\n  source: z.enum([\'historical\', \'real_time\', \'forecast\', \'external\', \'expert\']),\n  category: z.string(),\n});\n\nconst DecisionAlternativeSchema = z.object({\n  id: z.string(),\n  name: z.string(),\n  description: z.string(),\n  type: z.enum([\'recommended\', \'neutral\', \'not_recommended\']),\n  score: z.number().min(0).max(100),\n  confidence: z.number().min(0).max(1),\n  pros: z.array(z.string()),\n  cons: z.array(z.string()),\n  riskLevel: z.enum([\'low\', \'medium\', \'high\', \'critical\']),\n  estimatedImpact: z.object({\n    financial: z.number().optional(),\n    operational: z.string().optional(),\n    timeline: z.string().optional(),\n  }),\n  factors: z.array(z.object({\n    factorId: z.string(),\n    impact: z.number(),\n    reasoning: z.string(),\n  })),\n  implementationSteps: z.array(z.object({\n    step: z.number(),\n    action: z.string(),\n    estimatedTime: z.string(),\n    dependencies: z.array(z.string()).optional(),\n  })),\n});\n\nconst DecisionSchema = z.object({\n  id: z.string(),\n  type: z.enum([\n    \'investment\',\n    \'cost_reduction\',\n    \'pricing\',\n    \'hiring\',\n    \'vendor_selection\',\n    \'risk_mitigation\',\n    \'resource_allocation\',\n    \'strategic\',\n    \'operational\',\n    \'financial\',\n  ]),\n  title: z.string(),\n  description: z.string(),\n  context: z.string(),\n  urgency: z.enum([\'low\', \'medium\', \'high\', \'critical\']),\n  status: z.enum([\'pending\', \'in_review\', \'decided\', \'implemented\', \'cancelled\']),\n  createdAt: z.date(),\n  deadline: z.date().optional(),\n  factors: z.array(DecisionFactorSchema),\n  alternatives: z.array(DecisionAlternativeSchema),\n  recommendedAlternative: z.string(),\n  aiConfidence: z.number().min(0).max(1),\n  decisionMaker: z.string().optional(),\n  finalDecision: z.string().optional(),\n  decisionRationale: z.string().optional(),\n  decidedAt: z.date().optional(),\n  outcome: z.object({\n    success: z.boolean().optional(),\n    actualImpact: z.record(z.unknown()).optional(),\n    lessons: z.array(z.string()).optional(),\n  }).optional(),\n  stakeholders: z.array(z.object({\n    id: z.string(),\n    name: z.string(),\n    role: z.string(),\n    influence: z.enum([\'low\', \'medium\', \'high\']),\n    preference: z.string().optional(),\n  })).optional(),\n});\n\ntype DecisionFactor = z.infer<typeof DecisionFactorSchema>;\ntype DecisionAlternative = z.infer<typeof DecisionAlternativeSchema>;\ntype Decision = z.infer<typeof DecisionSchema>;\n\n// ============================================================================\n// DECISION RECOMMENDATIONS STORE\n// ============================================================================\n\ninterface DecisionStore {\n  decisions: Decision[];\n  selectedDecision: Decision | null;\n  \n  // Actions\n  createDecision: (decision: Omit<Decision, \'id\' | \'createdAt\' | \'status\' | \'factors\' | \'alternatives\' | \'recommendedAlternative\' | \'aiConfidence\'>) => string;\n  analyzeDecision: (decisionId: string) => Promise<void>;\n  makeDecision: (decisionId: string, alternativeId: string, rationale: string) => void;\n  cancelDecision: (decisionId: string) => void;\n  \n  // Queries\n  getPendingDecisions: () => Decision[];\n  getDecisionFactors: (decisionId: string) => DecisionFactor[];\n  getAlternatives: (decisionId: string) => DecisionAlternative[];\n  getRecommendedAlternative: (decisionId: string) => DecisionAlternative | undefined;\n}\n\nconst DecisionContext = createContext<DecisionStore | null>(null);\n\nexport const useDecisionRecommendations = () => {\n  const context = useContext(DecisionContext);\n  if (!context) {\n    throw new Error(\'useDecisionRecommendations must be used within DecisionProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst sampleDecisions: Decision[] = [\n  {\n    id: \'dec-001\',\n    type: \'investment\',\n    title: \'New Manufacturing Equipment Investment\',\n    description: \'Decision on whether to invest $2.5M in new manufacturing equipment to increase production capacity by 40%.\',\n    context: \'Current equipment is 8 years old and operating at 85% capacity. Demand forecasts show 25% growth over the next 2 years.\',\n    urgency: \'high\',\n    status: \'pending\',\n    createdAt: new Date(\'2024-01-18\'),\n    deadline: new Date(\'2024-02-15\'),\n    factors: [\n      {\n        id: \'f1\',\n        name: \'Demand Forecast\',\n        description: \'Projected demand growth from AI forecasting model\',\n        weight: 0.25,\n        value: 0.8,\n        confidence: 0.85,\n        source: \'forecast\',\n        category: \'Market\',\n      },\n      {\n        id: \'f2\',\n        name: \'Current Equipment Condition\',\n        description: \'Age and reliability of existing equipment\',\n        weight: 0.15,\n        value: -0.4,\n        confidence: 0.95,\n        source: \'historical\',\n        category: \'Operations\',\n      },\n      {\n        id: \'f3\',\n        name: \'Cash Position\',\n        description: \'Available capital for investment\',\n        weight: 0.2,\n        value: 0.6,\n        confidence: 0.9,\n        source: \'real_time\',\n        category: \'Financial\',\n      },\n      {\n        id: \'f4\',\n        name: \'Competitor Activity\',\n        description: \'Competitors investing in similar capacity\',\n        weight: 0.15,\n        value: 0.7,\n        confidence: 0.7,\n        source: \'external\',\n        category: \'Competitive\',\n      },\n      {\n        id: \'f5\',\n        name: \'ROI Timeline\',\n        description: \'Expected time to recover investment\',\n        weight: 0.15,\n        value: 0.3,\n        confidence: 0.75,\n        source: \'forecast\',\n        category: \'Financial\',\n      },\n      {\n        id: \'f6\',\n        name: \'Technology Risk\',\n        description: \'Risk of technology becoming obsolete\',\n        weight: 0.1,\n        value: 0.2,\n        confidence: 0.6,\n        source: \'expert\',\n        category: \'Risk\',\n      },\n    ],\n    alternatives: [\n      {\n        id: \'alt-1\',\n        name: \'Full Investment Now\',\n        description: \'Proceed with full $2.5M investment immediately\',\n        type: \'recommended\',\n        score: 82,\n        confidence: 0.78,\n        pros: [\n          \'Captures market opportunity quickly\',\n          \'40% capacity increase meets projected demand\',\n          \'Reduces maintenance costs by 30%\',\n          \'Energy efficiency savings of 15%\',\n        ],\n        cons: [\n          \'Significant capital outlay\',\n          \'18-month ROI timeline\',\n          \'Implementation disruption risk\',\n        ],\n        riskLevel: \'medium\',\n        estimatedImpact: {\n          financial: 500000,\n          operational: \'40% capacity increase\',\n          timeline: \'18 months to full ROI\',\n        },\n        factors: [\n          { factorId: \'f1\', impact: 0.9, reasoning: \'Aligns perfectly with demand forecast\' },\n          { factorId: \'f2\', impact: 0.8, reasoning: \'Replaces aging equipment proactively\' },\n          { factorId: \'f3\', impact: 0.5, reasoning: \'Manageable with current cash position\' },\n        ],\n        implementationSteps: [\n          { step: 1, action: \'Approve capital expenditure\', estimatedTime: \'1 week\' },\n          { step: 2, action: \'Issue RFP to vendors\', estimatedTime: \'2 weeks\' },\n          { step: 3, action: \'Vendor selection and negotiation\', estimatedTime: \'4 weeks\', dependencies: [\'RFP responses\'] },\n          { step: 4, action: \'Installation and training\', estimatedTime: \'8 weeks\', dependencies: [\'Contract signed\'] },\n          { step: 5, action: \'Go-live and optimization\', estimatedTime: \'4 weeks\', dependencies: [\'Installation complete\'] },\n        ],\n      },\n      {\n        id: \'alt-2\',\n        name: \'Phased Investment\',\n        description: \'Invest $1.2M now, evaluate results, then decide on remaining $1.3M\',\n        type: \'neutral\',\n        score: 68,\n        confidence: 0.72,\n        pros: [\n          \'Lower initial capital requirement\',\n          \'Opportunity to evaluate before full commitment\',\n          \'Reduced implementation risk\',\n        ],\n        cons: [\n          \'Delayed capacity expansion\',\n          \'Potential lost sales during evaluation\',\n          \'Higher total cost due to two implementations\',\n        ],\n        riskLevel: \'low\',\n        estimatedImpact: {\n          financial: 300000,\n          operational: \'20% capacity increase initially\',\n          timeline: \'24 months to full ROI\',\n        },\n        factors: [\n          { factorId: \'f1\', impact: 0.5, reasoning: \'Only partially meets demand growth\' },\n          { factorId: \'f3\', impact: 0.8, reasoning: \'Better for cash flow management\' },\n        ],\n        implementationSteps: [\n          { step: 1, action: \'Phase 1 implementation\', estimatedTime: \'3 months\' },\n          { step: 2, action: \'Evaluation period\', estimatedTime: \'6 months\' },\n          { step: 3, action: \'Phase 2 decision\', estimatedTime: \'1 week\' },\n        ],\n      },\n      {\n        id: \'alt-3\',\n        name: \'Defer Investment\',\n        description: \'Wait 6 months and reassess market conditions\',\n        type: \'not_recommended\',\n        score: 35,\n        confidence: 0.65,\n        pros: [\n          \'Preserves capital for other opportunities\',\n          \'More time to evaluate market conditions\',\n        ],\n        cons: [\n          \'Risk of lost market share to competitors\',\n          \'Equipment reliability may decline\',\n          \'May miss vendor discounts\',\n        ],\n        riskLevel: \'high\',\n        estimatedImpact: {\n          financial: -200000,\n          operational: \'Risk of capacity constraints\',\n          timeline: \'6+ months delay\',\n        },\n        factors: [\n          { factorId: \'f1\', impact: -0.7, reasoning: \'High risk of missing demand window\' },\n          { factorId: \'f4\', impact: -0.6, reasoning: \'Competitors gaining advantage\' },\n        ],\n        implementationSteps: [],\n      },\n    ],\n    recommendedAlternative: \'alt-1\',\n    aiConfidence: 0.82,\n    stakeholders: [\n      { id: \'s1\', name: \'CFO\', role: \'Financial Approval\', influence: \'high\', preference: \'Phased approach preferred\' },\n      { id: \'s2\', name: \'COO\', role: \'Operations\', influence: \'high\', preference: \'Full investment recommended\' },\n      { id: \'s3\', name: \'VP Sales\', role: \'Sales\', influence: \'medium\', preference: \'Capacity needed soon\' },\n    ],\n  },\n  {\n    id: \'dec-002\',\n    type: \'vendor_selection\',\n    title: \'ERP System Vendor Selection\',\n    description: \'Select vendor for new enterprise resource planning system implementation.\',\n    context: \'Current ERP is end-of-life. Need to migrate to modern cloud-based solution within 18 months.\',\n    urgency: \'high\',\n    status: \'in_review\',\n    createdAt: new Date(\'2024-01-10\'),\n    deadline: new Date(\'2024-02-28\'),\n    factors: [\n      {\n        id: \'f1\',\n        name: \'Total Cost of Ownership\',\n        description: \'5-year TCO including licensing, implementation, and maintenance\',\n        weight: 0.25,\n        value: 0,\n        confidence: 0.8,\n        source: \'external\',\n        category: \'Financial\',\n      },\n      {\n        id: \'f2\',\n        name: \'Feature Fit\',\n        description: \'Alignment of features with business requirements\',\n        weight: 0.2,\n        value: 0,\n        confidence: 0.85,\n        source: \'expert\',\n        category: \'Functional\',\n      },\n      {\n        id: \'f3\',\n        name: \'Implementation Risk\',\n        description: \'Risk assessment of implementation timeline and success\',\n        weight: 0.2,\n        value: 0,\n        confidence: 0.7,\n        source: \'external\',\n        category: \'Risk\',\n      },\n    ],\n    alternatives: [\n      {\n        id: \'alt-1\',\n        name: \'Vendor A (SAP)\',\n        description: \'Enterprise-grade solution with comprehensive features\',\n        type: \'neutral\',\n        score: 72,\n        confidence: 0.75,\n        pros: [\'Industry leading features\', \'Strong support ecosystem\', \'Proven scalability\'],\n        cons: [\'Higher cost\', \'Longer implementation\', \'Complex customization\'],\n        riskLevel: \'medium\',\n        estimatedImpact: { financial: 1200000, timeline: \'18 months\' },\n        factors: [],\n        implementationSteps: [],\n      },\n      {\n        id: \'alt-2\',\n        name: \'Vendor B (Oracle)\',\n        description: \'Cloud-native ERP with strong financials module\',\n        type: \'recommended\',\n        score: 78,\n        confidence: 0.78,\n        pros: [\'Best-in-class financials\', \'Faster implementation\', \'Lower TCO\'],\n        cons: [\'Less manufacturing depth\', \'Fewer consultants available\'],\n        riskLevel: \'medium\',\n        estimatedImpact: { financial: 950000, timeline: \'14 months\' },\n        factors: [],\n        implementationSteps: [],\n      },\n    ],\n    recommendedAlternative: \'alt-2\',\n    aiConfidence: 0.78,\n  },\n  {\n    id: \'dec-003\',\n    type: \'hiring\',\n    title: \'Engineering Team Expansion\',\n    description: \'Decision on hiring 15 additional engineers for new product development.\',\n    context: \'Product roadmap requires expanded engineering capacity. Competing priorities for budget allocation.\',\n    urgency: \'medium\',\n    status: \'pending\',\n    createdAt: new Date(\'2024-01-15\'),\n    factors: [\n      {\n        id: \'f1\',\n        name: \'Talent Availability\',\n        description: \'Current job market conditions for engineers\',\n        weight: 0.2,\n        value: -0.3,\n        confidence: 0.7,\n        source: \'external\',\n        category: \'Market\',\n      },\n      {\n        id: \'f2\',\n        name: \'Budget Availability\',\n        description: \'Available budget for new headcount\',\n        weight: 0.25,\n        value: 0.5,\n        confidence: 0.9,\n        source: \'real_time\',\n        category: \'Financial\',\n      },\n      {\n        id: \'f3\',\n        name: \'Product Roadmap Impact\',\n        description: \'Impact on product delivery timeline\',\n        weight: 0.3,\n        value: 0.8,\n        confidence: 0.85,\n        source: \'forecast\',\n        category: \'Strategic\',\n      },\n    ],\n    alternatives: [\n      {\n        id: \'alt-1\',\n        name: \'Full Hiring (15 engineers)\',\n        description: \'Proceed with full hiring plan\',\n        type: \'recommended\',\n        score: 75,\n        confidence: 0.72,\n        pros: [\'Accelerates product roadmap\', \'Builds long-term capability\'],\n        cons: [\'High cost\', \'Recruiting challenge\', \'Onboarding time\'],\n        riskLevel: \'medium\',\n        estimatedImpact: { financial: -1800000, timeline: \'6 months to onboard\' },\n        factors: [],\n        implementationSteps: [],\n      },\n      {\n        id: \'alt-2\',\n        name: \'Phased Hiring (8 engineers now)\',\n        description: \'Hire 8 now, evaluate in 6 months\',\n        type: \'neutral\',\n        score: 65,\n        confidence: 0.7,\n        pros: [\'Lower initial cost\', \'Manageable onboarding\'],\n        cons: [\'Slower product progress\', \'May miss market window\'],\n        riskLevel: \'low\',\n        estimatedImpact: { financial: -960000, timeline: \'4 months to onboard\' },\n        factors: [],\n        implementationSteps: [],\n      },\n    ],\n    recommendedAlternative: \'alt-1\',\n    aiConfidence: 0.72,\n  },\n];\n\n// ============================================================================\n// DECISION PROVIDER\n// ============================================================================\n\nexport const DecisionProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [decisions, setDecisions] = useState<Decision[]>(sampleDecisions);\n  const [selectedDecision, setSelectedDecision] = useState<Decision | null>(null);\n\n  const createDecision = useCallback((decision: Omit<Decision, \'id\' | \'createdAt\' | \'status\' | \'factors\' | \'alternatives\' | \'recommendedAlternative\' | \'aiConfidence\'>): string => {\n    const id = `dec-${Date.now()}`;\n    const newDecision: Decision = {\n      ...decision,\n      id,\n      createdAt: new Date(),\n      status: \'pending\',\n      factors: [],\n      alternatives: [],\n      recommendedAlternative: \'\',\n      aiConfidence: 0,\n    };\n    setDecisions(prev => [...prev, newDecision]);\n    return id;\n  }, []);\n\n  const analyzeDecision = useCallback(async (decisionId: string) => {\n    // Simulate AI analysis\n    setDecisions(prev => prev.map(d =>\n      d.id === decisionId ? { ...d, status: \'in_review\' as const } : d\n    ));\n\n    await new Promise(resolve => setTimeout(resolve, 2000));\n\n    // Add analysis results (simplified)\n    setDecisions(prev => prev.map(d => {\n      if (d.id !== decisionId) return d;\n      return {\n        ...d,\n        aiConfidence: 0.75 + Math.random() * 0.2,\n      };\n    }));\n  }, []);\n\n  const makeDecision = useCallback((decisionId: string, alternativeId: string, rationale: string) => {\n    setDecisions(prev => prev.map(d =>\n      d.id === decisionId ? {\n        ...d,\n        status: \'decided\' as const,\n        finalDecision: alternativeId,\n        decisionRationale: rationale,\n        decidedAt: new Date(),\n      } : d\n    ));\n  }, []);\n\n  const cancelDecision = useCallback((decisionId: string) => {\n    setDecisions(prev => prev.map(d =>\n      d.id === decisionId ? { ...d, status: \'cancelled\' as const } : d\n    ));\n  }, []);\n\n  const getPendingDecisions = useCallback(() => {\n    return decisions.filter(d => d.status === \'pending\' || d.status === \'in_review\');\n  }, [decisions]);\n\n  const getDecisionFactors = useCallback((decisionId: string) => {\n    const decision = decisions.find(d => d.id === decisionId);\n    return decision?.factors || [];\n  }, [decisions]);\n\n  const getAlternatives = useCallback((decisionId: string) => {\n    const decision = decisions.find(d => d.id === decisionId);\n    return decision?.alternatives || [];\n  }, [decisions]);\n\n  const getRecommendedAlternative = useCallback((decisionId: string) => {\n    const decision = decisions.find(d => d.id === decisionId);\n    if (!decision) return undefined;\n    return decision.alternatives.find(a => a.id === decision.recommendedAlternative);\n  }, [decisions]);\n\n  const value = useMemo(() => ({\n    decisions,\n    selectedDecision,\n    setSelectedDecision,\n    createDecision,\n    analyzeDecision,\n    makeDecision,\n    cancelDecision,\n    getPendingDecisions,\n    getDecisionFactors,\n    getAlternatives,\n    getRecommendedAlternative,\n  }), [\n    decisions, selectedDecision,\n    createDecision, analyzeDecision, makeDecision, cancelDecision,\n    getPendingDecisions, getDecisionFactors, getAlternatives, getRecommendedAlternative,\n  ]);\n\n  return (\n    <DecisionContext.Provider value={value}>\n      {children}\n    </DecisionContext.Provider>\n  );\n};\n\n// ============================================================================\n// DECISION LIST COMPONENT\n// ============================================================================\n\ninterface DecisionListProps {\n  onSelectDecision: (decision: Decision) => void;\n}\n\nexport const DecisionList: React.FC<DecisionListProps> = ({ onSelectDecision }) => {\n  const { decisions } = useDecisionRecommendations();\n\n  const getUrgencyColor = (urgency: Decision[\'urgency\']) => {\n    const colors: Record<string, string> = {\n      low: \'bg-gray-100 text-gray-700\',\n      medium: \'bg-blue-100 text-blue-700\',\n      high: \'bg-orange-100 text-orange-700\',\n      critical: \'bg-red-100 text-red-700\',\n    };\n    return colors[urgency];\n  };\n\n  const getStatusColor = (status: Decision[\'status\']) => {\n    const colors: Record<string, string> = {\n      pending: \'bg-yellow-100 text-yellow-700\',\n      in_review: \'bg-blue-100 text-blue-700\',\n      decided: \'bg-green-100 text-green-700\',\n      implemented: \'bg-purple-100 text-purple-700\',\n      cancelled: \'bg-gray-100 text-gray-500\',\n    };\n    return colors[status];\n  };\n\n  return (\n    <div className="space-y-3">\n      {decisions.map(decision => (\n        <div\n          key={decision.id}\n          onClick={() => onSelectDecision(decision)}\n          className="border rounded-lg p-4 hover:shadow-md transition-shadow cursor-pointer bg-white"\n        >\n          <div className="flex items-start justify-between mb-2">\n            <div>\n              <div className="flex items-center gap-2 mb-1">\n                <span className={`px-2 py-0.5 text-xs rounded-full ${getUrgencyColor(decision.urgency)}`}>\n                  {decision.urgency}\n                </span>\n                <span className={`px-2 py-0.5 text-xs rounded-full ${getStatusColor(decision.status)}`}>\n                  {decision.status.replace(\'_\', \' \')}\n                </span>\n              </div>\n              <h3 className="font-medium">{decision.title}</h3>\n            </div>\n            {decision.aiConfidence > 0 && (\n              <div className="text-right">\n                <p className="text-xs text-gray-500">AI Confidence</p>\n                <p className="font-semibold text-blue-600">{Math.round(decision.aiConfidence * 100)}%</p>\n              </div>\n            )}\n          </div>\n\n          <p className="text-sm text-gray-600 line-clamp-2">{decision.description}</p>\n\n          <div className="flex items-center gap-4 mt-3 text-xs text-gray-500">\n            <span className="px-2 py-0.5 bg-gray-100 rounded">{decision.type.replace(\'_\', \' \')}</span>\n            {decision.deadline && (\n              <span>Due: {new Date(decision.deadline).toLocaleDateString()}</span>\n            )}\n            <span>{decision.alternatives.length} alternatives</span>\n          </div>\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// DECISION DETAIL COMPONENT\n// ============================================================================\n\ninterface DecisionDetailProps {\n  decision: Decision;\n  onBack: () => void;\n}\n\nexport const DecisionDetail: React.FC<DecisionDetailProps> = ({ decision, onBack }) => {\n  const { analyzeDecision, makeDecision, cancelDecision } = useDecisionRecommendations();\n  const [selectedAlternative, setSelectedAlternative] = useState<string | null>(null);\n  const [rationale, setRationale] = useState(\'\');\n  const [showConfirmDialog, setShowConfirmDialog] = useState(false);\n\n  const handleConfirm = () => {\n    if (selectedAlternative && rationale.trim()) {\n      makeDecision(decision.id, selectedAlternative, rationale);\n      setShowConfirmDialog(false);\n    }\n  };\n\n  const getAlternativeTypeColor = (type: DecisionAlternative[\'type\']) => {\n    const colors: Record<string, string> = {\n      recommended: \'border-green-500 bg-green-50\',\n      neutral: \'border-gray-300 bg-white\',\n      not_recommended: \'border-red-300 bg-red-50\',\n    };\n    return colors[type];\n  };\n\n  const getRiskColor = (risk: DecisionAlternative[\'riskLevel\']) => {\n    const colors: Record<string, string> = {\n      low: \'text-green-600\',\n      medium: \'text-yellow-600\',\n      high: \'text-orange-600\',\n      critical: \'text-red-600\',\n    };\n    return colors[risk];\n  };\n\n  return (\n    <div className="h-full flex flex-col">\n      {/* Header */}\n      <div className="border-b bg-white p-4">\n        <button onClick={onBack} className="text-sm text-gray-600 hover:text-gray-900 mb-2">← Back</button>\n        <h1 className="text-xl font-semibold">{decision.title}</h1>\n        <p className="text-sm text-gray-600 mt-1">{decision.description}</p>\n        \n        <div className="flex items-center gap-4 mt-3">\n          <span className="px-2 py-0.5 text-xs bg-blue-100 text-blue-700 rounded">\n            {decision.type.replace(\'_\', \' \')}\n          </span>\n          <span className="text-sm text-gray-500">\n            AI Confidence: <span className="font-semibold text-blue-600">{Math.round(decision.aiConfidence * 100)}%</span>\n          </span>\n        </div>\n      </div>\n\n      {/* Content */}\n      <div className="flex-1 overflow-auto p-4 bg-gray-50">\n        <div className="grid gap-6 lg:grid-cols-2">\n          {/* Factors */}\n          <div>\n            <h3 className="text-lg font-medium mb-3">Decision Factors</h3>\n            <div className="space-y-3">\n              {decision.factors.map(factor => (\n                <div key={factor.id} className="bg-white border rounded-lg p-3">\n                  <div className="flex items-start justify-between">\n                    <div>\n                      <h4 className="font-medium text-sm">{factor.name}</h4>\n                      <p className="text-xs text-gray-500 mt-0.5">{factor.description}</p>\n                    </div>\n                    <div className="text-right">\n                      <p className="text-xs text-gray-500">Weight: {Math.round(factor.weight * 100)}%</p>\n                      <p className="text-xs text-gray-500">Confidence: {Math.round(factor.confidence * 100)}%</p>\n                    </div>\n                  </div>\n                  <div className="mt-2 flex items-center gap-2">\n                    <div className="flex-1 h-2 bg-gray-200 rounded-full overflow-hidden">\n                      <div\n                        className={`h-full ${factor.value > 0 ? \'bg-green-500\' : factor.value < 0 ? \'bg-red-500\' : \'bg-gray-400\'}`}\n                        style={{ width: `${Math.abs(factor.value) * 100}%`, marginLeft: factor.value < 0 ? \'auto\' : 0 }}\n                      />\n                    </div>\n                    <span className={`text-sm font-medium ${factor.value > 0 ? \'text-green-600\' : factor.value < 0 ? \'text-red-600\' : \'text-gray-500\'}`}>\n                      {factor.value > 0 ? \'+\' : \'\'}{Math.round(factor.value * 100)}\n                    </span>\n                  </div>\n                  <div className="mt-2 flex items-center gap-2 text-xs">\n                    <span className="px-2 py-0.5 bg-gray-100 rounded">{factor.category}</span>\n                    <span className="text-gray-500">Source: {factor.source.replace(\'_\', \' \')}</span>\n                  </div>\n                </div>\n              ))}\n            </div>\n          </div>\n\n          {/* Alternatives */}\n          <div>\n            <h3 className="text-lg font-medium mb-3">Alternatives</h3>\n            <div className="space-y-4">\n              {decision.alternatives.map(alternative => (\n                <div\n                  key={alternative.id}\n                  onClick={() => decision.status === \'pending\' && setSelectedAlternative(alternative.id)}\n                  className={`border-2 rounded-lg p-4 cursor-pointer transition-all ${getAlternativeTypeColor(alternative.type)} ${\n                    selectedAlternative === alternative.id ? \'ring-2 ring-blue-500\' : \'\'\n                  }`}\n                >\n                  <div className="flex items-start justify-between mb-2">\n                    <div>\n                      <div className="flex items-center gap-2">\n                        <h4 className="font-medium">{alternative.name}</h4>\n                        {alternative.type === \'recommended\' && (\n                          <span className="px-2 py-0.5 text-xs bg-green-500 text-white rounded">AI Recommended</span>\n                        )}\n                      </div>\n                      <p className="text-sm text-gray-600 mt-1">{alternative.description}</p>\n                    </div>\n                    <div className="text-right">\n                      <p className="text-2xl font-bold">{alternative.score}</p>\n                      <p className="text-xs text-gray-500">Score</p>\n                    </div>\n                  </div>\n\n                  <div className="grid grid-cols-2 gap-4 mt-3">\n                    <div>\n                      <h5 className="text-xs font-medium text-green-700 mb-1">Pros</h5>\n                      <ul className="text-xs text-gray-600 space-y-0.5">\n                        {alternative.pros.slice(0, 3).map((pro, i) => (\n                          <li key={i} className="flex items-start gap-1">\n                            <span className="text-green-500">✓</span>\n                            {pro}\n                          </li>\n                        ))}\n                      </ul>\n                    </div>\n                    <div>\n                      <h5 className="text-xs font-medium text-red-700 mb-1">Cons</h5>\n                      <ul className="text-xs text-gray-600 space-y-0.5">\n                        {alternative.cons.slice(0, 3).map((con, i) => (\n                          <li key={i} className="flex items-start gap-1">\n                            <span className="text-red-500">✗</span>\n                            {con}\n                          </li>\n                        ))}\n                      </ul>\n                    </div>\n                  </div>\n\n                  <div className="flex items-center gap-4 mt-3 text-xs">\n                    <span>Risk: <span className={`font-medium ${getRiskColor(alternative.riskLevel)}`}>{alternative.riskLevel}</span></span>\n                    {alternative.estimatedImpact.financial && (\n                      <span>Impact: ${Math.abs(alternative.estimatedImpact.financial).toLocaleString()}</span>\n                    )}\n                    <span>Confidence: {Math.round(alternative.confidence * 100)}%</span>\n                  </div>\n\n                  {/* Implementation steps */}\n                  {alternative.implementationSteps.length > 0 && (\n                    <div className="mt-3 pt-3 border-t">\n                      <h5 className="text-xs font-medium text-gray-700 mb-2">Implementation Steps</h5>\n                      <div className="space-y-1">\n                        {alternative.implementationSteps.slice(0, 4).map(step => (\n                          <div key={step.step} className="flex items-center gap-2 text-xs">\n                            <span className="w-5 h-5 rounded-full bg-blue-100 text-blue-600 flex items-center justify-center font-medium">\n                              {step.step}\n                            </span>\n                            <span className="flex-1">{step.action}</span>\n                            <span className="text-gray-500">{step.estimatedTime}</span>\n                          </div>\n                        ))}\n                      </div>\n                    </div>\n                  )}\n                </div>\n              ))}\n            </div>\n          </div>\n        </div>\n      </div>\n\n      {/* Actions */}\n      {decision.status === \'pending\' && (\n        <div className="border-t p-4 bg-white">\n          <div className="flex items-center gap-4">\n            <div className="flex-1">\n              <textarea\n                value={rationale}\n                onChange={(e) => setRationale(e.target.value)}\n                placeholder="Add your decision rationale..."\n                className="w-full px-3 py-2 border rounded-lg text-sm"\n                rows={2}\n              />\n            </div>\n            <div className="flex gap-2">\n              <button\n                onClick={() => cancelDecision(decision.id)}\n                className="px-4 py-2 border rounded-lg hover:bg-gray-100"\n              >\n                Cancel\n              </button>\n              <button\n                onClick={() => setShowConfirmDialog(true)}\n                disabled={!selectedAlternative || !rationale.trim()}\n                className="px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600 disabled:opacity-50"\n              >\n                Confirm Decision\n              </button>\n            </div>\n          </div>\n        </div>\n      )}\n\n      {/* Confirm Dialog */}\n      {showConfirmDialog && (\n        <div className="fixed inset-0 bg-black/50 flex items-center justify-center z-50">\n          <div className="bg-white rounded-lg shadow-xl w-full max-w-md p-6">\n            <h2 className="text-lg font-semibold mb-4">Confirm Decision</h2>\n            <p className="text-sm text-gray-600 mb-4">\n              You are about to select: <strong>{decision.alternatives.find(a => a.id === selectedAlternative)?.name}</strong>\n            </p>\n            <div className="flex justify-end gap-2">\n              <button\n                onClick={() => setShowConfirmDialog(false)}\n                className="px-4 py-2 border rounded-lg hover:bg-gray-100"\n              >\n                Cancel\n              </button>\n              <button\n                onClick={handleConfirm}\n                className="px-4 py-2 bg-green-500 text-white rounded-lg hover:bg-green-600"\n              >\n                Confirm\n              </button>\n            </div>\n          </div>\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN DECISION RECOMMENDATIONS COMPONENT\n// ============================================================================\n\nexport const DecisionRecommendations: React.FC = () => {\n  const { selectedDecision, setSelectedDecision } = useDecisionRecommendations();\n\n  return (\n    <div className="h-full flex flex-col">\n      <div className="p-4 border-b bg-white">\n        <h1 className="text-xl font-semibold">AI Decision Recommendations</h1>\n        <p className="text-sm text-gray-500">Data-driven decision support with explainable AI</p>\n      </div>\n\n      <div className="flex-1 overflow-auto p-4 bg-gray-50">\n        {selectedDecision ? (\n          <DecisionDetail decision={selectedDecision} onBack={() => setSelectedDecision(null)} />\n        ) : (\n          <DecisionList onSelectDecision={setSelectedDecision} />\n        )}\n      </div>\n    </div>\n  );\n};\n\nexport default DecisionRecommendations;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/ai/decision-recommendations.tsx\' created successfully.") </create-file> </tool_result>'}
{'role': 'assistant', 'content': 'Now let me create the Explainability Layer component for the AI System.\n\n<function_calls>\n<create-file file_path="frontend/src/components/ai/explainability-layer.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst FeatureImportanceSchema = z.object({\n  feature: z.string(),\n  importance: z.number().min(0).max(1),\n  contribution: z.number(), // Actual contribution to the prediction\n  direction: z.enum([\'positive\', \'negative\', \'neutral\']),\n  shapValue: z.number().optional(), // SHAP value for local explanation\n  description: z.string().optional(),\n});\n\nconst DecisionPathSchema = z.object({\n  step: z.number(),\n  condition: z.string(),\n  outcome: z.string(),\n  confidence: z.number(),\n  samples: z.number().optional(), // Number of samples at this node\n});\n\nconst ExplanationSchema = z.object({\n  id: z.string(),\n  modelId: z.string(),\n  predictionId: z.string(),\n  predictionType: z.enum([\'classification\', \'regression\', \'forecast\', \'anomaly\', \'recommendation\']),\n  input: z.record(z.unknown()),\n  output: z.record(z.unknown()),\n  confidence: z.number(),\n  \n  // Global explanation\n  globalFeatureImportance: z.array(FeatureImportanceSchema),\n  \n  // Local explanation (for this specific prediction)\n  localFeatureImportance: z.array(FeatureImportanceSchema),\n  \n  // Decision path (for tree-based models)\n  decisionPath: z.array(DecisionPathSchema).optional(),\n  \n  // Counterfactual explanations\n  counterfactuals: z.array(z.object({\n    changes: z.record(z.unknown()),\n    newPrediction: z.unknown(),\n    distance: z.number(),\n    description: z.string(),\n  })).optional(),\n  \n  // Attention weights (for transformer-based models)\n  attentionWeights: z.array(z.array(z.number())).optional(),\n  \n  // Natural language explanation\n  naturalLanguageExplanation: z.string(),\n  \n  // Confidence breakdown\n  confidenceBreakdown: z.object({\n    dataQuality: z.number(),\n    modelCertainty: z.number(),\n    featureReliability: z.number(),\n    domainExpertAgreement: z.number().optional(),\n  }),\n  \n  // What-if scenarios\n  whatIfScenarios: z.array(z.object({\n    name: z.string(),\n    inputChanges: z.record(z.unknown()),\n    expectedOutput: z.unknown(),\n    explanation: z.string(),\n  })).optional(),\n  \n  createdAt: z.date(),\n});\n\ntype FeatureImportance = z.infer<typeof FeatureImportanceSchema>;\ntype DecisionPath = z.infer<typeof DecisionPathSchema>;\ntype Explanation = z.infer<typeof ExplanationSchema>;\n\n// ============================================================================\n// EXPLAINABILITY STORE\n// ============================================================================\n\ninterface ExplainabilityStore {\n  explanations: Explanation[];\n  selectedExplanation: Explanation | null;\n  \n  // Actions\n  getExplanation: (predictionId: string) => Explanation | undefined;\n  generateExplanation: (modelId: string, predictionId: string, input: Record<string, unknown>, output: Record<string, unknown>) => Promise<Explanation>;\n  generateCounterfactuals: (explanationId: string, count: number) => Promise<void>;\n  runWhatIf: (explanationId: string, changes: Record<string, unknown>) => Promise<unknown>;\n  \n  // Visualization helpers\n  getFeatureImportanceChart: (explanationId: string) => { features: string[]; values: number[] };\n  getDecisionTreeVisualization: (explanationId: string) => DecisionPath[] | undefined;\n  getConfidenceBreakdownChart: (explanationId: string) => { labels: string[]; values: number[] };\n}\n\nconst ExplainabilityContext = createContext<ExplainabilityStore | null>(null);\n\nexport const useExplainability = () => {\n  const context = useContext(ExplainabilityContext);\n  if (!context) {\n    throw new Error(\'useExplainability must be used within ExplainabilityProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst sampleExplanations: Explanation[] = [\n  {\n    id: \'exp-001\',\n    modelId: \'fraud-detection-v2\',\n    predictionId: \'pred-12345\',\n    predictionType: \'classification\',\n    input: {\n      amount: 125000,\n      vendor_id: \'vendor-abc\',\n      time_of_day: \'14:30\',\n      day_of_week: \'Monday\',\n      vendor_age_days: 365,\n      avg_transaction_amount: 25000,\n      transaction_frequency: \'monthly\',\n      payment_method: \'wire_transfer\',\n    },\n    output: {\n      prediction: \'fraudulent\',\n      probability: 0.92,\n    },\n    confidence: 0.92,\n    globalFeatureImportance: [\n      { feature: \'amount\', importance: 0.28, contribution: 0.35, direction: \'positive\', description: \'Transaction amount relative to historical average\' },\n      { feature: \'vendor_age_days\', importance: 0.18, contribution: 0.15, direction: \'positive\', description: \'How long the vendor relationship exists\' },\n      { feature: \'payment_method\', importance: 0.15, contribution: 0.12, direction: \'positive\', description: \'Wire transfers have higher fraud risk\' },\n      { feature: \'time_of_day\', importance: 0.12, contribution: 0.08, direction: \'positive\', description: \'Unusual timing for this vendor\' },\n      { feature: \'transaction_frequency\', importance: 0.10, contribution: 0.06, direction: \'neutral\', description: \'Matches expected frequency\' },\n    ],\n    localFeatureImportance: [\n      { feature: \'amount\', importance: 0.45, contribution: 0.52, direction: \'positive\', shapValue: 0.28, description: \'5x higher than average for this vendor\' },\n      { feature: \'vendor_age_days\', importance: 0.20, contribution: -0.08, direction: \'negative\', shapValue: -0.04, description: \'Long relationship reduces fraud likelihood\' },\n      { feature: \'payment_method\', importance: 0.18, contribution: 0.15, direction: \'positive\', shapValue: 0.08, description: \'Wire transfer chosen instead of usual ACH\' },\n      { feature: \'time_of_day\', importance: 0.12, contribution: 0.10, direction: \'positive\', shapValue: 0.05, description: \'Different from vendor\\\'s typical pattern\' },\n      { feature: \'day_of_week\', importance: 0.05, contribution: 0.02, direction: \'positive\', shapValue: 0.01, description: \'Monday is unusual for this vendor\' },\n    ],\n    decisionPath: [\n      { step: 1, condition: \'amount > 100000\', outcome: \'True\', confidence: 1.0, samples: 150 },\n      { step: 2, condition: \'payment_method = wire_transfer\', outcome: \'True\', confidence: 1.0, samples: 45 },\n      { step: 3, condition: \'amount / avg_amount > 3\', outcome: \'True\', confidence: 0.95, samples: 12 },\n      { step: 4, condition: \'vendor_age_days < 30\', outcome: \'False\', confidence: 1.0, samples: 8 },\n      { step: 5, condition: \'time_deviation > 2hrs\', outcome: \'True\', confidence: 0.85, samples: 5 },\n    ],\n    counterfactuals: [\n      {\n        changes: { amount: 50000, payment_method: \'ach\' },\n        newPrediction: \'legitimate\',\n        distance: 0.35,\n        description: \'If the amount was $50,000 and paid via ACH, the transaction would likely be legitimate\',\n      },\n      {\n        changes: { amount: 75000, payment_method: \'wire_transfer\' },\n        newPrediction: \'legitimate\',\n        distance: 0.42,\n        description: \'If the amount was reduced to $75,000 while keeping wire transfer, risk would be lower\',\n      },\n    ],\n    naturalLanguageExplanation: \'This transaction was flagged as potentially fraudulent primarily because the amount ($125,000) is 5 times higher than the historical average for this vendor ($25,000). Additionally, the payment method changed from the usual ACH to wire transfer, which carries higher fraud risk. While the vendor has a long relationship (365 days) which normally reduces fraud likelihood, the combination of unusual amount and payment method triggers high suspicion. The transaction timing also deviates from the vendor\\\'s typical pattern.\',\n    confidenceBreakdown: {\n      dataQuality: 0.95,\n      modelCertainty: 0.92,\n      featureReliability: 0.88,\n      domainExpertAgreement: 0.85,\n    },\n    whatIfScenarios: [\n      {\n        name: \'Lower Amount\',\n        inputChanges: { amount: 50000 },\n        expectedOutput: { prediction: \'legitimate\', probability: 0.78 },\n        explanation: \'Reducing the amount to $50,000 would significantly decrease fraud probability\',\n      },\n      {\n        name: \'Different Payment Method\',\n        inputChanges: { payment_method: \'ach\' },\n        expectedOutput: { prediction: \'requires_review\', probability: 0.55 },\n        explanation: \'Using ACH instead of wire transfer would reduce but not eliminate suspicion\',\n      },\n    ],\n    createdAt: new Date(\'2024-01-20T14:35:00\'),\n  },\n  {\n    id: \'exp-002\',\n    modelId: \'revenue-forecast-v3\',\n    predictionId: \'pred-67890\',\n    predictionType: \'forecast\',\n    input: {\n      historical_revenue: [1200000, 1150000, 1300000, 1250000],\n      marketing_spend: 150000,\n      economic_index: 1.05,\n      seasonality_factor: 1.1,\n    },\n    output: {\n      prediction: 1450000,\n      confidence_interval: [1320000, 1580000],\n    },\n    confidence: 0.87,\n    globalFeatureImportance: [\n      { feature: \'historical_revenue\', importance: 0.40, contribution: 0.35, direction: \'positive\' },\n      { feature: \'marketing_spend\', importance: 0.25, contribution: 0.18, direction: \'positive\' },\n      { feature: \'seasonality_factor\', importance: 0.20, contribution: 0.15, direction: \'positive\' },\n      { feature: \'economic_index\', importance: 0.15, contribution: 0.10, direction: \'positive\' },\n    ],\n    localFeatureImportance: [\n      { feature: \'historical_revenue\', importance: 0.38, contribution: 0.32, direction: \'positive\', shapValue: 0.28 },\n      { feature: \'seasonality_factor\', importance: 0.28, contribution: 0.22, direction: \'positive\', shapValue: 0.18 },\n      { feature: \'marketing_spend\', importance: 0.20, contribution: 0.15, direction: \'positive\', shapValue: 0.12 },\n      { feature: \'economic_index\', importance: 0.14, contribution: 0.08, direction: \'positive\', shapValue: 0.06 },\n    ],\n    naturalLanguageExplanation: \'The model predicts revenue of $1.45M for the next period, an increase of 16% from the previous quarter. This prediction is primarily driven by the seasonal uptick factor (1.1x) typical for Q4, combined with increased marketing spend ($150K, up 20%). The historical revenue trend shows consistent growth averaging 8% YoY. The positive economic index (1.05) supports continued consumer spending. The 95% confidence interval ranges from $1.32M to $1.58M.\',\n    confidenceBreakdown: {\n      dataQuality: 0.92,\n      modelCertainty: 0.87,\n      featureReliability: 0.90,\n    },\n    whatIfScenarios: [\n      {\n        name: \'Reduced Marketing\',\n        inputChanges: { marketing_spend: 100000 },\n        expectedOutput: { prediction: 1380000, confidence_interval: [1250000, 1510000] },\n        explanation: \'33% reduction in marketing would decrease forecast by ~$70K\',\n      },\n      {\n        name: \'Economic Downturn\',\n        inputChanges: { economic_index: 0.95 },\n        expectedOutput: { prediction: 1350000, confidence_interval: [1180000, 1520000] },\n        explanation: \'Economic slowdown would reduce forecast and increase uncertainty\',\n      },\n    ],\n    createdAt: new Date(\'2024-01-20T10:00:00\'),\n  },\n];\n\n// ============================================================================\n// EXPLAINABILITY PROVIDER\n// ============================================================================\n\nexport const ExplainabilityProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [explanations, setExplanations] = useState<Explanation[]>(sampleExplanations);\n  const [selectedExplanation, setSelectedExplanation] = useState<Explanation | null>(null);\n\n  const getExplanation = useCallback((predictionId: string) => {\n    return explanations.find(e => e.predictionId === predictionId);\n  }, [explanations]);\n\n  const generateExplanation = useCallback(async (\n    modelId: string,\n    predictionId: string,\n    input: Record<string, unknown>,\n    output: Record<string, unknown>\n  ): Promise<Explanation> => {\n    // Simulate explanation generation\n    await new Promise(resolve => setTimeout(resolve, 1000));\n\n    const explanation: Explanation = {\n      id: `exp-${Date.now()}`,\n      modelId,\n      predictionId,\n      predictionType: \'classification\',\n      input,\n      output,\n      confidence: 0.75 + Math.random() * 0.2,\n      globalFeatureImportance: Object.keys(input).slice(0, 5).map((feature, i) => ({\n        feature,\n        importance: 0.3 - (i * 0.05),\n        contribution: Math.random() * 0.3,\n        direction: Math.random() > 0.5 ? \'positive\' : \'negative\',\n      })),\n      localFeatureImportance: Object.keys(input).slice(0, 5).map((feature, i) => ({\n        feature,\n        importance: 0.35 - (i * 0.06),\n        contribution: Math.random() * 0.35,\n        direction: Math.random() > 0.5 ? \'positive\' : \'negative\',\n        shapValue: Math.random() * 0.2 - 0.1,\n      })),\n      naturalLanguageExplanation: \'This prediction is based on the provided input features. The model has analyzed the patterns and determined the most likely outcome based on historical data.\',\n      confidenceBreakdown: {\n        dataQuality: 0.85 + Math.random() * 0.1,\n        modelCertainty: 0.8 + Math.random() * 0.15,\n        featureReliability: 0.85 + Math.random() * 0.1,\n      },\n      createdAt: new Date(),\n    };\n\n    setExplanations(prev => [...prev, explanation]);\n    return explanation;\n  }, []);\n\n  const generateCounterfactuals = useCallback(async (explanationId: string, count: number) => {\n    await new Promise(resolve => setTimeout(resolve, 500));\n\n    setExplanations(prev => prev.map(exp => {\n      if (exp.id !== explanationId) return exp;\n\n      const counterfactuals = Array.from({ length: count }, (_, i) => ({\n        changes: { feature_a: Math.random() * 100, feature_b: \'modified\' },\n        newPrediction: \'alternative\',\n        distance: 0.2 + (i * 0.1),\n        description: `Counterfactual ${i + 1}: If the input was modified, the prediction would change`,\n      }));\n\n      return { ...exp, counterfactuals };\n    }));\n  }, []);\n\n  const runWhatIf = useCallback(async (explanationId: string, changes: Record<string, unknown>) => {\n    await new Promise(resolve => setTimeout(resolve, 300));\n    \n    const explanation = explanations.find(e => e.id === explanationId);\n    if (!explanation) return null;\n\n    // Simulate what-if analysis\n    return { prediction: \'modified\', probability: 0.75 };\n  }, [explanations]);\n\n  const getFeatureImportanceChart = useCallback((explanationId: string) => {\n    const explanation = explanations.find(e => e.id === explanationId);\n    if (!explanation) return { features: [], values: [] };\n\n    const local = explanation.localFeatureImportance;\n    return {\n      features: local.map(f => f.feature),\n      values: local.map(f => f.shapValue || f.contribution),\n    };\n  }, [explanations]);\n\n  const getDecisionTreeVisualization = useCallback((explanationId: string) => {\n    const explanation = explanations.find(e => e.id === explanationId);\n    return explanation?.decisionPath;\n  }, [explanations]);\n\n  const getConfidenceBreakdownChart = useCallback((explanationId: string) => {\n    const explanation = explanations.find(e => e.id === explanationId);\n    if (!explanation) return { labels: [], values: [] };\n\n    const { confidenceBreakdown } = explanation;\n    return {\n      labels: Object.keys(confidenceBreakdown).map(k => k.replace(/([A-Z])/g, \' $1\').trim()),\n      values: Object.values(confidenceBreakdown),\n    };\n  }, [explanations]);\n\n  const value = useMemo(() => ({\n    explanations,\n    selectedExplanation,\n    setSelectedExplanation,\n    getExplanation,\n    generateExplanation,\n    generateCounterfactuals,\n    runWhatIf,\n    getFeatureImportanceChart,\n    getDecisionTreeVisualization,\n    getConfidenceBreakdownChart,\n  }), [\n    explanations, selectedExplanation,\n    getExplanation, generateExplanation, generateCounterfactuals, runWhatIf,\n    getFeatureImportanceChart, getDecisionTreeVisualization, getConfidenceBreakdownChart,\n  ]);\n\n  return (\n    <ExplainabilityContext.Provider value={value}>\n      {children}\n    </ExplainabilityContext.Provider>\n  );\n};\n\n// ============================================================================\n// FEATURE IMPORTANCE CHART COMPONENT\n// ============================================================================\n\ninterface FeatureImportanceChartProps {\n  features: FeatureImportance[];\n  title?: string;\n}\n\nexport const FeatureImportanceChart: React.FC<FeatureImportanceChartProps> = ({ features, title = \'Feature Importance\' }) => {\n  const sortedFeatures = [...features].sort((a, b) => Math.abs(b.importance) - Math.abs(a.importance));\n  const maxImportance = Math.max(...features.map(f => f.importance));\n\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <h3 className="text-sm font-medium text-gray-700 mb-4">{title}</h3>\n      <div className="space-y-3">\n        {sortedFeatures.map((feature, idx) => (\n          <div key={idx} className="space-y-1">\n            <div className="flex items-center justify-between text-sm">\n              <span className="font-medium">{feature.feature}</span>\n              <span className={`text-xs ${feature.direction === \'positive\' ? \'text-green-600\' : feature.direction === \'negative\' ? \'text-red-600\' : \'text-gray-500\'}`}>\n                {feature.direction === \'positive\' ? \'↑\' : feature.direction === \'negative\' ? \'↓\' : \'→\'} {(feature.importance * 100).toFixed(0)}%\n              </span>\n            </div>\n            <div className="h-2 bg-gray-100 rounded-full overflow-hidden">\n              <div\n                className={`h-full rounded-full transition-all ${\n                  feature.direction === \'positive\' ? \'bg-green-500\' :\n                  feature.direction === \'negative\' ? \'bg-red-500\' :\n                  \'bg-gray-400\'\n                }`}\n                style={{ width: `${(feature.importance / maxImportance) * 100}%` }}\n              />\n            </div>\n            {feature.description && (\n              <p className="text-xs text-gray-500">{feature.description}</p>\n            )}\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// DECISION PATH VISUALIZATION COMPONENT\n// ============================================================================\n\ninterface DecisionPathVisualizationProps {\n  path: DecisionPath[];\n}\n\nexport const DecisionPathVisualization: React.FC<DecisionPathVisualizationProps> = ({ path }) => {\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <h3 className="text-sm font-medium text-gray-700 mb-4">Decision Path</h3>\n      <div className="space-y-0">\n        {path.map((node, idx) => (\n          <div key={idx} className="flex items-start">\n            {/* Connecting line */}\n            {idx > 0 && (\n              <div className="absolute ml-3" style={{ marginTop: \'-1rem\', height: \'1rem\' }}>\n                <div className="w-0.5 h-4 bg-gray-300 ml-3" />\n              </div>\n            )}\n            \n            <div className="flex items-start gap-3">\n              <div className={`w-6 h-6 rounded-full flex items-center justify-center text-xs font-medium ${\n                node.outcome === \'True\' ? \'bg-green-100 text-green-700\' : \'bg-red-100 text-red-700\'\n              }`}>\n                {node.step}\n              </div>\n              <div className="flex-1 pb-4">\n                <div className="flex items-center gap-2">\n                  <code className="text-xs bg-gray-100 px-2 py-1 rounded">{node.condition}</code>\n                  <span className={`text-xs px-2 py-0.5 rounded ${\n                    node.outcome === \'True\' ? \'bg-green-50 text-green-700\' : \'bg-red-50 text-red-700\'\n                  }`}>\n                    {node.outcome}\n                  </span>\n                </div>\n                <div className="flex items-center gap-3 mt-1 text-xs text-gray-500">\n                  <span>Confidence: {(node.confidence * 100).toFixed(0)}%</span>\n                  {node.samples && <span>Samples: {node.samples}</span>}\n                </div>\n              </div>\n            </div>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// COUNTERFACTUAL EXPLANATIONS COMPONENT\n// ============================================================================\n\ninterface CounterfactualsProps {\n  counterfactuals: NonNullable<Explanation[\'counterfactuals\']>;\n  onRunWhatIf?: (changes: Record<string, unknown>) => void;\n}\n\nexport const Counterfactuals: React.FC<CounterfactualsProps> = ({ counterfactuals, onRunWhatIf }) => {\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <h3 className="text-sm font-medium text-gray-700 mb-4">What Would Change the Outcome?</h3>\n      <div className="space-y-3">\n        {counterfactuals.map((cf, idx) => (\n          <div key={idx} className="border rounded-lg p-3 bg-gradient-to-r from-blue-50 to-white">\n            <div className="flex items-start justify-between">\n              <div className="flex-1">\n                <p className="text-sm text-gray-700">{cf.description}</p>\n                <div className="mt-2 flex flex-wrap gap-2">\n                  {Object.entries(cf.changes).map(([key, value]) => (\n                    <span key={key} className="text-xs bg-blue-100 text-blue-700 px-2 py-0.5 rounded">\n                      {key}: {String(value)}\n                    </span>\n                  ))}\n                </div>\n                <div className="mt-2 text-xs text-gray-500">\n                  New prediction: <span className="font-medium text-green-700">{String(cf.newPrediction)}</span>\n                  <span className="ml-2">• Distance: {cf.distance.toFixed(2)}</span>\n                </div>\n              </div>\n              {onRunWhatIf && (\n                <button\n                  onClick={() => onRunWhatIf(cf.changes)}\n                  className="text-xs text-blue-600 hover:text-blue-800"\n                >\n                  Apply\n                </button>\n              )}\n            </div>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// CONFIDENCE BREAKDOWN COMPONENT\n// ============================================================================\n\ninterface ConfidenceBreakdownProps {\n  breakdown: Explanation[\'confidenceBreakdown\'];\n}\n\nexport const ConfidenceBreakdown: React.FC<ConfidenceBreakdownProps> = ({ breakdown }) => {\n  const entries = Object.entries(breakdown);\n\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <h3 className="text-sm font-medium text-gray-700 mb-4">Confidence Breakdown</h3>\n      <div className="space-y-3">\n        {entries.map(([key, value]) => (\n          <div key={key}>\n            <div className="flex items-center justify-between text-sm mb-1">\n              <span className="text-gray-600 capitalize">{key.replace(/([A-Z])/g, \' $1\')}</span>\n              <span className="font-medium">{(value * 100).toFixed(0)}%</span>\n            </div>\n            <div className="h-2 bg-gray-100 rounded-full overflow-hidden">\n              <div\n                className={`h-full rounded-full ${\n                  value >= 0.9 ? \'bg-green-500\' :\n                  value >= 0.7 ? \'bg-yellow-500\' :\n                  \'bg-red-500\'\n                }`}\n                style={{ width: `${value * 100}%` }}\n              />\n            </div>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// NATURAL LANGUAGE EXPLANATION COMPONENT\n// ============================================================================\n\ninterface NaturalLanguageExplanationProps {\n  explanation: string;\n}\n\nexport const NaturalLanguageExplanation: React.FC<NaturalLanguageExplanationProps> = ({ explanation }) => {\n  return (\n    <div className="bg-gradient-to-r from-blue-50 to-indigo-50 rounded-lg border border-blue-200 p-4">\n      <div className="flex items-start gap-3">\n        <div className="w-8 h-8 rounded-full bg-blue-500 flex items-center justify-center text-white">\n          💡\n        </div>\n        <div>\n          <h3 className="text-sm font-medium text-blue-900 mb-2">AI Explanation</h3>\n          <p className="text-sm text-gray-700 leading-relaxed">{explanation}</p>\n        </div>\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// WHAT-IF SCENARIOS COMPONENT\n// ============================================================================\n\ninterface WhatIfScenariosProps {\n  scenarios: NonNullable<Explanation[\'whatIfScenarios\']>;\n  onSelectScenario?: (scenario: Explanation[\'whatIfScenarios\'][0]) => void;\n}\n\nexport const WhatIfScenarios: React.FC<WhatIfScenariosProps> = ({ scenarios, onSelectScenario }) => {\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <h3 className="text-sm font-medium text-gray-700 mb-4">What-If Scenarios</h3>\n      <div className="space-y-3">\n        {scenarios.map((scenario, idx) => (\n          <div\n            key={idx}\n            onClick={() => onSelectScenario?.(scenario)}\n            className="border rounded-lg p-3 hover:shadow-md transition-shadow cursor-pointer"\n          >\n            <div className="flex items-center justify-between mb-2">\n              <h4 className="font-medium text-sm">{scenario.name}</h4>\n              <span className="text-xs text-gray-500">Click to apply</span>\n            </div>\n            <p className="text-xs text-gray-600 mb-2">{scenario.explanation}</p>\n            <div className="flex flex-wrap gap-1">\n              {Object.entries(scenario.inputChanges).map(([key, value]) => (\n                <span key={key} className="text-xs bg-gray-100 px-2 py-0.5 rounded">\n                  {key}: {String(value)}\n                </span>\n              ))}\n            </div>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// EXPLANATION DETAIL COMPONENT\n// ============================================================================\n\ninterface ExplanationDetailProps {\n  explanation: Explanation;\n  onBack: () => void;\n}\n\nexport const ExplanationDetail: React.FC<ExplanationDetailProps> = ({ explanation, onBack }) => {\n  const { runWhatIf } = useExplainability();\n\n  return (\n    <div className="h-full flex flex-col">\n      {/* Header */}\n      <div className="border-b bg-white p-4">\n        <button onClick={onBack} className="text-sm text-gray-600 hover:text-gray-900 mb-2">← Back</button>\n        <div className="flex items-center justify-between">\n          <div>\n            <h1 className="text-xl font-semibold">Prediction Explanation</h1>\n            <p className="text-sm text-gray-500">Model: {explanation.modelId}</p>\n          </div>\n          <div className="text-right">\n            <p className="text-2xl font-bold text-blue-600">{Math.round(explanation.confidence * 100)}%</p>\n            <p className="text-xs text-gray-500">Confidence</p>\n          </div>\n        </div>\n      </div>\n\n      {/* Content */}\n      <div className="flex-1 overflow-auto p-4 bg-gray-50">\n        <div className="space-y-4">\n          {/* Natural Language Explanation */}\n          <NaturalLanguageExplanation explanation={explanation.naturalLanguageExplanation} />\n\n          {/* Input/Output */}\n          <div className="grid gap-4 md:grid-cols-2">\n            <div className="bg-white rounded-lg border p-4">\n              <h3 className="text-sm font-medium text-gray-700 mb-3">Input Features</h3>\n              <div className="space-y-2">\n                {Object.entries(explanation.input).map(([key, value]) => (\n                  <div key={key} className="flex justify-between text-sm">\n                    <span className="text-gray-600">{key}</span>\n                    <span className="font-medium">{String(value)}</span>\n                  </div>\n                ))}\n              </div>\n            </div>\n            <div className="bg-white rounded-lg border p-4">\n              <h3 className="text-sm font-medium text-gray-700 mb-3">Prediction Output</h3>\n              <div className="space-y-2">\n                {Object.entries(explanation.output).map(([key, value]) => (\n                  <div key={key} className="flex justify-between text-sm">\n                    <span className="text-gray-600">{key}</span>\n                    <span className="font-medium text-blue-600">{String(value)}</span>\n                  </div>\n                ))}\n              </div>\n            </div>\n          </div>\n\n          {/* Feature Importance */}\n          <div className="grid gap-4 md:grid-cols-2">\n            <FeatureImportanceChart features={explanation.localFeatureImportance} title="Local Feature Importance" />\n            <FeatureImportanceChart features={explanation.globalFeatureImportance} title="Global Feature Importance" />\n          </div>\n\n          {/* Confidence Breakdown */}\n          <ConfidenceBreakdown breakdown={explanation.confidenceBreakdown} />\n\n          {/* Decision Path */}\n          {explanation.decisionPath && (\n            <DecisionPathVisualization path={explanation.decisionPath} />\n          )}\n\n          {/* Counterfactuals */}\n          {explanation.counterfactuals && explanation.counterfactuals.length > 0 && (\n            <Counterfactuals counterfactuals={explanation.counterfactuals} />\n          )}\n\n          {/* What-If Scenarios */}\n          {explanation.whatIfScenarios && explanation.whatIfScenarios.length > 0 && (\n            <WhatIfScenarios scenarios={explanation.whatIfScenarios} />\n          )}\n        </div>\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// EXPLANATION LIST COMPONENT\n// ============================================================================\n\ninterface ExplanationListProps {\n  onSelectExplanation: (explanation: Explanation) => void;\n}\n\nexport const ExplanationList: React.FC<ExplanationListProps> = ({ onSelectExplanation }) => {\n  const { explanations } = useExplainability();\n\n  const getTypeColor = (type: Explanation[\'predictionType\']) => {\n    const colors: Record<string, string> = {\n      classification: \'bg-blue-100 text-blue-700\',\n      regression: \'bg-green-100 text-green-700\',\n      forecast: \'bg-purple-100 text-purple-700\',\n      anomaly: \'bg-red-100 text-red-700\',\n      recommendation: \'bg-yellow-100 text-yellow-700\',\n    };\n    return colors[type];\n  };\n\n  return (\n    <div className="space-y-3">\n      {explanations.map(exp => (\n        <div\n          key={exp.id}\n          onClick={() => onSelectExplanation(exp)}\n          className="border rounded-lg p-4 hover:shadow-md transition-shadow cursor-pointer bg-white"\n        >\n          <div className="flex items-start justify-between mb-2">\n            <div>\n              <span className={`px-2 py-0.5 text-xs rounded-full ${getTypeColor(exp.predictionType)}`}>\n                {exp.predictionType}\n              </span>\n              <p className="text-sm text-gray-500 mt-1">Prediction: {exp.predictionId}</p>\n            </div>\n            <div className="text-right">\n              <p className="text-lg font-bold text-blue-600">{Math.round(exp.confidence * 100)}%</p>\n              <p className="text-xs text-gray-500">confidence</p>\n            </div>\n          </div>\n\n          <p className="text-sm text-gray-600 line-clamp-2">{exp.naturalLanguageExplanation}</p>\n\n          <div className="flex items-center gap-2 mt-3 text-xs text-gray-500">\n            <span>Model: {exp.modelId}</span>\n            <span>•</span>\n            <span>{new Date(exp.createdAt).toLocaleString()}</span>\n          </div>\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN EXPLAINABILITY LAYER COMPONENT\n// ============================================================================\n\nexport const ExplainabilityLayer: React.FC = () => {\n  const { selectedExplanation, setSelectedExplanation } = useExplainability();\n\n  return (\n    <div className="h-full flex flex-col">\n      <div className="p-4 border-b bg-white">\n        <h1 className="text-xl font-semibold">AI Explainability Layer</h1>\n        <p className="text-sm text-gray-500">Transparent AI decisions with explainable insights</p>\n      </div>\n\n      <div className="flex-1 overflow-auto p-4 bg-gray-50">\n        {selectedExplanation ? (\n          <ExplanationDetail explanation={selectedExplanation} onBack={() => setSelectedExplanation(null)} />\n        ) : (\n          <ExplanationList onSelectExplanation={setSelectedExplanation} />\n        )}\n      </div>\n    </div>\n  );\n};\n\nexport default ExplainabilityLayer;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/ai/explainability-layer.tsx\' created successfully.") </create-file> </tool_result>'}
{'role': 'assistant', 'content': 'Now let me create the final AI System component: Contract Analysis Tool.\n\n<function_calls>\n<create-file file_path="frontend/src/components/ai/contract-analysis.tsx">\n\'use client\';\n\nimport React, { createContext, useContext, useState, useCallback, useMemo } from \'react\';\nimport { z } from \'zod\';\n\n// ============================================================================\n// TYPES & SCHEMAS\n// ============================================================================\n\nconst ContractClauseSchema = z.object({\n  id: z.string(),\n  type: z.enum([\n    \'payment_terms\',\n    \'termination\',\n    \'liability\',\n    \'confidentiality\',\n    \'intellectual_property\',\n    \'indemnification\',\n    \'warranty\',\n    \'force_majeure\',\n    \'dispute_resolution\',\n    \'governing_law\',\n    \'assignment\',\n    \'non_compete\',\n    \'non_solicitation\',\n    \'data_protection\',\n    \'audit_rights\',\n    \'price_adjustment\',\n    \'renewal\',\n    \'exclusivity\',\n    \'most_favored_nation\',\n    \'limitation_of_liability\',\n    \'other\',\n  ]),\n  title: z.string(),\n  content: z.string(),\n  location: z.object({\n    section: z.string(),\n    page: z.number().optional(),\n    startPosition: z.number().optional(),\n    endPosition: z.number().optional(),\n  }),\n  importance: z.enum([\'critical\', \'high\', \'medium\', \'low\']),\n  riskLevel: z.enum([\'high\', \'medium\', \'low\', \'none\']),\n  extractedData: z.record(z.unknown()).optional(),\n  suggestions: z.array(z.object({\n    type: z.enum([\'warning\', \'recommendation\', \'info\']),\n    message: z.string(),\n    proposedChange: z.string().optional(),\n  })).optional(),\n  relatedClauses: z.array(z.string()).optional(),\n});\n\nconst ContractEntitySchema = z.object({\n  id: z.string(),\n  type: z.enum([\'party\', \'date\', \'amount\', \'duration\', \'jurisdiction\', \'product\', \'service\', \'other\']),\n  name: z.string(),\n  value: z.string(),\n  aliases: z.array(z.string()).optional(),\n  mentions: z.array(z.object({\n    location: z.string(),\n    context: z.string(),\n  })).optional(),\n});\n\nconst ContractRiskSchema = z.object({\n  id: z.string(),\n  type: z.enum([\n    \'unfavorable_terms\',\n    \'missing_clause\',\n    \'ambiguous_language\',\n    \'compliance_issue\',\n    \'financial_exposure\',\n    \'termination_risk\',\n    \'liability_exposure\',\n    \'data_privacy\',\n    \'ip_risk\',\n    \'regulatory\',\n  ]),\n  severity: z.enum([\'critical\', \'high\', \'medium\', \'low\']),\n  title: z.string(),\n  description: z.string(),\n  affectedClauses: z.array(z.string()),\n  recommendation: z.string(),\n  potentialImpact: z.string(),\n  mitigation: z.string().optional(),\n});\n\nconst ContractComparisonSchema = z.object({\n  id: z.string(),\n  clauseId: z.string(),\n  originalText: z.string(),\n  revisedText: z.string(),\n  changeType: z.enum([\'added\', \'removed\', \'modified\', \'unchanged\']),\n  significance: z.enum([\'major\', \'minor\', \'trivial\']),\n  impactAssessment: z.string().optional(),\n});\n\nconst ContractAnalysisResultSchema = z.object({\n  id: z.string(),\n  contractId: z.string(),\n  contractName: z.string(),\n  contractType: z.enum([\n    \'nda\', \'msa\', \'sow\', \'purchase_agreement\', \'service_agreement\',\n    \'employment\', \'lease\', \'license\', \'partnership\', \'other\',\n  ]),\n  analyzedAt: z.date(),\n  analysisVersion: z.string(),\n  overallRiskScore: z.number().min(0).max(100),\n  \n  // Extracted elements\n  parties: z.array(ContractEntitySchema),\n  clauses: z.array(ContractClauseSchema),\n  keyDates: z.array(z.object({\n    type: z.string(),\n    date: z.date(),\n    description: z.string(),\n  })),\n  financialTerms: z.array(z.object({\n    type: z.string(),\n    amount: z.number(),\n    currency: z.string(),\n    frequency: z.string().optional(),\n    conditions: z.string().optional(),\n  })),\n  \n  // Risk analysis\n  risks: z.array(ContractRiskSchema),\n  \n  // Summary\n  executiveSummary: z.string(),\n  keyPoints: z.array(z.string()),\n  \n  // Comparison (if comparing versions)\n  comparison: z.array(ContractComparisonSchema).optional(),\n  \n  // Compliance check\n  complianceStatus: z.object({\n    gdpr: z.enum([\'compliant\', \'partial\', \'non_compliant\', \'not_applicable\']),\n    sox: z.enum([\'compliant\', \'partial\', \'non_compliant\', \'not_applicable\']),\n    hipaa: z.enum([\'compliant\', \'partial\', \'non_compliant\', \'not_applicable\']),\n    pci: z.enum([\'compliant\', \'partial\', \'non_compliant\', \'not_applicable\']),\n    industrySpecific: z.record(z.enum([\'compliant\', \'partial\', \'non_compliant\', \'not_applicable\'])).optional(),\n  }),\n  \n  // AI recommendations\n  recommendations: z.array(z.object({\n    priority: z.enum([\'urgent\', \'high\', \'medium\', \'low\']),\n    category: z.string(),\n    recommendation: z.string(),\n    rationale: z.string(),\n  })),\n});\n\ntype ContractClause = z.infer<typeof ContractClauseSchema>;\ntype ContractEntity = z.infer<typeof ContractEntitySchema>;\ntype ContractRisk = z.infer<typeof ContractRiskSchema>;\ntype ContractAnalysisResult = z.infer<typeof ContractAnalysisResultSchema>;\n\n// ============================================================================\n// CONTRACT ANALYSIS STORE\n// ============================================================================\n\ninterface ContractAnalysisStore {\n  analyses: ContractAnalysisResult[];\n  selectedAnalysis: ContractAnalysisResult | null;\n  isAnalyzing: boolean;\n  \n  // Actions\n  analyzeContract: (contractId: string, contractName: string, content: string) => Promise<ContractAnalysisResult>;\n  compareContracts: (originalId: string, revisedId: string) => Promise<void>;\n  exportAnalysis: (analysisId: string, format: \'pdf\' | \'docx\' | \'json\') => void;\n  \n  // Queries\n  getClauseById: (analysisId: string, clauseId: string) => ContractClause | undefined;\n  getRisksBySeverity: (analysisId: string, severity: ContractRisk[\'severity\']) => ContractRisk[];\n  getClausesByType: (analysisId: string, type: ContractClause[\'type\']) => ContractClause[];\n}\n\nconst ContractAnalysisContext = createContext<ContractAnalysisStore | null>(null);\n\nexport const useContractAnalysis = () => {\n  const context = useContext(ContractAnalysisContext);\n  if (!context) {\n    throw new Error(\'useContractAnalysis must be used within ContractAnalysisProvider\');\n  }\n  return context;\n};\n\n// ============================================================================\n// SAMPLE DATA\n// ============================================================================\n\nconst sampleAnalyses: ContractAnalysisResult[] = [\n  {\n    id: \'analysis-001\',\n    contractId: \'contract-001\',\n    contractName: \'Master Services Agreement - TechCorp\',\n    contractType: \'msa\',\n    analyzedAt: new Date(\'2024-01-20T10:30:00\'),\n    analysisVersion: \'2.1.0\',\n    overallRiskScore: 35,\n    parties: [\n      {\n        id: \'party-1\',\n        type: \'party\',\n        name: \'TechCorp Inc.\',\n        value: \'Service Provider\',\n        mentions: [{ location: \'Section 1.1\', context: \'"Provider" means TechCorp Inc.\' }],\n      },\n      {\n        id: \'party-2\',\n        type: \'party\',\n        name: \'Acme Corporation\',\n        value: \'Client\',\n        mentions: [{ location: \'Section 1.1\', context: \'"Client" means Acme Corporation\' }],\n      },\n    ],\n    clauses: [\n      {\n        id: \'clause-001\',\n        type: \'payment_terms\',\n        title: \'Payment Terms\',\n        content: \'Client shall pay all invoiced amounts within thirty (30) days of receipt of invoice. Late payments shall accrue interest at the rate of 1.5% per month.\',\n        location: { section: \'Section 4.1\', page: 3 },\n        importance: \'high\',\n        riskLevel: \'low\',\n        extractedData: { paymentPeriod: \'30 days\', lateFeeRate: \'1.5% per month\' },\n        suggestions: [\n          { type: \'info\', message: \'Standard payment terms\' },\n        ],\n      },\n      {\n        id: \'clause-002\',\n        type: \'termination\',\n        title: \'Termination for Convenience\',\n        content: \'Either party may terminate this Agreement for any reason upon ninety (90) days written notice to the other party.\',\n        location: { section: \'Section 8.1\', page: 7 },\n        importance: \'critical\',\n        riskLevel: \'medium\',\n        extractedData: { noticePeriod: \'90 days\' },\n        suggestions: [\n          { type: \'warning\', message: \'90-day notice period is longer than industry standard (30-60 days)\' },\n          { type: \'recommendation\', message: \'Consider negotiating to 60 days for more flexibility\', proposedChange: \'Upon sixty (60) days written notice\' },\n        ],\n      },\n      {\n        id: \'clause-003\',\n        type: \'limitation_of_liability\',\n        title: \'Limitation of Liability\',\n        content: \'In no event shall either party be liable for indirect, incidental, special, or consequential damages. Provider\\\'s total liability shall not exceed the fees paid in the twelve (12) months preceding the claim.\',\n        location: { section: \'Section 11.2\', page: 10 },\n        importance: \'critical\',\n        riskLevel: \'high\',\n        extractedData: { liabilityCap: \'12 months fees\', exclusions: [\'indirect\', \'incidental\', \'special\', \'consequential\'] },\n        suggestions: [\n          { type: \'warning\', message: \'Liability cap may be insufficient for enterprise engagements\' },\n          { type: \'recommendation\', message: \'Consider increasing liability cap or adding carve-outs for data breaches\' },\n        ],\n      },\n      {\n        id: \'clause-004\',\n        type: \'data_protection\',\n        title: \'Data Protection\',\n        content: \'Provider shall comply with all applicable data protection laws including GDPR and CCPA. Provider shall implement appropriate technical and organizational measures to protect Personal Data.\',\n        location: { section: \'Section 14\', page: 12 },\n        importance: \'high\',\n        riskLevel: \'low\',\n        extractedData: { regulations: [\'GDPR\', \'CCPA\'] },\n        suggestions: [\n          { type: \'info\', message: \'Includes reference to major privacy regulations\' },\n        ],\n      },\n      {\n        id: \'clause-005\',\n        type: \'indemnification\',\n        title: \'Indemnification\',\n        content: \'Provider shall indemnify, defend, and hold harmless Client from any third-party claims arising from Provider\\\'s breach of this Agreement or infringement of intellectual property rights.\',\n        location: { section: \'Section 10.1\', page: 9 },\n        importance: \'high\',\n        riskLevel: \'medium\',\n        extractedData: { indemnificationScope: \'breach and IP infringement\' },\n        suggestions: [\n          { type: \'warning\', message: \'Indemnification is one-way (Provider to Client only)\' },\n          { type: \'recommendation\', message: \'Consider mutual indemnification for fairness\' },\n        ],\n      },\n    ],\n    keyDates: [\n      { type: \'Effective Date\', date: new Date(\'2024-02-01\'), description: \'Agreement becomes effective\' },\n      { type: \'Initial Term End\', date: new Date(\'2025-01-31\'), description: \'End of initial 1-year term\' },\n      { type: \'Auto-Renewal Notice\', date: new Date(\'2024-11-30\'), description: \'Deadline to prevent auto-renewal\' },\n    ],\n    financialTerms: [\n      { type: \'Base Fee\', amount: 250000, currency: \'USD\', frequency: \'annual\' },\n      { type: \'Implementation Fee\', amount: 50000, currency: \'USD\', frequency: \'one-time\' },\n    ],\n    risks: [\n      {\n        id: \'risk-001\',\n        type: \'liability_exposure\',\n        severity: \'high\',\n        title: \'Insufficient Liability Cap\',\n        description: \'The liability cap of 12 months fees may not adequately cover potential damages in case of significant service disruption or data breach.\',\n        affectedClauses: [\'clause-003\'],\n        recommendation: \'Negotiate increased liability cap or add specific carve-outs for data breaches and security incidents.\',\n        potentialImpact: \'Potential uncovered damages exceeding $250,000 in case of major incident.\',\n        mitigation: \'Consider purchasing additional insurance coverage.\',\n      },\n      {\n        id: \'risk-002\',\n        type: \'unfavorable_terms\',\n        severity: \'medium\',\n        title: \'Long Termination Notice Period\',\n        description: \'90-day termination notice period reduces flexibility to exit the agreement.\',\n        affectedClauses: [\'clause-002\'],\n        recommendation: \'Negotiate reduction to 60 or 30 days notice period.\',\n        potentialImpact: \'Limited ability to quickly respond to changing business needs or service issues.\',\n      },\n      {\n        id: \'risk-003\',\n        type: \'unfavorable_terms\',\n        severity: \'medium\',\n        title: \'One-Way Indemnification\',\n        description: \'Indemnification clause only protects Client, not Provider.\',\n        affectedClauses: [\'clause-005\'],\n        recommendation: \'Consider requesting mutual indemnification obligations.\',\n        potentialImpact: \'Provider bears all indemnification risk without reciprocal protection.\',\n      },\n    ],\n    executiveSummary: \'This Master Services Agreement between TechCorp Inc. (Provider) and Acme Corporation (Client) establishes terms for technology services. The agreement has an initial one-year term with automatic renewal. Key concerns include a liability cap limited to 12 months of fees, a longer-than-standard 90-day termination notice period, and one-way indemnification. Data protection provisions are comprehensive and reference GDPR and CCPA compliance. Overall contract risk is moderate with a score of 35/100.\',\n    keyPoints: [\n      \'One-year initial term with auto-renewal\',\n      \'$250,000 annual base fee plus $50,000 implementation\',\n      \'30-day payment terms with 1.5% monthly late fee\',\n      \'90-day termination notice required\',\n      \'Liability capped at 12 months of fees\',\n      \'Includes GDPR and CCPA compliance provisions\',\n    ],\n    complianceStatus: {\n      gdpr: \'compliant\',\n      sox: \'not_applicable\',\n      hipaa: \'not_applicable\',\n      pci: \'partial\',\n    },\n    recommendations: [\n      {\n        priority: \'urgent\',\n        category: \'Liability\',\n        recommendation: \'Negotiate increased liability cap or add data breach carve-out\',\n        rationale: \'Current cap may not cover significant security incidents\',\n      },\n      {\n        priority: \'high\',\n        category: \'Termination\',\n        recommendation: \'Reduce termination notice period to 60 days\',\n        rationale: \'Current 90-day period limits operational flexibility\',\n      },\n      {\n        priority: \'medium\',\n        category: \'Indemnification\',\n        recommendation: \'Request mutual indemnification clause\',\n        rationale: \'Provides balanced risk allocation between parties\',\n      },\n    ],\n  },\n  {\n    id: \'analysis-002\',\n    contractId: \'contract-002\',\n    contractName: \'Non-Disclosure Agreement - GlobalTech\',\n    contractType: \'nda\',\n    analyzedAt: new Date(\'2024-01-19T14:00:00\'),\n    analysisVersion: \'2.1.0\',\n    overallRiskScore: 15,\n    parties: [\n      {\n        id: \'party-3\',\n        type: \'party\',\n        name: \'GlobalTech Solutions\',\n        value: \'Disclosing Party\',\n      },\n      {\n        id: \'party-4\',\n        type: \'party\',\n        name: \'Our Company\',\n        value: \'Receiving Party\',\n      },\n    ],\n    clauses: [\n      {\n        id: \'clause-010\',\n        type: \'confidentiality\',\n        title: \'Confidentiality Obligations\',\n        content: \'Receiving Party shall maintain all Confidential Information in strict confidence and shall not disclose such information to any third party without prior written consent.\',\n        location: { section: \'Section 2.1\', page: 1 },\n        importance: \'critical\',\n        riskLevel: \'low\',\n        suggestions: [{ type: \'info\', message: \'Standard confidentiality language\' }],\n      },\n      {\n        id: \'clause-011\',\n        type: \'termination\',\n        title: \'Term and Duration\',\n        content: \'This Agreement shall remain in effect for a period of five (5) years from the Effective Date.\',\n        location: { section: \'Section 5\', page: 2 },\n        importance: \'high\',\n        riskLevel: \'low\',\n        extractedData: { duration: \'5 years\' },\n        suggestions: [{ type: \'info\', message: \'5-year term is standard for NDAs\' }],\n      },\n    ],\n    keyDates: [\n      { type: \'Effective Date\', date: new Date(\'2024-01-15\'), description: \'Agreement effective\' },\n      { type: \'Expiration\', date: new Date(\'2029-01-15\'), description: \'NDA expires\' },\n    ],\n    financialTerms: [],\n    risks: [],\n    executiveSummary: \'This is a standard mutual Non-Disclosure Agreement with a 5-year term. The agreement defines confidential information broadly and includes standard exceptions. No significant risks identified.\',\n    keyPoints: [\n      \'Mutual NDA with 5-year term\',\n      \'Broad definition of confidential information\',\n      \'Standard exceptions for publicly known information\',\n    ],\n    complianceStatus: {\n      gdpr: \'not_applicable\',\n      sox: \'not_applicable\',\n      hipaa: \'not_applicable\',\n      pci: \'not_applicable\',\n    },\n    recommendations: [],\n  },\n];\n\n// ============================================================================\n// CONTRACT ANALYSIS PROVIDER\n// ============================================================================\n\nexport const ContractAnalysisProvider: React.FC<{ children: React.ReactNode }> = ({ children }) => {\n  const [analyses, setAnalyses] = useState<ContractAnalysisResult[]>(sampleAnalyses);\n  const [selectedAnalysis, setSelectedAnalysis] = useState<ContractAnalysisResult | null>(null);\n  const [isAnalyzing, setIsAnalyzing] = useState(false);\n\n  const analyzeContract = useCallback(async (\n    contractId: string,\n    contractName: string,\n    content: string\n  ): Promise<ContractAnalysisResult> => {\n    setIsAnalyzing(true);\n\n    // Simulate analysis\n    await new Promise(resolve => setTimeout(resolve, 3000));\n\n    const analysis: ContractAnalysisResult = {\n      id: `analysis-${Date.now()}`,\n      contractId,\n      contractName,\n      contractType: \'other\',\n      analyzedAt: new Date(),\n      analysisVersion: \'2.1.0\',\n      overallRiskScore: Math.floor(Math.random() * 60),\n      parties: [],\n      clauses: [],\n      keyDates: [],\n      financialTerms: [],\n      risks: [],\n      executiveSummary: \'Contract analysis completed. Please review the detailed findings.\',\n      keyPoints: [],\n      complianceStatus: {\n        gdpr: \'not_applicable\',\n        sox: \'not_applicable\',\n        hipaa: \'not_applicable\',\n        pci: \'not_applicable\',\n      },\n      recommendations: [],\n    };\n\n    setAnalyses(prev => [...prev, analysis]);\n    setIsAnalyzing(false);\n    return analysis;\n  }, []);\n\n  const compareContracts = useCallback(async (originalId: string, revisedId: string) => {\n    // Simulate comparison\n    await new Promise(resolve => setTimeout(resolve, 1500));\n  }, []);\n\n  const exportAnalysis = useCallback((analysisId: string, format: \'pdf\' | \'docx\' | \'json\') => {\n    const analysis = analyses.find(a => a.id === analysisId);\n    if (!analysis) return;\n\n    const content = format === \'json\' \n      ? JSON.stringify(analysis, null, 2)\n      : `Contract Analysis Report: ${analysis.contractName}`;\n\n    const blob = new Blob([content], { type: \'text/plain\' });\n    const url = URL.createObjectURL(blob);\n    const a = document.createElement(\'a\');\n    a.href = url;\n    a.download = `${analysis.contractName}-analysis.${format}`;\n    a.click();\n  }, [analyses]);\n\n  const getClauseById = useCallback((analysisId: string, clauseId: string) => {\n    const analysis = analyses.find(a => a.id === analysisId);\n    return analysis?.clauses.find(c => c.id === clauseId);\n  }, [analyses]);\n\n  const getRisksBySeverity = useCallback((analysisId: string, severity: ContractRisk[\'severity\']) => {\n    const analysis = analyses.find(a => a.id === analysisId);\n    return analysis?.risks.filter(r => r.severity === severity) || [];\n  }, [analyses]);\n\n  const getClausesByType = useCallback((analysisId: string, type: ContractClause[\'type\']) => {\n    const analysis = analyses.find(a => a.id === analysisId);\n    return analysis?.clauses.filter(c => c.type === type) || [];\n  }, [analyses]);\n\n  const value = useMemo(() => ({\n    analyses,\n    selectedAnalysis,\n    isAnalyzing,\n    setSelectedAnalysis,\n    analyzeContract,\n    compareContracts,\n    exportAnalysis,\n    getClauseById,\n    getRisksBySeverity,\n    getClausesByType,\n  }), [\n    analyses, selectedAnalysis, isAnalyzing,\n    analyzeContract, compareContracts, exportAnalysis,\n    getClauseById, getRisksBySeverity, getClausesByType,\n  ]);\n\n  return (\n    <ContractAnalysisContext.Provider value={value}>\n      {children}\n    </ContractAnalysisContext.Provider>\n  );\n};\n\n// ============================================================================\n// RISK SCORE GAUGE COMPONENT\n// ============================================================================\n\ninterface RiskScoreGaugeProps {\n  score: number;\n}\n\nexport const RiskScoreGauge: React.FC<RiskScoreGaugeProps> = ({ score }) => {\n  const getRiskColor = (s: number) => {\n    if (s >= 70) return \'#ef4444\';\n    if (s >= 40) return \'#f59e0b\';\n    return \'#10b981\';\n  };\n\n  const color = getRiskColor(score);\n  const angle = (score / 100) * 180;\n\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <h3 className="text-sm font-medium text-gray-700 mb-3">Overall Risk Score</h3>\n      <div className="flex items-center justify-center">\n        <svg width="200" height="120" viewBox="0 0 200 120">\n          {/* Background arc */}\n          <path\n            d="M 20 100 A 80 80 0 0 1 180 100"\n            fill="none"\n            stroke="#e5e7eb"\n            strokeWidth="20"\n            strokeLinecap="round"\n          />\n          {/* Score arc */}\n          <path\n            d="M 20 100 A 80 80 0 0 1 180 100"\n            fill="none"\n            stroke={color}\n            strokeWidth="20"\n            strokeLinecap="round"\n            strokeDasharray={`${(score / 100) * 251.2} 251.2`}\n          />\n          {/* Score text */}\n          <text x="100" y="90" textAnchor="middle" className="text-3xl font-bold" fill={color}>\n            {score}\n          </text>\n        </svg>\n      </div>\n      <div className="flex justify-between text-xs text-gray-500 mt-2 px-4">\n        <span>Low Risk</span>\n        <span>Moderate</span>\n        <span>High Risk</span>\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// CLAUSES LIST COMPONENT\n// ============================================================================\n\ninterface ClausesListProps {\n  clauses: ContractClause[];\n  onSelectClause: (clause: ContractClause) => void;\n  selectedClauseId?: string;\n}\n\nexport const ClausesList: React.FC<ClausesListProps> = ({ clauses, onSelectClause, selectedClauseId }) => {\n  const getImportanceColor = (importance: ContractClause[\'importance\']) => {\n    const colors: Record<string, string> = {\n      critical: \'bg-red-100 text-red-700\',\n      high: \'bg-orange-100 text-orange-700\',\n      medium: \'bg-yellow-100 text-yellow-700\',\n      low: \'bg-gray-100 text-gray-700\',\n    };\n    return colors[importance];\n  };\n\n  const getRiskColor = (risk: ContractClause[\'riskLevel\']) => {\n    const colors: Record<string, string> = {\n      high: \'bg-red-500\',\n      medium: \'bg-yellow-500\',\n      low: \'bg-green-500\',\n      none: \'bg-gray-300\',\n    };\n    return colors[risk];\n  };\n\n  return (\n    <div className="space-y-2">\n      {clauses.map(clause => (\n        <div\n          key={clause.id}\n          onClick={() => onSelectClause(clause)}\n          className={`border rounded-lg p-3 cursor-pointer transition-all ${\n            selectedClauseId === clause.id ? \'ring-2 ring-blue-500 bg-blue-50\' : \'bg-white hover:shadow-md\'\n          }`}\n        >\n          <div className="flex items-start justify-between">\n            <div className="flex items-center gap-2">\n              <span className={`w-2 h-2 rounded-full ${getRiskColor(clause.riskLevel)}`} />\n              <h4 className="font-medium text-sm">{clause.title}</h4>\n            </div>\n            <span className={`px-2 py-0.5 text-xs rounded ${getImportanceColor(clause.importance)}`}>\n              {clause.importance}\n            </span>\n          </div>\n          <p className="text-xs text-gray-500 mt-1">{clause.location.section}</p>\n          {clause.suggestions && clause.suggestions.length > 0 && (\n            <div className="flex gap-1 mt-2">\n              {clause.suggestions.slice(0, 2).map((s, i) => (\n                <span key={i} className={`px-1.5 py-0.5 text-xs rounded ${\n                  s.type === \'warning\' ? \'bg-yellow-100 text-yellow-700\' :\n                  s.type === \'recommendation\' ? \'bg-blue-100 text-blue-700\' :\n                  \'bg-gray-100 text-gray-700\'\n                }`}>\n                  {s.type}\n                </span>\n              ))}\n            </div>\n          )}\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// CLAUSE DETAIL COMPONENT\n// ============================================================================\n\ninterface ClauseDetailProps {\n  clause: ContractClause;\n  onClose: () => void;\n}\n\nexport const ClauseDetail: React.FC<ClauseDetailProps> = ({ clause, onClose }) => {\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <div className="flex items-start justify-between mb-3">\n        <div>\n          <h3 className="font-medium">{clause.title}</h3>\n          <p className="text-sm text-gray-500">{clause.location.section}</p>\n        </div>\n        <button onClick={onClose} className="text-gray-400 hover:text-gray-600">✕</button>\n      </div>\n\n      <div className="bg-gray-50 rounded-lg p-3 mb-3">\n        <p className="text-sm text-gray-700 whitespace-pre-wrap">{clause.content}</p>\n      </div>\n\n      {clause.extractedData && Object.keys(clause.extractedData).length > 0 && (\n        <div className="mb-3">\n          <h4 className="text-xs font-medium text-gray-500 mb-2">EXTRACTED DATA</h4>\n          <div className="grid grid-cols-2 gap-2">\n            {Object.entries(clause.extractedData).map(([key, value]) => (\n              <div key={key} className="bg-blue-50 rounded p-2">\n                <p className="text-xs text-gray-500">{key}</p>\n                <p className="text-sm font-medium">{String(value)}</p>\n              </div>\n            ))}\n          </div>\n        </div>\n      )}\n\n      {clause.suggestions && clause.suggestions.length > 0 && (\n        <div>\n          <h4 className="text-xs font-medium text-gray-500 mb-2">AI SUGGESTIONS</h4>\n          <div className="space-y-2">\n            {clause.suggestions.map((s, i) => (\n              <div key={i} className={`p-2 rounded-lg ${\n                s.type === \'warning\' ? \'bg-yellow-50 border border-yellow-200\' :\n                s.type === \'recommendation\' ? \'bg-blue-50 border border-blue-200\' :\n                \'bg-gray-50 border border-gray-200\'\n              }`}>\n                <div className="flex items-center gap-2 mb-1">\n                  <span className={`text-xs font-medium ${\n                    s.type === \'warning\' ? \'text-yellow-700\' :\n                    s.type === \'recommendation\' ? \'text-blue-700\' :\n                    \'text-gray-700\'\n                  }`}>\n                    {s.type.toUpperCase()}\n                  </span>\n                </div>\n                <p className="text-sm text-gray-700">{s.message}</p>\n                {s.proposedChange && (\n                  <div className="mt-2 bg-white rounded p-2 border">\n                    <p className="text-xs text-gray-500 mb-1">Proposed Change:</p>\n                    <p className="text-sm font-medium text-green-700">{s.proposedChange}</p>\n                  </div>\n                )}\n              </div>\n            ))}\n          </div>\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// RISKS LIST COMPONENT\n// ============================================================================\n\ninterface RisksListProps {\n  risks: ContractRisk[];\n}\n\nexport const RisksList: React.FC<RisksListProps> = ({ risks }) => {\n  const getSeverityColor = (severity: ContractRisk[\'severity\']) => {\n    const colors: Record<string, string> = {\n      critical: \'bg-red-100 border-red-300\',\n      high: \'bg-orange-100 border-orange-300\',\n      medium: \'bg-yellow-100 border-yellow-300\',\n      low: \'bg-gray-100 border-gray-300\',\n    };\n    return colors[severity];\n  };\n\n  const getSeverityBadge = (severity: ContractRisk[\'severity\']) => {\n    const colors: Record<string, string> = {\n      critical: \'bg-red-500 text-white\',\n      high: \'bg-orange-500 text-white\',\n      medium: \'bg-yellow-500 text-yellow-900\',\n      low: \'bg-gray-500 text-white\',\n    };\n    return colors[severity];\n  };\n\n  return (\n    <div className="space-y-3">\n      {risks.map(risk => (\n        <div key={risk.id} className={`border rounded-lg p-4 ${getSeverityColor(risk.severity)}`}>\n          <div className="flex items-start justify-between mb-2">\n            <div className="flex items-center gap-2">\n              <span className={`px-2 py-0.5 text-xs font-medium rounded ${getSeverityBadge(risk.severity)}`}>\n                {risk.severity.toUpperCase()}\n              </span>\n              <h4 className="font-medium">{risk.title}</h4>\n            </div>\n          </div>\n          <p className="text-sm text-gray-700 mb-3">{risk.description}</p>\n          <div className="bg-white rounded p-2 mb-2">\n            <p className="text-xs text-gray-500">Recommendation</p>\n            <p className="text-sm text-gray-700">{risk.recommendation}</p>\n          </div>\n          <div className="text-xs text-gray-600">\n            <span className="font-medium">Impact:</span> {risk.potentialImpact}\n          </div>\n        </div>\n      ))}\n      {risks.length === 0 && (\n        <div className="text-center py-8 text-gray-500">\n          <p className="text-sm">No significant risks identified</p>\n        </div>\n      )}\n    </div>\n  );\n};\n\n// ============================================================================\n// COMPLIANCE STATUS COMPONENT\n// ============================================================================\n\ninterface ComplianceStatusProps {\n  status: ContractAnalysisResult[\'complianceStatus\'];\n}\n\nexport const ComplianceStatus: React.FC<ComplianceStatusProps> = ({ status }) => {\n  const getStatusColor = (s: string) => {\n    const colors: Record<string, string> = {\n      compliant: \'bg-green-100 text-green-700\',\n      partial: \'bg-yellow-100 text-yellow-700\',\n      non_compliant: \'bg-red-100 text-red-700\',\n      not_applicable: \'bg-gray-100 text-gray-500\',\n    };\n    return colors[s];\n  };\n\n  const getStatusIcon = (s: string) => {\n    const icons: Record<string, string> = {\n      compliant: \'✓\',\n      partial: \'◐\',\n      non_compliant: \'✗\',\n      not_applicable: \'—\',\n    };\n    return icons[s];\n  };\n\n  return (\n    <div className="bg-white rounded-lg border p-4">\n      <h3 className="text-sm font-medium text-gray-700 mb-3">Compliance Status</h3>\n      <div className="grid grid-cols-2 gap-2">\n        {Object.entries(status).filter(([k]) => k !== \'industrySpecific\').map(([regulation, s]) => (\n          <div key={regulation} className="flex items-center gap-2 p-2 bg-gray-50 rounded">\n            <span className={`w-6 h-6 rounded-full flex items-center justify-center text-sm ${getStatusColor(s)}`}>\n              {getStatusIcon(s)}\n            </span>\n            <span className="text-sm font-medium uppercase">{regulation}</span>\n          </div>\n        ))}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// ANALYSIS DETAIL COMPONENT\n// ============================================================================\n\ninterface AnalysisDetailProps {\n  analysis: ContractAnalysisResult;\n  onBack: () => void;\n}\n\nexport const AnalysisDetail: React.FC<AnalysisDetailProps> = ({ analysis, onBack }) => {\n  const [activeTab, setActiveTab] = useState<\'summary\' | \'clauses\' | \'risks\' | \'recommendations\'>(\'summary\');\n  const [selectedClause, setSelectedClause] = useState<ContractClause | null>(null);\n  const { exportAnalysis } = useContractAnalysis();\n\n  return (\n    <div className="h-full flex flex-col">\n      {/* Header */}\n      <div className="border-b bg-white p-4">\n        <button onClick={onBack} className="text-sm text-gray-600 hover:text-gray-900 mb-2">← Back</button>\n        <div className="flex items-center justify-between">\n          <div>\n            <h1 className="text-xl font-semibold">{analysis.contractName}</h1>\n            <p className="text-sm text-gray-500">\n              {analysis.contractType.toUpperCase()} • Analyzed {new Date(analysis.analyzedAt).toLocaleDateString()}\n            </p>\n          </div>\n          <div className="flex gap-2">\n            <button\n              onClick={() => exportAnalysis(analysis.id, \'pdf\')}\n              className="px-3 py-1.5 border rounded-lg text-sm hover:bg-gray-50"\n            >\n              Export PDF\n            </button>\n          </div>\n        </div>\n\n        {/* Tabs */}\n        <div className="flex gap-1 mt-4">\n          {([\'summary\', \'clauses\', \'risks\', \'recommendations\'] as const).map(tab => (\n            <button\n              key={tab}\n              onClick={() => setActiveTab(tab)}\n              className={`px-4 py-2 text-sm font-medium rounded-t-lg transition-colors ${\n                activeTab === tab\n                  ? \'bg-white border border-b-white -mb-px\'\n                  : \'text-gray-600 hover:text-gray-900\'\n              }`}\n            >\n              {tab.charAt(0).toUpperCase() + tab.slice(1)}\n              {tab === \'risks\' && analysis.risks.length > 0 && (\n                <span className="ml-1 px-1.5 py-0.5 bg-red-100 text-red-700 rounded-full text-xs">\n                  {analysis.risks.length}\n                </span>\n              )}\n            </button>\n          ))}\n        </div>\n      </div>\n\n      {/* Content */}\n      <div className="flex-1 overflow-auto p-4 bg-gray-50">\n        {activeTab === \'summary\' && (\n          <div className="space-y-4">\n            <RiskScoreGauge score={analysis.overallRiskScore} />\n            \n            <div className="bg-white rounded-lg border p-4">\n              <h3 className="text-sm font-medium text-gray-700 mb-2">Executive Summary</h3>\n              <p className="text-sm text-gray-700">{analysis.executiveSummary}</p>\n            </div>\n\n            <div className="bg-white rounded-lg border p-4">\n              <h3 className="text-sm font-medium text-gray-700 mb-2">Key Points</h3>\n              <ul className="space-y-1">\n                {analysis.keyPoints.map((point, i) => (\n                  <li key={i} className="flex items-start gap-2 text-sm">\n                    <span className="text-blue-500 mt-1">•</span>\n                    {point}\n                  </li>\n                ))}\n              </ul>\n            </div>\n\n            <div className="grid gap-4 md:grid-cols-2">\n              {/* Parties */}\n              <div className="bg-white rounded-lg border p-4">\n                <h3 className="text-sm font-medium text-gray-700 mb-2">Parties</h3>\n                <div className="space-y-2">\n                  {analysis.parties.map(party => (\n                    <div key={party.id} className="flex items-center justify-between">\n                      <span className="font-medium text-sm">{party.name}</span>\n                      <span className="text-xs bg-gray-100 px-2 py-0.5 rounded">{party.value}</span>\n                    </div>\n                  ))}\n                </div>\n              </div>\n\n              {/* Key Dates */}\n              <div className="bg-white rounded-lg border p-4">\n                <h3 className="text-sm font-medium text-gray-700 mb-2">Key Dates</h3>\n                <div className="space-y-2">\n                  {analysis.keyDates.map((kd, i) => (\n                    <div key={i} className="flex items-center justify-between text-sm">\n                      <span className="text-gray-600">{kd.type}</span>\n                      <span className="font-medium">{new Date(kd.date).toLocaleDateString()}</span>\n                    </div>\n                  ))}\n                </div>\n              </div>\n            </div>\n\n            {/* Financial Terms */}\n            {analysis.financialTerms.length > 0 && (\n              <div className="bg-white rounded-lg border p-4">\n                <h3 className="text-sm font-medium text-gray-700 mb-2">Financial Terms</h3>\n                <div className="space-y-2">\n                  {analysis.financialTerms.map((ft, i) => (\n                    <div key={i} className="flex items-center justify-between p-2 bg-gray-50 rounded">\n                      <span className="text-sm text-gray-600">{ft.type}</span>\n                      <span className="font-medium">{ft.currency} {ft.amount.toLocaleString()}</span>\n                    </div>\n                  ))}\n                </div>\n              </div>\n            )}\n\n            <ComplianceStatus status={analysis.complianceStatus} />\n          </div>\n        )}\n\n        {activeTab === \'clauses\' && (\n          <div className="grid gap-4 lg:grid-cols-2">\n            <ClausesList\n              clauses={analysis.clauses}\n              onSelectClause={setSelectedClause}\n              selectedClauseId={selectedClause?.id}\n            />\n            {selectedClause && (\n              <ClauseDetail clause={selectedClause} onClose={() => setSelectedClause(null)} />\n            )}\n          </div>\n        )}\n\n        {activeTab === \'risks\' && (\n          <RisksList risks={analysis.risks} />\n        )}\n\n        {activeTab === \'recommendations\' && (\n          <div className="space-y-3">\n            {analysis.recommendations.map((rec, i) => (\n              <div key={i} className="bg-white rounded-lg border p-4">\n                <div className="flex items-center gap-2 mb-2">\n                  <span className={`px-2 py-0.5 text-xs font-medium rounded ${\n                    rec.priority === \'urgent\' ? \'bg-red-100 text-red-700\' :\n                    rec.priority === \'high\' ? \'bg-orange-100 text-orange-700\' :\n                    rec.priority === \'medium\' ? \'bg-yellow-100 text-yellow-700\' :\n                    \'bg-gray-100 text-gray-700\'\n                  }`}>\n                    {rec.priority.toUpperCase()}\n                  </span>\n                  <span className="text-xs bg-blue-100 text-blue-700 px-2 py-0.5 rounded">{rec.category}</span>\n                </div>\n                <p className="font-medium text-gray-900">{rec.recommendation}</p>\n                <p className="text-sm text-gray-600 mt-1">{rec.rationale}</p>\n              </div>\n            ))}\n            {analysis.recommendations.length === 0 && (\n              <div className="text-center py-8 text-gray-500">\n                <p className="text-sm">No recommendations at this time</p>\n              </div>\n            )}\n          </div>\n        )}\n      </div>\n    </div>\n  );\n};\n\n// ============================================================================\n// ANALYSIS LIST COMPONENT\n// ============================================================================\n\ninterface AnalysisListProps {\n  onSelectAnalysis: (analysis: ContractAnalysisResult) => void;\n}\n\nexport const AnalysisList: React.FC<AnalysisListProps> = ({ onSelectAnalysis }) => {\n  const { analyses } = useContractAnalysis();\n\n  const getRiskColor = (score: number) => {\n    if (score >= 70) return \'text-red-600\';\n    if (score >= 40) return \'text-yellow-600\';\n    return \'text-green-600\';\n  };\n\n  const getTypeLabel = (type: ContractAnalysisResult[\'contractType\']) => {\n    const labels: Record<string, string> = {\n      nda: \'NDA\',\n      msa: \'MSA\',\n      sow: \'SOW\',\n      purchase_agreement: \'Purchase Agreement\',\n      service_agreement: \'Service Agreement\',\n      employment: \'Employment\',\n      lease: \'Lease\',\n      license: \'License\',\n      partnership: \'Partnership\',\n      other: \'Other\',\n    };\n    return labels[type];\n  };\n\n  return (\n    <div className="space-y-3">\n      {analyses.map(analysis => (\n        <div\n          key={analysis.id}\n          onClick={() => onSelectAnalysis(analysis)}\n          className="border rounded-lg p-4 hover:shadow-md transition-shadow cursor-pointer bg-white"\n        >\n          <div className="flex items-start justify-between mb-2">\n            <div>\n              <h3 className="font-medium">{analysis.contractName}</h3>\n              <p className="text-sm text-gray-500">{getTypeLabel(analysis.contractType)}</p>\n            </div>\n            <div className="text-right">\n              <p className={`text-2xl font-bold ${getRiskColor(analysis.overallRiskScore)}`}>\n                {analysis.overallRiskScore}\n              </p>\n              <p className="text-xs text-gray-500">Risk Score</p>\n            </div>\n          </div>\n\n          <div className="flex items-center gap-4 text-xs text-gray-500">\n            <span>{analysis.clauses.length} clauses</span>\n            <span>•</span>\n            <span>{analysis.risks.length} risks</span>\n            <span>•</span>\n            <span>{new Date(analysis.analyzedAt).toLocaleDateString()}</span>\n          </div>\n        </div>\n      ))}\n    </div>\n  );\n};\n\n// ============================================================================\n// MAIN CONTRACT ANALYSIS COMPONENT\n// ============================================================================\n\nexport const ContractAnalysis: React.FC = () => {\n  const { selectedAnalysis, setSelectedAnalysis, isAnalyzing, analyzeContract } = useContractAnalysis();\n  const [showUploadDialog, setShowUploadDialog] = useState(false);\n  const [uploadProgress, setUploadProgress] = useState(0);\n\n  const handleUpload = async (file: File) => {\n    setUploadProgress(0);\n    setShowUploadDialog(true);\n\n    // Simulate upload progress\n    for (let i = 0; i <= 100; i += 10) {\n      await new Promise(resolve => setTimeout(resolve, 100));\n      setUploadProgress(i);\n    }\n\n    const analysis = await analyzeContract(`contract-${Date.now()}`, file.name, \'\');\n    setSelectedAnalysis(analysis);\n    setShowUploadDialog(false);\n  };\n\n  return (\n    <div className="h-full flex flex-col">\n      <div className="p-4 border-b bg-white">\n        <div className="flex items-center justify-between">\n          <div>\n            <h1 className="text-xl font-semibold">Contract Analysis</h1>\n            <p className="text-sm text-gray-500">AI-powered contract review and risk assessment</p>\n          </div>\n          <label className="px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600 cursor-pointer">\n            <input\n              type="file"\n              accept=".pdf,.docx,.doc,.txt"\n              className="hidden"\n              onChange={(e) => {\n                const file = e.target.files?.[0];\n                if (file) handleUpload(file);\n              }}\n            />\n            Upload Contract\n          </label>\n        </div>\n      </div>\n\n      <div className="flex-1 overflow-auto p-4 bg-gray-50">\n        {selectedAnalysis ? (\n          <AnalysisDetail analysis={selectedAnalysis} onBack={() => setSelectedAnalysis(null)} />\n        ) : (\n          <AnalysisList onSelectAnalysis={setSelectedAnalysis} />\n        )}\n      </div>\n\n      {/* Upload Dialog */}\n      {showUploadDialog && (\n        <div className="fixed inset-0 bg-black/50 flex items-center justify-center z-50">\n          <div className="bg-white rounded-lg shadow-xl w-full max-w-md p-6">\n            <h2 className="text-lg font-semibold mb-4">Analyzing Contract</h2>\n            <div className="mb-4">\n              <div className="h-2 bg-gray-200 rounded-full overflow-hidden">\n                <div\n                  className="h-full bg-blue-500 transition-all duration-300"\n                  style={{ width: `${uploadProgress}%` }}\n                />\n              </div>\n              <p className="text-sm text-gray-500 mt-2">{uploadProgress}% complete</p>\n            </div>\n            <p className="text-sm text-gray-600">\n              {uploadProgress < 30 && \'Uploading document...\'}\n              {uploadProgress >= 30 && uploadProgress < 60 && \'Extracting text and clauses...\'}\n              {uploadProgress >= 60 && uploadProgress < 90 && \'Analyzing risks and compliance...\'}\n              {uploadProgress >= 90 && \'Generating recommendations...\'}\n            </p>\n          </div>\n        </div>\n      )}\n    </div>\n  );\n};\n\nexport default ContractAnalysis;\n</create-file>\n</function_calls>'}
{'role': 'user', 'content': '<tool_result> <create-file> ToolResult(success=True, output="File \'frontend/src/components/ai/contract-analysis.tsx\' created successfully.") </create-file> </tool_result>'}