Fix PMA gateway LE cert domain resolution
parent
20d3d016c2
commit
7dd77c6ccd
|
|
@ -1029,7 +1029,7 @@ actions:
|
|||
user: root
|
||||
commands:
|
||||
- bash /home/litespeed/mbmanager/scripts/dbreset.sh >/dev/null
|
||||
- bash /home/litespeed/mbmanager/pma-gateway/create_pma_gateway.sh --validity="${settings.validity}" --slug="${settings.slug}"
|
||||
- bash /home/litespeed/mbmanager/pma-gateway/create_pma_gateway.sh --validity="${settings.validity}" --slug="${settings.slug}" --cert-domain="${env.domain}" --email="${user.email}"
|
||||
- return:
|
||||
type: info
|
||||
message: "Gateway URL: ${response.out}"
|
||||
|
|
|
|||
|
|
@ -4,19 +4,23 @@
|
|||
# Script: create_pma_gateway.sh
|
||||
# Purpose: Create a time-limited gateway URL for phpMyAdmin on Virtuozzo LLSMP.
|
||||
# Uses Let's Encrypt cert in the dedicated phpMyAdmin vhost (port 8443).
|
||||
# Dynamically detects Let's Encrypt certificate paths.
|
||||
# Usage: create_pma_gateway.sh --validity=30 [--slug=myalias]
|
||||
# Resolves certs for the environment domain and can issue cert on demand.
|
||||
# Usage: create_pma_gateway.sh --validity=30 [--slug=myalias] [--cert-domain=env.example.com] [--email=admin@example.com]
|
||||
# Outputs: Prints the generated URL.
|
||||
# ==============================================================================
|
||||
set -euo pipefail
|
||||
|
||||
SLUG=""
|
||||
VALIDITY=30 # minutes
|
||||
CERT_DOMAIN=""
|
||||
CONTACT_EMAIL=""
|
||||
|
||||
for arg in "$@"; do
|
||||
case $arg in
|
||||
--slug=*) SLUG="${arg#*=}" ;;
|
||||
--validity=*) VALIDITY="${arg#*=}" ;;
|
||||
--cert-domain=*) CERT_DOMAIN="${arg#*=}" ;;
|
||||
--email=*) CONTACT_EMAIL="${arg#*=}" ;;
|
||||
*) echo "ERROR: Unknown argument $arg"; exit 1 ;;
|
||||
esac
|
||||
done
|
||||
|
|
@ -25,13 +29,30 @@ if [[ -z "$SLUG" ]]; then
|
|||
SLUG=$(openssl rand -hex 4) # 8-char random
|
||||
fi
|
||||
|
||||
# Determine environment public host (no node prefix) - used for certificate lookup and URL
|
||||
if [[ -n "${JELASTIC_ENV_DOMAIN:-}" ]]; then
|
||||
ENV_HOST="$JELASTIC_ENV_DOMAIN"
|
||||
else
|
||||
ENV_HOST=$(hostname -f)
|
||||
ENV_HOST=${ENV_HOST#node*-} # strip nodeXXXX-
|
||||
# Reject unresolved template placeholders if they are passed through literally.
|
||||
if [[ "$CERT_DOMAIN" == *'${'* ]]; then
|
||||
CERT_DOMAIN=""
|
||||
fi
|
||||
if [[ "$CONTACT_EMAIL" == *'${'* ]]; then
|
||||
CONTACT_EMAIL=""
|
||||
fi
|
||||
|
||||
# Prefer explicit cert domain and fallback to Jelastic environment domain.
|
||||
if [[ -z "$CERT_DOMAIN" ]]; then
|
||||
if [[ -n "${JELASTIC_ENV_DOMAIN:-}" ]]; then
|
||||
CERT_DOMAIN="$JELASTIC_ENV_DOMAIN"
|
||||
else
|
||||
CERT_DOMAIN=$(hostname -f)
|
||||
CERT_DOMAIN=${CERT_DOMAIN#node*-} # strip nodeXXXX-
|
||||
fi
|
||||
fi
|
||||
|
||||
# Fallback for email when not explicitly passed.
|
||||
if [[ -z "$CONTACT_EMAIL" ]] && [[ -n "${JELASTIC_USER_EMAIL:-}" ]]; then
|
||||
CONTACT_EMAIL="$JELASTIC_USER_EMAIL"
|
||||
fi
|
||||
|
||||
ENV_HOST="$CERT_DOMAIN"
|
||||
|
||||
PMADB_DIR="/usr/share/phpMyAdmin"
|
||||
GATEWAY_FILE="$PMADB_DIR/access-db-$SLUG.php"
|
||||
|
|
@ -57,41 +78,80 @@ token="$base.$mac"
|
|||
VHOST_CONFIG="/usr/share/phpMyAdmin/vhost.conf"
|
||||
NEEDS_RESTART=0
|
||||
|
||||
# --- MODIFICATION: Dynamically determine Let's Encrypt Cert Paths ---
|
||||
# --- Let's Encrypt certificate resolution for ENV_HOST ---
|
||||
LE_LIVE_DIR="/etc/letsencrypt/live"
|
||||
LE_CERT_DIR=""
|
||||
|
||||
# Attempt to find the directory matching ENV_HOST
|
||||
if [[ -d "$LE_LIVE_DIR/$ENV_HOST" ]]; then
|
||||
# Attempt exact match first.
|
||||
if [[ -d "$LE_LIVE_DIR/$ENV_HOST" ]] && [[ -f "$LE_LIVE_DIR/$ENV_HOST/privkey.pem" ]] && [[ -f "$LE_LIVE_DIR/$ENV_HOST/fullchain.pem" ]]; then
|
||||
LE_CERT_DIR="$LE_LIVE_DIR/$ENV_HOST"
|
||||
echo "INFO: Found Let's Encrypt cert directory matching ENV_HOST: $LE_CERT_DIR" >&2
|
||||
else
|
||||
# If not found, iterate through subdirectories in $LE_LIVE_DIR to find a suitable one
|
||||
# This is a fallback, assuming there might be only one relevant cert directory.
|
||||
# Or, you could add more logic here to match patterns if needed.
|
||||
for dir in "$LE_LIVE_DIR"/*/; do
|
||||
if [[ -d "$dir" ]]; then
|
||||
candidate_dir=$(basename "$dir")
|
||||
echo "INFO: Checking Let's Encrypt cert directory: $candidate_dir" >&2
|
||||
# Add more specific checks here if multiple domains exist and you need to pick the right one.
|
||||
# For now, just pick the first one that has the required files.
|
||||
if [[ -f "$dir/privkey.pem" ]] && [[ -f "$dir/fullchain.pem" ]]; then
|
||||
LE_CERT_DIR="$dir"
|
||||
echo "INFO: Found Let's Encrypt cert directory with required files: $LE_CERT_DIR" >&2
|
||||
break
|
||||
fi
|
||||
echo "INFO: Found exact Let's Encrypt cert directory: $LE_CERT_DIR" >&2
|
||||
fi
|
||||
|
||||
# Then try certbot-suffixed directories (e.g., domain-0001).
|
||||
if [[ -z "$LE_CERT_DIR" ]]; then
|
||||
for dir in "$LE_LIVE_DIR/$ENV_HOST"-*/; do
|
||||
if [[ -d "$dir" ]] && [[ -f "$dir/privkey.pem" ]] && [[ -f "$dir/fullchain.pem" ]]; then
|
||||
LE_CERT_DIR="${dir%/}"
|
||||
echo "INFO: Found suffixed Let's Encrypt cert directory: $LE_CERT_DIR" >&2
|
||||
break
|
||||
fi
|
||||
done
|
||||
fi
|
||||
|
||||
# If no cert exists yet, attempt one-time issuance for ENV_HOST.
|
||||
if [[ -z "$LE_CERT_DIR" ]]; then
|
||||
echo "WARNING: No Let's Encrypt certificate found for '$ENV_HOST'. Attempting to issue one now..." >&2
|
||||
|
||||
CERTBOT_CMD=""
|
||||
if command -v certbot >/dev/null 2>&1; then
|
||||
CERTBOT_CMD="certbot"
|
||||
elif [[ -x "/opt/certbot/certbot-auto" ]]; then
|
||||
CERTBOT_CMD="/opt/certbot/certbot-auto"
|
||||
fi
|
||||
|
||||
if [[ -z "$CERTBOT_CMD" ]]; then
|
||||
echo "FATAL: certbot is not available and no existing Let's Encrypt certificate was found for '$ENV_HOST'." >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
WEBROOT_PATH="/var/www/webroot/ROOT"
|
||||
ACME_CHALLENGE_DIR="$WEBROOT_PATH/.well-known/acme-challenge"
|
||||
sudo mkdir -p "$ACME_CHALLENGE_DIR"
|
||||
|
||||
if [[ -n "$CONTACT_EMAIL" ]]; then
|
||||
if ! sudo "$CERTBOT_CMD" certonly --webroot -w "$WEBROOT_PATH" -d "$ENV_HOST" --non-interactive --agree-tos --email "$CONTACT_EMAIL"; then
|
||||
echo "FATAL: Failed to issue Let's Encrypt certificate for '$ENV_HOST' using contact email '$CONTACT_EMAIL'." >&2
|
||||
exit 1
|
||||
fi
|
||||
else
|
||||
if ! sudo "$CERTBOT_CMD" certonly --webroot -w "$WEBROOT_PATH" -d "$ENV_HOST" --non-interactive --agree-tos --register-unsafely-without-email; then
|
||||
echo "FATAL: Failed to issue Let's Encrypt certificate for '$ENV_HOST' without contact email." >&2
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
|
||||
# Re-check exact and suffixed certificate directories after issuance.
|
||||
if [[ -d "$LE_LIVE_DIR/$ENV_HOST" ]] && [[ -f "$LE_LIVE_DIR/$ENV_HOST/privkey.pem" ]] && [[ -f "$LE_LIVE_DIR/$ENV_HOST/fullchain.pem" ]]; then
|
||||
LE_CERT_DIR="$LE_LIVE_DIR/$ENV_HOST"
|
||||
else
|
||||
for dir in "$LE_LIVE_DIR/$ENV_HOST"-*/; do
|
||||
if [[ -d "$dir" ]] && [[ -f "$dir/privkey.pem" ]] && [[ -f "$dir/fullchain.pem" ]]; then
|
||||
LE_CERT_DIR="${dir%/}"
|
||||
break
|
||||
fi
|
||||
done
|
||||
fi
|
||||
fi
|
||||
|
||||
# Set the final key and cert file paths based on the found directory
|
||||
if [[ -n "$LE_CERT_DIR" ]]; then
|
||||
LE_KEY_FILE="$LE_CERT_DIR/privkey.pem"
|
||||
LE_CERT_FILE="$LE_CERT_DIR/fullchain.pem"
|
||||
else
|
||||
echo "FATAL: Let's Encrypt certificate directory could not be found in $LE_LIVE_DIR for ENV_HOST: $ENV_HOST" >&2
|
||||
echo "FATAL: Let's Encrypt certificate directory could not be found for ENV_HOST: $ENV_HOST" >&2
|
||||
echo " Checked specific path: $LE_LIVE_DIR/$ENV_HOST" >&2
|
||||
echo " Checked other subdirectories for privkey.pem and fullchain.pem." >&2
|
||||
echo " Checked suffixed paths: $LE_LIVE_DIR/${ENV_HOST}-*" >&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue