flowey_lib_hvlite/
download_release_igvm_files_from_gh.rs

1// Copyright (c) Microsoft Corporation.
2// Licensed under the MIT License.
3
4use flowey::node::prelude::*;
5
6#[derive(Serialize, Deserialize)]
7pub struct ReleaseOutput {
8    // Individual artifact paths (may reside in different directories)
9    pub openhcl_direct: Option<PathBuf>,
10    pub openhcl: Option<PathBuf>,
11    pub openhcl_aarch64: Option<PathBuf>,
12}
13
14impl Artifact for ReleaseOutput {}
15
16#[derive(Serialize, Deserialize, Clone, Debug, Copy)]
17pub enum OpenhclReleaseVersion {
18    Release2411,
19    Release2505,
20}
21
22impl OpenhclReleaseVersion {
23    pub fn branch_name(&self) -> String {
24        match self {
25            OpenhclReleaseVersion::Release2411 => "release/2411".to_string(),
26            OpenhclReleaseVersion::Release2505 => "release/2505".to_string(),
27        }
28    }
29
30    pub const ALL: [OpenhclReleaseVersion; 2] = [
31        OpenhclReleaseVersion::Release2411,
32        OpenhclReleaseVersion::Release2505,
33    ];
34
35    pub fn latest() -> Self {
36        *Self::ALL.last().unwrap()
37    }
38}
39
40impl std::fmt::Display for OpenhclReleaseVersion {
41    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
42        let s = match self {
43            OpenhclReleaseVersion::Release2411 => "release-2411",
44            OpenhclReleaseVersion::Release2505 => "release-2505",
45        };
46        f.write_str(s)
47    }
48}
49
50pub mod resolve {
51    use super::OpenhclReleaseVersion;
52    use super::ReleaseOutput;
53    use crate::run_cargo_build::common::CommonArch;
54    use flowey::node::prelude::*;
55
56    flowey_request! {
57        pub struct Request {
58            pub release_igvm_files: WriteVar<ReleaseOutput>,
59            pub release_version: OpenhclReleaseVersion,
60            pub arch: CommonArch,
61        }
62    }
63
64    new_simple_flow_node!(struct Node);
65
66    impl SimpleFlowNode for Node {
67        type Request = Request;
68
69        fn imports(ctx: &mut ImportCtx<'_>) {
70            ctx.import::<flowey_lib_common::download_gh_artifact::Node>();
71            ctx.import::<flowey_lib_common::gh_latest_completed_workflow_id::Node>();
72        }
73
74        fn process_request(request: Self::Request, ctx: &mut NodeCtx<'_>) -> anyhow::Result<()> {
75            let branch_name: ReadVar<String> =
76                ReadVar::from_static(request.release_version.branch_name());
77
78            let run_id =
79                ctx.reqv(
80                    |v| flowey_lib_common::gh_latest_completed_workflow_id::Request {
81                        repo: "microsoft/openvmm".into(),
82                        branch: branch_name.clone(),
83                        pipeline_name: "openvmm-ci.yaml".into(),
84                        gh_workflow_id: v,
85                    },
86                );
87            let output = request.release_igvm_files;
88
89            let arch_str = match request.arch {
90                CommonArch::X86_64 => "x64",
91                CommonArch::Aarch64 => "aarch64",
92            };
93
94            let downloaded_artifact =
95                ctx.reqv(|v| flowey_lib_common::download_gh_artifact::Request {
96                    repo_owner: "microsoft".into(),
97                    repo_name: "openvmm".into(),
98                    file_name: format!("{arch_str}-openhcl-igvm"),
99                    path: v,
100                    run_id: run_id.clone(),
101                });
102            let arch = request.arch;
103
104            ctx.emit_rust_step("write to directory variables", |ctx| {
105                let downloaded_artifact = downloaded_artifact.claim(ctx);
106                let write_release_output = output.claim(ctx);
107
108                move |rt| {
109                    let mut openhcl_direct = None;
110                    let mut openhcl = None;
111                    let mut openhcl_aarch64 = None;
112
113                    match arch {
114                        CommonArch::X86_64 => {
115                            // x64 build contains both openhcl.bin and openhcl-direct.bin
116                            let x64_dir = rt.read(downloaded_artifact).join("x64-openhcl-igvm");
117                            openhcl_direct = Some(x64_dir.join("openhcl-direct.bin"));
118                            openhcl = Some(x64_dir.join("openhcl.bin"));
119                        }
120                        CommonArch::Aarch64 => {
121                            let aarch64_dir =
122                                rt.read(downloaded_artifact).join("aarch64-openhcl-igvm");
123                            openhcl_aarch64 = Some(aarch64_dir.join("openhcl-aarch64.bin"));
124                        }
125                    }
126
127                    rt.write_not_secret(
128                        write_release_output,
129                        &ReleaseOutput {
130                            openhcl_direct,
131                            openhcl,
132                            openhcl_aarch64,
133                        },
134                    );
135
136                    Ok(())
137                }
138            });
139
140            Ok(())
141        }
142    }
143}