CalejoControl/setup-server.sh

435 lines
14 KiB
Bash
Executable File

#!/bin/bash
# Calejo Control Adapter - One-Click Server Setup Script
# Automatically reads from existing deployment configuration files
set -e
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m' # No Color
# Default configuration
ENVIRONMENT="production"
SERVER_HOST=""
SSH_USERNAME=""
SSH_KEY_FILE=""
DRY_RUN=false
VERBOSE=false
# Function to print colored output
print_status() {
echo -e "${BLUE}[INFO]${NC} $1"
}
print_success() {
echo -e "${GREEN}[SUCCESS]${NC} $1"
}
print_warning() {
echo -e "${YELLOW}[WARNING]${NC} $1"
}
print_error() {
echo -e "${RED}[ERROR]${NC} $1"
}
# Function to display usage
usage() {
echo "Calejo Control Adapter - One-Click Server Setup"
echo "=================================================="
echo ""
echo "Usage: $0 [OPTIONS]"
echo ""
echo "Options:"
echo " -e, --environment Deployment environment (production, staging) [default: auto-detect]"
echo " -h, --host Server hostname or IP address [default: auto-detect]"
echo " -u, --user SSH username [default: auto-detect]"
echo " -k, --key SSH private key file [default: auto-detect]"
echo " --verbose Enable verbose output"
echo " --dry-run Show what would be done without making changes"
echo " --help Show this help message"
echo ""
echo "Examples:"
echo " $0 # Auto-detect and setup using existing config"
echo " $0 --dry-run # Show setup steps without executing"
echo " $0 -h custom-server.com # Override host from config"
echo ""
}
# Function to read deployment configuration from existing files
read_deployment_config() {
local config_dir="deploy"
print_status "Reading existing deployment configuration..."
# Read from production.yml if it exists
if [[ -f "$config_dir/config/production.yml" ]]; then
print_status "Found production configuration: $config_dir/config/production.yml"
# Extract values from production.yml
if [[ -z "$SSH_HOST" ]]; then
SSH_HOST=$(grep -E "^\s*host:\s*" "$config_dir/config/production.yml" | head -1 | sed 's/^[[:space:]]*host:[[:space:]]*//' | sed 's/^"//' | sed 's/"$//' | tr -d '\r')
[[ -n "$SSH_HOST" ]] && print_status " Host: $SSH_HOST"
fi
if [[ -z "$SSH_USERNAME" ]]; then
SSH_USERNAME=$(grep -E "^\s*username:\s*" "$config_dir/config/production.yml" | head -1 | sed 's/^[[:space:]]*username:[[:space:]]*//' | sed 's/^"//' | sed 's/"$//' | tr -d '\r')
[[ -n "$SSH_USERNAME" ]] && print_status " Username: $SSH_USERNAME"
fi
if [[ -z "$SSH_KEY_FILE" ]]; then
SSH_KEY_FILE=$(grep -E "^\s*key_file:\s*" "$config_dir/config/production.yml" | head -1 | sed 's/^[[:space:]]*key_file:[[:space:]]*//' | sed 's/^"//' | sed 's/"$//' | tr -d '\r')
[[ -n "$SSH_KEY_FILE" ]] && print_status " Key file: $SSH_KEY_FILE"
fi
fi
# Read from staging.yml if it exists
if [[ -f "$config_dir/config/staging.yml" ]]; then
print_status "Found staging configuration: $config_dir/config/staging.yml"
# Only use staging config if environment is staging
if [[ "$ENVIRONMENT" == "staging" ]]; then
if [[ -z "$SSH_HOST" ]]; then
SSH_HOST=$(grep -E "^\s*host:\s*" "$config_dir/config/staging.yml" | head -1 | sed 's/^[[:space:]]*host:[[:space:]]*//' | sed 's/^"//' | sed 's/"$//' | tr -d '\r')
[[ -n "$SSH_HOST" ]] && print_status " Host: $SSH_HOST"
fi
fi
fi
# Check for existing remote deployment script configuration
if [[ -f "$config_dir/ssh/deploy-remote.sh" ]]; then
print_status "Found remote deployment script: $config_dir/ssh/deploy-remote.sh"
# Extract default values from deploy-remote.sh
if [[ -z "$SSH_HOST" ]]; then
SSH_HOST=$(grep -E "SSH_HOST=" "$config_dir/ssh/deploy-remote.sh" | head -1 | cut -d'=' -f2 | tr -d '\"' | tr -d "\'")
[[ -n "$SSH_HOST" ]] && print_status " Host from script: $SSH_HOST"
fi
if [[ -z "$SSH_USERNAME" ]]; then
SSH_USERNAME=$(grep -E "SSH_USER=" "$config_dir/ssh/deploy-remote.sh" | head -1 | cut -d'=' -f2 | tr -d '\"' | tr -d "\'")
[[ -n "$SSH_USERNAME" ]] && print_status " Username from script: $SSH_USERNAME"
fi
if [[ -z "$SSH_KEY_FILE" ]]; then
SSH_KEY_FILE=$(grep -E "SSH_KEY=" "$config_dir/ssh/deploy-remote.sh" | head -1 | cut -d'=' -f2 | tr -d '\"' | tr -d "\'")
[[ -n "$SSH_KEY_FILE" ]] && print_status " Key file from script: $SSH_KEY_FILE"
fi
fi
# Set defaults if still empty
ENVIRONMENT=${ENVIRONMENT:-production}
SSH_HOST=${SSH_HOST:-localhost}
SSH_USERNAME=${SSH_USERNAME:-$USER}
SSH_KEY_FILE=${SSH_KEY_FILE:-~/.ssh/id_rsa}
# Use SSH_HOST as SERVER_HOST if not specified
SERVER_HOST=${SERVER_HOST:-$SSH_HOST}
print_success "Configuration loaded successfully"
}
# Function to parse command line arguments
parse_arguments() {
while [[ $# -gt 0 ]]; do
case $1 in
-e|--environment)
ENVIRONMENT="$2"
shift 2
;;
-h|--host)
SERVER_HOST="$2"
shift 2
;;
-u|--user)
SSH_USERNAME="$2"
shift 2
;;
-k|--key)
SSH_KEY_FILE="$2"
shift 2
;;
--verbose)
VERBOSE=true
shift
;;
--dry-run)
DRY_RUN=true
shift
;;
--help)
usage
exit 0
;;
*)
print_error "Unknown option: $1"
usage
exit 1
;;
esac
done
}
# Function to detect if running locally or needs remote setup
detect_deployment_type() {
if [[ -n "$SERVER_HOST" && "$SERVER_HOST" != "localhost" && "$SERVER_HOST" != "127.0.0.1" ]]; then
echo "remote"
else
echo "local"
fi
}
# Function to check prerequisites
check_prerequisites() {
print_status "Checking prerequisites..."
if [[ "$DRY_RUN" == "true" ]]; then
echo " [DRY RUN] Would check prerequisites"
return 0
fi
# For local deployment, check local Docker
if [[ "$DEPLOYMENT_TYPE" == "local" ]]; then
# Check Docker
if ! command -v docker &> /dev/null; then
print_error "Docker is not installed"
echo "Please install Docker first: https://docs.docker.com/get-docker/"
exit 1
fi
# Check Docker Compose
if ! command -v docker-compose &> /dev/null; then
print_error "Docker Compose is not installed"
echo "Please install Docker Compose first: https://docs.docker.com/compose/install/"
exit 1
fi
fi
# For remote deployment, we'll handle Docker installation automatically
if [[ "$DEPLOYMENT_TYPE" == "remote" ]]; then
print_status "Remote deployment - Docker will be installed automatically if needed"
fi
print_success "Prerequisites check passed"
}
# Function to setup local deployment
setup_local_deployment() {
print_status "Setting up local deployment..."
if [[ "$DRY_RUN" == "true" ]]; then
echo " [DRY RUN] Would setup local deployment"
return 0
fi
# Create necessary directories
mkdir -p ./data/postgres ./logs ./certs
# Generate default configuration if not exists
if [[ ! -f ".env" ]]; then
print_status "Creating default configuration..."
cp config/.env.example .env
print_success "Default configuration created"
fi
# Build and start services
print_status "Building and starting services..."
docker-compose up --build -d
print_success "Local deployment completed"
}
# Function to install Docker on remote server
install_docker_remote() {
local host="$1"
local user="$2"
local key_file="$3"
print_status "Installing Docker on remote server $host..."
if [[ "$DRY_RUN" == "true" ]]; then
echo " [DRY RUN] Would install Docker on $host"
return 0
fi
# Check if Docker is already installed
if ssh -o StrictHostKeyChecking=no -i "$key_file" "$user@$host" "command -v docker" &> /dev/null; then
print_success "Docker is already installed"
return 0
fi
# Install Docker using official script
print_status "Installing Docker using official script..."
ssh -o StrictHostKeyChecking=no -i "$key_file" "$user@$host" \
"curl -fsSL https://get.docker.com -o get-docker.sh && sh get-docker.sh"
# Add user to docker group
print_status "Adding user to docker group..."
ssh -o StrictHostKeyChecking=no -i "$key_file" "$user@$host" \
"usermod -aG docker $user"
# Install Docker Compose
print_status "Installing Docker Compose..."
ssh -o StrictHostKeyChecking=no -i "$key_file" "$user@$host" \
"curl -L \"https://github.com/docker/compose/releases/latest/download/docker-compose-$(uname -s)-$(uname -m)\" -o /usr/local/bin/docker-compose && chmod +x /usr/local/bin/docker-compose"
# Verify installation
if ssh -o StrictHostKeyChecking=no -i "$key_file" "$user@$host" "docker --version && docker-compose --version"; then
print_success "Docker and Docker Compose installed successfully"
return 0
else
print_error "Docker installation failed"
return 1
fi
}
# Function to setup remote deployment
setup_remote_deployment() {
print_status "Setting up remote deployment on $SERVER_HOST..."
if [[ "$DRY_RUN" == "true" ]]; then
echo " [DRY RUN] Would setup remote deployment on $SERVER_HOST"
return 0
fi
# Install Docker if needed
if ! ssh -o StrictHostKeyChecking=no -i "$SSH_KEY_FILE" "$SSH_USERNAME@$SERVER_HOST" "command -v docker" &> /dev/null; then
install_docker_remote "$SERVER_HOST" "$SSH_USERNAME" "$SSH_KEY_FILE"
fi
# Use existing deployment script
if [[ -f "deploy/ssh/deploy-remote.sh" ]]; then
print_status "Using existing remote deployment script..."
./deploy/ssh/deploy-remote.sh -e "$ENVIRONMENT"
else
print_error "Remote deployment script not found"
return 1
fi
print_success "Remote deployment completed"
}
# Function to validate setup
validate_setup() {
local host="$1"
print_status "Validating setup..."
if [[ "$DRY_RUN" == "true" ]]; then
echo " [DRY RUN] Would validate setup"
return 0
fi
# Test health endpoint
if curl -s "http://$host:8080/health" > /dev/null; then
print_success "Health check passed"
else
print_warning "Health check failed - service may still be starting"
fi
return 0
}
# Function to display setup completion message
display_completion_message() {
local deployment_type="$1"
local host="$2"
echo ""
echo "=================================================="
echo " SETUP COMPLETED SUCCESSFULLY!"
echo "=================================================="
echo ""
echo "🎉 Calejo Control Adapter is now running!"
echo ""
echo "🌍 Access URLs:"
echo " Dashboard: http://$host:8080/dashboard"
echo " REST API: http://$host:8080"
echo " Health Check: http://$host:8080/health"
echo " Grafana: http://$host:3000 (admin/admin)"
echo " Prometheus: http://$host:9091 (prometheus_user/prometheus_password)"
echo ""
echo "🔧 Next Steps:"
echo " 1. Open the dashboard in your browser"
echo " 2. Configure your SCADA systems and hardware"
echo " 3. Set up safety limits and user accounts"
echo " 4. Integrate with your existing infrastructure"
echo ""
if [[ "$deployment_type" == "local" ]]; then
echo "💡 Local Development Tips:"
echo " - View logs: docker-compose logs -f"
echo " - Stop services: docker-compose down"
echo " - Restart: docker-compose up -d"
else
echo "💡 Remote Server Tips:"
echo " - View logs: ssh -i $SSH_KEY_FILE $SSH_USERNAME@$host 'cd /opt/calejo-control-adapter && docker-compose logs -f'"
echo " - Stop services: ssh -i $SSH_KEY_FILE $SSH_USERNAME@$host 'cd /opt/calejo-control-adapter && docker-compose down'"
echo " - Restart: ssh -i $SSH_KEY_FILE $SSH_USERNAME@$host 'cd /opt/calejo-control-adapter && docker-compose up -d'"
fi
echo ""
echo "=================================================="
echo ""
}
# Main setup function
main() {
echo ""
echo "🚀 Calejo Control Adapter - One-Click Server Setup"
echo "=================================================="
echo ""
# Parse command line arguments
parse_arguments "$@"
# Read deployment configuration from files
read_deployment_config
# Detect deployment type
local deployment_type=$(detect_deployment_type)
# Display setup information
echo "Setup Configuration:"
echo " Environment: $ENVIRONMENT"
echo " Deployment: $deployment_type"
if [[ "$deployment_type" == "remote" ]]; then
echo " Server: $SERVER_HOST"
echo " User: $SSH_USERNAME"
else
echo " Server: localhost"
fi
if [[ "$DRY_RUN" == "true" ]]; then
echo " Mode: DRY RUN"
fi
echo ""
# Check prerequisites
check_prerequisites
# Perform deployment
if [[ "$deployment_type" == "local" ]]; then
setup_local_deployment
local final_host="localhost"
else
setup_remote_deployment
local final_host="$SERVER_HOST"
fi
# Validate setup
validate_setup "$final_host"
# Display completion message
display_completion_message "$deployment_type" "$final_host"
echo ""
print_success "One-click setup completed!"
echo ""
}
# Run main function
main "$@"