surf: expose BlobRef

The current `blob` function is limited to always associating a Blob
with a Commit.

Expose `BlobRef` through a `blob_ref` method, and add useful methods
and serialization to it.

Signed-off-by: Fintan Halpenny <fintan.halpenny@gmail.com>
X-Clacks-Overhead: GNU Terry Pratchett
This commit is contained in:
Fintan Halpenny
2023-11-22 14:53:09 +00:00
parent ab791d5f2c
commit d3dd777d95
2 changed files with 36 additions and 1 deletions
+30 -1
View File
@@ -95,7 +95,13 @@ impl<'a> Blob<BlobRef<'a>> {
/// Represents a blob with borrowed content bytes.
pub struct BlobRef<'a> {
inner: git2::Blob<'a>,
pub(crate) inner: git2::Blob<'a>,
}
impl<'a> BlobRef<'a> {
pub fn id(&self) -> Oid {
self.inner.id().into()
}
}
impl AsRef<[u8]> for BlobRef<'_> {
@@ -138,3 +144,26 @@ where
state.end()
}
}
#[cfg(feature = "serde")]
impl<'a> Serialize for BlobRef<'a> {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
const FIELDS: usize = 3;
let mut state = serializer.serialize_struct("BlobRef", FIELDS)?;
state.serialize_field("id", &self.id())?;
state.serialize_field("binary", &self.inner.is_binary())?;
let bytes = self.as_ref();
match std::str::from_utf8(bytes) {
Ok(s) => state.serialize_field("content", s)?,
Err(_) => {
let encoded = base64::encode(bytes);
state.serialize_field("content", &encoded)?
},
};
state.end()
}
}
+6
View File
@@ -301,6 +301,12 @@ impl Repository {
Ok(Blob::<BlobRef<'a>>::new(file.id(), git2_blob, last_commit))
}
pub fn blob_ref(&self, oid: Oid) -> Result<BlobRef<'_>, Error> {
Ok(BlobRef {
inner: self.find_blob(oid)?,
})
}
/// Returns the last commit, if exists, for a `path` in the history of
/// `rev`.
pub fn last_commit<P, C>(&self, path: &P, rev: C) -> Result<Option<Commit>, Error>