Files
omega-server/scripts/generate-secrets.sh
Fran Jurmanović 016728532c init bootstrap
2025-07-06 15:02:09 +02:00

164 lines
5.5 KiB
Bash

#!/bin/bash
# Bootstrap App - Secret Generation Script
# This script generates cryptographically secure secrets for the Bootstrap App
echo "Bootstrap App - Secret Generation Script"
echo "========================================"
echo ""
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
CYAN='\033[0;36m'
WHITE='\033[1;37m'
NC='\033[0m' # No Color
# Function to generate hex string
generate_hex_string() {
local length=$1
openssl rand -hex $length 2>/dev/null || xxd -l $length -p /dev/urandom | tr -d '\n'
}
# Function to generate base64 string
generate_base64_string() {
local length=$1
openssl rand -base64 $length 2>/dev/null || dd if=/dev/urandom bs=$length count=1 2>/dev/null | base64 | tr -d '\n'
}
# Check if required tools are available
check_dependencies() {
if ! command -v openssl >/dev/null 2>&1; then
if ! command -v xxd >/dev/null 2>&1; then
echo -e "${RED}Error: Neither openssl nor xxd is available. Please install one of them.${NC}"
exit 1
fi
fi
}
# Generate secrets
echo -e "${YELLOW}Generating cryptographically secure secrets...${NC}"
echo ""
check_dependencies
JWT_SECRET=$(generate_base64_string 64)
APP_SECRET=$(generate_hex_string 32)
APP_SECRET_CODE=$(generate_hex_string 32)
ENCRYPTION_KEY=$(generate_hex_string 16)
# Display generated secrets
echo -e "${CYAN}Generated Secrets:${NC}"
echo -e "${CYAN}==================${NC}"
echo ""
echo -e "${WHITE}JWT_SECRET=${NC}${YELLOW}$JWT_SECRET${NC}"
echo ""
echo -e "${WHITE}APP_SECRET=${NC}${YELLOW}$APP_SECRET${NC}"
echo ""
echo -e "${WHITE}APP_SECRET_CODE=${NC}${YELLOW}$APP_SECRET_CODE${NC}"
echo ""
echo -e "${WHITE}ENCRYPTION_KEY=${NC}${YELLOW}$ENCRYPTION_KEY${NC}"
echo ""
# Check if .env file exists
ENV_FILE=".env"
if [ -f "$ENV_FILE" ]; then
echo -e "${RED}Warning: .env file already exists!${NC}"
read -p "Do you want to update it with new secrets? (y/N): " -n 1 -r
echo
if [[ $REPLY =~ ^[Yy]$ ]]; then
UPDATE_FILE=true
else
UPDATE_FILE=false
echo -e "${YELLOW}Secrets generated but not written to file.${NC}"
fi
else
read -p "Create .env file with these secrets? (Y/n): " -n 1 -r
echo
if [[ $REPLY =~ ^[Nn]$ ]]; then
UPDATE_FILE=false
echo -e "${YELLOW}Secrets generated but not written to file.${NC}"
else
UPDATE_FILE=true
fi
fi
if [ "$UPDATE_FILE" = true ]; then
# Create or update .env file
if [ -f "$ENV_FILE" ]; then
# Backup existing file
BACKUP_FILE=".env.backup.$(date +%Y%m%d-%H%M%S)"
cp "$ENV_FILE" "$BACKUP_FILE"
echo -e "${GREEN}Backed up existing .env to $BACKUP_FILE${NC}"
# Update secrets in existing file
sed -i.tmp "s/^JWT_SECRET=.*/JWT_SECRET=$JWT_SECRET/" "$ENV_FILE"
sed -i.tmp "s/^APP_SECRET=.*/APP_SECRET=$APP_SECRET/" "$ENV_FILE"
sed -i.tmp "s/^APP_SECRET_CODE=.*/APP_SECRET_CODE=$APP_SECRET_CODE/" "$ENV_FILE"
sed -i.tmp "s/^ENCRYPTION_KEY=.*/ENCRYPTION_KEY=$ENCRYPTION_KEY/" "$ENV_FILE"
rm -f "$ENV_FILE.tmp"
echo -e "${GREEN}Updated .env file with new secrets${NC}"
else
# Create new .env file from template
if [ -f ".env.example" ]; then
cp ".env.example" "$ENV_FILE"
# Replace placeholder values with generated secrets
sed -i.tmp "s/^JWT_SECRET=.*/JWT_SECRET=$JWT_SECRET/" "$ENV_FILE"
sed -i.tmp "s/^APP_SECRET=.*/APP_SECRET=$APP_SECRET/" "$ENV_FILE"
sed -i.tmp "s/^APP_SECRET_CODE=.*/APP_SECRET_CODE=$APP_SECRET_CODE/" "$ENV_FILE"
sed -i.tmp "s/^ENCRYPTION_KEY=.*/ENCRYPTION_KEY=$ENCRYPTION_KEY/" "$ENV_FILE"
rm -f "$ENV_FILE.tmp"
echo -e "${GREEN}Created .env file from template with generated secrets${NC}"
else
# Create minimal .env file
cat > "$ENV_FILE" << EOF
# Bootstrap App Environment Configuration
# Generated on $(date '+%Y-%m-%d %H:%M:%S')
# CRITICAL SECURITY SETTINGS (REQUIRED)
JWT_SECRET=$JWT_SECRET
APP_SECRET=$APP_SECRET
APP_SECRET_CODE=$APP_SECRET_CODE
ENCRYPTION_KEY=$ENCRYPTION_KEY
# CORE APPLICATION SETTINGS
DB_NAME=app.db
PORT=3000
CORS_ALLOWED_ORIGIN=http://localhost:5173
DEFAULT_ADMIN_PASSWORD=change-this-password
EOF
echo -e "${GREEN}Created minimal .env file with generated secrets${NC}"
fi
fi
fi
echo ""
echo -e "${RED}Security Notes:${NC}"
echo -e "${RED}===============${NC}"
echo -e "${YELLOW}1. Keep these secrets secure and never commit them to version control${NC}"
echo -e "${YELLOW}2. Use different secrets for each environment (dev, staging, production)${NC}"
echo -e "${YELLOW}3. Rotate secrets regularly in production environments${NC}"
echo -e "${YELLOW}4. The ENCRYPTION_KEY is exactly 32 characters as required for AES-256${NC}"
echo -e "${YELLOW}5. Change the DEFAULT_ADMIN_PASSWORD immediately after first login${NC}"
echo ""
# Verify encryption key length
if [ ${#ENCRYPTION_KEY} -eq 32 ]; then
echo -e "${GREEN}✓ Encryption key length verified (32 characters = 32 bytes for AES-256)${NC}"
else
echo -e "${RED}✗ Warning: Encryption key length is incorrect! Got ${#ENCRYPTION_KEY} chars, expected 32${NC}"
fi
echo ""
echo -e "${CYAN}Next steps:${NC}"
echo -e "${WHITE}1. Review and customize the .env file if needed${NC}"
echo -e "${WHITE}2. Build and run the application: go run cmd/api/main.go${NC}"
echo -e "${WHITE}3. Change the default admin password on first login${NC}"
echo -e "${WHITE}4. Access the API documentation at: http://localhost:3000/swagger/${NC}"
echo ""
echo -e "${GREEN}Happy coding! 🚀${NC}"