// file: crates/knowledge-app-lib/unit_tests/repository_sync.rs // version: 1 #[derive(Clone, Copy, Debug, Eq, PartialEq)] struct FakeRepositoryError; struct FakeRepository { observed_revision: knowledge_git_api::GitRevision, reject_snapshot: bool, } impl FakeRepository { fn new(observed_revision: &str, reject_snapshot: bool) -> FakeRepository { return FakeRepository { observed_revision: knowledge_git_api::GitRevision::new(observed_revision), reject_snapshot }; } } impl knowledge_git_api::GitRepository for FakeRepository { type Error = FakeRepositoryError; fn refresh(&mut self, _source_id: &knowledge_domain_lib::SourceId) -> Result<(), Self::Error> { return Ok(()); } fn resolve_revision( &self, _source_id: &knowledge_domain_lib::SourceId, _reference: &knowledge_git_api::GitReference, ) -> Result { return Ok(self.observed_revision.clone()); } fn prepare_snapshot( &self, _source_id: &knowledge_domain_lib::SourceId, revision: &knowledge_git_api::GitRevision, ) -> Result { if self.reject_snapshot { return Err(FakeRepositoryError); } return Ok(knowledge_git_api::GitSnapshot::new(revision.clone(), std::path::PathBuf::from("/controlled/snapshot"))); } } fn source_id() -> Option { let result = knowledge_domain_lib::SourceId::new("snippets"); match result { Ok(value) => return Some(value), Err(_) => return None, } } fn signal(cause: knowledge_sync_api::RepositorySyncCause) -> Option { let id = match source_id() { Some(value) => value, None => return None, }; return Some(knowledge_sync_api::RepositorySyncSignal::new(id, cause)); } #[test] fn changed_revision_prepares_snapshot_and_returns_observed_revision() { let mut repository = FakeRepository::new("bbbb", false); let request = match signal(knowledge_sync_api::RepositorySyncCause::Explicit) { Some(value) => value, None => return, }; let reference = knowledge_git_api::GitReference::new("refs/heads/main"); let previous = knowledge_git_api::GitRevision::new("aaaa"); let result = crate::synchronize_repository(&mut repository, &request, &reference, Some(&previous)); assert!(result.is_ok()); let outcome = match result { Ok(value) => value, Err(_) => return, }; assert!(outcome.is_changed()); assert_eq!(outcome.revision().as_str(), "bbbb"); assert!(outcome.snapshot().is_some()); return; } #[test] fn unchanged_revision_does_not_prepare_snapshot() { let mut repository = FakeRepository::new("bbbb", true); let request = match signal(knowledge_sync_api::RepositorySyncCause::Explicit) { Some(value) => value, None => return, }; let reference = knowledge_git_api::GitReference::new("refs/heads/main"); let previous = knowledge_git_api::GitRevision::new("bbbb"); let result = crate::synchronize_repository(&mut repository, &request, &reference, Some(&previous)); assert!(result.is_ok()); let outcome = match result { Ok(value) => value, Err(_) => return, }; assert!(!outcome.is_changed()); assert_eq!(outcome.revision().as_str(), "bbbb"); assert!(outcome.snapshot().is_none()); return; } #[test] fn periodic_signal_uses_the_same_reconciliation_path() { let mut repository = FakeRepository::new("cccc", false); let request = match signal(knowledge_sync_api::RepositorySyncCause::Periodic) { Some(value) => value, None => return, }; let reference = knowledge_git_api::GitReference::new("refs/heads/main"); let result = crate::synchronize_repository(&mut repository, &request, &reference, None); assert!(result.is_ok()); let outcome = match result { Ok(value) => value, Err(_) => return, }; assert!(outcome.is_changed()); assert_eq!(outcome.revision().as_str(), "cccc"); assert!(outcome.snapshot().is_some()); return; }