Normally you need to renew your lets encrypt certificates every third month, so I'd suggest you use a cron job for that. That would be two commands, renew and then reload the web server to make sure it has the most recent certificates at hand.
With haproxy however you'd need to combine fullchain and the key, so let's make a script to automate the process. Here's what I'm using:
# Create cert directories
sudo mkdir -p /etc/certs
sudo chmod -R 777 /etc/certs
# Copy fullchain and private key for all ceritifactes on server
for cert in `sudo find /etc/letsencrypt/live/ -type d`
if [[ $cert == *"."* ]]; then
sudo cat $cert/fullchain.pem $cert/privkey.pem > /etc/certs/$domain.pem
echo "generating: $cert"
# Update permissions
sudo chmod -R 644 /etc/certs
sudo chown -R root:root /etc/certs
# Reload haproxy to apply updates
sudo systemctl reload haproxy
This is called from a cron job, after running
certbot --renew. First I create a new folder,
/etc/certs, I temporary give it full permissions just to work in peace. Then I look for certificates in
/etc/letsencrypt/live which is where the latest version of all available certificates on the server is located. Then I copy
privkey.pem into a new file named after the domain and put it in the new folder
/etc/certs. Last I change the permissions of that folder and reload
Now, all you need to do is to enable SNI in
haproxy configuration, look for your web server front end block and add the line below. That will look for a cert matching the domain name and hence work in a multi domain setup with virtual hosts as well. SNI where historically considered as bad practice, but with more and more shared hosting it's now considered as acceptable, and even common.
Additional lines below enables http2, and set the min TLS version to 1.2. This will increase your security and speed up your site but probably lock out 1% of your visitors who doesn't use modern and up to date browsers.
bind 0.0.0.0:443 ssl crt /etc/certs/ alpn h2,http/1.1 ssl-min-ver TLSv1.2