You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
				
					
					
						
							280 lines
						
					
					
						
							9.9 KiB
						
					
					
				
			
		
		
		
			
			
			
		
		
	
	
							280 lines
						
					
					
						
							9.9 KiB
						
					
					
				
								#!/usr/bin/env sh
							 | 
						|
								
							 | 
						|
								# Script for acme.sh to deploy certificates to lighttpd
							 | 
						|
								#
							 | 
						|
								# The following variables can be exported:
							 | 
						|
								#
							 | 
						|
								# export DEPLOY_LIGHTTPD_PEM_NAME="${domain}.pem"
							 | 
						|
								#
							 | 
						|
								# Defines the name of the PEM file.
							 | 
						|
								# Defaults to "<domain>.pem"
							 | 
						|
								#
							 | 
						|
								# export DEPLOY_LIGHTTPD_PEM_PATH="/etc/lighttpd"
							 | 
						|
								#
							 | 
						|
								# Defines location of PEM file for Lighttpd.
							 | 
						|
								# Defaults to /etc/lighttpd
							 | 
						|
								#
							 | 
						|
								# export DEPLOY_LIGHTTPD_RELOAD="systemctl reload lighttpd"
							 | 
						|
								#
							 | 
						|
								# OPTIONAL: Reload command used post deploy
							 | 
						|
								# This defaults to be a no-op (ie "true").
							 | 
						|
								# It is strongly recommended to set this something that makes sense
							 | 
						|
								# for your distro.
							 | 
						|
								#
							 | 
						|
								# export DEPLOY_LIGHTTPD_ISSUER="yes"
							 | 
						|
								#
							 | 
						|
								# OPTIONAL: Places CA file as "${DEPLOY_LIGHTTPD_PEM}.issuer"
							 | 
						|
								# Note: Required for OCSP stapling to work
							 | 
						|
								#
							 | 
						|
								# export DEPLOY_LIGHTTPD_BUNDLE="no"
							 | 
						|
								#
							 | 
						|
								# OPTIONAL: Deploy this certificate as part of a multi-cert bundle
							 | 
						|
								# This adds a suffix to the certificate based on the certificate type
							 | 
						|
								# eg RSA certificates will have .rsa as a suffix to the file name
							 | 
						|
								# Lighttpd will load all certificates and provide one or the other
							 | 
						|
								# depending on client capabilities
							 | 
						|
								# Note: This functionality requires Lighttpd was compiled against
							 | 
						|
								# a version of OpenSSL that supports this.
							 | 
						|
								#
							 | 
						|
								
							 | 
						|
								########  Public functions #####################
							 | 
						|
								
							 | 
						|
								#domain keyfile certfile cafile fullchain
							 | 
						|
								lighttpd_deploy() {
							 | 
						|
								  _cdomain="$1"
							 | 
						|
								  _ckey="$2"
							 | 
						|
								  _ccert="$3"
							 | 
						|
								  _cca="$4"
							 | 
						|
								  _cfullchain="$5"
							 | 
						|
								
							 | 
						|
								  # Some defaults
							 | 
						|
								  DEPLOY_LIGHTTPD_PEM_PATH_DEFAULT="/etc/lighttpd"
							 | 
						|
								  DEPLOY_LIGHTTPD_PEM_NAME_DEFAULT="${_cdomain}.pem"
							 | 
						|
								  DEPLOY_LIGHTTPD_BUNDLE_DEFAULT="no"
							 | 
						|
								  DEPLOY_LIGHTTPD_ISSUER_DEFAULT="yes"
							 | 
						|
								  DEPLOY_LIGHTTPD_RELOAD_DEFAULT="true"
							 | 
						|
								
							 | 
						|
								  _debug _cdomain "${_cdomain}"
							 | 
						|
								  _debug _ckey "${_ckey}"
							 | 
						|
								  _debug _ccert "${_ccert}"
							 | 
						|
								  _debug _cca "${_cca}"
							 | 
						|
								  _debug _cfullchain "${_cfullchain}"
							 | 
						|
								
							 | 
						|
								  # PEM_PATH is optional. If not provided then assume "${DEPLOY_LIGHTTPD_PEM_PATH_DEFAULT}"
							 | 
						|
								  _getdeployconf DEPLOY_LIGHTTPD_PEM_PATH
							 | 
						|
								  _debug2 DEPLOY_LIGHTTPD_PEM_PATH "${DEPLOY_LIGHTTPD_PEM_PATH}"
							 | 
						|
								  if [ -n "${DEPLOY_LIGHTTPD_PEM_PATH}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_pem_path="${DEPLOY_LIGHTTPD_PEM_PATH}"
							 | 
						|
								    _savedomainconf Le_Deploy_lighttpd_pem_path "${Le_Deploy_lighttpd_pem_path}"
							 | 
						|
								  elif [ -z "${Le_Deploy_lighttpd_pem_path}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_pem_path="${DEPLOY_LIGHTTPD_PEM_PATH_DEFAULT}"
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # Ensure PEM_PATH exists
							 | 
						|
								  if [ -d "${Le_Deploy_lighttpd_pem_path}" ]; then
							 | 
						|
								    _debug "PEM_PATH ${Le_Deploy_lighttpd_pem_path} exists"
							 | 
						|
								  else
							 | 
						|
								    _err "PEM_PATH ${Le_Deploy_lighttpd_pem_path} does not exist"
							 | 
						|
								    return 1
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # PEM_NAME is optional. If not provided then assume "${DEPLOY_LIGHTTPD_PEM_NAME_DEFAULT}"
							 | 
						|
								  _getdeployconf DEPLOY_LIGHTTPD_PEM_NAME
							 | 
						|
								  _debug2 DEPLOY_LIGHTTPD_PEM_NAME "${DEPLOY_LIGHTTPD_PEM_NAME}"
							 | 
						|
								  if [ -n "${DEPLOY_LIGHTTPD_PEM_NAME}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_pem_name="${DEPLOY_LIGHTTPD_PEM_NAME}"
							 | 
						|
								    _savedomainconf Le_Deploy_lighttpd_pem_name "${Le_Deploy_lighttpd_pem_name}"
							 | 
						|
								  elif [ -z "${Le_Deploy_lighttpd_pem_name}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_pem_name="${DEPLOY_LIGHTTPD_PEM_NAME_DEFAULT}"
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # BUNDLE is optional. If not provided then assume "${DEPLOY_LIGHTTPD_BUNDLE_DEFAULT}"
							 | 
						|
								  _getdeployconf DEPLOY_LIGHTTPD_BUNDLE
							 | 
						|
								  _debug2 DEPLOY_LIGHTTPD_BUNDLE "${DEPLOY_LIGHTTPD_BUNDLE}"
							 | 
						|
								  if [ -n "${DEPLOY_LIGHTTPD_BUNDLE}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_bundle="${DEPLOY_LIGHTTPD_BUNDLE}"
							 | 
						|
								    _savedomainconf Le_Deploy_lighttpd_bundle "${Le_Deploy_lighttpd_bundle}"
							 | 
						|
								  elif [ -z "${Le_Deploy_lighttpd_bundle}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_bundle="${DEPLOY_LIGHTTPD_BUNDLE_DEFAULT}"
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # ISSUER is optional. If not provided then assume "${DEPLOY_LIGHTTPD_ISSUER_DEFAULT}"
							 | 
						|
								  _getdeployconf DEPLOY_LIGHTTPD_ISSUER
							 | 
						|
								  _debug2 DEPLOY_LIGHTTPD_ISSUER "${DEPLOY_LIGHTTPD_ISSUER}"
							 | 
						|
								  if [ -n "${DEPLOY_LIGHTTPD_ISSUER}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_issuer="${DEPLOY_LIGHTTPD_ISSUER}"
							 | 
						|
								    _savedomainconf Le_Deploy_lighttpd_issuer "${Le_Deploy_lighttpd_issuer}"
							 | 
						|
								  elif [ -z "${Le_Deploy_lighttpd_issuer}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_issuer="${DEPLOY_LIGHTTPD_ISSUER_DEFAULT}"
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # RELOAD is optional. If not provided then assume "${DEPLOY_LIGHTTPD_RELOAD_DEFAULT}"
							 | 
						|
								  _getdeployconf DEPLOY_LIGHTTPD_RELOAD
							 | 
						|
								  _debug2 DEPLOY_LIGHTTPD_RELOAD "${DEPLOY_LIGHTTPD_RELOAD}"
							 | 
						|
								  if [ -n "${DEPLOY_LIGHTTPD_RELOAD}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_reload="${DEPLOY_LIGHTTPD_RELOAD}"
							 | 
						|
								    _savedomainconf Le_Deploy_lighttpd_reload "${Le_Deploy_lighttpd_reload}"
							 | 
						|
								  elif [ -z "${Le_Deploy_lighttpd_reload}" ]; then
							 | 
						|
								    Le_Deploy_lighttpd_reload="${DEPLOY_LIGHTTPD_RELOAD_DEFAULT}"
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # Set the suffix depending if we are creating a bundle or not
							 | 
						|
								  if [ "${Le_Deploy_lighttpd_bundle}" = "yes" ]; then
							 | 
						|
								    _info "Bundle creation requested"
							 | 
						|
								    # Initialise $Le_Keylength if its not already set
							 | 
						|
								    if [ -z "${Le_Keylength}" ]; then
							 | 
						|
								      Le_Keylength=""
							 | 
						|
								    fi
							 | 
						|
								    if _isEccKey "${Le_Keylength}"; then
							 | 
						|
								      _info "ECC key type detected"
							 | 
						|
								      _suffix=".ecdsa"
							 | 
						|
								    else
							 | 
						|
								      _info "RSA key type detected"
							 | 
						|
								      _suffix=".rsa"
							 | 
						|
								    fi
							 | 
						|
								  else
							 | 
						|
								    _suffix=""
							 | 
						|
								  fi
							 | 
						|
								  _debug _suffix "${_suffix}"
							 | 
						|
								
							 | 
						|
								  # Set variables for later
							 | 
						|
								  _pem="${Le_Deploy_lighttpd_pem_path}/${Le_Deploy_lighttpd_pem_name}${_suffix}"
							 | 
						|
								  _issuer="${_pem}.issuer"
							 | 
						|
								  _ocsp="${_pem}.ocsp"
							 | 
						|
								  _reload="${Le_Deploy_lighttpd_reload}"
							 | 
						|
								
							 | 
						|
								  _info "Deploying PEM file"
							 | 
						|
								  # Create a temporary PEM file
							 | 
						|
								  _temppem="$(_mktemp)"
							 | 
						|
								  _debug _temppem "${_temppem}"
							 | 
						|
								  cat "${_ckey}" "${_ccert}" "${_cca}" >"${_temppem}"
							 | 
						|
								  _ret="$?"
							 | 
						|
								
							 | 
						|
								  # Check that we could create the temporary file
							 | 
						|
								  if [ "${_ret}" != "0" ]; then
							 | 
						|
								    _err "Error code ${_ret} returned during PEM file creation"
							 | 
						|
								    [ -f "${_temppem}" ] && rm -f "${_temppem}"
							 | 
						|
								    return ${_ret}
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # Move PEM file into place
							 | 
						|
								  _info "Moving new certificate into place"
							 | 
						|
								  _debug _pem "${_pem}"
							 | 
						|
								  cat "${_temppem}" >"${_pem}"
							 | 
						|
								  _ret=$?
							 | 
						|
								
							 | 
						|
								  # Clean up temp file
							 | 
						|
								  [ -f "${_temppem}" ] && rm -f "${_temppem}"
							 | 
						|
								
							 | 
						|
								  # Deal with any failure of moving PEM file into place
							 | 
						|
								  if [ "${_ret}" != "0" ]; then
							 | 
						|
								    _err "Error code ${_ret} returned while moving new certificate into place"
							 | 
						|
								    return ${_ret}
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # Update .issuer file if requested
							 | 
						|
								  if [ "${Le_Deploy_lighttpd_issuer}" = "yes" ]; then
							 | 
						|
								    _info "Updating .issuer file"
							 | 
						|
								    _debug _issuer "${_issuer}"
							 | 
						|
								    cat "${_cca}" >"${_issuer}"
							 | 
						|
								    _ret="$?"
							 | 
						|
								
							 | 
						|
								    if [ "${_ret}" != "0" ]; then
							 | 
						|
								      _err "Error code ${_ret} returned while copying issuer/CA certificate into place"
							 | 
						|
								      return ${_ret}
							 | 
						|
								    fi
							 | 
						|
								  else
							 | 
						|
								    [ -f "${_issuer}" ] && _err "Issuer file update not requested but .issuer file exists"
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # Update .ocsp file if certificate was requested with --ocsp/--ocsp-must-staple option
							 | 
						|
								  if [ -z "${Le_OCSP_Staple}" ]; then
							 | 
						|
								    Le_OCSP_Staple="0"
							 | 
						|
								  fi
							 | 
						|
								  if [ "${Le_OCSP_Staple}" = "1" ]; then
							 | 
						|
								    _info "Updating OCSP stapling info"
							 | 
						|
								    _debug _ocsp "${_ocsp}"
							 | 
						|
								    _info "Extracting OCSP URL"
							 | 
						|
								    _ocsp_url=$(${ACME_OPENSSL_BIN:-openssl} x509 -noout -ocsp_uri -in "${_pem}")
							 | 
						|
								    _debug _ocsp_url "${_ocsp_url}"
							 | 
						|
								
							 | 
						|
								    # Only process OCSP if URL was present
							 | 
						|
								    if [ "${_ocsp_url}" != "" ]; then
							 | 
						|
								      # Extract the hostname from the OCSP URL
							 | 
						|
								      _info "Extracting OCSP URL"
							 | 
						|
								      _ocsp_host=$(echo "${_ocsp_url}" | cut -d/ -f3)
							 | 
						|
								      _debug _ocsp_host "${_ocsp_host}"
							 | 
						|
								
							 | 
						|
								      # Only process the certificate if we have a .issuer file
							 | 
						|
								      if [ -r "${_issuer}" ]; then
							 | 
						|
								        # Check if issuer cert is also a root CA cert
							 | 
						|
								        _subjectdn=$(${ACME_OPENSSL_BIN:-openssl} x509 -in "${_issuer}" -subject -noout | cut -d'/' -f2,3,4,5,6,7,8,9,10)
							 | 
						|
								        _debug _subjectdn "${_subjectdn}"
							 | 
						|
								        _issuerdn=$(${ACME_OPENSSL_BIN:-openssl} x509 -in "${_issuer}" -issuer -noout | cut -d'/' -f2,3,4,5,6,7,8,9,10)
							 | 
						|
								        _debug _issuerdn "${_issuerdn}"
							 | 
						|
								        _info "Requesting OCSP response"
							 | 
						|
								        # If the issuer is a CA cert then our command line has "-CAfile" added
							 | 
						|
								        if [ "${_subjectdn}" = "${_issuerdn}" ]; then
							 | 
						|
								          _cafile_argument="-CAfile \"${_issuer}\""
							 | 
						|
								        else
							 | 
						|
								          _cafile_argument=""
							 | 
						|
								        fi
							 | 
						|
								        _debug _cafile_argument "${_cafile_argument}"
							 | 
						|
								        # if OpenSSL/LibreSSL is v1.1 or above, the format for the -header option has changed
							 | 
						|
								        _openssl_version=$(${ACME_OPENSSL_BIN:-openssl} version | cut -d' ' -f2)
							 | 
						|
								        _debug _openssl_version "${_openssl_version}"
							 | 
						|
								        _openssl_major=$(echo "${_openssl_version}" | cut -d '.' -f1)
							 | 
						|
								        _openssl_minor=$(echo "${_openssl_version}" | cut -d '.' -f2)
							 | 
						|
								        if [ "${_openssl_major}" -eq "1" ] && [ "${_openssl_minor}" -ge "1" ] || [ "${_openssl_major}" -ge "2" ]; then
							 | 
						|
								          _header_sep="="
							 | 
						|
								        else
							 | 
						|
								          _header_sep=" "
							 | 
						|
								        fi
							 | 
						|
								        # Request the OCSP response from the issuer and store it
							 | 
						|
								        _openssl_ocsp_cmd="${ACME_OPENSSL_BIN:-openssl} ocsp \
							 | 
						|
								          -issuer \"${_issuer}\" \
							 | 
						|
								          -cert \"${_pem}\" \
							 | 
						|
								          -url \"${_ocsp_url}\" \
							 | 
						|
								          -header Host${_header_sep}\"${_ocsp_host}\" \
							 | 
						|
								          -respout \"${_ocsp}\" \
							 | 
						|
								          -verify_other \"${_issuer}\" \
							 | 
						|
								          ${_cafile_argument} \
							 | 
						|
								          | grep -q \"${_pem}: good\""
							 | 
						|
								        _debug _openssl_ocsp_cmd "${_openssl_ocsp_cmd}"
							 | 
						|
								        eval "${_openssl_ocsp_cmd}"
							 | 
						|
								        _ret=$?
							 | 
						|
								      else
							 | 
						|
								        # Non fatal: No issuer file was present so no OCSP stapling file created
							 | 
						|
								        _err "OCSP stapling in use but no .issuer file was present"
							 | 
						|
								      fi
							 | 
						|
								    else
							 | 
						|
								      # Non fatal: No OCSP url was found int the certificate
							 | 
						|
								      _err "OCSP update requested but no OCSP URL was found in certificate"
							 | 
						|
								    fi
							 | 
						|
								
							 | 
						|
								    # Non fatal: Check return code of openssl command
							 | 
						|
								    if [ "${_ret}" != "0" ]; then
							 | 
						|
								      _err "Updating OCSP stapling failed with return code ${_ret}"
							 | 
						|
								    fi
							 | 
						|
								  else
							 | 
						|
								    # An OCSP file was already present but certificate did not have OCSP extension
							 | 
						|
								    if [ -f "${_ocsp}" ]; then
							 | 
						|
								      _err "OCSP was not requested but .ocsp file exists."
							 | 
						|
								      # Could remove the file at this step, although Lighttpd just ignores it in this case
							 | 
						|
								      # rm -f "${_ocsp}" || _err "Problem removing stale .ocsp file"
							 | 
						|
								    fi
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  # Reload Lighttpd
							 | 
						|
								  _debug _reload "${_reload}"
							 | 
						|
								  eval "${_reload}"
							 | 
						|
								  _ret=$?
							 | 
						|
								  if [ "${_ret}" != "0" ]; then
							 | 
						|
								    _err "Error code ${_ret} during reload"
							 | 
						|
								    return ${_ret}
							 | 
						|
								  else
							 | 
						|
								    _info "Reload successful"
							 | 
						|
								  fi
							 | 
						|
								
							 | 
						|
								  return 0
							 | 
						|
								}
							 |