Hello, I need assistance with accessing client certificates from a servlet. This is not a servlet code question but a configuration question. The call to: request.getAttribute("javax.servlet.request.X509Certificate");
is not returning any certificates. The last time that I needed to do this was Tomcat 7 and a lot has changed. When connecting with a browser, a trusted connection is established. Javax.net.debug output shows my client certificate and a complete chain have been accepted. I have also limited the TLS version to TSSv1.2. What have I missed? Thanks, Chris Evans OS: Ubuntu 22-04 Tomcat Version: 10.1.36 TLS Logging: env | grep OPT CATALINA_OPTS=-Djavax.net.debug=ssl,handshake Connector Configuration: <Connector port="8443" protocol="org.apache.coyote.http11.Http11Nio2Protocol" sslImplementationName="org.apache.tomcat.util.net.jsse.JSSEImplementation" maxParameterCount="1000" scheme="https" xmlValidation="true" maxThreads="150" SSLEnabled="true" secure="true" > <SSLHostConfig certificateVerificationDepth="4" truststoreFile="/home/ubuntu/tomcat/-REDACTED-.jks" truststorePassword="-REDACTED-" protocols="TLSv1.2" certificateVerification="required" > <Certificate certificateFile="/home/ubuntu/tomcat/serverCert.pem" certificateChainFile="/home/ubuntu/tomcat/serverChain.pem" certificateKeyFile="/home/ubuntu/tomcat/rsaKey.pem" type="RSA" /> </SSLHostConfig> </Connector> Java: @WebServlet("/hello") public class HelloServlet extends HttpServlet { @Override protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { System.out.println("HelloServlet"); response.setContentType("text/html"); response.getWriter().println("<h1>Hello, World!</h1>"); // Retrieve client certificate X509Certificate[] certs = (X509Certificate[]) request.getAttribute("javax.servlet.request.X509Certificate"); if (certs != null && certs.length > 0) { response.getWriter().println("Client Cert Subject: " + certs[0].getSubjectX500Principal()); } else { response.getWriter().println("No Client Certificate Found."); } } } WARNINGS: javax.net.ssl|WARNING|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.816 UTC|SSLExtensions.java:227|Ignore impact of unsupported extension: server_name javax.net.ssl|DEBUG|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.817 UTC|SSLExtensions.java:219|Ignore unavailable extension: max_fragment_length javax.net.ssl|WARNING|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.817 UTC|SSLExtensions.java:227|Ignore impact of unsupported extension: status_request javax.net.ssl|WARNING|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.818 UTC|SSLExtensions.java:227|Ignore impact of unsupported extension: supported_groups javax.net.ssl|WARNING|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.818 UTC|SSLExtensions.java:227|Ignore impact of unsupported extension: ec_point_formats javax.net.ssl|WARNING|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.821 UTC|SSLExtensions.java:227|Ignore impact of unsupported extension: application_layer_protocol_negotiation javax.net.ssl|DEBUG|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.821 UTC|SSLExtensions.java:219|Ignore unavailable extension: status_request_v2 javax.net.ssl|WARNING|21|https-jsse-nio2-8443-exec-2|2025-02-25 20:34:04.823 UTC|SSLExtensions.java:227|Ignore impact of unsupported extension: extended_master_secret PROPRIETARY INFORMATION. This email may contain proprietary and privileged material for the sole use of the intended recipient. Any review or distribution of such material by others is strictly prohibited. If you are not the intended recipient please contact the sender and delete all copies.