walker_common/retrieve/
mod.rs1mod error;
4pub use error::*;
5
6use crate::utils::{hex::Hex, url::Urlify};
7use digest::{Digest, Output};
8use std::{
9 fmt::{Debug, Formatter},
10 ops::{Deref, DerefMut},
11};
12use time::OffsetDateTime;
13
14pub trait RetrievedDocument: Urlify + Debug {
15 type Discovered: Urlify + Debug;
16}
17
18#[derive(Clone, PartialEq, Eq)]
20pub struct RetrievedDigest<D: Digest> {
21 pub expected: String,
23 pub actual: Output<D>,
25}
26
27impl<D: Digest> RetrievedDigest<D> {
28 pub fn validate(&self) -> Result<(), (&str, String)> {
29 let actual = Hex(&self.actual).to_lower();
30 if self.expected == actual {
31 Ok(())
32 } else {
33 Err((&self.expected, actual))
34 }
35 }
36}
37
38impl<D: Digest> Debug for RetrievedDigest<D> {
39 fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
40 f.debug_struct("RetrievedDigest")
41 .field("expected", &self.expected)
42 .field("actual", &Hex(&self.actual))
43 .finish()
44 }
45}
46
47#[derive(Clone)]
49pub struct RetrievingDigest<D: Digest> {
50 pub expected: String,
51 pub current: D,
52}
53
54impl<D> Deref for RetrievingDigest<D>
55where
56 D: Digest,
57{
58 type Target = D;
59
60 fn deref(&self) -> &Self::Target {
61 &self.current
62 }
63}
64
65impl<D> DerefMut for RetrievingDigest<D>
66where
67 D: Digest,
68{
69 fn deref_mut(&mut self) -> &mut Self::Target {
70 &mut self.current
71 }
72}
73
74impl<D> From<RetrievingDigest<D>> for RetrievedDigest<D>
75where
76 D: Digest,
77{
78 fn from(value: RetrievingDigest<D>) -> Self {
79 Self {
80 expected: value.expected,
81 actual: value.current.finalize(),
82 }
83 }
84}
85
86#[derive(Clone, Debug, Default)]
88pub struct RetrievalMetadata {
89 pub last_modification: Option<OffsetDateTime>,
91 pub etag: Option<String>,
93}