cyberchef_ngx_cloudpanel/install-cyberchef.sh
2024-12-12 20:27:20 +05:30

289 lines
No EOL
8.4 KiB
Bash

#!/bin/bash
# Script to install Docker and CyberChef with verification and redeployment capabilities
# Must be run with root privileges
# Error handling
set -e
trap 'echo "Error on line $LINENO. Exit code: $?"' ERR
# Configuration
INSTALL_DIR="/docker/cyberchef"
COMPOSE_FILE="${INSTALL_DIR}/docker-compose.yml"
LOG_FILE="/var/log/cyberchef-install.log"
CYBERCHEF_VERSION="latest"
CONTAINER_NAME="cyberchef"
# Utility functions
check_port_availability() {
local port=$1
if lsof -i ":$port" >/dev/null 2>&1; then
local process_info=$(lsof -i ":$port" | tail -n 1)
local pid=$(echo "$process_info" | awk '{print $2}')
local process_name=$(echo "$process_info" | awk '{print $1}')
log_message "⚠ Error: Port $port is already in use by process $process_name (PID: $pid)"
return 1
fi
return 0
}
check_required_ports() {
local required_ports=(8000)
local ports_in_use=()
for port in "${required_ports[@]}"; do
if ! check_port_availability "$port"; then
ports_in_use+=($port)
fi
done
if [ ${#ports_in_use[@]} -ne 0 ]; then
log_message "The following required ports are already in use: ${ports_in_use[*]}"
log_message "Please free these ports before proceeding with the installation."
log_message "You can either:"
log_message "1. Stop the services using these ports"
log_message "2. Modify the docker-compose.yml to use different ports"
log_message "3. Run 'lsof -i :<port>' to identify which process is using each port"
return 1
fi
log_message "✓ All required ports are available"
return 0
}
log_message() {
local message="[$(date '+%Y-%m-%d %H:%M:%S')] $1"
echo "$message"
echo "$message" >> "$LOG_FILE"
}
show_container_status() {
log_message "Current container status:"
echo "----------------------------------------"
docker compose ps --format "table {{.Name}}\t{{.Status}}\t{{.Ports}}"
echo "----------------------------------------"
}
check_service_status() {
local container_name="cyberchef-web-1"
# Check if container exists and is running
if ! docker ps -q -f name="$container_name" >/dev/null 2>&1; then
log_message "Container $container_name not found"
return 1
fi
local status=$(docker inspect -f '{{.State.Status}}' "$container_name" 2>/dev/null)
if [ "$status" != "running" ]; then
log_message "Container status is $status, expected running"
return 1
fi
# Give the nginx server inside container time to start
local max_attempts=30
local attempt=1
local delay=2
while [ $attempt -le $max_attempts ]; do
if curl -sf http://localhost:8000 >/dev/null 2>&1; then
log_message "Web service is responding on port 8000"
return 0
fi
log_message "Waiting for web service to respond (attempt $attempt/$max_attempts)..."
sleep $delay
attempt=$((attempt + 1))
done
log_message "Web service failed to respond after $max_attempts attempts"
return 1
}
verify_installation() {
log_message "Verifying CyberChef installation..."
if ! check_service_status; then
log_message "CyberChef service is not running properly"
return 1
fi
log_message "CyberChef service is running properly"
return 0
}
check_docker_version() {
local current_version=$(docker --version | cut -d ' ' -f3 | cut -d ',' -f1)
log_message "Current Docker version: $current_version"
# Check for updates
apt-get update >/dev/null 2>&1
local available_version=$(apt-cache policy docker-ce | grep Candidate | cut -d ' ' -f4)
if [ "$current_version" != "$available_version" ]; then
log_message "New Docker version available: $available_version"
read -p "Do you want to upgrade Docker? (y/N) " -n 1 -r
echo
if [[ $REPLY =~ ^[Yy]$ ]]; then
apt-get install -y docker-ce docker-ce-cli containerd.io
fi
fi
}
redeploy_service() {
log_message "Redeploying CyberChef..."
cd "$INSTALL_DIR"
docker compose down
docker compose up -d
# Wait for service to be healthy
local retries=0
while ! check_service_status && [ $retries -lt 5 ]; do
log_message "Waiting for CyberChef to become healthy..."
sleep 10
retries=$((retries + 1))
done
if [ $retries -eq 5 ]; then
log_message "Failed to redeploy CyberChef after 5 attempts"
return 1
fi
log_message "CyberChef redeployed successfully"
return 0
}
backup_existing_data() {
if [ -d "$INSTALL_DIR" ]; then
local backup_dir="${INSTALL_DIR}_backup_$(date +%Y%m%d_%H%M%S)"
log_message "Creating backup of existing installation at $backup_dir"
cp -r "$INSTALL_DIR" "$backup_dir"
fi
}
check_existing_installation() {
log_message "Checking existing CyberChef installation..."
if [ -f "$COMPOSE_FILE" ]; then
log_message "Existing installation found"
show_container_status
if verify_installation; then
log_message "✓ CyberChef is running correctly"
log_message "✓ CyberChef is accessible at http://localhost:8000"
return 0
else
log_message "⚠ Service issues detected. Starting recovery process..."
return 1
fi
fi
return 1
}
# Main script execution starts here
# Check if script is run as root
if [ "$EUID" -ne 0 ]; then
echo "Please run as root"
exit 1
fi
# Initialize log file
mkdir -p "$(dirname "$LOG_FILE")"
touch "$LOG_FILE"
log_message "Starting CyberChef installation/verification script"
# Check if Docker is installed
if ! command -v docker &> /dev/null; then
log_message "Docker not found. Installing Docker..."
curl -fsSL https://get.docker.com -o get-docker.sh
sh get-docker.sh
apt-get update
apt-get install -y docker-compose-plugin
log_message "Docker installed successfully"
else
log_message "Docker already installed"
check_docker_version
fi
# Check existing installation or proceed with new installation
if check_existing_installation; then
exit 0
else
if [ -f "$COMPOSE_FILE" ]; then
# Attempt to recover existing installation
backup_existing_data
if ! redeploy_service; then
log_message "Failed to redeploy CyberChef. Manual intervention may be required."
exit 1
fi
else
# New installation
log_message "Starting new CyberChef installation"
# Create installation directory
mkdir -p "$INSTALL_DIR"
cd "$INSTALL_DIR"
# Check if required ports are available
if ! check_required_ports; then
log_message "⚠ Port conflict detected. Please resolve the conflicts and run the script again."
exit 1
fi
# Create docker-compose.yml
cat > docker-compose.yml <<'EOF'
version: "3.8"
services:
web:
image: mpepping/cyberchef:latest
container_name: cyberchef-web
restart: unless-stopped
networks:
- cyberchef_network
ports:
- "8000:8000"
healthcheck:
test: ["CMD", "curl", "-f", "http://localhost:8000"]
interval: 30s
timeout: 10s
retries: 5
environment:
- TZ=UTC
volumes:
- cyberchef_data:/opt/cyberchef
networks:
cyberchef_network:
driver: bridge
volumes:
cyberchef_data:
name: cyberchef_data
EOF
# Start services
log_message "Starting CyberChef service..."
docker compose up -d
# Give service time to initialize
log_message "Waiting for service to initialize..."
# Initial wait for container to start up
sleep 5
# Verify installation
if verify_installation; then
log_message "✓ Installation completed successfully!"
show_container_status
log_message "Important next steps:"
log_message "1. Set up a reverse proxy in CloudPanel"
log_message "2. Create SSL certificate for your domain"
log_message "3. Access CyberChef at http://localhost:8000"
else
log_message "Installation completed but service is not running properly"
log_message "Please check the logs and try redeploying the service"
exit 1
fi
fi
fi