[hypervisor] Add management actions to charm
Add management actions to hypervisor charm to allow enabling / disabling the compute service, and get a list of running guests on that hypervisor. Change-Id: Ibea004be22462aff5a4d64704c67970af1b038d1 Signed-off-by: Guillaume Boutry <guillaume.boutry@canonical.com>
This commit is contained in:
parent
87364abd0e
commit
66a4ae378f
@ -62,6 +62,25 @@ actions:
|
|||||||
description: |
|
description: |
|
||||||
List host NICS, and which one are candidates for use as external NIC.
|
List host NICS, and which one are candidates for use as external NIC.
|
||||||
additionalProperties: false
|
additionalProperties: false
|
||||||
|
disable:
|
||||||
|
description: |
|
||||||
|
Prevent new instances from being created.
|
||||||
|
params:
|
||||||
|
reason:
|
||||||
|
type: string
|
||||||
|
description: Reason for disabling the hypervisor
|
||||||
|
default: Stopped via operator action
|
||||||
|
additionalProperties: false
|
||||||
|
enable:
|
||||||
|
description: |
|
||||||
|
Allow new instances to be created.
|
||||||
|
additionalProperties: false
|
||||||
|
running-guests:
|
||||||
|
description: |
|
||||||
|
List the running guests on the hypervisor.
|
||||||
|
|
||||||
|
Only lists guests created by the OpenStack cloud.
|
||||||
|
additionalProperties: false
|
||||||
|
|
||||||
requires:
|
requires:
|
||||||
amqp:
|
amqp:
|
||||||
|
@ -71,6 +71,10 @@ DATA_BINDING = "data"
|
|||||||
MTLS_USAGES = {x509.OID_SERVER_AUTH, x509.OID_CLIENT_AUTH}
|
MTLS_USAGES = {x509.OID_SERVER_AUTH, x509.OID_CLIENT_AUTH}
|
||||||
|
|
||||||
|
|
||||||
|
class HypervisorError(Exception):
|
||||||
|
"""Custom exception for Hypervisor errors."""
|
||||||
|
|
||||||
|
|
||||||
@sunbeam_tracing.trace_type
|
@sunbeam_tracing.trace_type
|
||||||
class MTlsCertificatesHandler(sunbeam_rhandlers.TlsCertificatesHandler):
|
class MTlsCertificatesHandler(sunbeam_rhandlers.TlsCertificatesHandler):
|
||||||
"""Handler for certificates interface."""
|
"""Handler for certificates interface."""
|
||||||
@ -178,6 +182,18 @@ class HypervisorOperatorCharm(sunbeam_charm.OSBaseOperatorCharm):
|
|||||||
self.on.list_nics_action,
|
self.on.list_nics_action,
|
||||||
self._list_nics_action,
|
self._list_nics_action,
|
||||||
)
|
)
|
||||||
|
self.framework.observe(
|
||||||
|
self.on.enable_action,
|
||||||
|
self._enable_action,
|
||||||
|
)
|
||||||
|
self.framework.observe(
|
||||||
|
self.on.disable_action,
|
||||||
|
self._disable_action,
|
||||||
|
)
|
||||||
|
self.framework.observe(
|
||||||
|
self.on.running_guests_action,
|
||||||
|
self._running_guests_action,
|
||||||
|
)
|
||||||
self.framework.observe(
|
self.framework.observe(
|
||||||
self.on.install,
|
self.on.install,
|
||||||
self._on_install,
|
self._on_install,
|
||||||
@ -231,6 +247,14 @@ class HypervisorOperatorCharm(sunbeam_charm.OSBaseOperatorCharm):
|
|||||||
return None
|
return None
|
||||||
return str(address)
|
return str(address)
|
||||||
|
|
||||||
|
def _proxy_configs(self) -> dict[str, str]:
|
||||||
|
"""Return proxy configs."""
|
||||||
|
return {
|
||||||
|
"HTTPS_PROXY": os.environ.get("JUJU_CHARM_HTTPS_PROXY", ""),
|
||||||
|
"HTTP_PROXY": os.environ.get("JUJU_CHARM_HTTP_PROXY", ""),
|
||||||
|
"NO_PROXY": os.environ.get("JUJU_CHARM_NO_PROXY", ""),
|
||||||
|
}
|
||||||
|
|
||||||
def check_relation_exists(self, relation_name: str) -> bool:
|
def check_relation_exists(self, relation_name: str) -> bool:
|
||||||
"""Check if a relation exists or not."""
|
"""Check if a relation exists or not."""
|
||||||
if self.model.get_relation(relation_name):
|
if self.model.get_relation(relation_name):
|
||||||
@ -325,14 +349,13 @@ class HypervisorOperatorCharm(sunbeam_charm.OSBaseOperatorCharm):
|
|||||||
if new_snap_settings:
|
if new_snap_settings:
|
||||||
self.set_snap_data(new_snap_settings)
|
self.set_snap_data(new_snap_settings)
|
||||||
|
|
||||||
def _list_nics_action(self, event: ActionEvent):
|
def _hypervisor_cli_cmd(self, cmd: str):
|
||||||
"""Run list_nics action."""
|
"""Helper to run cli commands on the snap."""
|
||||||
cache = self.get_snap_cache()
|
cache = self.get_snap_cache()
|
||||||
hypervisor = cache["openstack-hypervisor"]
|
hypervisor = cache["openstack-hypervisor"]
|
||||||
|
|
||||||
if not hypervisor.present:
|
if not hypervisor.present:
|
||||||
event.fail("Hypervisor is not installed")
|
raise HypervisorError("Hypervisor is not installed")
|
||||||
return
|
|
||||||
|
|
||||||
process = subprocess.run(
|
process = subprocess.run(
|
||||||
[
|
[
|
||||||
@ -340,10 +363,8 @@ class HypervisorOperatorCharm(sunbeam_charm.OSBaseOperatorCharm):
|
|||||||
"run",
|
"run",
|
||||||
"openstack-hypervisor",
|
"openstack-hypervisor",
|
||||||
"--verbose",
|
"--verbose",
|
||||||
"list-nics",
|
]
|
||||||
"--format",
|
+ cmd.split(),
|
||||||
"json",
|
|
||||||
],
|
|
||||||
capture_output=True,
|
capture_output=True,
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -352,12 +373,54 @@ class HypervisorOperatorCharm(sunbeam_charm.OSBaseOperatorCharm):
|
|||||||
stdout = process.stdout.decode("utf-8")
|
stdout = process.stdout.decode("utf-8")
|
||||||
logger.debug("stdout: %s", stdout)
|
logger.debug("stdout: %s", stdout)
|
||||||
if process.returncode != 0:
|
if process.returncode != 0:
|
||||||
event.fail(stderr)
|
raise HypervisorError(stderr)
|
||||||
|
|
||||||
|
return stdout
|
||||||
|
|
||||||
|
def _list_nics_action(self, event: ActionEvent):
|
||||||
|
"""Run list_nics action."""
|
||||||
|
try:
|
||||||
|
stdout = self._hypervisor_cli_cmd("list-nics --format json")
|
||||||
|
except HypervisorError as e:
|
||||||
|
event.fail(str(e))
|
||||||
return
|
return
|
||||||
|
|
||||||
# cli returns a json dict with keys "nics" and "candidate"
|
# cli returns a json dict with keys "nics" and "candidate"
|
||||||
event.set_results({"result": stdout})
|
event.set_results({"result": stdout})
|
||||||
|
|
||||||
|
def _enable_action(self, event: ActionEvent):
|
||||||
|
"""Run enable action."""
|
||||||
|
try:
|
||||||
|
stdout = self._hypervisor_cli_cmd("hypervisor enable")
|
||||||
|
except HypervisorError as e:
|
||||||
|
event.fail(str(e))
|
||||||
|
return
|
||||||
|
|
||||||
|
event.set_results({"result": stdout})
|
||||||
|
|
||||||
|
def _disable_action(self, event: ActionEvent):
|
||||||
|
"""Run disable action."""
|
||||||
|
try:
|
||||||
|
stdout = self._hypervisor_cli_cmd("hypervisor disable")
|
||||||
|
except HypervisorError as e:
|
||||||
|
event.fail(str(e))
|
||||||
|
return
|
||||||
|
|
||||||
|
event.set_results({"result": stdout})
|
||||||
|
|
||||||
|
def _running_guests_action(self, event: ActionEvent):
|
||||||
|
"""List running openstack guests."""
|
||||||
|
try:
|
||||||
|
stdout = self._hypervisor_cli_cmd(
|
||||||
|
"hypervisor running-guests --format json"
|
||||||
|
)
|
||||||
|
except HypervisorError as e:
|
||||||
|
event.fail(str(e))
|
||||||
|
return
|
||||||
|
|
||||||
|
# cli returns a json list
|
||||||
|
event.set_results({"result": stdout})
|
||||||
|
|
||||||
def ensure_services_running(self):
|
def ensure_services_running(self):
|
||||||
"""Ensure systemd services running."""
|
"""Ensure systemd services running."""
|
||||||
# This should taken care of by the snap
|
# This should taken care of by the snap
|
||||||
@ -476,6 +539,7 @@ class HypervisorOperatorCharm(sunbeam_charm.OSBaseOperatorCharm):
|
|||||||
"identity.password": contexts.identity_credentials.password,
|
"identity.password": contexts.identity_credentials.password,
|
||||||
"identity.project-domain-id": contexts.identity_credentials.project_domain_id,
|
"identity.project-domain-id": contexts.identity_credentials.project_domain_id,
|
||||||
"identity.project-domain-name": contexts.identity_credentials.project_domain_name,
|
"identity.project-domain-name": contexts.identity_credentials.project_domain_name,
|
||||||
|
"identity.project-id": contexts.identity_credentials.project_id,
|
||||||
"identity.project-name": contexts.identity_credentials.project_name,
|
"identity.project-name": contexts.identity_credentials.project_name,
|
||||||
"identity.region-name": contexts.identity_credentials.region,
|
"identity.region-name": contexts.identity_credentials.region,
|
||||||
"identity.user-domain-id": contexts.identity_credentials.user_domain_id,
|
"identity.user-domain-id": contexts.identity_credentials.user_domain_id,
|
||||||
|
@ -150,6 +150,7 @@ class TestCharm(test_utils.CharmTestCase):
|
|||||||
"identity.password": "user-password",
|
"identity.password": "user-password",
|
||||||
"identity.project-domain-id": "pdomain-id",
|
"identity.project-domain-id": "pdomain-id",
|
||||||
"identity.project-domain-name": "pdomain_-ame",
|
"identity.project-domain-name": "pdomain_-ame",
|
||||||
|
"identity.project-id": "uproj-id",
|
||||||
"identity.project-name": "user-project",
|
"identity.project-name": "user-project",
|
||||||
"identity.region-name": "region12",
|
"identity.region-name": "region12",
|
||||||
"identity.user-domain-id": "udomain-id",
|
"identity.user-domain-id": "udomain-id",
|
||||||
@ -261,6 +262,7 @@ class TestCharm(test_utils.CharmTestCase):
|
|||||||
"identity.password": "user-password",
|
"identity.password": "user-password",
|
||||||
"identity.project-domain-id": "pdomain-id",
|
"identity.project-domain-id": "pdomain-id",
|
||||||
"identity.project-domain-name": "pdomain_-ame",
|
"identity.project-domain-name": "pdomain_-ame",
|
||||||
|
"identity.project-id": "uproj-id",
|
||||||
"identity.project-name": "user-project",
|
"identity.project-name": "user-project",
|
||||||
"identity.region-name": "region12",
|
"identity.region-name": "region12",
|
||||||
"identity.user-domain-id": "udomain-id",
|
"identity.user-domain-id": "udomain-id",
|
||||||
|
Loading…
x
Reference in New Issue
Block a user