Certbot doesn't understand my Apache httpd vhost

My domain is: www.reppep.com

I ran this command: certbot -d www.reppep.com

It produced this output:
Saving debug log to /var/log/letsencrypt/letsencrypt.log
Certificate not yet due for renewal

You have an existing certificate that has exactly the same domains or certificate name you requested and isn't close to expiry.
(ref: /etc/letsencrypt/renewal/www.reppep.com.conf)

What would you like to do?


1: Attempt to reinstall this existing certificate
2: Renew & replace the certificate (may be subject to CA rate limits)


Select the appropriate number [1-2] then [enter] (press 'c' to cancel): 1
Deploying certificate
Successfully deployed certificate for www.reppep.com to /etc/httpd/conf.d/www.reppep.com.conf
Failed redirect for www.reppep.com
Unable to set the redirect enhancement for www.reppep.com.

NEXT STEPS:

  • The certificate was saved, but could not be installed (installer: apache). After fixing the error shown below, try installing it again by running:
    certbot install --cert-name www.reppep.com

Unable to find corresponding HTTP vhost; Unable to create one as intended addresses conflict; Current configuration does not support automated redirection
Ask for help or search for solutions at https://community.letsencrypt.org. See the logfile /var/log/letsencrypt/letsencrypt.log or re-run Certbot with -v for more details.

My web server is (include version): Apache httpd-2.4.57-11.el9_4.1.x86_64

The operating system my web server runs on is (include version): Rocky Linux 9.4

My hosting provider, if applicable, is: Linode

