inspect_git/
inspect_git.rs1#[cfg(unix)]
4fn main() -> Result<(), Box<dyn std::error::Error>> {
5 use ic_host_tools::{
6 provenance::{IgnoreSubmodules, StatusOptions, UntrackedFiles, capture_git},
7 tool::{AdmittedTool, ExecutionContext, OutputLimits, ToolSpec},
8 };
9 use std::{ffi::OsString, io, path::PathBuf, time::Duration};
10
11 let invalid = |message| io::Error::new(io::ErrorKind::InvalidInput, message);
12 let mut args = std::env::args_os().skip(1);
13 let mut required = || {
14 args.next().ok_or_else(|| invalid(
15 "usage: inspect_git TOOL SHA256 VERSION WORKDIR MAX_TOOL_BYTES MAX_STDOUT_BYTES MAX_STDERR_BYTES TIMEOUT_MS UNTRACKED SUBMODULES",
16 ))
17 };
18 let executable = PathBuf::from(required()?);
19 let digest = required()?
20 .into_string()
21 .map_err(|_| invalid("digest must be UTF-8"))?
22 .parse()?;
23 let version = required()?
24 .into_string()
25 .map_err(|_| invalid("version must be UTF-8"))?;
26 let directory = PathBuf::from(required()?);
27 let mut number = || -> Result<u64, Box<dyn std::error::Error>> {
28 Ok(required()?
29 .to_str()
30 .ok_or_else(|| invalid("limits must be UTF-8"))?
31 .parse()?)
32 };
33 let executable_bytes = number()?;
34 let limits = OutputLimits {
35 stdout_bytes: usize::try_from(number()?)?,
36 stderr_bytes: usize::try_from(number()?)?,
37 timeout: Duration::from_millis(number()?),
38 };
39 let untracked = match required()?.to_str() {
40 Some("no") => UntrackedFiles::No,
41 Some("normal") => UntrackedFiles::Normal,
42 Some("all") => UntrackedFiles::All,
43 _ => return Err(invalid("untracked must be no, normal or all").into()),
44 };
45 let ignore_submodules = match required()?.to_str() {
46 Some("none") => IgnoreSubmodules::None,
47 Some("untracked") => IgnoreSubmodules::Untracked,
48 Some("dirty") => IgnoreSubmodules::Dirty,
49 Some("all") => IgnoreSubmodules::All,
50 _ => return Err(invalid("submodules must be none, untracked, dirty or all").into()),
51 };
52 if args.next().is_some() {
53 return Err(invalid("unexpected argument").into());
54 }
55 let context = ExecutionContext {
58 current_dir: &directory,
59 environment: &[],
60 };
61 let git = AdmittedTool::admit(
62 &ToolSpec {
63 executable: &executable,
64 sha256: digest,
65 executable_bytes,
66 version_arguments: &[OsString::from("--version")],
67 version_identity: &version,
68 },
69 &context,
70 limits,
71 )?;
72 let observed = capture_git(
73 &git,
74 &context,
75 StatusOptions {
76 untracked,
77 ignore_submodules,
78 },
79 limits,
80 )?;
81 println!("revision={}", observed.revision);
82 println!("tree={}", observed.tree);
83 println!("dirty={}", observed.is_dirty());
84 println!("status_bytes={}", observed.status_identity.bytes);
85 println!("status_sha256={}", observed.status_identity.sha256);
86 Ok(())
87}
88
89#[cfg(not(unix))]
90fn main() -> Result<(), std::io::Error> {
91 Err(std::io::Error::new(
92 std::io::ErrorKind::Unsupported,
93 "Git observations require a supported Unix host",
94 ))
95}