Skip to main content

harmos_operations/lifecycle/
status.rs

1/* ***
2 *
3 * Harmos
4 *
5 * SPDX-License-Identifier: Apache-2.0
6 *
7 * ***
8 */
9
10/* === Modules === */
11
12/* === Re-Exports === */
13
14/* === Imports === */
15
16// Standard Library Imports
17
18// Third Party Imports
19
20// Local Imports
21#[cfg(feature = "runtime")]
22use harmos_sdk::operations::instances::InstanceAccess;
23
24#[cfg(feature = "runtime")]
25use crate::{Error, Operation, Response};
26use harmos_domain::operations::instance::Id;
27
28/* === Constants === */
29
30/* === Macros === */
31
32/* === Type Aliases === */
33
34/* === Structs === */
35
36#[harmos::operation(
37    harmos_path = crate,
38    resources = [InstanceAccess],
39    id = "host.operations.status",
40    response = super::InstanceState,
41    policy = super::POLICY,
42    visibility = Shared,
43    grpc(package = "harmos.host.v1", service = "Operations", method = "Status"),
44)]
45#[derive(Clone, Default, PartialEq)]
46pub struct Status {
47    pub instance: u64,
48}
49
50#[harmos::message(harmos_path = crate)]
51#[derive(Clone, Default, PartialEq)]
52pub struct InstanceState {
53    pub phase: String,
54    pub outcome: String,
55    pub cancellation_requested: bool,
56    pub attempt: u32,
57}
58
59/* === Enums === */
60
61/* === Traits === */
62
63/* === Implementations === */
64
65impl Status {
66    pub fn of(instance: Id) -> Self {
67        Self { instance: instance.value() }
68    }
69}
70
71#[cfg(feature = "runtime")]
72impl Operation for Status {
73    type Error = Error;
74
75    async fn run(self, context: harmos_sdk::Context<'_, Self>) -> Result<Response<super::InstanceState>, Error> {
76        let access = context.resource::<harmos_sdk::operations::instances::InstanceAccess>();
77
78        let instance = access.0.owned(Id::new(self.instance)).ok_or(Error::UnknownInstance(self.instance))?;
79        Ok(super::InstanceState::from(instance.status()).into())
80    }
81}
82
83impl From<harmos_domain::operations::instance::Status> for InstanceState {
84    fn from(status: harmos_domain::operations::instance::Status) -> Self {
85        Self {
86            phase: status.phase.as_str().to_owned(),
87            outcome: status.outcome.map(harmos_domain::operations::instance::Outcome::as_str).unwrap_or_default().to_owned(),
88            cancellation_requested: status.cancellation_requested,
89            attempt: status.attempt,
90        }
91    }
92}
93
94impl TryFrom<&InstanceState> for harmos_domain::operations::instance::Status {
95    type Error = harmos_domain::operations::instance::ParseError;
96
97    fn try_from(state: &InstanceState) -> Result<Self, Self::Error> {
98        let phase = state.phase.parse::<harmos_domain::operations::instance::Phase>()?;
99        let outcome = match state.outcome.as_str() {
100            "" => None,
101            outcome => Some(outcome.parse::<harmos_domain::operations::instance::Outcome>()?),
102        };
103        Ok(Self {
104            phase,
105            outcome,
106            cancellation_requested: state.cancellation_requested,
107            attempt: state.attempt,
108        })
109    }
110}
111
112/* === Public Functions === */
113
114/* === Private Functions === */
115
116/* === Tests === */