roder_code_index/
proofs.rs1use roder_api::code_index::{CodeChunk, ContentProof, MerkleHash};
2
3pub fn proof_for_chunk(
4 workspace_root_hash: impl Into<MerkleHash>,
5 generation_id: impl Into<String>,
6 chunk: &CodeChunk,
7) -> ContentProof {
8 ContentProof {
9 path_hash: chunk.path_hash.clone(),
10 content_hash: chunk.content_hash.clone(),
11 workspace_root_hash: workspace_root_hash.into(),
12 generation_id: generation_id.into(),
13 }
14}
15
16pub fn verify_chunk_proof(
17 proof: &ContentProof,
18 expected_workspace_root_hash: &str,
19 chunk: &CodeChunk,
20) -> bool {
21 proof.workspace_root_hash == expected_workspace_root_hash
22 && proof.path_hash == chunk.path_hash
23 && proof.content_hash == chunk.content_hash
24}
25
26#[cfg(test)]
27mod tests {
28 use std::path::PathBuf;
29
30 use roder_api::code_index::{CodeByteRange, CodeLineRange};
31
32 use super::*;
33
34 #[test]
35 fn proofs_verify_chunk_possession() {
36 let chunk = CodeChunk {
37 chunk_hash: "chunk".to_string(),
38 path: PathBuf::from("src/lib.rs"),
39 path_hash: "path".to_string(),
40 byte_range: CodeByteRange { start: 0, end: 10 },
41 line_range: CodeLineRange { start: 1, end: 1 },
42 content_hash: "content".to_string(),
43 language: Some("rust".to_string()),
44 symbol_hint: Some("lib".to_string()),
45 };
46 let proof = proof_for_chunk("root", "gen", &chunk);
47
48 assert!(verify_chunk_proof(&proof, "root", &chunk));
49
50 let mut mismatched = chunk.clone();
51 mismatched.content_hash = "other".to_string();
52 assert!(!verify_chunk_proof(&proof, "root", &mismatched));
53 }
54}