Radish alpha
r
rad:zwTxygwuz5LDGBq255RA2CbNGrz8
Radicle CI broker
Radicle
Git
feat: add metadata about CI run to RSS feed entries
Merged liw opened 1 year ago

Signed-off-by: Lars Wirzenius liw@liw.fi

feat: produce RSS feed of unfinished CI runs

That’s CI runs that have been triggered, are running, but have not finished.

Signed-off-by: Lars Wirzenius liw@liw.fi

2 files changed +77 -0 0c5eaeb8 00ca0e8f
modified ci-broker.md
@@ -2176,6 +2176,7 @@ then file reports/status.json exists
when I run jq .event_queue_length reports/status.json
then stdout is exactly "0\n"
~~~
+

# Acceptance criteria for upgrades

_What:_ The node operator can safely upgrade the CI broker. At the
modified src/pages.rs
@@ -40,6 +40,7 @@ use crate::{

const BROKER_RSS: &str = "index.rss";
const FAILURE_RSS: &str = "failed.rss";
+
const UNFINISHED_RSS: &str = "unfinished.rss";
const CSS: &str = include_str!("radicle-ci.css");
const REFERESH_INTERVAL: &str = "300";
const UPDATE_INTERVAL: Duration = Duration::from_secs(60);
@@ -627,6 +628,22 @@ impl PageData {
        Ok(channel.build())
    }

+
    fn unfinished_as_rss(&self) -> Result<Channel, PageError> {
+
        let mut channel = ChannelBuilder::default();
+
        channel
+
            .title("Radicle CI broker run information")
+
            .description("All CI runs known to this instance of the Radicle CI broker.")
+
            .link("FIXME:link");
+
        for (_alias, repo_id) in self.repos() {
+
            for run in self.runs(repo_id) {
+
                if run.state() == RunState::Triggered || run.state() == RunState::Running {
+
                    channel.item(Self::rss_item_from_run(run)?);
+
                }
+
            }
+
        }
+
        Ok(channel.build())
+
    }
+

    fn rss_item_from_run(run: &Run) -> Result<Item, PageError> {
        let mut guid = Guid::default();
        guid.set_value(run.broker_run_id().to_string());
@@ -646,10 +663,22 @@ impl PageData {
            parse_timestamp(&ts).map_err(|err| PageError::RssTimestamp(ts.clone(), err))?;
        let ts = rfc822_timestamp(parsed).map_err(|err| PageError::RssTimestamp(ts, err))?;

+
        let entry = RssEntry {
+
            repoid: run.repo_id(),
+
            commit: match run.whence() {
+
                Whence::Branch { commit, .. } => *commit,
+
                Whence::Patch { commit, .. } => *commit,
+
            },
+
            info_url: run.adapter_info_url().map(String::from),
+
            status: run.state(),
+
            result: run.result().cloned(),
+
        };
+

        let mut item = ItemBuilder::default()
            .title(Some(title))
            .guid(Some(guid))
            .pub_date(Some(ts))
+
            .content(entry.to_html().serialize())
            .build();

        if let Some(url) = run.adapter_info_url() {
@@ -660,6 +689,48 @@ impl PageData {
    }
}

+
struct RssEntry {
+
    repoid: RepoId,
+
    commit: Oid,
+
    info_url: Option<String>,
+
    status: RunState,
+
    result: Option<RunResult>,
+
}
+

+
impl RssEntry {
+
    fn to_html(&self) -> Element {
+
        Element::new(Tag::Div)
+
            .with_class("ci_run")
+
            .with_child(
+
                Element::new(Tag::Span)
+
                    .with_class("repoid")
+
                    .with_text(&self.repoid.to_string()),
+
            )
+
            .with_child(
+
                Element::new(Tag::Span)
+
                    .with_class("commit")
+
                    .with_text(&self.commit.to_string()),
+
            )
+
            .with_child(
+
                Element::new(Tag::Span)
+
                    .with_class("info_url")
+
                    .with_text(self.info_url.as_deref().unwrap_or("")),
+
            )
+
            .with_child(
+
                Element::new(Tag::Span)
+
                    .with_class("status")
+
                    .with_text(&self.status.to_string()),
+
            )
+
            .with_child(Element::new(Tag::Span).with_class("result").with_text(
+
                match &self.result {
+
                    None => "undetermined",
+
                    Some(RunResult::Success) => "success",
+
                    Some(RunResult::Failure) => "failure",
+
                },
+
            ))
+
    }
+
}
+

/// Data for status pages for CI broker.
///
/// There is a "front page" with status about the broker, and a list
@@ -803,6 +874,11 @@ impl StatusPage {
            let channel = data.failed_as_rss()?;
            let rss = channel.to_string();
            Self::write_file(&filename, &rss)?;
+

+
            let filename = dirname.join(UNFINISHED_RSS);
+
            let channel = data.unfinished_as_rss()?;
+
            let rss = channel.to_string();
+
            Self::write_file(&filename, &rss)?;
        }
        Ok(())
    }