Improve STX-O HTTPs decoupling from the platform

This commit improves and addresses issues introduced by [1] and other
FQDN / TLS issues.

The change [1] only addressed a portion of the certificate management
requirements. Initially, it was assumed that only one certificate
(openstack-helm.crt) was needed. However, further inspection revealed
that three files are necessary: the certificate file, the certificate
key, and the CA certificate (though the CA certificate is optional).

This update improves the approach by allowing users to customize the
paths of these certificate files. Users can either utilize the default
system commands (os-certificate-install, ca-certificate-install) to
install the certificates or specify their own custom certificates and
paths. This provides flexibility while maintaining compatibility with
existing system commands.

This by itself was not sufficiente to solve the [2] issue. For that,
the patch 0005 for openstack-helm [3] had to be udpated to include
the HTTPS endpoint configuration for the Keystone Admin endpoint. The
way this patch was written, this endpoint would remain as HTTP even if
the certificates were configured, which can be considered a security
flaw, as someone with bad intentions could have access to Keystone
services in plain HTTP, or even spoof the traffic between the services.

[1] https://review.opendev.org/c/starlingx/openstack-armada-app/+/926641
[2] https://bugs.launchpad.net/starlingx/+bug/2080979
[3] https://opendev.org/starlingx/openstack-armada-app/src/branch/master/openstack-helm/debian/deb_folder/patches/0005-Allow-set-public-endpoint-url-for-keystone-endpoints.patch
[4] https://review.opendev.org/c/starlingx/docs/+/930392

Test Plan:
  Base:
  - PASS: Build STX-Openstack tarball
  - PASS: Apply STX-Openstack
  - PASS: Verify all app communications is being done via HTTP

  Applying the TLS / FQDN configuration before the first apply:
    Using system commands:
    - PASS: Using the `system os-certificate-install` and
            `system ca-certificate-install` commands, apply HTTPS and
            reapply the STX-Openstack application. Verify all
            communications are done via HTTPS
    - PASS: Check the Helm overrides for various charts and make sure
            that all "cacert", "crt" and "key" fields are present.
    - PASS: Verify that all Openstack endpoints are with FQDN and HTTPS
    - PASS: Make sure commands are reaching the HTTPS endpoints

    Using a custom path for the certificates:
    - PASS: Make Helm overrides to the `openstackCertificateFile`,
            `openstackCertificateKeyFile` and
            `openstackCertificateCAFile` fields. Verify that the app
            applies normally
    - PASS: Check the Helm overrides for various charts and make sure
            that all "cacert", "crt" and "key" fields are present.
    - PASS: Verify that all Openstack endpoints are with FQDN and HTTPS
    - PASS: Make sure commands are reaching the HTTPS endpoints

  Applying the TLS / FQDN configuration after the first apply:
    Using system commands:
    - PASS*: Using the `system os-certificate-install` and
            `system ca-certificate-install` commands, apply HTTPS and
            reapply the STX-Openstack application. Verify all
            communications are done via HTTPS

    Using a custom path for the certificates:
    - PASS: Make Helm overrides to the `openstackCertificateFile`,
            `openstackCertificateKeyFile` and
            `openstackCertificateCAFile` fields. Verify that the app
            applies normally
    - PASS: Check the Helm overrides for various charts and make sure
            that all "cacert", "crt" and "key" fields are present.
    - PASS: Verify that all Openstack endpoints are with FQDN and HTTPS
    - PASS: Make sure commands are reaching the HTTPS endpoints

*: This test case has a doc input on [4]. This method (using system
commands to install the STX-Openstack certificates after the application
is already applied) involves waiting for the endpoints to be
reconfigured.

Closes-Bug: 2080979

Change-Id: I57221bcadbed28dd9c00689cfeb6e11219a05de6
Signed-off-by: Lucas de Ataides <lucas.deataidesbarreto@windriver.com>
This commit is contained in:
Lucas de Ataides 2024-09-02 16:29:28 -03:00
parent 693bf136bd
commit 4c79b9bc53
21 changed files with 239 additions and 75 deletions

View File

