Pound + Letsencrypt para Play Framework y AWS CloudFront

Pound + Letsencrypt para Play Framework y AWS CloudFront

Fondo

Tengo una antigua aplicación web Play Framework que ofrece activos de dos CDN ( siteassetsy courseassets), que se implementan con AWS CloudFront.Librase ejecuta en la misma máquina virtual que la aplicación web y simplemente actúa como un punto final SSL porque la versión anterior de Play Framework utilizada no maneja SSL. Pound se vincula al puerto 80 y 443. La aplicación web Play se vincula al puerto 9000.

Anteriormente utilicé un certificado comodín SSL de Symantec para los activos CDN y la aplicación web. Ahora que a los certificados SSL de Symantec solo les quedan unos pocos días antes de que ya no sean válidos, he decidido usar AWS Certificate Manager para proporcionar certificados SSL de dominio único para las CDN y usar Letsencrypt para proporcionar un certificado SSL de dominio único para las CDN. Aplicación Web. Los certificados Letsencrypt sólo duran 90 días, por lo que deben actualizarse automáticamente.

Pound quiere certificados SSL en formato PEM, pero Letsencrypt no parece tener una manera conveniente de proporcionar un formato PEM. Letsencrypt no tiene ninguna disposición especial para Play Framework como lo hace para Apache httpd, Tomcat u otros frameworks conocidos.

No quiero desconectar la aplicación web para actualizar el certificado SSL utilizado por Pound.

Configuración de libra actual

A continuación se muestra mi /etc/pound/pound.cfgversión actual para Pound 2.7f-0ubuntu1. Esta configuración tiene algunos años y probablemente deba actualizarse, y Pound probablemente también debería actualizarse.

# Global options

User    "root"
Group   "root"

# Logging: (goes to syslog by default)
#  0  no logging
#  1  normal
#  2  extended
#  3  Apache-style (common log format)
#  4 (same as 3 but without the virtual host information)
#  5 (same as 4 but with information about the Service and BackEnd used)
LogLevel 5

# Check backend every X secs:
Alive    30

# Use hardware-accelleration card supported by openssl(1):
#SSLEngine  "<hw>"

# poundctl control socket
Control "/var/run/poundctl.socket"

# Redirect all http requests on port 80 to https on port 443
# The Play Framework webapp never sees these redirected requests because Pound handles them
ListenHTTP
  Address 0.0.0.0
  Port 80
  Err500 "/usr/local/etc/pound_error_500"
  Err503 "/usr/local/etc/pound_error_500"
  Service
    Redirect 301 "https://www.scalacourses.com"
  End
End

# Redirect all requests on port 443 to the Play Framework webapp on port 9443
ListenHTTPS
  Address 0.0.0.0
  Port 443
  Err500 "/usr/local/etc/pound_error_500"
  Err503 "/usr/local/etc/pound_error_500"
  Cert "/var/work/training/cadenza/conf/ssl/scalacourses.com.pound.pem"
  Disable SSLv3
  Ciphers "EECDH+ECDSA+AESGCM:EECDH+ECDSA+SHA384:EECDH+ECDSA+SHA256:ECDH+AESGCM:ECDH+AES256:ECDH+AES128:ECDH+3DES:RSA+AESGCM:RSA+AES:RSA+3DES:!eNULL:!LOW:!aNULL:!MD5:!DSS"
  SSLAllowClientRenegotiation     0
  SSLHonorCipherOrder 1
  HeadRemove "X-Forwarded-Proto"
  HeadRemove "x-forwarded-proto"
  AddHeader "x-forwarded-proto: https"
  Service
    BackEnd
      #HTTPS
      Address 127.0.0.1
      Port 9000
    End
  End
End

Preguntas

  1. La versión 0.17.0 del cliente certbot ACME se instaló mediante: sudo apt install certbot

    veo queversión certbot 0.21.0está disponible. ¿Debo usar esta versión más nueva en lugar de la predeterminada proporcionada por Ubuntu 17.10?

  2. ¿Existe una versión razonable de Pound disponible en un PPA de Debian? Anteriormente tenía que construir Pound yo mismo, pero preferiría usar una versión prediseñada.https://launchpad.net/ubuntu/+source/poundtiene la versión 2.7-1.3… ¿es esta la mejor versión estable?
  3. ¿Qué cambios se requieren en la configuración de Libra /etc/pound/pound.cfg? Claramente será necesario actualizar esta línea: Cert "/var/work/training/cadenza/conf/ssl/scalacourses.com.pound.pem"

    Es posible que sea necesario actualizar esta línea cuando se actualice Pound: Ciphers "EECDH+ECDSA+AESGCM:EECDH+ECDSA+SHA384:EECDH+ECDSA+SHA256:ECDH+AESGCM:ECDH+AES256:ECDH+AES128:ECDH+3DES:RSA+AESGCM:RSA+AES:RSA+3DES:!eNULL:!LOW:!aNULL:!MD5:!DSS"

    ¿Qué otras líneas podrían necesitar agregarse, eliminarse o modificarse? Sé que Pound no debería ejecutarse como root, pero eso se puede tratar por separado.

  4. Necesita una secuencia de comandos para aprovisionar inicialmente el certificado SSL Letsencrypt para Pound. Parece que elrobot certificadoEl programa utilizado por Letsencrypt quiere vincularse al puerto 80, pero Pound se vincula a este puerto y no quiero desactivar la aplicación web para actualizar el certificado SSL. ¿Hay alguna manera de ejecutarlo en la misma máquina virtual que Pound, o debería ejecutarlo en otra máquina virtual y copiar el certificado generado en formato PEM cuando esté listo?

  5. Necesita un script que pueda invocarse mediante cron cada 45 días para actualizar los certificados SSL.

