On Thu, Jan 5, 2017 at 2:08 PM Mark Thomas <ma...@apache.org> wrote:

> On 05/01/2017 21:05, Jesse Schulman wrote:
> > We are using tomcat-embed 8.5.9, java8 and running on Centos7.  Given
> > Tomcat's new support for SNI, we wish to support adding/removing/updating
> > certificates via our application at runtime without restarting tomcat or
> > binding/unbinding the port.
> >
> > Our configuration is very simple, we have a single servlet for all
> > requests, so we have a single connector/endpoint to manage all
> > SSLHostConfigs.
> >
> > It appears that by manipulating the list of SSLHostConfig objects in the
> > AbstractEndpoint we can achieve what we want, there however don't appear
> to
> > be any public methods available that allow that kind of operation.
>
> It should be possible with the current API. What can't you do?
>
>
I don't think I can modify an existing/added SSLHostConfig (remove an old
expiring certificate and add a new certificate).  I also don't think I can
remove the SSLHostConfig for a given SNI hostname once it has been added.

> I was able to extend a few tomcat classes (Connector,
> > AbstractHttp11JsseProtocol, NioEndpoint) to expose what I need and verify
> > that I can change the SSLHostConfig at runtime, however I would prefer to
> > use APIs fully supported by tomcat.
> >
> > Is there any way to do what I want with the currently available APIs, or
> > are there any plans to expose this kind of functionality?
>
> It depends exactly what you want to do.
>
> AbstractEndpoint.addSslHostConfig()
> AbstractEndpoint.findSslHostConfigs()
>
> should be enough.
>

It seems addSslHostConfig does a putIfAbsent, which means I can't replace
an existing SSLHostConfig to update the certificate for an SNI hostname (or
the default SSLHostConfig).  I also can't remove an SSLHostConfig entirely,
which is something we'd like to support in our application.  For me it
would be simplest to create a new SSLHostConfig and replace the old one
when there is a need to update a certificate.


>
> > If not, are there any risks or issues with taking the approach described
> > above by extending classes to expose what I need?
>
> It depends what you want to do. Generally, there is a risk we'll change
> an API you are depending on since a lot of those are treated as internal
> APIs. Some sample code might help.
>

I would of course test when we upgrade tomcat, and leverage any new APIs
that would allow me to remove any of my custom code.

I extended AbstractHttp11JsseProtocol just so I could control which
endpoint implementation was used and so I could get access to my endpoint
implementation.  My protocol is basically a copy of Http11NioProtocol that
constructs my endpoint implementation and has a getter for the same.

The endpoint is where I added functionality and looks like this:

public class MyNioEndpoint extends NioEndpoint {
    private static final MyLogger LOGGER =
MyLogger.getLogger(MyNioEndpoint.class.getName());

    public void removeSSLHostConfig(String sniHostName) {
        if (Strings.isNullOrEmpty(sniHostName)) {
            LOGGER.error("Cannot remove host config for invalid hostname: "
+ sniHostName);
            return;
        }

        if (sniHostName.equals(getDefaultSSLHostConfigName())) {
            LOGGER.error("Cannot remove default SSLHostConfig");
            return;
        }

        SSLHostConfig removed = sslHostConfigs.remove(sniHostName);
        if (removed != null)
            releaseSSLContext(removed);
    }

    public void addOrUpdateSSLHostConfig(SSLHostConfig config) {
        if (config == null) {
            LOGGER.error("null SSLHostConfig provided");
            return;
        }

        String hostName = config.getHostName();
        if (Strings.isNullOrEmpty(hostName)) {
            LOGGER.error("Invalid SSLHostConfig provided, cannot
add/update, hostname was empty");
            return;
        }

        for (SSLHostConfig loadedConfig : findSslHostConfigs()) {
            if (hostName.equals(loadedConfig.getHostName())) {
                sslHostConfigs.remove(hostName);
                releaseSSLContext(loadedConfig);
                addSslHostConfig(loadedConfig);
                return;
            }
        }

        addSslHostConfig(config);
    }

}

Thanks for the reply, your help/suggestions are much appreciated!
Jesse


>
> Mark
>
> ---------------------------------------------------------------------
> To unsubscribe, e-mail: users-unsubscr...@tomcat.apache.org
> For additional commands, e-mail: users-h...@tomcat.apache.org
>
>

Reply via email to