# Integration Example - Adding New Features to Dashboard This guide shows how to integrate the new React components into the existing StrikePackageGPT dashboard. ## Current Architecture StrikePackageGPT currently uses: - **Backend**: FastAPI (Python) - **Frontend**: HTML templates with Jinja2 (no React build system yet) - **Static files**: Served from `services/dashboard/static/` ## Integration Options ### Option 1: Add React Build System (Recommended for Production) This approach sets up a proper React application: 1. **Create React App Structure** ```bash cd services/dashboard npm init -y npm install react react-dom npm install --save-dev @babel/core @babel/preset-react webpack webpack-cli babel-loader css-loader style-loader npm install cytoscape # For NetworkMap ``` 2. **Create webpack.config.js** ```javascript const path = require('path'); module.exports = { entry: './src/index.jsx', output: { path: path.resolve(__dirname, 'static/dist'), filename: 'bundle.js' }, module: { rules: [ { test: /\.jsx?$/, exclude: /node_modules/, use: { loader: 'babel-loader', options: { presets: ['@babel/preset-react'] } } }, { test: /\.css$/, use: ['style-loader', 'css-loader'] } ] }, resolve: { extensions: ['.js', '.jsx'] } }; ``` 3. **Create src/index.jsx** ```jsx import React from 'react'; import ReactDOM from 'react-dom'; import App from './App'; ReactDOM.render(, document.getElementById('root')); ``` 4. **Create src/App.jsx** ```jsx import React, { useState } from 'react'; import NetworkMap from '../NetworkMap'; import VoiceControls from '../VoiceControls'; import HelpChat from '../HelpChat'; import GuidedWizard from '../GuidedWizard'; function App() { const [showHelp, setShowHelp] = useState(false); const [showWizard, setShowWizard] = useState(false); const [currentScanId, setCurrentScanId] = useState(null); return (

StrikePackageGPT Dashboard

