1use serde::Serialize;
2
3use crate::{PROJECT_NAME, VERSION};
4
5pub const BUILD_INFO_SCHEMA_VERSION: u32 = 1;
6
7#[derive(Clone, Copy, Debug, Eq, PartialEq, Serialize)]
8pub struct BuildInfo {
9 pub schema_version: u32,
10 pub project: &'static str,
11 pub version: &'static str,
12 pub source_revision: Option<&'static str>,
13 pub source_dirty: Option<bool>,
14}
15
16fn nonempty(value: &'static str) -> Option<&'static str> {
17 (!value.is_empty()).then_some(value)
18}
19
20pub const fn from_embedded(
21 source_revision: Option<&'static str>,
22 source_dirty: Option<bool>,
23) -> BuildInfo {
24 BuildInfo {
25 schema_version: BUILD_INFO_SCHEMA_VERSION,
26 project: PROJECT_NAME,
27 version: VERSION,
28 source_revision,
29 source_dirty,
30 }
31}
32
33pub fn current() -> BuildInfo {
34 from_embedded(
35 nonempty(env!("GIT_SLOP_SOURCE_REVISION")),
36 env!("GIT_SLOP_SOURCE_DIRTY").parse().ok(),
37 )
38}
39
40#[cfg(test)]
41mod tests {
42 use super::*;
43
44 #[test]
45 fn build_info_keeps_the_public_identity_shape() {
46 let revision = "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa";
47 let info = from_embedded(Some(revision), Some(false));
48 assert_eq!(info.schema_version, 1);
49 assert_eq!(info.project, "git-slop");
50 assert_eq!(info.version, env!("CARGO_PKG_VERSION"));
51 assert_eq!(info.source_revision, Some(revision));
52 assert_eq!(info.source_dirty, Some(false));
53 }
54}