I can login to a root shell on my machine (yes or no, or I don't know): yes

I'm using a control panel to manage my site (no, or provide the name and version of the control panel): no

The version of my client is (e.g. output of certbot --version or certbot-auto --version if you're using Certbot): certbot 2.11.0

Is there a specification for what certbot requires or needs in vhost files to work properly? Should I ask the certbot people instead of here?

This webserver has many valid domain names. Pre-production it was rocky.reppep.com. Now it's www.reppep.com. I had a certbot cert for www.reppep.com, but after a recent update and reboot, it reverted to a rocky cert. I had several vhost files for www & rocky vhosts, but consolidated down to one while trying to fix this issue. Here's the relevant snippet:

[root@rocky ~]# cat /etc/httpd/conf.d/www.reppep.com.conf

# This vhost only redirects to HTTPS
<VirtualHost *:80>
	ServerName www.reppep.com
	ServerAlias www rocky rocky.reppep.com img.reppep.com img.chrispepper.com
	UseCanonicalName on
#	RedirectPermanent / https://rocky.reppep.com/
#	RedirectPermanent / https://www.reppep.com/

	CustomLog "|/usr/sbin/cronolog /var/log/httpd/%Y/%Y-%m-www-access_log" combined
	RewriteEngine on
	RewriteCond %{SERVER_NAME} =img.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =img.chrispepper.com [OR]
	RewriteCond %{SERVER_NAME} =rocky.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =www.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =www [OR]
	RewriteCond %{SERVER_NAME} =rocky
	RewriteRule ^ https://www.reppep.com%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>

####

<IfModule mod_ssl.c>
	<VirtualHost *:443>
		ServerName www.reppep.com
#		ServerAlias www rocky rocky.reppep.com img.reppep.com
#		Redirect / https://your-server-hostname/
#		RedirectPermanent / https://rocky.reppep.com/
#		RedirectPermanent / https://www.reppep.com/

		Include    /etc/letsencrypt/options-ssl-apache.conf
		SSLCertificateFile /etc/letsencrypt/live/www.reppep.com/fullchain.pem
		SSLCertificateKeyFile /etc/letsencrypt/live/www.reppep.com/privkey.pem
	</VirtualHost>
</IfModule>

UseCanonicalName on

...

[root@rocky ~]# certbot -d www.reppep.com
Saving debug log to /var/log/letsencrypt/letsencrypt.log
Certificate not yet due for renewal

You have an existing certificate that has exactly the same domains or certificate name you requested and isn't close to expiry.
(ref: /etc/letsencrypt/renewal/www.reppep.com.conf)

What would you like to do?


1: Attempt to reinstall this existing certificate
2: Renew & replace the certificate (may be subject to CA rate limits)


Select the appropriate number [1-2] then [enter] (press 'c' to cancel): 1
Deploying certificate
Successfully deployed certificate for www.reppep.com to /etc/httpd/conf.d/www.reppep.com.conf
Failed redirect for www.reppep.com
Unable to set the redirect enhancement for www.reppep.com.

NEXT STEPS:

  • The certificate was saved, but could not be installed (installer: apache). After fixing the error shown below, try installing it again by running:
    certbot install --cert-name www.reppep.com

Unable to find corresponding HTTP vhost; Unable to create one as intended addresses conflict; Current configuration does not support automated redirection
Ask for help or search for solutions at https://community.letsencrypt.org. See the logfile /var/log/letsencrypt/letsencrypt.log or re-run Certbot with -v for more details.

[root@rocky ~]# certbot install --cert-name www.reppep.com
Saving debug log to /var/log/letsencrypt/letsencrypt.log
Deploying certificate
Successfully deployed certificate for www.reppep.com to /etc/httpd/conf.d/www.reppep.com.conf
Failed redirect for www.reppep.com
Unable to set the redirect enhancement for www.reppep.com.
Unable to find corresponding HTTP vhost; Unable to create one as intended addresses conflict; Current configuration does not support automated redirection
Ask for help or search for solutions at https://community.letsencrypt.org. See the logfile /var/log/letsencrypt/letsencrypt.log or re-run Certbot with -v for more details.

Please show:
sudo apachectl -t -D DUMP_VHOSTS
sudo httpd -t -D DUMP_VHOSTS

The Rocky Linux RPMs I'm using contain their deficient replacement for apachectl.

[root@rocky ~]# apachectl -t -D DUMP_VHOSTS
Passing arguments to httpd using apachectl is no longer supported.
You can only start/stop/restart httpd using this script.
To pass extra arguments to httpd, see the httpd.service(8)
man page.
[root@rocky ~]# httpd -t -D DUMP_VHOSTS

VirtualHost configuration:
*:443                  is a NameVirtualHost
         default server www.reppep.com (/etc/httpd/conf.d/ssl.conf:40)
         port 443 namevhost www.reppep.com (/etc/httpd/conf.d/ssl.conf:40)
         port 443 namevhost www.reppep.com (/etc/httpd/conf.d/www.reppep.com.conf:23)
*:80                   is a NameVirtualHost
         default server www.reppep.com (/etc/httpd/conf.d/www.reppep.com.conf:2)
         port 80 namevhost www.reppep.com (/etc/httpd/conf.d/www.reppep.com.conf:2)
                 alias www
                 alias rocky
                 alias rocky.reppep.com
                 alias img.reppep.com
                 alias img.chrispepper.com
         port 80 namevhost www.davemak.com (/etc/httpd/conf.d/vhost.d/davemak.com.conf:1)
                 alias davemak.com
                 alias www.davemak.org
                 alias davemak.org
         port 80 namevhost www.jamesjgerber.com (/etc/httpd/conf.d/vhost.d/jamesjgerber.com.conf:1)
                 alias jamesjgerber.com
                 alias www.jamesgerber.com
                 alias jamesgerber.com
         port 80 namevhost julia.reppep.com (/etc/httpd/conf.d/vhost.d/julia.conf:1)
                 alias julia
         port 80 namevhost molly.reppep.com (/etc/httpd/conf.d/vhost.d/molly.conf:1)
                 alias molly

[root@rocky ~]#

I am not sure why Certbot fails to find a port 80 VirtualHost for this name.

But, you have duplicate domain name:port for port 443. HTTPS requests to that domain are getting a faulty cert chain that includes a self-signed cert.

Apache starts up even with this kind of overlap but it causes lots of problems.

Would you show the contents of those two config files?

Thank you very much. I didn't notice that. I moved the 80-to-443 redirect into another file, and the rest of www.reppep.com.conf to the end of ssl.conf. I moved the old www.reppep.com.conf file into a subdirectory where it will not load.

It looks like certbot is putting new certs into my port 80 redirect file, but not updating paths in ssl.conf.

[root@rocky conf.d]# apachectl configtest
Syntax OK
[root@rocky conf.d]# apachectl restart
[root@rocky conf.d]# ls
autoindex.conf README ssl.conf vhost.d www.reppep.com.80.conf
DISABLED rename.DIS userdir.conf welcome.conf

[root@rocky conf.d]# cat www.reppep.com.80.conf

# This vhost only redirects to HTTPS
<VirtualHost *:80>
	ServerName www.reppep.com
	ServerAlias www rocky rocky.reppep.com img.reppep.com img.chrispepper.com
	UseCanonicalName on
#	RedirectPermanent / https://rocky.reppep.com/
#	RedirectPermanent / https://www.reppep.com/

	CustomLog "|/usr/sbin/cronolog /var/log/httpd/%Y/%Y-%m-www-access_log" combined
	RewriteEngine on
	RewriteCond %{SERVER_NAME} =img.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =img.chrispepper.com [OR]
	RewriteCond %{SERVER_NAME} =rocky.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =www.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =www [OR]
	RewriteCond %{SERVER_NAME} =rocky
	RewriteRule ^ https://www.reppep.com%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>

[root@rocky conf.d]# cat ssl.conf

#
# When we also provide SSL we have to listen to the 
# standard HTTPS port in addition.
#
Listen 443 https

##
##  SSL Global Context
##
##  All SSL configuration in this context applies both to
##  the main server and all SSL-enabled virtual hosts.
##

#   Pass Phrase Dialog:
#   Configure the pass phrase gathering process.
#   The filtering dialog program (`builtin' is a internal
#   terminal dialog) has to provide the pass phrase on stdout.
SSLPassPhraseDialog exec:/usr/libexec/httpd-ssl-pass-dialog

#   Inter-Process Session Cache:
#   Configure the SSL Session Cache: First the mechanism 
#   to use and second the expiring timeout (in seconds).
SSLSessionCache         shmcb:/run/httpd/sslcache(512000)
SSLSessionCacheTimeout  300

#
# Use "SSLCryptoDevice" to enable any supported hardware
# accelerators. Use "openssl engine -v" to list supported
# engine names.  NOTE: If you enable an accelerator and the
# server does not start, consult the error logs and ensure
# your accelerator is functioning properly. 
#
SSLCryptoDevice builtin
#SSLCryptoDevice ubsec

##
## SSL Virtual Host Context
##

<VirtualHost _default_:443>

# General setup for the virtual host, inherited from global configuration
#DocumentRoot "/var/www/html"
#ServerName www.example.com:443

# Use separate log files for the SSL virtual host; note that LogLevel
# is not inherited from httpd.conf.
#ErrorLog logs/ssl_error_log
#TransferLog logs/ssl_access_log
LogLevel warn

#   SSL Engine Switch:
#   Enable/Disable SSL for this virtual host.
SSLEngine on

#   List the protocol versions which clients are allowed to connect with.
#   The OpenSSL system profile is used by default.  See
#   update-crypto-policies(8) for more details.
#SSLProtocol all -SSLv3
#SSLProxyProtocol all -SSLv3

#   User agents such as web browsers are not configured for the user's
#   own preference of either security or performance, therefore this
#   must be the prerogative of the web server administrator who manages
#   cpu load versus confidentiality, so enforce the server's cipher order.
SSLHonorCipherOrder on

#   SSL Cipher Suite:
#   List the ciphers that the client is permitted to negotiate.
#   See the mod_ssl documentation for a complete list.
#   The OpenSSL system profile is configured by default.  See
#   update-crypto-policies(8) for more details.
SSLCipherSuite PROFILE=SYSTEM
SSLProxyCipherSuite PROFILE=SYSTEM

#   Point SSLCertificateFile at a PEM encoded certificate.  If
#   the certificate is encrypted, then you will be prompted for a
#   pass phrase.  Note that restarting httpd will prompt again.  Keep
#   in mind that if you have both an RSA and a DSA certificate you
#   can configure both in parallel (to also allow the use of DSA
#   ciphers, etc.)
#   Some ECC cipher suites (http://www.ietf.org/rfc/rfc4492.txt)
#   require an ECC certificate which can also be configured in
#   parallel.
SSLCertificateFile /etc/pki/tls/certs/localhost.crt

#   Server Private Key:
#   If the key is not combined with the certificate, use this
#   directive to point at the key file.  Keep in mind that if
#   you've both a RSA and a DSA private key you can configure
#   both in parallel (to also allow the use of DSA ciphers, etc.)
#   ECC keys, when in use, can also be configured in parallel
SSLCertificateKeyFile /etc/pki/tls/private/localhost.key

#   Server Certificate Chain:
#   Point SSLCertificateChainFile at a file containing the
#   concatenation of PEM encoded CA certificates which form the
#   certificate chain for the server certificate. Alternatively
#   the referenced file can be the same as SSLCertificateFile
#   when the CA certificates are directly appended to the server
#   certificate for convenience.
#SSLCertificateChainFile /etc/pki/tls/certs/server-chain.crt

#   Certificate Authority (CA):
#   Set the CA certificate verification path where to find CA
#   certificates for client authentication or alternatively one
#   huge file containing all of them (file must be PEM encoded)
#SSLCACertificateFile /etc/pki/tls/certs/ca-bundle.crt

#   Client Authentication (Type):
#   Client certificate verification type and depth.  Types are
#   none, optional, require and optional_no_ca.  Depth is a
#   number which specifies how deeply to verify the certificate
#   issuer chain before deciding the certificate is not valid.
#SSLVerifyClient require
#SSLVerifyDepth  10

#   Access Control:
#   With SSLRequire you can do per-directory access control based
#   on arbitrary complex boolean expressions containing server
#   variable checks and other lookup directives.  The syntax is a
#   mixture between C and Perl.  See the mod_ssl documentation
#   for more details.
#<Location />
#SSLRequire (    %{SSL_CIPHER} !~ m/^(EXP|NULL)/ \
#            and %{SSL_CLIENT_S_DN_O} eq "Snake Oil, Ltd." \
#            and %{SSL_CLIENT_S_DN_OU} in {"Staff", "CA", "Dev"} \
#            and %{TIME_WDAY} >= 1 and %{TIME_WDAY} <= 5 \
#            and %{TIME_HOUR} >= 8 and %{TIME_HOUR} <= 20       ) \
#           or %{REMOTE_ADDR} =~ m/^192\.76\.162\.[0-9]+$/
#</Location>

#   SSL Engine Options:
#   Set various options for the SSL engine.
#   o FakeBasicAuth:
#     Translate the client X.509 into a Basic Authorisation.  This means that
#     the standard Auth/DBMAuth methods can be used for access control.  The
#     user name is the `one line' version of the client's X.509 certificate.
#     Note that no password is obtained from the user. Every entry in the user
#     file needs this password: `xxj31ZMTZzkVA'.
#   o ExportCertData:
#     This exports two additional environment variables: SSL_CLIENT_CERT and
#     SSL_SERVER_CERT. These contain the PEM-encoded certificates of the
#     server (always existing) and the client (only existing when client
#     authentication is used). This can be used to import the certificates
#     into CGI scripts.
#   o StdEnvVars:
#     This exports the standard SSL/TLS related `SSL_*' environment variables.
#     Per default this exportation is switched off for performance reasons,
#     because the extraction step is an expensive operation and is usually
#     useless for serving static content. So one usually enables the
#     exportation for CGI and SSI requests only.
#   o StrictRequire:
#     This denies access when "SSLRequireSSL" or "SSLRequire" applied even
#     under a "Satisfy any" situation, i.e. when it applies access is denied
#     and no other module can change it.
#   o OptRenegotiate:
#     This enables optimized SSL connection renegotiation handling when SSL
#     directives are used in per-directory context. 
#SSLOptions +FakeBasicAuth +ExportCertData +StrictRequire
<FilesMatch "\.(cgi|shtml|phtml|php)$">
    SSLOptions +StdEnvVars
</FilesMatch>
<Directory "/var/www/cgi-bin">
    SSLOptions +StdEnvVars
</Directory>

#   SSL Protocol Adjustments:
#   The safe and default but still SSL/TLS standard compliant shutdown
#   approach is that mod_ssl sends the close notify alert but doesn't wait for
#   the close notify alert from client. When you need a different shutdown
#   approach you can use one of the following variables:
#   o ssl-unclean-shutdown:
#     This forces an unclean shutdown when the connection is closed, i.e. no
#     SSL close notify alert is sent or allowed to be received.  This violates
#     the SSL/TLS standard but is needed for some brain-dead browsers. Use
#     this when you receive I/O errors because of the standard approach where
#     mod_ssl sends the close notify alert.
#   o ssl-accurate-shutdown:
#     This forces an accurate shutdown when the connection is closed, i.e. a
#     SSL close notify alert is sent and mod_ssl waits for the close notify
#     alert of the client. This is 100% SSL/TLS standard compliant, but in
#     practice often causes hanging connections with brain-dead browsers. Use
#     this only for browsers where you know that their SSL implementation
#     works correctly. 
#   Notice: Most problems of broken clients are also related to the HTTP
#   keep-alive facility, so you usually additionally want to disable
#   keep-alive for those clients, too. Use variable "nokeepalive" for this.
#   Similarly, one has to force some clients to use HTTP/1.0 to workaround
#   their broken HTTP/1.1 implementation. Use variables "downgrade-1.0" and
#   "force-response-1.0" for this.
BrowserMatch "MSIE [2-5]" \
         nokeepalive ssl-unclean-shutdown \
         downgrade-1.0 force-response-1.0

#   Per-Server Logging:
#   The home of a custom SSL log file. Use this when you want a
#   compact non-error SSL logfile on a virtual host basis.
CustomLog logs/ssl_request_log \
          "%t %h %{SSL_PROTOCOL}x %{SSL_CIPHER}x \"%r\" %b"

</VirtualHost>


CustomLog    "|/usr/sbin/cronolog /var/log/httpd/%Y/%Y-%m-ssl-access_log" combined
#TransferLog "|/usr/sbin/cronolog /var/log/httpd/%Y/%Y-%m-ssl_access_log"
ErrorLog     "|/usr/sbin/cronolog /var/log/httpd/%Y/%Y-%m-ssl_error_log"

#Listen 0.0.0.0:443 https
<FilesMatch "\.(cgi|shtml|phtml|php)$">
	SSLOptions +StdEnvVars
</FilesMatch>

DirectoryIndex index.shtml index.html index.htm

DocumentRoot "/home/web/www.reppep.com/"
<Directory   "/home/web/www.reppep.com/">
	Options All +Indexes -Includes +MultiViews
#	AllowOverride None +ExecCGI
</Directory>

AddType text/html .pl
AddType text/html .text
AddHandler markdown .text
Action markdown /cgi-bin/Markdown.cgi
ScriptAlias /cgi-bin/ /home/web/www.reppep.com/cgi-bin/

<Location /server-status>
	SetHandler server-status
	Order deny,allow
	Deny from all
	Allow from 127.0.0.1
</Location>
<Location /server-info>
	SetHandler server-info
	Order deny,allow
	Deny from all
	Allow from 127.0.0.1
</Location>

RedirectPermanent /chris         https://www.reppep.com/~pepper
RedirectPermanent /pepper        https://www.reppep.com/~pepper
RedirectPermanent /pepper/album  https://www.reppep.com/~pepper/album
RedirectPermanent /pepper/video  https://www.reppep.com/~pepper/video
RedirectPermanent /julia/gallery https://www.reppep.com/img/julia/gallery
RedirectPermanent /julia/preblog https://www.reppep.com/img/julia/preblog

Alias /img/julia /img/julia
<Directory /img/julia>
	Options All +Indexes +Includes +MultiViews
	AuthType Digest
	AuthName Julia
	AuthUserFile /home/web/htdigest
	Require user julia
</Directory>

[root@rocky conf.d]# certbot -d www.reppep.com
Saving debug log to /var/log/letsencrypt/letsencrypt.log
Certificate not yet due for renewal

You have an existing certificate that has exactly the same domains or certificate name you requested and isn't close to expiry.
(ref: /etc/letsencrypt/renewal/www.reppep.com.conf)

What would you like to do?


1: Attempt to reinstall this existing certificate
2: Renew & replace the certificate (may be subject to CA rate limits)


Select the appropriate number [1-2] then [enter] (press 'c' to cancel): 1
Deploying certificate
Some rewrite rules copied from /etc/httpd/conf.d/www.reppep.com.80.conf were disabled in the vhost for your HTTPS site located at /etc/httpd/conf.d/www.reppep.com.80-le-ssl.conf because they have the potential to create redirection loops.
Successfully deployed certificate for www.reppep.com to /etc/httpd/conf.d/www.reppep.com.80-le-ssl.conf
Added an HTTP->HTTPS rewrite in addition to other RewriteRules; you may wish to check for overall consistency.
Congratulations! You have successfully enabled HTTPS on https://www.reppep.com


If you like Certbot, please consider supporting our work by:


[root@rocky conf.d]# ls
autoindex.conf ssl.conf www.reppep.com.80.conf
DISABLED userdir.conf www.reppep.com.80-le-ssl.conf
README vhost.d
rename.DIS welcome.conf

[root@rocky conf.d]# cat www.reppep.com.80.conf

# This vhost only redirects to HTTPS
<VirtualHost *:80>
	ServerName www.reppep.com
	ServerAlias www rocky rocky.reppep.com img.reppep.com img.chrispepper.com
	UseCanonicalName on
#	RedirectPermanent / https://rocky.reppep.com/
#	RedirectPermanent / https://www.reppep.com/

	CustomLog "|/usr/sbin/cronolog /var/log/httpd/%Y/%Y-%m-www-access_log" combined
	RewriteEngine on
	RewriteCond %{SERVER_NAME} =img.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =img.chrispepper.com [OR]
	RewriteCond %{SERVER_NAME} =rocky.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =www.reppep.com [OR]
	RewriteCond %{SERVER_NAME} =www [OR]
	RewriteCond %{SERVER_NAME} =rocky
	RewriteRule ^ https://www.reppep.com%{REQUEST_URI} [END,NE,R=permanent]
RewriteCond %{SERVER_NAME} =www [OR]
RewriteCond %{SERVER_NAME} =www.reppep.com [OR]
RewriteCond %{SERVER_NAME} =rocky [OR]
RewriteCond %{SERVER_NAME} =rocky.reppep.com [OR]
RewriteCond %{SERVER_NAME} =img.chrispepper.com [OR]
RewriteCond %{SERVER_NAME} =img.reppep.com
RewriteRule ^ https://%{SERVER_NAME}%{REQUEST_URI} [END,NE,R=permanent]
</VirtualHost>
[root@rocky conf.d]# cat www.reppep.com.80-le-ssl.conf 
<IfModule mod_ssl.c>
<VirtualHost *:443>
	ServerName www.reppep.com
	ServerAlias www rocky rocky.reppep.com img.reppep.com img.chrispepper.com
	UseCanonicalName on
#	RedirectPermanent / https://rocky.reppep.com/
#	RedirectPermanent / https://www.reppep.com/

	CustomLog "|/usr/sbin/cronolog /var/log/httpd/%Y/%Y-%m-www-access_log" combined
	RewriteEngine on
# Some rewrite rules in this file were disabled on your HTTPS site,
# because they have the potential to create redirection loops.

# 	RewriteCond %{SERVER_NAME} =img.reppep.com [OR]
# 	RewriteCond %{SERVER_NAME} =img.chrispepper.com [OR]
# 	RewriteCond %{SERVER_NAME} =rocky.reppep.com [OR]
# 	RewriteCond %{SERVER_NAME} =www.reppep.com [OR]
# 	RewriteCond %{SERVER_NAME} =www [OR]
# 	RewriteCond %{SERVER_NAME} =rocky
# 	RewriteRule ^ https://www.reppep.com%{REQUEST_URI} [END,NE,R=permanent]

SSLCertificateFile /etc/letsencrypt/live/www.reppep.com/fullchain.pem
SSLCertificateKeyFile /etc/letsencrypt/live/www.reppep.com/privkey.pem
Include /etc/letsencrypt/options-ssl-apache.conf
</VirtualHost>
</IfModule>

[root@rocky conf.d]# apachectl restart
[root@rocky conf.d]# certbot certificates
Saving debug log to /var/log/letsencrypt/letsencrypt.log


Found the following certs:
Certificate Name: www.reppep.com
Serial Number: 336e65ed14fabc46be8139c22681a100077
Key Type: ECDSA
Domains: www.reppep.com
Expiry Date: 2024-12-13 22:35:58+00:00 (VALID: 50 days)
Certificate Path: /etc/letsencrypt/live/www.reppep.com/fullchain.pem
Private Key Path: /etc/letsencrypt/live/www.reppep.com/privkey.pem


[root@rocky conf.d]# more /etc/letsencrypt/options-ssl-apache.conf

# This file contains important security parameters. If you modify this file
# manually, Certbot will be unable to automatically provide future security
# updates. Instead, Certbot will print and log an error message with a path to
# the up-to-date file that you will need to refer to when manually updating
# this file. Contents are based on https://ssl-config.mozilla.org

SSLEngine on

# Intermediate configuration, tweak to your needs
SSLProtocol             all -SSLv2 -SSLv3 -TLSv1 -TLSv1.1
SSLCipherSuite          ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA25
6:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-ECDSA-CHACHA20
-POLY1305:ECDHE-RSA-CHACHA20-POLY1305:DHE-RSA-AES128-GCM-SHA256:DHE-RSA-AES256-G
CM-SHA384
SSLHonorCipherOrder     off
SSLSessionTickets       off

SSLOptions +StrictRequire

# Add vhost name to log entries:
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-agent}i\"" vhost_c
ombined
LogFormat "%v %h %l %u %t \"%r\" %>s %b" vhost_common
[root@rocky conf.d]# grep Cert ssl.conf 
#   Point SSLCertificateFile at a PEM encoded certificate.  If
SSLCertificateFile /etc/pki/tls/certs/localhost.crt
SSLCertificateKeyFile /etc/pki/tls/private/localhost.key
#   Server Certificate Chain:
#   Point SSLCertificateChainFile at a file containing the
#   the referenced file can be the same as SSLCertificateFile
#SSLCertificateChainFile /etc/pki/tls/certs/server-chain.crt
#   Certificate Authority (CA):
#SSLCACertificateFile /etc/pki/tls/certs/ca-bundle.crt
#   o ExportCertData:
#SSLOptions +FakeBasicAuth +ExportCertData +StrictRequire

[root@rocky conf.d]#

Ah. So the conflict is because pre-certbot, I defined a vhost for www.reppep.com on port 80 in www.reppep.com.80.conf, and ssl.conf contained a vhost for www.reppep.com on port 443. certbot copied my port-80 vhost and changed it to a port-443 vhost, which then conflicted with the one in ssl.conf.

ssl.conf has no servername:

So, it defaults to whatever was defined in the main config file.
[which should NOT have been defined as an FQDN that would be served within a vhost]

I'm not sure what your bracketed comment means, but ServerName www.reppep.com is set in several places, including httpd.conf.

[root@rocky conf.d]# grep -i servername ../conf/*
../conf/httpd.conf:# **ServerName** gives the name and port that the server uses to identify itself.
../conf/httpd.conf:#**ServerName** www.example.com:80
../conf/httpd.conf:**ServerName** www.reppep.com
[root@rocky conf.d]# grep -i servername *.conf
ssl.conf:#**ServerName** www.example.com:443
www.reppep.com.80.conf: **ServerName** www.reppep.com
www.reppep.com.80-le-ssl.conf: **ServerName** www.reppep.com

And it should NOT be there [httpd.conf].
Not when you plan on serving that name within a vhost.

I've done it that way for a very long time, but I defer to you as the certbot expert. I commented it out in httpd.conf.

[root@rocky conf.d]# grep -Ri servername /etc/httpd/*/*.conf
/etc/httpd/conf.d/ssl.conf:#ServerName www.example.com:443
/etc/httpd/conf.d/www.reppep.com.80.conf:	ServerName www.reppep.com
/etc/httpd/conf.d/www.reppep.com.80-le-ssl.conf:	ServerName www.reppep.com
/etc/httpd/conf/httpd.conf:# ServerName gives the name and port that the server uses to identify itself.
/etc/httpd/conf/httpd.conf:#ServerName www.example.com:80
/etc/httpd/conf/httpd.conf:#ServerName www.reppep.com

The hostname is rocky, which I'd like to leave but am considering changing. It looks like httpd is picking it up, and I may change it to www.reppep.com to avoid that.

[root@rocky conf.d]# httpd -t -D DUMP_VHOSTS
AH00558: httpd: Could not reliably determine the server's fully qualified domain name, using rocky.reppep.com. Set the 'ServerName' directive globally to suppress this message
VirtualHost configuration:
*:443                  is a NameVirtualHost
         default server rocky.reppep.com (/etc/httpd/conf.d/ssl.conf:40)
         port 443 namevhost rocky.reppep.com (/etc/httpd/conf.d/ssl.conf:40)
         port 443 namevhost www.reppep.com (/etc/httpd/conf.d/www.reppep.com.80-le-ssl.conf:2)
                 alias www
                 alias rocky
                 alias rocky.reppep.com
                 alias img.reppep.com
                 alias img.chrispepper.com
*:80                   is a NameVirtualHost
         default server www.reppep.com (/etc/httpd/conf.d/www.reppep.com.80.conf:2)
         port 80 namevhost www.reppep.com (/etc/httpd/conf.d/www.reppep.com.80.conf:2)
                 alias www
                 alias rocky
                 alias rocky.reppep.com
                 alias img.reppep.com
                 alias img.chrispepper.com
         port 80 namevhost www.davemak.com (/etc/httpd/conf.d/vhost.d/davemak.com.conf:1)
                 alias davemak.com
                 alias www.davemak.org
                 alias davemak.org
         port 80 namevhost www.jamesjgerber.com (/etc/httpd/conf.d/vhost.d/jamesjgerber.com.conf:1)
                 alias jamesjgerber.com
                 alias www.jamesgerber.com
                 alias jamesgerber.com
         port 80 namevhost julia.reppep.com (/etc/httpd/conf.d/vhost.d/julia.conf:1)
                 alias julia
         port 80 namevhost molly.reppep.com (/etc/httpd/conf.d/vhost.d/molly.conf:1)
                 alias molly
[root@rocky conf.d]# hostname
rocky.reppep.com
[root@rocky conf.d]# head -40 /etc/httpd/conf.d/ssl.conf | tail -1
<VirtualHost _default_:443>

The easiest way is to make sure all of your VirtualHost have a ServerName (and optionally ServerAlias).

Then you are not relying on Apache using the default hostname.

And make sure each VirtualHost is for a unique set of server names and port

Looks like you still have overlap with rocky.reppap.com. If you don't want that Virtualhost in your ssl.conf to process incoming requests just add a ServerName for something like "mydefault.com" or other nonsense.

Thanks. I think that's just the default, and it should never actually be user visible. After a restart my cert is working again, so I'm good for now. I may well be back next time I need to invoke certbot, though...

Thank you both, very much!

You should give it a name.
But not a name that would be served by any vhost [served now, nor in the future].
I suggest something more functionally descriptive - like: rack04server03.reppep.com

Call it what it is - not what it does [or will do].

You could try this anytime. It checks the renew process without disrupting existing production certs or Apache

sudo certbot renew --dry-run