I've figured out why no certificates were being returned from 9300
. The
elasticsearch.yml
contained the following xpack related config:
xpack.security.enabled: false
xpack.security.audit.enabled: false
xpack.ml.enabled: false
xpack.watcher.enabled: false
xpack.graph.enabled: false
xpack.security.transport.ssl.enabled: true
xpack.security.transport.ssl.verification_mode: certificate
xpack.security.transport.ssl.client_authentication: required
xpack.security.transport.ssl.keystore.path: foo-certificates.p12
xpack.security.transport.ssl.truststore.path: foo-certificates.p12
xpack.security.http.ssl.enabled: false
Note the first line of that!
xpack.security.enabled
was false
due to the configuration I'm using having initially been used with earlier versions of Elasticsearch where the security stuff cost money and we didn't need it. And I'd forgotten it was there, far enough away from the newly added xpack.security.transport.ssl
settings in the file that it took me a while to notice it. Having set xpack.security.enabled
to true
if I use openssl s_client
to connect to 9300
I get expected output including the certificate.
Whilst my problem was obviously largely self inflicted I think it's worth me explaining what I did as it feels like Elasticsearch has behaved somewhat unhelpfully.
I installed Elasticsearch on all three nodes from the rpm using dnf
module of Ansible and Ansible. Then I put in place configuration with
xpack.security.transport.ssl.enabled: false
xpack.security.http.ssl.enabled: false
for simplicity just to check I could get a working cluster. Then I reinstalled it all with
xpack.security.transport.ssl.enabled: true
xpack.security.http.ssl.enabled: false
and followed
to create a certificate without a password (for simplicity while experimenting). Having followed that Elasticsearch refused to start with an error about not being able to read foo-certificates.p12
which turned out to be because I'd put the file in /usr/share/elasticsearch/
by mistake. I moved it to /etc/elasticsearch/
and Elasticsearch still didn't start because of filesystem permissions. I fixed that and then got:
Caused by: org.elasticsearch.common.ssl.SslConfigException: cannot read
configured [PKCS12] keystore (as a truststore)
[/etc/elasticsearch/foo-certificates.p12] - this is usually caused by an
incorrect password; (a keystore password was provided)
Which was confusing because I had not set a password, because my certificate didn't have one.
While investigating that I discovered the rpm has post install scripts which create a certificate with a password and a keystore with the password in. (All the output of the rpm post install scripts which is visible when you install the rpm manually with rpm
or dnf
, and tells you about a certificate being created and a password set for the elastic
user, is not visible, at least by default, when you install with Ansible dnf
module.) The documentation I followed mentions the need to add a password for your certificate to the keystore, if you set one, but it doesn't say anything about how a password will already be in the keystore if you installed with the rpm and Elasticsearch will try to use that with a certificate you made yourself that doesn't have a password.
To get Elasticsearch to use foo-certificates.p12
I deleted the keystores on all the nodes and then created empty ones. I have repeated this whole process several times to confirm my findings with consistent results.
So after setting
xpack.security.transport.ssl.enabled: true
I had to fix several issues that prevented Elasticsearch from starting because of problems relating to transport SSL configuration. Having fixed those issues and getting a working cluster it seems reasonable to assume that transport SSL would be being used. If Elasticsearch isn't trying to use transport SSL then why refuse to start because it can't read a certificate for transport SSL. But evidently it is possible to give Elasticsearch configuration which means it will refuse to start
because of problems with transport SSL, but won't use transport SSL once those problems are fixed.
The issue I have now is that with xpack.security.enabled
being true
authentication is in effect on the REST API. All I wanted to do was enable transport SSL. I can't see a way to get transport SSL without the REST API authentication.