{currentScanId && ( console.log('Host clicked:', host)} /> )}
{/* Floating components */} setShowHelp(false)} currentPage="dashboard" /> {showWizard && ( { console.log('Wizard completed:', data); setShowWizard(false); }} onCancel={() => setShowWizard(false)} /> )}
); } function handleVoiceCommand(result) { console.log('Voice command:', result); // Handle voice commands } export default App; ``` 5. **Update package.json scripts** ```json { "scripts": { "build": "webpack --mode production", "dev": "webpack --mode development --watch" } } ``` 6. **Build and Deploy** ```bash npm run build ``` 7. **Update templates/index.html** ```html StrikePackageGPT
``` --- ### Option 2: Use Components via CDN (Quick Start) For quick testing without build system: 1. **Create static/js/components.js** ```javascript // Load React and ReactDOM from CDN // Then include the component code // Example: Simple integration function initStrikePackageGPT() { // Initialize voice controls const voiceContainer = document.createElement('div'); voiceContainer.id = 'voice-controls'; document.body.appendChild(voiceContainer); // Initialize help chat button const helpButton = document.createElement('button'); helpButton.textContent = 'πŸ’¬ Help'; helpButton.onclick = () => toggleHelpChat(); document.body.appendChild(helpButton); } document.addEventListener('DOMContentLoaded', initStrikePackageGPT); ``` 2. **Update templates/index.html** ```html StrikePackageGPT
``` --- ### Option 3: Progressive Enhancement (Current Setup Compatible) Use the new features as API endpoints with vanilla JavaScript: 1. **Create static/js/app.js** ```javascript // Voice Control Integration class VoiceController { constructor() { this.isListening = false; this.mediaRecorder = null; this.setupButton(); } setupButton() { const button = document.createElement('button'); button.id = 'voice-button'; button.innerHTML = 'πŸŽ™οΈ'; button.onclick = () => this.toggleListening(); document.body.appendChild(button); } async toggleListening() { if (!this.isListening) { await this.startListening(); } else { this.stopListening(); } } async startListening() { const stream = await navigator.mediaDevices.getUserMedia({ audio: true }); this.mediaRecorder = new MediaRecorder(stream); const chunks = []; this.mediaRecorder.ondataavailable = (e) => chunks.push(e.data); this.mediaRecorder.onstop = async () => { const blob = new Blob(chunks, { type: 'audio/webm' }); await this.processAudio(blob); stream.getTracks().forEach(track => track.stop()); }; this.mediaRecorder.start(); this.isListening = true; document.getElementById('voice-button').innerHTML = '⏸️'; } stopListening() { if (this.mediaRecorder) { this.mediaRecorder.stop(); this.isListening = false; document.getElementById('voice-button').innerHTML = 'πŸŽ™οΈ'; } } async processAudio(blob) { const formData = new FormData(); formData.append('audio', blob); const response = await fetch('/api/voice/transcribe', { method: 'POST', body: formData }); const result = await response.json(); console.log('Transcribed:', result.text); // Route command const cmdResponse = await fetch('/api/voice/command', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ text: result.text }) }); const command = await cmdResponse.json(); this.executeCommand(command); } executeCommand(command) { // Execute the command based on routing info console.log('Command:', command); } } // Help Chat Integration class HelpChat { constructor() { this.isOpen = false; this.messages = []; this.sessionId = `session-${Date.now()}`; this.setupUI(); } setupUI() { const container = document.createElement('div'); container.id = 'help-chat'; container.style.display = 'none'; document.body.appendChild(container); const button = document.createElement('button'); button.id = 'help-button'; button.innerHTML = 'πŸ’¬'; button.onclick = () => this.toggle(); document.body.appendChild(button); } toggle() { this.isOpen = !this.isOpen; const chat = document.getElementById('help-chat'); chat.style.display = this.isOpen ? 'block' : 'none'; if (this.isOpen && this.messages.length === 0) { this.addMessage('assistant', 'Hi! How can I help you?'); } } async sendMessage(text) { this.addMessage('user', text); const response = await fetch('/api/llm/chat', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ message: text, session_id: this.sessionId }) }); const result = await response.json(); this.addMessage('assistant', result.message); } addMessage(role, content) { this.messages.push({ role, content }); this.render(); } render() { const chat = document.getElementById('help-chat'); chat.innerHTML = this.messages.map(msg => `
${msg.content}
`).join(''); } } // Network Map Integration class NetworkMapViewer { constructor(containerId) { this.container = document.getElementById(containerId); this.hosts = []; } async loadScan(scanId) { const response = await fetch(`/api/nmap/hosts?scan_id=${scanId}`); const data = await response.json(); this.hosts = data.hosts || []; this.render(); } render() { this.container.innerHTML = `
${this.hosts.map(host => this.renderHost(host)).join('')}
`; } renderHost(host) { const iconUrl = `/static/${this.getIcon(host)}.svg`; return `
${host.os_type}
${host.ip}
${host.hostname || 'Unknown'}
${host.os_type || 'Unknown OS'}
`; } getIcon(host) { const osType = (host.os_type || '').toLowerCase(); if (osType.includes('windows')) return 'windows'; if (osType.includes('linux')) return 'linux'; if (osType.includes('mac')) return 'mac'; if (host.device_type?.includes('server')) return 'server'; if (host.device_type?.includes('network')) return 'network'; return 'unknown'; } exportCSV() { const csv = [ ['IP', 'Hostname', 'OS', 'Device Type', 'Ports'].join(','), ...this.hosts.map(h => [ h.ip, h.hostname || '', h.os_type || '', h.device_type || '', (h.ports || []).map(p => p.port).join(';') ].join(',')) ].join('\n'); const blob = new Blob([csv], { type: 'text/csv' }); const url = URL.createObjectURL(blob); const a = document.createElement('a'); a.href = url; a.download = `network-${Date.now()}.csv`; a.click(); } showHostDetails(ip) { const host = this.hosts.find(h => h.ip === ip); alert(JSON.stringify(host, null, 2)); } } // Initialize on page load document.addEventListener('DOMContentLoaded', () => { window.voiceController = new VoiceController(); window.helpChat = new HelpChat(); window.networkMap = new NetworkMapViewer('network-map-container'); }); ``` 2. **Add CSS (static/css/components.css)** ```css /* Voice Button */ #voice-button { position: fixed; bottom: 20px; right: 20px; width: 60px; height: 60px; border-radius: 50%; border: none; background: #3498DB; color: white; font-size: 24px; cursor: pointer; box-shadow: 0 4px 12px rgba(0,0,0,0.2); z-index: 1000; } /* Help Chat */ #help-chat { position: fixed; right: 20px; top: 20px; width: 400px; height: 600px; background: white; border-radius: 8px; box-shadow: 0 4px 20px rgba(0,0,0,0.2); z-index: 999; padding: 20px; overflow-y: auto; } #help-button { position: fixed; top: 20px; right: 20px; background: #3498DB; color: white; border: none; padding: 10px 20px; border-radius: 4px; cursor: pointer; z-index: 1001; } .message { margin: 10px 0; padding: 10px; border-radius: 8px; } .message.user { background: #3498DB; color: white; text-align: right; } .message.assistant { background: #ECF0F1; color: #2C3E50; } /* Network Map */ .network-map { width: 100%; padding: 20px; } .hosts { display: grid; grid-template-columns: repeat(auto-fill, minmax(200px, 1fr)); gap: 15px; margin-top: 20px; } .host { border: 1px solid #ddd; border-radius: 8px; padding: 15px; cursor: pointer; transition: all 0.2s; } .host:hover { box-shadow: 0 4px 12px rgba(0,0,0,0.1); transform: translateY(-2px); } .host img { width: 48px; height: 48px; } .host-info { margin-top: 10px; } ``` 3. **Update templates/index.html** ```html StrikePackageGPT
``` --- ## Testing the Integration ### Test Voice Control 1. Open browser console 2. Click the mic button 3. Speak a command 4. Check console for transcription result ### Test Help Chat 1. Click the help button 2. Type a message 3. Wait for AI response ### Test Network Map ```javascript // In browser console networkMap.loadScan('your-scan-id'); ``` --- ## Deployment Checklist - [ ] Choose integration method (build system vs progressive enhancement) - [ ] Install required npm packages (if using React build) - [ ] Configure API endpoints in backend - [ ] Add environment variables for API keys - [ ] Test voice control permissions - [ ] Verify LLM service connectivity - [ ] Test network map with real scan data - [ ] Configure CORS if needed - [ ] Add error handling for API failures - [ ] Test on multiple browsers - [ ] Document any additional setup steps --- ## Next Steps 1. Choose your integration approach 2. Set up the build system (if needed) 3. Test each component individually 4. Integrate components into main dashboard 5. Add error handling and loading states 6. Style components to match your theme 7. Deploy and test in production environment For questions or issues, refer to FEATURES.md or use the Help Chat! 😊