# SneakyScanner Deployment Guide ## Table of Contents 1. [Overview](#overview) 2. [Prerequisites](#prerequisites) 3. [Quick Start](#quick-start) 4. [Configuration](#configuration) 5. [First-Time Setup](#first-time-setup) 6. [Running the Application](#running-the-application) 7. [Using the Web Interface](#using-the-web-interface) 8. [Volume Management](#volume-management) 9. [Health Monitoring](#health-monitoring) 10. [Troubleshooting](#troubleshooting) 11. [Security Considerations](#security-considerations) 12. [Upgrading](#upgrading) 13. [Backup and Restore](#backup-and-restore) --- ## Overview SneakyScanner is deployed as a Docker container running a Flask web application with an integrated network scanner. The application requires privileged mode and host networking to perform network scans using masscan and nmap. **Architecture:** - **Web Application**: Flask app on port 5000 with modern web UI - **Database**: SQLite (persisted to volume) - stores all configurations, scan results, and settings - **Background Jobs**: APScheduler for async scan execution - **Scanner**: masscan, nmap, sslyze, Playwright - **Config Management**: Database-backed configuration system managed entirely via web UI - **Scheduling**: Cron-based scheduled scans with dashboard management --- ## Prerequisites ### System Requirements - **Operating System**: Linux (Ubuntu 20.04+, Debian 11+, or similar) - **Docker**: Version 20.10+ or Docker Engine 24.0+ - **Docker Compose**: Version 2.0+ (or docker-compose 1.29+) - **Memory**: Minimum 2GB RAM (4GB+ recommended) - **Disk Space**: Minimum 5GB free space - **Permissions**: Root/sudo access for Docker privileged mode ### Network Requirements - Outbound internet access for Docker image downloads - Access to target networks for scanning - Port 5000 available on host (or configure alternative) ### Install Docker and Docker Compose **Ubuntu/Debian:** ```bash # Install Docker curl -fsSL https://get.docker.com -o get-docker.sh sudo sh get-docker.sh # Add your user to docker group sudo usermod -aG docker $USER newgrp docker # Verify installation docker --version docker compose version ``` **Other Linux distributions:** See [Docker installation guide](https://docs.docker.com/engine/install/) --- ## Quick Start For users who want to get started immediately with the web application: **Option 1: Automated Setup (Recommended)** ```bash # 1. Clone the repository git clone cd SneakyScan # 2. Run the setup script ./setup.sh # 3. Access the web interface # Open browser to: http://localhost:5000 # Login with password from ./admin_password.txt or ./logs/admin_password.txt ``` The setup script automatically: - Generates secure random keys (SECRET_KEY, ENCRYPTION_KEY) - Prompts for password or generates a random one - Creates required directories - Builds Docker image - Starts the application - Auto-initializes database on first run **Option 2: Manual Setup** ```bash # 1. Clone the repository git clone cd SneakyScan # 2. Create environment file cp .env.example .env # Edit .env and set SECRET_KEY and SNEAKYSCANNER_ENCRYPTION_KEY # Optionally set INITIAL_PASSWORD (leave blank for auto-generation) nano .env # 3. Build and start (database auto-initializes on first run) docker compose up --build -d # 4. Check logs for auto-generated password (if not set in .env) docker compose logs web | grep "Password" # Or check: ./logs/admin_password.txt # 5. Access the web interface # Open browser to: http://localhost:5000 ``` **Alternative: Standalone CLI Scanner** For quick one-off scans without the web interface: ```bash # Build and run with standalone compose file docker compose -f docker-compose-standalone.yml build docker compose -f docker-compose-standalone.yml up # Results saved to ./output/ directory ``` **Note**: `docker-compose.yml` (web application) is now the default. Use `docker-compose-standalone.yml` for CLI-only scans. --- ## Configuration ### Environment Variables SneakyScanner is configured via environment variables. The recommended approach is to use a `.env` file. **UDP Port Scanning** - UDP Port scanning is disabled by default. - You can turn it on via the .env variable. - By Default, UDP port scanning only scans the top 20 ports, for convenience I have included the NMAP top 100 UDP ports as well. #### Creating Your .env File ```bash # Copy the example file cp .env.example .env # Generate secure keys # SECRET_KEY: Flask session secret (64-character hex string) python3 -c "import secrets; print('SECRET_KEY=' + secrets.token_hex(32))" >> .env # SNEAKYSCANNER_ENCRYPTION_KEY: Fernet key for database encryption (32 url-safe base64 bytes) python3 -c "from cryptography.fernet import Fernet; print('SNEAKYSCANNER_ENCRYPTION_KEY=' + Fernet.generate_key().decode())" >> .env # Edit other settings as needed nano .env ``` #### Key Configuration Options | Variable | Description | Default | Required | |----------|-------------|---------|----------| | `FLASK_ENV` | Environment mode (`production` or `development`) | `production` | Yes | | `FLASK_DEBUG` | Enable debug mode (`true` or `false`) | `false` | Yes | | `SECRET_KEY` | Flask session secret (change in production!) | `dev-secret-key-change-in-production` | **Yes** | | `SNEAKYSCANNER_ENCRYPTION_KEY` | Encryption key for sensitive settings | (empty) | **Yes** | | `DATABASE_URL` | SQLite database path | `sqlite:////app/data/sneakyscanner.db` | Yes | | `INITIAL_PASSWORD` | Password for first-run initialization (leave empty to auto-generate) | (empty) | No | | `LOG_LEVEL` | Logging level (DEBUG, INFO, WARNING, ERROR) | `INFO` | No | | `SCHEDULER_EXECUTORS` | Number of concurrent scan threads | `2` | No | | `SCHEDULER_JOB_DEFAULTS_MAX_INSTANCES` | Max instances of same job | `3` | No | | `CORS_ORIGINS` | CORS allowed origins (comma-separated) | `*` | No | **Important Security Note:** - **ALWAYS** change `SECRET_KEY` and `SNEAKYSCANNER_ENCRYPTION_KEY` in production - Never commit `.env` file to version control - Use strong, randomly-generated keys --- ## First-Time Setup ### Step 1: Prepare Directories The application needs these directories (created automatically by Docker): ```bash # Verify directories exist ls -la data/ output/ logs/ # If missing, create them mkdir -p data output logs ``` ### Step 2: Configure Scan Targets After starting the application, create scan configurations using the web UI: **Creating Configurations via Web UI** 1. Navigate to **Configs** in the web interface 2. Click **"Create New Config"** 3. Use the form-based config creator: - Enter site name - Enter CIDR range (e.g., `192.168.1.0/24`) - Select expected TCP/UDP ports from dropdowns - Optionally enable ping checks 4. Click **"Save Configuration"** 5. Configuration is saved to database and immediately available for scans and schedules **Note**: All configurations are stored in the database, not as files. This provides better reliability, easier backup, and seamless management through the web interface. ### Step 3: Build Docker Image ```bash # Build the image (takes 5-10 minutes on first run) docker compose -f docker-compose.yml build # Verify image was created docker images | grep sneakyscanner ``` ### Step 4: Initialize Database **Automatic Initialization (Recommended)** As of Phase 5, the database is automatically initialized on first run: ```bash # Just start the application docker compose up -d # On first run, the entrypoint script will: # - Detect no existing database # - Generate a random password (if INITIAL_PASSWORD not set in .env) # - Save password to ./logs/admin_password.txt # - Initialize database schema # - Create default settings and alert rules # - Start the Flask application # Check logs to see the auto-generated password docker compose logs web | grep "Password" # Or view the password file cat logs/admin_password.txt ``` **Manual Initialization (Advanced)** You can still manually initialize the database if needed: ```bash # Initialize database and set application password docker compose run --rm init-db --password "YourSecurePassword" --force # The init-db command will: # - Create database schema # - Set the application password (bcrypt hashed) # - Create default settings with encryption # - Create default alert rules # Verify database was created ls -lh data/sneakyscanner.db ``` **Password Management:** - Leave `INITIAL_PASSWORD` blank in `.env` for auto-generation - Auto-generated passwords are saved to `./logs/admin_password.txt` - For custom password, set `INITIAL_PASSWORD` in `.env` - Minimum 8 characters recommended - Use a strong, unique password - Store securely (password manager) **Note**: The init-db service is defined with `profiles: [tools]` in docker-compose.yml, which means it won't start automatically with `docker compose up`. However, the web service now handles initialization automatically via the entrypoint script. ### Step 5: Verify Configuration ```bash # Check database file was created ls -lh data/sneakyscanner.db # Verify Docker Compose configuration docker compose -f docker-compose.yml config ``` --- ## Running the Application ### Starting the Application ```bash # Start in detached mode (background) docker compose -f docker-compose.yml up -d # View logs during startup docker compose -f docker-compose.yml logs -f web # Expected output: # web_1 | INFO:werkzeug: * Running on http://0.0.0.0:5000/ (Press CTRL+C to quit) ``` ### Accessing the Web Interface 1. Open browser to: **http://localhost:5000** 2. Login with the password you set during database initialization (username is not required - single-user mode) 3. Dashboard will display: - Recent scans with status indicators - Summary statistics (total scans, IPs, ports, services) - Trend charts showing infrastructure changes over time - Quick actions (run scan, create config, view schedules) ### Stopping the Application ```bash # Stop containers (preserves data) docker compose -f docker-compose.yml down # Stop and remove volumes (WARNING: deletes all data!) docker compose -f docker-compose.yml down -v ``` ### Restarting the Application ```bash # Restart all services docker compose -f docker-compose.yml restart # Restart only the web service docker compose -f docker-compose.yml restart web ``` ### Viewing Logs ```bash # View all logs docker compose -f docker-compose.yml logs # Follow logs in real-time docker compose -f docker-compose.yml logs -f # View last 100 lines docker compose -f docker-compose.yml logs --tail=100 # View logs for specific service docker compose -f docker-compose.yml logs web ``` --- ## Using the Web Interface ### Dashboard Overview The dashboard provides a central view of your scanning activity: **Key Sections:** - **Summary Statistics**: Total scans, IPs discovered, open ports, services detected - **Recent Scans**: Last 10 scans with status, timestamp, and quick actions - **Trend Charts**: Port count trends over time using Chart.js - **Quick Actions**: Buttons to run scans, create configs, manage schedules ### Managing Scan Configurations All scan configurations are stored in the database and managed entirely through the web interface. **Creating Configs:** 1. Navigate to **Configs** → **Create New Config** 2. Fill in the configuration form: - Enter site name (e.g., "Production Servers") - Enter CIDR range (e.g., `192.168.1.0/24`) - Select expected TCP/UDP ports from dropdowns - Enable/disable ping checks 3. Click **"Save Configuration"** 4. Configuration is immediately stored in database and available for use **Editing Configs:** 1. Navigate to **Configs** → Select config from list 2. Click **"Edit"** button 3. Modify any fields in the configuration form 4. Click **"Save Changes"** to update database **Viewing Configs:** - Navigate to **Configs** page to see all saved configurations - Each config shows site name, CIDR range, and expected ports - Click on any config to view full details **Deleting Configs:** - Click **"Delete"** button next to any config - **Warning**: Cannot delete configs used by active schedules - Deletion removes the configuration from the database permanently **Note**: All configurations are database-backed, providing automatic backups when you backup the database file. ### Running Scans **Manual Scans:** 1. Navigate to **Dashboard** or **Scans** 2. Click **"Run Scan Now"** 3. Select configuration file from dropdown 4. Click **"Start Scan"** 5. Scan executes in background (APScheduler) 6. Monitor progress on **Scans** page **Scheduled Scans:** 1. Navigate to **Schedules** → **Create Schedule** 2. Enter schedule name (e.g., "Daily production scan") 3. Select config file 4. Enter cron expression (e.g., `0 2 * * *` for 2 AM daily) 5. Enable schedule 6. Scans run automatically in background **Cron Expression Examples:** - `0 2 * * *` - Daily at 2 AM - `0 */6 * * *` - Every 6 hours - `0 0 * * 0` - Weekly on Sunday at midnight - `0 0 1 * *` - Monthly on 1st at midnight ### Viewing Scan Results **Scan List:** - Navigate to **Scans** page - View all historical scans with filters - Click scan ID to view details **Scan Details:** - Full scan results organized by site - Discovered IPs, ports, services - SSL/TLS certificate information - TLS version support and cipher suites - Service version detection - Screenshots of web services - Download buttons (JSON, HTML, ZIP) **Trend Analysis:** - Charts showing port count changes over time - Identify infrastructure drift - Track service version updates --- ## Volume Management ### Understanding Volumes SneakyScanner uses several mounted volumes for data persistence: | Volume | Container Path | Purpose | Important? | |--------|----------------|---------|------------| | `./data` | `/app/data` | SQLite database (contains configurations, scan history, settings) | **Critical** | | `./output` | `/app/output` | Scan results (JSON, HTML, ZIP, screenshots) | Yes | | `./logs` | `/app/logs` | Application logs (rotating file handler) | No | **Note**: All scan configurations are stored in the SQLite database (`./data/sneakyscanner.db`). There is no separate configs directory or YAML files. Backing up the database file ensures all your configurations are preserved. ### Backing Up Data ```bash # Create backup directory mkdir -p backups/$(date +%Y%m%d) # Backup database (includes all configurations) cp data/sneakyscanner.db backups/$(date +%Y%m%d)/ # Backup scan outputs tar -czf backups/$(date +%Y%m%d)/output.tar.gz output/ ``` **Important**: The database backup includes all scan configurations, settings, schedules, and scan history. No separate configuration file backup is needed. ### Restoring Data ```bash # Stop application docker compose -f docker-compose.yml down # Restore database (includes all configurations) cp backups/YYYYMMDD/sneakyscanner.db data/ # Restore outputs tar -xzf backups/YYYYMMDD/output.tar.gz # Restart application docker compose -f docker-compose.yml up -d ``` **Note**: Restoring the database file restores all configurations, settings, schedules, and scan history. ### Cleaning Up Old Scan Results **Option A: Using the Web UI (Recommended)** 1. Navigate to **Scans** page 2. Select scans you want to delete 3. Click **"Delete"** button 4. Confirm deletion (removes database records and all associated files) **Option B: Manual Cleanup** ```bash # Find old scan results (older than 30 days) find output/ -type f -name "scan_report_*.json" -mtime +30 # Delete old scan results and screenshots find output/ -type f -mtime +30 -delete find output/ -type d -empty -delete # Note: Manual deletion doesn't remove database records # Use the web UI or API for complete cleanup ``` **Option C: Using the API** ```bash # Delete a specific scan (removes DB records + files) curl -X DELETE http://localhost:5000/api/scans/{scan_id} \ -b cookies.txt ``` --- ## API Usage Examples SneakyScanner provides a comprehensive REST API for automation and integration. All API endpoints require authentication via session cookies. ### Authentication ```bash # Login and save session cookie curl -X POST http://localhost:5000/api/auth/login \ -H "Content-Type: application/json" \ -d '{"password": "YourPassword"}' \ -c cookies.txt # Logout curl -X POST http://localhost:5000/api/auth/logout \ -b cookies.txt ``` ### Config Management ```bash # List all configs curl http://localhost:5000/api/configs \ -b cookies.txt # Get specific config by ID curl http://localhost:5000/api/configs/1 \ -b cookies.txt # Create new config curl -X POST http://localhost:5000/api/configs \ -H "Content-Type: application/json" \ -d '{ "name": "Test Network", "cidr": "10.0.0.0/24", "expected_ports": [ {"port": 80, "protocol": "tcp", "service": "http"}, {"port": 443, "protocol": "tcp", "service": "https"} ], "ping_expected": true }' \ -b cookies.txt # Update config curl -X PUT http://localhost:5000/api/configs/1 \ -H "Content-Type: application/json" \ -d '{ "name": "Updated Test Network", "cidr": "10.0.1.0/24" }' \ -b cookies.txt # Delete config curl -X DELETE http://localhost:5000/api/configs/1 \ -b cookies.txt ``` ### Scan Management ```bash # Trigger a scan (using config ID from database) curl -X POST http://localhost:5000/api/scans \ -H "Content-Type: application/json" \ -d '{"config_id": 1}' \ -b cookies.txt # List all scans curl http://localhost:5000/api/scans?page=1&per_page=20 \ -b cookies.txt # Get scan details curl http://localhost:5000/api/scans/123 \ -b cookies.txt # Check scan status curl http://localhost:5000/api/scans/123/status \ -b cookies.txt # Delete scan curl -X DELETE http://localhost:5000/api/scans/123 \ -b cookies.txt ``` ### Schedule Management ```bash # List schedules curl http://localhost:5000/api/schedules \ -b cookies.txt # Create schedule (using config ID from database) curl -X POST http://localhost:5000/api/schedules \ -H "Content-Type: application/json" \ -d '{ "name": "Daily Production Scan", "config_id": 1, "cron_expression": "0 2 * * *", "enabled": true }' \ -b cookies.txt # Update schedule curl -X PUT http://localhost:5000/api/schedules/1 \ -H "Content-Type: application/json" \ -d '{"enabled": false}' \ -b cookies.txt # Manually trigger scheduled scan curl -X POST http://localhost:5000/api/schedules/1/trigger \ -b cookies.txt # Delete schedule curl -X DELETE http://localhost:5000/api/schedules/1 \ -b cookies.txt ``` ### Settings Management ```bash # Get all settings (sanitized - passwords hidden) curl http://localhost:5000/api/settings \ -b cookies.txt # Update settings curl -X PUT http://localhost:5000/api/settings \ -H "Content-Type: application/json" \ -d '{ "retention_days": 90, "smtp_server": "smtp.gmail.com" }' \ -b cookies.txt # Test email configuration curl -X POST http://localhost:5000/api/settings/test-email \ -b cookies.txt # Health check (no auth required) curl http://localhost:5000/api/settings/health ``` ### Statistics ```bash # Get dashboard summary curl http://localhost:5000/api/stats/summary \ -b cookies.txt # Get trend data curl http://localhost:5000/api/stats/trends?days=30&metric=port_count \ -b cookies.txt # Get certificate expiry overview curl http://localhost:5000/api/stats/certificates \ -b cookies.txt ``` For complete API documentation, see `docs/API_REFERENCE.md`. --- ## Health Monitoring ### Health Check Endpoint SneakyScanner includes a built-in health check endpoint used by Docker's healthcheck: ```bash # Check application health curl http://localhost:5000/api/settings/health # Expected response (200 OK): # {"status": "healthy"} # This endpoint is also used by Docker Compose healthcheck # Defined in docker-compose.yml: # - Interval: 60s (check every minute) # - Timeout: 10s # - Retries: 3 # - Start period: 40s (grace period for app startup) ``` ### Docker Health Status ```bash # Check container health status docker ps | grep sneakyscanner-web # View health check logs docker inspect sneakyscanner-web | grep -A 10 Health ``` ### Monitoring Logs ```bash # Watch for errors in logs docker compose -f docker-compose.yml logs -f | grep ERROR # Check application log file tail -f logs/sneakyscanner.log ``` --- ## Troubleshooting ### Container Won't Start **Problem**: Container exits immediately after starting ```bash # Check logs for errors docker compose logs web # Common issues: # 1. Permission issues with volumes - check directory ownership # 2. Port 5000 already in use - change FLASK_PORT or stop conflicting service # 3. Database initialization failed - check logs for specific error # Check if database initialization is stuck docker compose logs web | grep -A 20 "First Run Detected" # If initialization failed, clean up and retry docker compose down rm -rf data/.db_initialized # Remove marker file docker compose up -d ``` ### Database Initialization Fails **Problem**: Automatic database initialization fails on first run ```bash # Check database directory permissions ls -la data/ # Fix permissions if needed sudo chown -R $USER:$USER data/ # View initialization logs docker compose logs web | grep -A 50 "Initializing database" # Clean up and retry initialization docker compose down rm -rf data/sneakyscanner.db data/.db_initialized docker compose up -d # Or manually initialize with specific password docker compose down rm -rf data/sneakyscanner.db data/.db_initialized docker compose run --rm init-db --password "YourPassword" --force docker compose up -d ``` **Can't Find Password File** **Problem**: Password file not created or can't be found ```bash # Check both possible locations cat admin_password.txt # Created by setup.sh cat logs/admin_password.txt # Created by Docker entrypoint # Check container logs for password docker compose logs web | grep -i password # If password file is missing, manually set one docker compose down docker compose run --rm init-db --password "YourNewPassword" --force docker compose up -d ``` ### Scans Fail with "Permission Denied" **Problem**: Scanner cannot run masscan/nmap ```bash # Verify container is running in privileged mode docker inspect sneakyscanner-web | grep Privileged # Should show: "Privileged": true # Verify network mode is host docker inspect sneakyscanner-web | grep NetworkMode # Should show: "NetworkMode": "host" # If not, verify docker-compose.yml has: # privileged: true # network_mode: host ``` ### Can't Access Web Interface **Problem**: Browser can't connect to http://localhost:5000 ```bash # Verify container is running docker ps | grep sneakyscanner-web # Check if Flask is listening docker compose -f docker-compose.yml exec web netstat -tlnp | grep 5000 # Check firewall rules sudo ufw status | grep 5000 # Try from container host curl http://localhost:5000/api/settings/health # Check logs for binding errors docker compose -f docker-compose.yml logs web | grep -i bind ``` ### Background Scans Not Running **Problem**: Scans stay in "running" status forever ```bash # Check scheduler is initialized docker compose -f docker-compose.yml logs web | grep -i scheduler # Check for job execution errors docker compose -f docker-compose.yml logs web | grep -i "execute_scan" # Verify APScheduler environment variables docker compose -f docker-compose.yml exec web env | grep SCHEDULER # Check for scan job errors docker compose -f docker-compose.yml logs web | grep -E "(ERROR|Exception|Traceback)" # Verify scanner executables are available docker compose -f docker-compose.yml exec web which masscan nmap ``` ### Configs Not Appearing in Web UI **Problem**: Created configs don't show up in web interface ```bash # Check database connectivity docker compose -f docker-compose.yml logs web | grep -i "database" # Verify database file exists and is readable ls -lh data/sneakyscanner.db # Check for errors when creating configs docker compose -f docker-compose.yml logs web | grep -i "config" # Try accessing configs via API curl http://localhost:5000/api/configs -b cookies.txt # If database is corrupted, check integrity docker compose -f docker-compose.yml exec web sqlite3 /app/data/sneakyscanner.db "PRAGMA integrity_check;" ``` ### Health Check Failing **Problem**: Docker health check shows "unhealthy" ```bash # Run health check manually docker compose -f docker-compose.yml exec web \ python3 -c "import urllib.request; print(urllib.request.urlopen('http://localhost:5000/api/settings/health').read())" # Check if health endpoint exists curl -v http://localhost:5000/api/settings/health # Common causes: # 1. Application crashed - check logs # 2. Database locked - check for long-running scans # 3. Flask not fully started - wait 40s (start_period) ``` --- ## Security Considerations ### Production Deployment Checklist - [ ] Changed `SECRET_KEY` to random value (64+ character hex string) - [ ] Changed `SNEAKYSCANNER_ENCRYPTION_KEY` to random Fernet key - [ ] Set strong application password via init-db - [ ] Set `FLASK_ENV=production` - [ ] Set `FLASK_DEBUG=false` - [ ] Configured proper `CORS_ORIGINS` (not `*`) - [ ] Using HTTPS/TLS (reverse proxy recommended) - [ ] Restricted network access (firewall rules) - [ ] Regular backups configured (database + configs) - [ ] Log monitoring enabled - [ ] Scheduled scans configured with appropriate frequency - [ ] Alert rules configured (Phase 5 - coming soon) - [ ] Webhook/email notifications configured (Phase 5 - coming soon) ### Network Security **Privileged Mode Considerations:** - Container runs with `--privileged` flag for raw socket access (masscan/nmap) - This grants extensive host capabilities - only run on trusted networks - Restrict Docker host access with firewall rules - Consider running on dedicated scan server **Recommendations:** ```bash # Restrict access to port 5000 with firewall sudo ufw allow from 192.168.1.0/24 to any port 5000 sudo ufw enable # Or use reverse proxy (nginx, Apache) with authentication ``` ### HTTPS/TLS Setup SneakyScanner does not include built-in TLS. For production, use a reverse proxy: **Example nginx configuration:** ```nginx server { listen 443 ssl http2; server_name scanner.example.com; ssl_certificate /path/to/cert.pem; ssl_certificate_key /path/to/key.pem; location / { proxy_pass http://localhost:5000; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; } } ``` ### File Permissions ```bash # Ensure proper ownership of data directories sudo chown -R $USER:$USER data/ output/ logs/ # Restrict database file permissions (contains configurations and sensitive data) chmod 600 data/sneakyscanner.db # Ensure database directory is writable chmod 700 data/ ``` --- ## Upgrading ### Upgrading to New Version ```bash # 1. Stop the application docker compose -f docker-compose.yml down # 2. Backup database cp data/sneakyscanner.db data/sneakyscanner.db.backup # 3. Pull latest code git pull origin master # 4. Rebuild Docker image docker compose -f docker-compose.yml build # 5. Run database migrations docker compose -f docker-compose.yml run --rm web alembic upgrade head # 6. Start application docker compose -f docker-compose.yml up -d # 7. Verify upgrade docker compose -f docker-compose.yml logs -f curl http://localhost:5000/api/settings/health ``` ### Rolling Back If upgrade fails: ```bash # Stop new version docker compose -f docker-compose.yml down # Restore database backup cp data/sneakyscanner.db.backup data/sneakyscanner.db # Checkout previous version git checkout # Rebuild and start docker compose -f docker-compose.yml build docker compose -f docker-compose.yml up -d ``` --- ## Backup and Restore ### Automated Backup Script Create `backup.sh`: ```bash #!/bin/bash BACKUP_DIR="backups/$(date +%Y%m%d_%H%M%S)" mkdir -p "$BACKUP_DIR" # Stop application for consistent backup docker compose -f docker-compose.yml stop web # Backup database (includes all configurations) cp data/sneakyscanner.db "$BACKUP_DIR/" # Backup outputs (last 30 days only) find output/ -type f -mtime -30 -exec cp --parents {} "$BACKUP_DIR/" \; # Restart application docker compose -f docker-compose.yml start web echo "Backup complete: $BACKUP_DIR" echo "Database backup includes all configurations, settings, and scan history" ``` Make executable and schedule with cron: ```bash chmod +x backup.sh # Add to crontab (daily at 2 AM) crontab -e # Add line: 0 2 * * * /path/to/SneakyScan/backup.sh ``` ### Restore from Backup ```bash # Stop application docker compose -f docker-compose.yml down # Restore database (includes all configurations) cp backups/YYYYMMDD_HHMMSS/sneakyscanner.db data/ # Restore output files cp -r backups/YYYYMMDD_HHMMSS/output/* output/ # Start application docker compose -f docker-compose.yml up -d ``` **Note**: Restoring the database file will restore all configurations, settings, schedules, and scan history from the backup. --- ## Support and Further Reading - **Project README**: `README.md` - General project information - **API Documentation**: `docs/API_REFERENCE.md` - Complete REST API reference - **Roadmap**: `docs/ROADMAP.md` - Project roadmap, feature plans, and architecture - **Issue Tracker**: File bugs and feature requests on GitHub --- ## What's New ### Phase 4+ (2025-11-17) - Database-Backed Configuration System ✅ - **Database-Backed Configs**: All configurations stored in SQLite database (no YAML files) - **Web-Based Config Creator**: Form-based UI for creating scan configs from CIDR ranges - **Config Management UI**: List, view, edit, and delete configs via web interface - **REST API**: Full config management via RESTful API with database storage - **Schedule Protection**: Prevents deleting configs used by active schedules - **Automatic Backups**: Configurations included in database backups ### Phase 3 (2025-11-14) - Dashboard & Scheduling ✅ - **Dashboard**: Summary stats, recent scans, trend charts - **Scheduled Scans**: Cron-based scheduling with web UI management - **Scan History**: Detailed scan results with full data display - **Chart.js Integration**: Port count trends over time ### Phase 2 (2025-11-14) - Web Application Core ✅ - **REST API**: Complete API for scan management - **Background Jobs**: APScheduler-based async execution - **Authentication**: Session-based login system - **Database Integration**: SQLite with SQLAlchemy ORM ### Coming Soon: Phase 5 - Email, Webhooks & Comparisons - Email notifications for infrastructure changes - Webhook integrations (Slack, PagerDuty, custom) - Scan comparison reports - Alert rule configuration --- **Last Updated**: 2025-11-24 **Version**: Phase 4+ - Database-Backed Configuration System