diff --git a/src/main.rs b/src/main.rs index c43e149..4d13714 100644 --- a/src/main.rs +++ b/src/main.rs @@ -2,7 +2,7 @@ mod fingerprint; mod raw; mod sign; mod utils; -//mod verify; +mod verify; use std::path::PathBuf; @@ -38,6 +38,15 @@ enum Action { /// The git revision to sign git_rev: String, }, + /// Verify the signature over some git revision + Verify { + /// The path to the base64 encoded public key to verify with + #[arg(short = 'k', long)] + public_key: PathBuf, + + /// The signed git revision to verify + git_rev: String, + }, } #[derive(Subcommand)] @@ -84,5 +93,9 @@ fn main() -> Result<()> { secret_key, git_rev: rev, } => sign::command(secret_key, rev), + Action::Verify { + public_key, + git_rev: rev, + } => verify::command(public_key, rev), } } diff --git a/src/verify.rs b/src/verify.rs new file mode 100644 index 0000000..4e06e42 --- /dev/null +++ b/src/verify.rs @@ -0,0 +1,26 @@ +//! Verify signatures stored under git references +//! with [`libsignify`]. + +use std::path::PathBuf; + +use anyhow::{Context, Result}; + +use crate::raw::verify::verify; +use crate::utils; + +/// Execute the `verify` command. +pub fn command(key_path: PathBuf, rev: String) -> Result<()> { + let repo = utils::open_repository()?; + let public_key = utils::get_public_key(key_path)?; + let tree_rev = { + let object_oid = repo + .revparse_single(&rev) + .context("Failed to look-up git object")? + .id(); + let key_fingerprint = utils::hash_bytes(&public_key.key()[..])?; + utils::craft_signature_reference(key_fingerprint, object_oid) + }; + verify(&repo, &public_key, &tree_rev, false)?; + println!("Signature verified successfully"); + Ok(()) +}