The following script can be used to assist with SRU verification of the Certbot family of packages: `#!/bin/bash` {{{ # This script tests Certbot packages in proposed-updates repos on Ubuntu. You # can use the script to test the Certbot packages found in other repositories # by installing them manually and running this script with the environment # variable CERTBOT_PREINSTALLED=1. # # WARNING: It runs as root and makes many global modifications to the system it # is run on so it should only be run on a machine temporarily set up for # testing. set -eo pipefail cd ~ if test "$(id -u)" -ne "0"; then echo "Must run as root to install packages and use Docker." >&2 exit 1 fi apt-get update apt-get install docker.io gawk gcc git libffi-dev lsb-release net-tools psmisc python3-dev wget -y wget https://github.com/docker/compose/releases/download/1.15.0-rc1/docker-compose-Linux-x86_64 -O /usr/local/bin/docker-compose chmod +x /usr/local/bin/docker-compose # Add a replacement for coverage which is a tool used by upstream devs. This # dummy script is a noop unless asked to run Certbot. cat << EOF > /usr/local/bin/coverage #!/bin/bash -e if [ "\$1" != "run" ]; then exit 0 fi while [ "\$1" != "\$(command -v certbot)" ]; do shift 1 done "\$@" EOF chmod +x /usr/local/bin/coverage codename=$(lsb_release -a 2>/dev/null | grep Codename | cut -f2) if [ "$CERTBOT_PREINSTALLED" != 1 ]; then echo "deb http://archive.ubuntu.com/ubuntu/ $codename-proposed restricted main multiverse universe" > /etc/apt/sources.list.d/proposed.list echo "Package: *" > /etc/apt/preferences.d/proposed-updates echo "Pin: release a=$codename-proposed" >> /etc/apt/preferences.d/proposed-updates echo "Pin-Priority: 400" >> /etc/apt/preferences.d/proposed-updates apt-get update if [ "$codename" = "xenial" ]; then apt-get install -y \ certbot/$codename-proposed \ letsencrypt/$codename-proposed \ python-acme/$codename-proposed \ python-certbot-apache/$codename-proposed \ python-josepy/$codename-proposed \ python-letsencrypt-apache/$codename-proposed \ python-letsencrypt/$codename-proposed else apt-get install -y \ certbot/$codename-proposed \ letsencrypt/$codename-proposed \ python3-acme/$codename-proposed \ python3-certbot-apache/$codename-proposed \ python3-josepy/$codename-proposed fi fi service apache2 stop if ! certbot plugins | grep apache; then echo "Certbot can't find the Apache plugin!" >&2 exit 1 fi if [ "$codename" = "xenial" ]; then cat << EOF > shim_test.py import acme.jose from acme.jose import b64 as acme_b64 import certbot import certbot_apache import josepy from josepy import b64 as jose_b64 import letsencrypt import letsencrypt_apache assert acme.jose is josepy assert acme.jose.RS512 is josepy.RS512 assert acme.jose.b64 is josepy.b64 assert acme.jose.b64.b64decode is josepy.b64.b64decode assert acme_b64 is jose_b64 assert acme_b64.b64decode is jose_b64.b64decode assert letsencrypt is certbot assert letsencrypt_apache is certbot_apache EOF python shim_test.py else if [ "$CERTBOT_PREINSTALLED" != 1 ]; then apt-get install python3-certbot-nginx/$codename-proposed -y fi service nginx stop if ! certbot plugins | grep nginx; then echo "Certbot can't find the nginx plugin!" >&2 exit 1 fi fi if [ "$(realpath $(command -v letsencrypt))" != "$(command -v certbot)" ]; then echo "letsencrypt is not a symlink to Certbot!" >&2 exit 1 fi if ! grep '^max-log-backups = 0$' /etc/letsencrypt/cli.ini; then echo "Certbot's built in log rotation is not disabled!" >&2 exit 1 fi if ! systemctl is-enabled certbot.timer; then echo "Certbot's systemd timer is not enabled!" >&2 exit 1 fi if [ ! -f /etc/cron.d/certbot ]; then echo "Certbot's cron tab enteries weren't found!" >&2 exit 1 fi certbot_version=$(certbot --version 2>&1 | grep "^certbot" | cut -d " " -f 2) git clone https://github.com/certbot/certbot --branch v$certbot_version --depth 1 cd certbot # Is Certbot version 0.40.0 or greater? # # TODO: The actual version number to check here is older than 0.40.0, but this works for now if [ "0.40.0" = $(echo -e "$certbot_version\n0.40.0" | sort -V | head -n1) ]; then apt install python3-venv -y python3 -m venv venv . ./venv/bin/activate letsencrypt-auto-source/pieces/pipstrap.py tools/pip_install_editable.py certbot-ci python -m pytest certbot-ci/certbot_integration_tests -n 4 # Start pebble running locally for apache-conf-test run_acme_server >/dev/null 2>&1 & export SERVER='https://localhost:14000/dir' until curl -k "$SERVER" 2>/dev/null; do echo waiting for pebble to start sleep 1 done deactivate else export GOPATH=${GOPATH:-$HOME/gopath} export BOULDERPATH=${BOULDERPATH:-$GOPATH/src/github.com/letsencrypt/boulder} git clone --branch ${BOULDERBRANCH:-master} --depth=1 https://github.com/letsencrypt/boulder ${BOULDERPATH} cd "$BOULDERPATH" # Turn TLS-SNI-01 back on in boulder because Certbot's old test scripts test # support for TLS-SNI-01 as well as other challenge types. sed -i 's/tls-alpn-01/tls-sni-01/g' test/config/ra.json cd ~- # Newer versions of boulder don't let you use example.org sed -i 's/example.org/domain.org/g' tests/boulder-integration.sh # Accept either output from openssl about must staple extension sed -i "s/grep '1.3.6.1.5.5.7.1.24'/grep -E 'status_request|1\\\.3\\\.6\\\.1\\\.5\\\.5\\\.7\\\.1\\\.24\'/" tests/certbot-boulder-integration.sh # Give the nginx config a dummy cert and key to use to satisfy newer versions of nginx. sed -i "s/listen 5001 ssl;/listen 5001 ssl;\n ssl_certificate \/etc\/ssl\/certs\/ssl-cert-snakeoil.pem;\n ssl_certificate_key \/etc\/ssl\/private\/ssl-cert-snakeoil.key;/" certbot-nginx/tests/boulder-integration.conf.sh shutdown=true for acme_version in "v1" "v2" ; do set +e FETCH_OUTPUT=$(tests/boulder-fetch.sh) if [ "$?" != 0 ] && echo "$FETCH_OUTPUT" | grep -q 'timed out'; then until curl http://localhost:4000/directory 2>/dev/null; do echo waiting for boulder sleep 1 done fi set -e BOULDER_INTEGRATION="$acme_version" tests/boulder-integration.sh if ${shutdown}; then # Reset the server to reset rate limits cd "$BOULDERPATH" docker-compose down cd ~- # Leave the server running for apache-conf-test shutdown=false fi done # Set SERVER for apache-conf-test using boulder that was left running # above. export SERVER='http://localhost:4001/directory' fi # These tests make the assumption that Apache is not already listening on port # 443. sed -i 's/Listen 443/Listen 12345/g' /etc/apache2/ports.conf if ! certbot-apache/certbot_apache/tests/apache-conf-files/apache-conf-test --debian-modules; then echo "Apache tests failed!" >&2 exit 1 fi echo "Success!" echo "Package versions tested:" if [ "$codename" = "xenial" ]; then dpkg-query -W certbot letsencrypt python-josepy python-acme python-certbot python-certbot-apache python-letsencrypt python-letsencrypt-apache else dpkg-query -W certbot letsencrypt python3-josepy python3-acme python3-certbot python3-certbot-apache python3-certbot-nginx fi }}}