Skip to content

Commit

Permalink
Pass cacert as a file path to cloud.yaml (#98)
Browse files Browse the repository at this point in the history
* Pass cacert as a file path to cloud.yaml

* Modify test_configure_ssl_ca to verify cacert is written to a file

* Use pathlib for config paths

* Remove redundant code and improve ssl_ca file verification
  • Loading branch information
Deezzir authored Sep 6, 2024
1 parent 6a5b5a4 commit f00e1fe
Show file tree
Hide file tree
Showing 3 changed files with 14 additions and 9 deletions.
13 changes: 8 additions & 5 deletions src/charm.py
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@

import logging
import os
from pathlib import Path
from typing import Any, Optional

import ops
Expand All @@ -34,7 +35,8 @@
# store the clouds.yaml where it's easily accessible by the openstack-exporter snap
# This is the SNAP_COMMON directory for the exporter snap, which is accessible,
# unversioned, and retained across updates of the snap.
OS_CLIENT_CONFIG = f"/var/snap/{SNAP_NAME}/common/clouds.yaml"
OS_CLIENT_CONFIG = Path(f"/var/snap/{SNAP_NAME}/common/clouds.yaml")
OS_CLIENT_CONFIG_CACERT = Path(f"/var/snap/{SNAP_NAME}/common/cacert.pem")


class OpenstackExporterOperatorCharm(ops.CharmBase):
Expand Down Expand Up @@ -90,6 +92,9 @@ def _write_cloud_config(self, data: dict[str, str]) -> None:
since v2 was removed a long time ago (Queens release)
https://docs.openstack.org/keystone/latest/contributor/http-api.html
"""
OS_CLIENT_CONFIG.parent.mkdir(parents=True, exist_ok=True)
OS_CLIENT_CONFIG_CACERT.write_text(self.config["ssl_ca"])

auth_url = "{protocol}://{hostname}:{port}/v3".format(
protocol=data["service_protocol"],
hostname=data["service_hostname"],
Expand All @@ -110,14 +115,12 @@ def _write_cloud_config(self, data: dict[str, str]) -> None:
"auth_url": auth_url,
},
"verify": data["service_protocol"] == "https",
"cacert": self.config["ssl_ca"],
"cacert": str(OS_CLIENT_CONFIG_CACERT),
}
}
}

os.makedirs(os.path.dirname(OS_CLIENT_CONFIG), exist_ok=True)
with open(OS_CLIENT_CONFIG, "w") as f:
yaml.dump(contents, f)
OS_CLIENT_CONFIG.write_text(yaml.dump(contents))

def _get_keystone_data(self) -> dict[str, str]:
"""Get keystone data if ready, otherwise empty dict."""
Expand Down
8 changes: 5 additions & 3 deletions tests/integration/tests/charm_tests/openstack_exporter.py
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ def test_clouds_yaml(self):
results = model.run_on_leader(APP_NAME, command)
clouds_yaml_path = results.get("Stdout", "").strip()
self.assertEqual(int(results.get("Code", "-1")), 0)
self.assertEqual(clouds_yaml_path, OS_CLIENT_CONFIG)
self.assertEqual(clouds_yaml_path, str(OS_CLIENT_CONFIG))

# Make sure the clouds yaml is not empty and it's a valid yaml
command = f"cat $(sudo snap get {SNAP_NAME} os-client-config)"
Expand Down Expand Up @@ -161,8 +161,10 @@ def test_configure_ssl_ca(self):
results = model.run_on_leader(APP_NAME, command)
clouds_yaml = results.get("Stdout", "").strip()
data = yaml.safe_load(clouds_yaml)
cacert = data["clouds"][CLOUD_NAME]["cacert"]
self.assertEqual(cacert, f"{new_value}")
cacert_path = data["clouds"][CLOUD_NAME]["cacert"]

# Verify ssl_ca was written to the file
model.block_until_file_has_contents(APP_NAME, cacert_path, new_value)

# Verify the exporter crashes because of wrong ssl_ca
command = "curl -q localhost:9180/metrics"
Expand Down
2 changes: 1 addition & 1 deletion tests/integration/tests/charm_tests/setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,6 @@ def setup_export_ssl_ca_config():
model.set_application_config("openstack-exporter", {"ssl_ca": cacert})
model.block_until_file_has_contents(
"openstack-exporter",
f"/var/snap/{SNAP_NAME}/common/clouds.yaml",
f"/var/snap/{SNAP_NAME}/common/cacert.pem",
"-----BEGIN CERTIFICATE-----",
)

0 comments on commit f00e1fe

Please sign in to comment.