@ -1,19 +1,27 @@
From b272e8ff3a78f38ab82df7995233705611e99f81 Mon Sep 17 00:00:00 2001
From 412b3d1afa534675d3fce56f9fa5a3e9d95b62de Mon Sep 17 00:00:00 2001
From: Angie Wang <angie.wang@windriver.com>
Date: Tue, 1 Sep 2020 00:00:22 -0400
Subject: [PATCH] Allow set public endpoint url for keystone endpoints
[ Use public endpoint for admin url]
Signed-off-by: Lucas de Ataides <lucas.deataidesbarreto@windriver.com>
---
keystone/templates/job-db-sync.yaml | 4 ++++
1 file changed, 4 insertions(+)
keystone/templates/job-db-sync.yaml | 8 ++++++++
1 file changed, 8 insertions(+)
diff --git a/keystone/templates/job-db-sync.yaml b/keystone/templates/job-db-sync.yaml
index a4ff67d8..08e82d78 100644
index a4ff67d8..37db4464 100644
--- a/keystone/templates/job-db-sync.yaml
+++ b/keystone/templates/job-db-sync.yaml
@@ -25,7 +25,11 @@ env:
@@ -23,9 +23,17 @@ helm.sh/hook-weight: "-4"
{{- $envAll := index . 0 -}}
env:
- name: OS_BOOTSTRAP_ADMIN_URL
+ {{- if and (hasKey $envAll.Values.endpoints.identity "force_public_endpoint") $envAll.Values.endpoints.identity.force_public_endpoint }}
+ value: {{ tuple "identity" "public" "api" $envAll | include "helm-toolkit.endpoints.keystone_endpoint_uri_lookup" }}
+ {{- else }}
value: {{ tuple "identity" "admin" "api" $envAll | include "helm-toolkit.endpoints.keystone_endpoint_uri_lookup" }}
+ {{- end }}
- name: OS_BOOTSTRAP_INTERNAL_URL
+ {{- if and (hasKey $envAll.Values.endpoints.identity "force_public_endpoint") $envAll.Values.endpoints.identity.force_public_endpoint }}
+ value: {{ tuple "identity" "public" "api" $envAll | include "helm-toolkit.endpoints.keystone_endpoint_uri_lookup" }}
@ -24,5 +32,5 @@ index a4ff67d8..08e82d78 100644
value: {{ tuple "identity" "public" "api" $envAll | include "helm-toolkit.endpoints.keystone_endpoint_uri_lookup" }}
- name: OPENSTACK_CONFIG_FILE
--
2.25.1
2.34.1

View File

@ -113,5 +113,7 @@ CLIENTS_WORKING_DIR = "/var/opt/openstack"
CLIENTS_WORKING_DIR_GROUP = "openstack"
CLIENTS_WORKING_DIR_USER = "sysadmin"
CERT_RELATIVE_PATH = "ssl"
CERT_FILE_NAME = "openstack-helm.crt"
# Openstack certificates names
OPENSTACK_CERT = "openstack-cert"
OPENSTACK_CERT_KEY = "openstack-cert-key"
OPENSTACK_CERT_CA = "openstack-cert-ca"

View File

