Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
139 changes: 139 additions & 0 deletions startupscript/dataproc/startup.sh
Original file line number Diff line number Diff line change
Expand Up @@ -762,6 +762,145 @@ if [[ -f ~/.ssh-agent/environment ]]; then
fi
EOF

###################################
# Setup Knox certificate auto-renewal
###################################
# Knox Gateway SSL certificates expire. Setup annual renewal
# to prevent Component Gateway web interfaces from becoming inactive.

emit "Setting up Knox Gateway certificate auto-renewal..."

readonly KNOX_REGEN_SCRIPT="/usr/local/bin/regenerate-knox-cert.sh"
readonly KNOX_CRON_FILE="/etc/cron.d/knox-cert-regeneration"

# Create the regeneration script
cat << 'KNOX_REGEN_EOF' > "${KNOX_REGEN_SCRIPT}"
#!/bin/bash
#
# Name: regenerate-knox-cert.sh
#
# Description:
# Script to regenerate the Knox Gateway SSL certificate on a Dataproc cluster.
#
# Reference:
# https://docs.cloud.google.com/dataproc/docs/concepts/accessing/dataproc-gateways#regenerate
#

set -o errexit
set -o nounset
set -o pipefail
set -o xtrace

# Knox keystore configuration
readonly KNOX_KEYSTORE="/var/lib/knox/security/keystores/gateway.jks"
readonly BACKUP_DIR="/var/lib/knox/security/keystores/backup"
readonly BACKUP_TIMESTAMP=$(date +%Y%m%d_%H%M%S)
readonly BACKUP_FILE="${BACKUP_DIR}/gateway_${BACKUP_TIMESTAMP}.jks"

#######################################
# Emit a message with a timestamp
# Logs are captured by systemd journal when run via cron
#######################################
function emit() {
echo "$(date '+%Y-%m-%d %H:%M:%S') $*"
}
readonly -f emit

emit "Starting Knox Gateway SSL certificate regeneration check..."

# Only run on the dataproc master node. Exit with error if otherwise.
ROLE="$(/usr/share/google/get_metadata_value attributes/dataproc-role)"
if [[ "${ROLE}" != 'Master' ]]; then
emit "ERROR: This script must be run on the Dataproc master node. Current role: ${ROLE}"
exit 1
fi
readonly ROLE

emit "Running on Dataproc master node."

# Check if keystore exists
if [[ ! -f "${KNOX_KEYSTORE}" ]]; then
emit "ERROR: Knox keystore not found at ${KNOX_KEYSTORE}"
exit 1
fi

# Check certificate year before proceeding
emit "Checking certificate year..."
CERT_INFO=$(echo "" | keytool -list -v -keystore "${KNOX_KEYSTORE}" 2>&1)

# Extract the certificate creation date and year
CERT_CREATION_DATE=$(echo "${CERT_INFO}" | grep -i "Creation date:" | head -n 1 | sed 's/.*Creation date: //')

if [[ -z "${CERT_CREATION_DATE}" ]]; then
emit "WARNING: Could not extract certificate creation date. Proceeding with regeneration."
else
# Extract year from certificate date (last token)
CERT_YEAR=$(echo "${CERT_CREATION_DATE}" | awk '{print $NF}')
CURRENT_YEAR=$(date +%Y)

emit "Certificate creation date: ${CERT_CREATION_DATE}"
emit "Certificate year: ${CERT_YEAR}"
emit "Current year: ${CURRENT_YEAR}"

# Only regenerate if certificate is from a previous year
if [[ "${CERT_YEAR}" == "${CURRENT_YEAR}" ]]; then
emit "Certificate was created this year (${CURRENT_YEAR}). Skipping regeneration."
exit 0
fi

emit "Certificate is from year ${CERT_YEAR}. Proceeding with regeneration..."
fi

# Create backup directory if it doesn't exist
mkdir -p "${BACKUP_DIR}"

# Backup the current keystore
emit "Backing up current keystore to ${BACKUP_FILE}"
cp "${KNOX_KEYSTORE}" "${BACKUP_FILE}"

if [[ ! -f "${BACKUP_FILE}" ]]; then
emit "ERROR: Failed to create backup of keystore"
exit 1
fi

emit "Backup created successfully."

# Remove the old keystore to trigger regeneration
emit "Removing old keystore..."
rm -f "${KNOX_KEYSTORE}"

# Restart Knox service to generate new certificate
emit "Restarting Knox service to generate new certificate..."
systemctl restart knox

emit "Knox Gateway SSL certificate regeneration completed successfully."

exit 0
KNOX_REGEN_EOF

chmod +x "${KNOX_REGEN_SCRIPT}"

# Create cron job
# Use systemd-cat to send output to journalctl with identifier 'knox-cert-regen'
cat << EOF > "${KNOX_CRON_FILE}"
# Knox Gateway SSL Certificate Regeneration
# Checks certificate year and regenerates if from previous year
# Logs are sent to journalctl and can be viewed with: journalctl -t knox-cert-regen

# Check annually at 2 AM on January 1st (ensures cert is regenerated yearly)
0 2 1 1 * root systemd-cat -t knox-cert-regen ${KNOX_REGEN_SCRIPT}

# Also check on reboot (regenerates only if cert is from previous year)
@reboot root sleep 60 && systemd-cat -t knox-cert-regen ${KNOX_REGEN_SCRIPT}
EOF

chmod 644 "${KNOX_CRON_FILE}"

emit "Knox certificate auto-renewal configured successfully"
emit "Cron job created at ${KNOX_CRON_FILE}"
emit "Certificate year will be checked at 2 AM on January 1st every year and on reboot."
emit "Certificate will be regenerated only if from a previous year."

#############################
# Setup instance boot service
#############################
Expand Down
Loading