Respuesta1

Configure un pequeño httpd (Nginx, Apache...) que escuche en localhost (127.0.0.1:80) y haga que el directorio [DOCUMENT_ROOT]/.well-known/acme-challenge/ pueda escribirse para el usuario que ejecuta esto. httpd. Que en la configuración de libra crear

Servicio "letsencrypt"
    HeadRequire "Host: .*"
    URL "/.well-known/acme-challenge/.*"
    back-end
        Dirección 127.0.0.1
        Puerto 80
    Fin
Fin

antes de todas las demás reglas. Ahora deberías poder hacer algo como

certbot-auto certonly --email [email protected] -d www.example.com -d example.com --verbose --agree-tos --webroot --webroot-path /var/www/localhost/htdocs/

Cambie "/var/www/localhost" a Document_root de su httpd local. Sólo tienes que hacerlo una vez. Y más adelante puedes hacer algo como

# add --dry-run to test it certbot-auto renew --post-hook "/etc/init.d/pound restart" for i in ls /etc/letsencrypt/live/; do cp /etc/letsencrypt/live/$i/privkey.pem /opt/pound_certs/$i.pem ; cat /etc/letsencrypt/live/$i/fullchain.pem >> /opt/pound_certs/$i.pem ; done

Y, por supuesto, no olvide agregar el archivo pem en la configuración de libra más adelante ;-) Sé que el post-hook llega tarde. Sin embargo, Letsencrypt emitirá nuevos certificados 10 días antes de que caduquen los antiguos. Entonces, si permites realizar un cronjob todos los días, no habrá ningún problema.

Respuesta2

  1. La versión actual de certbotfunciona bien, no es necesaria la última.
  2. Todavía no conozco una versión prediseñada de Pound a partir de fuentes recientes.
  3. Solo tuve que cambiar la Certlínea, lo cual tiene sentido porque (todavía) no he actualizado Pound.
  4. El script se puede ejecutar en cualquier máquina virtual porque no se vincula al puerto 80 ni al puerto 443 cuando se utiliza un desafío DNS.

A continuación se muestra certbot53un script que escribí para usar.jed/certbot-ruta53para autenticación mediante desafío DNS. Este script se basa en unrelaciones públicasque envié y certbot-route53que corrige dos errores.

#!/bin/bash

#STAGING=--staging
CERT_DIR=/etc/pound/certbot
DOMAIN=scalacourses.com
MAIL_ADDR='[email protected]'
SCRIPT_NAME=certbot-route53.sh

if [ ! -d "$CERT_DIR/letsencrypt" ]; then sudo mkdir -p $CERT_DIR/letsencrypt; fi
sudo chmod 777 "$CERT_DIR/letsencrypt"

cd $CERT_DIR

if [ ! -f "$CERT_DIR/$SCRIPT_NAME" ]; then
  sudo curl -sL https://git.io/vylLx -o $SCRIPT_NAME
  sudo chmod a+x certbot-route53.sh
fi

./$SCRIPT_NAME \
  --agree-tos \
  --manual-public-ip-logging-ok \
  --domains $DOMAIN,www.$DOMAIN \
  --renew-by-default \
  --email $MAIL_ADDR $STAGING

PRIV_KEY="$CERT_DIR/letsencrypt/live/$DOMAIN/privkey.pem"
FULL_CHAIN="$CERT_DIR/letsencrypt/live/$DOMAIN/fullchain.pem"
COMBINED="$CERT_DIR/combined-for-pound.pem"
cat "$PRIV_KEY" "$FULL_CHAIN" | sudo tee "$COMBINED" > /dev/null
  1. Actualmente estoy volviendo a ejecutar el mismo script mediante un trabajo cron. Esto significa que no estoy actualizando los certificados, sino que los estoy reemplazando. No está claro cuál podría ser el beneficio de actualizar un certificado. Aquí está la cronentrada, que ejecuta el script como mi ID de usuario cada 2 meses; Ingresé esto después de escribir sudo crontab -e:

    0 0 1 */2 * su mslinn /usr/local/bin/certbot53
    

información relacionada