@ -299,16 +299,20 @@ class OpenstackBaseHelm(FluxCDBaseHelm):
def _get_endpoint_public_tls(self):
overrides = {}
if (os.path.exists(constants.OPENSTACK_CERT_FILE) and
os.path.exists(constants.OPENSTACK_CERT_KEY_FILE)):
certificates = app_utils.get_openstack_certificate_files()
cert_file = certificates[app_constants.OPENSTACK_CERT]
cert_key_file = certificates[app_constants.OPENSTACK_CERT_KEY]
cert_ca_file = certificates[app_constants.OPENSTACK_CERT_CA]
if (os.path.exists(cert_file) and os.path.exists(cert_key_file)):
overrides.update({
'crt': self._get_file_content(constants.OPENSTACK_CERT_FILE),
'key': self._get_file_content(
constants.OPENSTACK_CERT_KEY_FILE),
'crt': self._get_file_content(cert_file),
'key': self._get_file_content(cert_key_file),
})
if os.path.exists(constants.OPENSTACK_CERT_CA_FILE):
if os.path.exists(cert_ca_file):
overrides.update({
'ca': self._get_file_content(constants.OPENSTACK_CERT_CA_FILE),
'ca': self._get_file_content(cert_ca_file),
})
return overrides
@ -745,7 +749,10 @@ class OpenstackBaseHelm(FluxCDBaseHelm):
@staticmethod
def get_ca_file():
return app_utils.get_certificate_file()
# This function returns the path for the CA cert file INSIDE the container,
# no on the host machine. If you're changing this, be mindful of changing
# the same path in the helm-toolkit.
return '/etc/ssl/certs/openstack-helm.crt'
def _enable_certificates(self, overrides):
overrides = self._update_overrides(overrides, {

View File

@ -45,8 +45,16 @@ class AodhGetOverrideTest(AodhHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_aodh_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -44,8 +44,16 @@ class BarbicanGetOverrideTest(BarbicanHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_barbican_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -46,8 +46,16 @@ class CeilometerGetOverrideTest(CeilometerHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_ceilometer_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -60,8 +60,16 @@ class CinderGetOverrideTest(CinderConversionTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_cinder_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -48,8 +48,16 @@ class FmRestApiGetOverrideTest(FmRestApiHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_fm_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -48,8 +48,16 @@ class GlanceGetOverrideTest(GlanceHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_glance_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -45,8 +45,16 @@ class GnocchiGetOverrideTest(GnocchiHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_gnocchi_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -49,8 +49,16 @@ class HeatGetOverrideTest(HeatHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_heat_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -45,8 +45,16 @@ class HorizonGetOverrideTest(HorizonHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_horizon_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -46,8 +46,16 @@ class KeystoneGetOverrideTest(KeystoneHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_keystone_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -45,8 +45,16 @@ class KeystoneApiProxyGetOverrideTest(KeystoneApiProxyHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_keystone_api_proxy_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -59,8 +59,16 @@ class NeutronGetOverrideTest(NeutronHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_neutron_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -101,8 +101,16 @@ class NovaGetOverrideTest(NovaHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_nova_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -66,8 +66,16 @@ class NovaApiProxyGetOverrideTest(NovaApiProxyHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_nova_api_proxy_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -38,8 +38,16 @@ class PlacementGetOverrideTest(PlacementHelmTestCase,
@mock.patch('six.moves.builtins.open', mock.mock_open(read_data="fake"))
@mock.patch('k8sapp_openstack.utils.is_openstack_https_ready', return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test_placement_overrides_https_enabled(self, *_):
overrides = self.operator.get_helm_chart_overrides(

View File

@ -7,6 +7,7 @@
import mock
from sysinv.tests.db import base as dbbase
from k8sapp_openstack.common import constants as app_constants
from k8sapp_openstack.lifecycle import lifecycle_openstack
@ -16,17 +17,21 @@ class OpenstackAppLifecycleOperatorTest(dbbase.ControllerHostTestCase):
self.lifecycle = lifecycle_openstack.OpenstackAppLifecycleOperator()
@mock.patch("k8sapp_openstack.utils.is_openstack_https_ready", return_value=False)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
)
def test__semantic_check_openstack_https_not_ready(self, *_):
self.assertFalse(self.lifecycle._semantic_check_openstack_https_ready())
@mock.patch("k8sapp_openstack.utils.is_openstack_https_ready", return_value=True)
@mock.patch(
'k8sapp_openstack.utils.get_certificate_file',
return_value='/var/opt/openstack/ssl/openstack-helm.crt'
'k8sapp_openstack.helm.openstack.OpenstackBaseHelm.get_ca_file',
return_value='/etc/ssl/private/openstack/ca-cert.pem'
)
@mock.patch(
'k8sapp_openstack.utils.get_openstack_certificate_files',
return_value={
app_constants.OPENSTACK_CERT: '/etc/ssl/private/openstack/cert.pem',
app_constants.OPENSTACK_CERT_KEY: '/etc/ssl/private/openstack/key.pem',
app_constants.OPENSTACK_CERT_CA: '/etc/ssl/private/openstack/ca-cert.pem'
}
)
def test__semantic_check_openstack_https_ready(self, *_):
self.assertTrue(self.lifecycle._semantic_check_openstack_https_ready())

View File

@ -24,29 +24,42 @@ LOG = logging.getLogger(__name__)
def is_openstack_https_ready():
"""Check if OpenStack is ready for HTTPS.
"""Return whether the openstack certificates are ready or not.
Returns true if the HTTPss certificate is in place
at the Openstack working directory
Returns true if the HTTPs certificates are present in the
defined directory.
"""
return os.path.isfile(get_certificate_file())
certificates = get_openstack_certificate_files()
for cert_name in certificates:
# The CA certificate (Certificate Authority) is not
# required for HTTPs to be enabled, so we skip it.
if cert_name == app_constants.OPENSTACK_CERT_CA:
continue
# Check if the file exist
if not os.path.isfile(certificates[cert_name]):
return False
return True
def get_certificate_file() -> str:
"""Get OpenStack certificate file path.
def get_openstack_certificate_files() -> dict[str, str]:
"""Get Openstack certificate files
:returns: str -- The certificate file path.
:returns: dict[str, str] -- a dictionary of the files
"""
# By default, the certificate file name and directory
# are stored in the constants
openstack_dir = get_clients_working_directory()
cert_directory = app_constants.CERT_RELATIVE_PATH
cert_file_name = app_constants.CERT_FILE_NAME
# By default, the certificate files are stored in
# the default platform directory
openstack_cert_file_path = constants.OPENSTACK_CERT_FILE
openstack_cert_key_file_path = constants.OPENSTACK_CERT_KEY_FILE
openstack_cert_ca_file_path = constants.OPENSTACK_CERT_CA_FILE
db = dbapi.get_instance()
if db is None:
return os.path.join(openstack_dir, cert_directory, cert_file_name)
return {
app_constants.OPENSTACK_CERT: openstack_cert_file_path,
app_constants.OPENSTACK_CERT_KEY: openstack_cert_key_file_path,
app_constants.OPENSTACK_CERT_CA: openstack_cert_ca_file_path
}
# However, the user might have overriden the default
# certiticate path and file name. If that is the case,
@ -63,13 +76,22 @@ def get_certificate_file() -> str:
user_overrides = yaml.load(
override.user_overrides, Loader=yaml.FullLoader
)
cert_directory = user_overrides.get(
"certRelativePath", app_constants.CERT_RELATIVE_PATH
openstack_cert_file_path = user_overrides.get(
"openstackCertificateFile", constants.OPENSTACK_CERT_FILE
)
cert_file_name = user_overrides.get(
"certFileName", app_constants.CERT_FILE_NAME
openstack_cert_key_file_path = user_overrides.get(
"openstackCertificateKeyFile", constants.OPENSTACK_CERT_KEY_FILE
)
return os.path.join(openstack_dir, cert_directory, cert_file_name)
openstack_cert_ca_file_path = user_overrides.get(
"openstackCertificateCAFile", constants.OPENSTACK_CERT_CA_FILE
)
return {
app_constants.OPENSTACK_CERT: openstack_cert_file_path,
app_constants.OPENSTACK_CERT_KEY: openstack_cert_key_file_path,
app_constants.OPENSTACK_CERT_CA: openstack_cert_ca_file_path
}
def directory_files(path: str) -> Generator:

View File

@ -174,10 +174,10 @@ secrets:
workingDirectoryPath: /var/opt/openstack
# These values are not used directly by the 'Clients' chart, but they are
# stored here because they are relative to the 'workingDirectoryPath'.
certRelativePath: ssl
certFileName: openstack-helm.crt
# These values are not used directly by the 'Clients' chart.
openstackCertificateFile: /etc/ssl/private/openstack/cert.pem
openstackCertificateKeyFile: /etc/ssl/private/openstack/key.pem
openstackCertificateCAFile: /etc/ssl/private/openstack/ca-cert.pem
conf: {}