merge radicle-source into radicle-surf

Initially, radicle-source was envisioned to be another layer on top
of radicle-surf, however, it ended up duplicating a lot of concepts.

We consolidate them by merging radicle-source into radicle-surf.
This meant removing modules branch.rs, tag.rs, oid.rs and error.rs.
This commit is contained in:
Han Xu
2022-09-21 17:07:06 -07:00
parent ff97333d0a
commit eb1653cdb7
19 changed files with 184 additions and 395 deletions
+2 -2
View File
@@ -87,8 +87,8 @@ jobs:
# The 'main' branch is needed for radicle-surf vcs::git::tests::test_submodule_failure,
# however actions/checkout uses the default branch 'master' at this moment.
# We will improve the test soon to remove this need.
- run: git branch main
- run: git branch -u origin/main main
# - run: git branch main
# - run: git branch -u origin/main main
- uses: actions-rs/toolchain@v1
with:
profile: minimal
-1
View File
@@ -6,7 +6,6 @@ members = [
"radicle-git-ext",
"radicle-git-types",
"radicle-macros",
"radicle-source",
"radicle-std-ext",
"radicle-surf",
# TODO: port gitd-lib over
-31
View File
@@ -1,31 +0,0 @@
[package]
name = "radicle-source"
description = "A high level API for browsing source files"
version = "0.4.0"
authors = ["The Radicle Team <dev@radicle.xyz>"]
edition = "2018"
homepage = "https://github.com/radicle-dev/radicle-surf"
repository = "https://github.com/radicle-dev/radicle-surf"
license = "GPL-3.0-or-later"
[features]
syntax = ["syntect"]
[dependencies]
base64 = "0.13"
log = "0.4"
lazy_static = "1.4"
nonempty = "0.6"
serde = { version = "1.0", features = [ "derive" ] }
syntect = { version = "4.2", optional = true }
thiserror = "1.0"
[dependencies.git2]
version = ">= 0.12"
default-features = false
features = []
[dependencies.radicle-surf]
version = "^0.8.0"
features = ["serialize"]
path = "../radicle-surf"
-108
View File
@@ -1,108 +0,0 @@
// This file is part of radicle-surf
// <https://github.com/radicle-dev/radicle-surf>
//
// Copyright (C) 2019-2020 The Radicle Team <dev@radicle.xyz>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 3 or
// later as published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
use std::fmt;
use serde::{Deserialize, Serialize};
use radicle_surf::vcs::git::{self, Browser, RefScope};
use crate::error::Error;
/// Branch name representation.
#[derive(Clone, Debug, Eq, Ord, PartialEq, PartialOrd, Deserialize, Serialize)]
pub struct Branch(pub(crate) String);
impl From<String> for Branch {
fn from(name: String) -> Self {
Self(name)
}
}
impl From<git::Branch> for Branch {
fn from(branch: git::Branch) -> Self {
Self(branch.name.to_string())
}
}
impl fmt::Display for Branch {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self.0)
}
}
/// Given a project id to a repo returns the list of branches.
///
/// # Errors
///
/// Will return [`Error`] if the project doesn't exist or the surf interaction
/// fails.
pub fn branches(browser: &Browser<'_>, filter: RefScope) -> Result<Vec<Branch>, Error> {
let mut branches = browser
.list_branches(filter)?
.into_iter()
.map(|b| Branch(b.name.name().to_string()))
.collect::<Vec<Branch>>();
branches.sort();
Ok(branches)
}
/// Information about a locally checked out repository.
#[derive(Deserialize, Serialize)]
pub struct LocalState {
/// List of branches.
branches: Vec<Branch>,
}
/// Given a path to a repo returns the list of branches and if it is managed by
/// coco.
///
/// # Errors
///
/// Will return [`Error`] if the repository doesn't exist.
pub fn local_state(repo_path: &str, default_branch: &str) -> Result<LocalState, Error> {
let repo = git2::Repository::open(repo_path).map_err(git::error::Error::from)?;
let first_branch = repo
.branches(Some(git2::BranchType::Local))
.map_err(git::error::Error::from)?
.filter_map(|branch_result| {
let (branch, _) = branch_result.ok()?;
let name = branch.name().ok()?;
name.map(String::from)
})
.min()
.ok_or(Error::NoBranches)?;
let repo = git::Repository::new(repo_path)?;
let browser = match Browser::new(&repo, git::Branch::local(default_branch)) {
Ok(browser) => browser,
Err(_) => Browser::new(&repo, git::Branch::local(&first_branch))?,
};
let mut branches = browser
.list_branches(RefScope::Local)?
.into_iter()
.map(|b| Branch(b.name.name().to_string()))
.collect::<Vec<Branch>>();
branches.sort();
Ok(LocalState { branches })
}
-46
View File
@@ -1,46 +0,0 @@
// This file is part of radicle-surf
// <https://github.com/radicle-dev/radicle-surf>
//
// Copyright (C) 2019-2020 The Radicle Team <dev@radicle.xyz>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 3 or
// later as published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
use radicle_surf::{file_system, git};
/// An error occurred when interacting with [`radicle_surf`] for browsing source
/// code.
#[derive(Debug, thiserror::Error)]
pub enum Error {
/// We expect at least one [`crate::revision::Revisions`] when looking at a
/// project, however the computation found none.
#[error(
"while trying to get user revisions we could not find any, there should be at least one"
)]
EmptyRevisions,
/// An error occurred during a [`radicle_surf::file_system`] operation.
#[error(transparent)]
FileSystem(#[from] file_system::Error),
/// An error occurred during a [`radicle_surf::git`] operation.
#[error(transparent)]
Git(#[from] git::error::Error),
/// When trying to query a repositories branches, but there are none.
#[error("the repository has no branches")]
NoBranches,
/// Trying to find a file path which could not be found.
#[error("the path '{0}' was not found")]
PathNotFound(file_system::Path),
}
-51
View File
@@ -1,51 +0,0 @@
// This file is part of radicle-surf
// <https://github.com/radicle-dev/radicle-surf>
//
// Copyright (C) 2019-2020 The Radicle Team <dev@radicle.xyz>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 3 or
// later as published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
//! Source code related functionality.
/// To avoid incompatible versions of `radicle-surf`, `radicle-source`
/// re-exports the package under the `surf` alias.
pub use radicle_surf as surf;
pub mod branch;
pub use branch::{branches, local_state, Branch, LocalState};
pub mod commit;
pub use commit::{commit, commits, Commit};
pub mod error;
pub use error::Error;
pub mod object;
pub use object::{blob, tree, Blob, BlobContent, Info, ObjectType, Tree};
pub mod oid;
pub use oid::Oid;
pub mod person;
pub use person::Person;
pub mod revision;
pub use revision::Revision;
#[cfg(feature = "syntax")]
pub mod syntax;
#[cfg(feature = "syntax")]
pub use syntax::SYNTAX_SET;
pub mod tag;
pub use tag::{tags, Tag};
-44
View File
@@ -1,44 +0,0 @@
// This file is part of radicle-surf
// <https://github.com/radicle-dev/radicle-surf>
//
// Copyright (C) 2019-2020 The Radicle Team <dev@radicle.xyz>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 3 or
// later as published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
use std::convert::TryFrom;
use serde::{Deserialize, Serialize};
#[derive(Clone, Copy, Debug, Deserialize, Serialize)]
#[serde(try_from = "&str", into = "String")]
pub struct Oid(pub git2::Oid);
impl TryFrom<&str> for Oid {
type Error = git2::Error;
fn try_from(value: &str) -> Result<Self, Self::Error> {
value.parse().map(Oid)
}
}
impl From<Oid> for String {
fn from(oid: Oid) -> Self {
oid.0.to_string()
}
}
impl From<Oid> for git2::Oid {
fn from(oid: Oid) -> Self {
oid.0
}
}
-60
View File
@@ -1,60 +0,0 @@
// This file is part of radicle-surf
// <https://github.com/radicle-dev/radicle-surf>
//
// Copyright (C) 2019-2020 The Radicle Team <dev@radicle.xyz>
//
// This program is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License version 3 or
// later as published by the Free Software Foundation.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
use std::fmt;
use serde::Serialize;
use radicle_surf::{git::RefScope, vcs::git::Browser};
use crate::error::Error;
/// Tag name representation.
///
/// We still need full tag support.
#[derive(Clone, Debug, Eq, Ord, PartialEq, PartialOrd, Serialize)]
pub struct Tag(pub(crate) String);
impl From<String> for Tag {
fn from(name: String) -> Self {
Self(name)
}
}
impl fmt::Display for Tag {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "{}", self.0)
}
}
/// Retrieves the list of [`Tag`] for the given project `id`.
///
/// # Errors
///
/// Will return [`Error`] if the project doesn't exist or the surf interaction
/// fails.
pub fn tags(browser: &Browser<'_>) -> Result<Vec<Tag>, Error> {
let tag_names = browser.list_tags(RefScope::Local)?;
let mut tags: Vec<Tag> = tag_names
.into_iter()
.map(|tag_name| Tag(tag_name.name().to_string()))
.collect();
tags.sort();
Ok(tags)
}
+2
View File
@@ -24,9 +24,11 @@ serialize = ["serde"]
gh-actions = []
[dependencies]
base64 = "0.13"
either = "1.5"
nom = "6"
nonempty = "0.5"
radicle-git-ext = { path = "../radicle-git-ext", features = ["serde"] }
regex = ">= 1.5.5"
serde = { features = ["serde_derive"], optional = true, version = "1" }
thiserror = "1.0"
@@ -15,22 +15,27 @@
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
//! Represents a commit.
use std::convert::TryFrom as _;
#[cfg(feature = "serialize")]
use serde::{
ser::{SerializeStruct as _, Serializer},
Serialize,
};
use radicle_surf::{
use crate::{
diff,
vcs::git::{self, Browser, Rev},
file_system,
person::Person,
revision::Revision,
vcs::git::{self, BranchName, Browser, Rev},
};
use crate::{branch::Branch, error::Error, person::Person, revision::Revision};
/// Commit statistics.
#[derive(Clone, Serialize)]
#[cfg_attr(feature = "serialize", derive(Serialize))]
#[derive(Clone)]
pub struct Stats {
/// Additions.
pub additions: u64,
@@ -39,7 +44,8 @@ pub struct Stats {
}
/// Representation of a changeset between two revs.
#[derive(Clone, Serialize)]
#[cfg_attr(feature = "serialize", derive(Serialize))]
#[derive(Clone)]
pub struct Commit {
/// The commit header.
pub header: Header,
@@ -48,7 +54,7 @@ pub struct Commit {
/// The changeset introduced by this commit.
pub diff: diff::Diff,
/// The list of branches this commit belongs to.
pub branches: Vec<Branch>,
pub branches: Vec<BranchName>,
}
/// Representation of a code commit.
@@ -101,6 +107,7 @@ impl From<&git::Commit> for Header {
}
}
#[cfg(feature = "serialize")]
impl Serialize for Header {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
@@ -118,12 +125,12 @@ impl Serialize for Header {
}
/// A selection of commit headers and their statistics.
#[derive(Serialize)]
#[cfg_attr(feature = "serialize", derive(Serialize))]
pub struct Commits {
/// The commit headers
pub headers: Vec<Header>,
/// The statistics for the commit headers
pub stats: radicle_surf::vcs::git::Stats,
pub stats: git::Stats,
}
/// Retrieves a [`Commit`].
@@ -188,7 +195,7 @@ pub fn commit(browser: &mut Browser<'_>, sha1: git2::Oid) -> Result<Commit, Erro
let branches = browser
.revision_branches(sha1)?
.into_iter()
.map(Branch::from)
.map(|b| b.name)
.collect();
Ok(Commit {
@@ -241,3 +248,19 @@ where
Ok(Commits { headers, stats })
}
/// An error reported by commit API.
#[derive(Debug, thiserror::Error)]
pub enum Error {
/// An error occurred during a file system operation.
#[error(transparent)]
FileSystem(#[from] file_system::Error),
/// An error occurred during a git operation.
#[error(transparent)]
Git(#[from] git::error::Error),
/// Trying to find a file path which could not be found.
#[error("the path '{0}' was not found")]
PathNotFound(file_system::Path),
}
+17
View File
@@ -86,6 +86,23 @@ pub mod diff;
pub mod file_system;
pub mod vcs;
pub mod commit;
pub use commit::{commit, commits, Commit};
pub mod object;
pub use object::{blob, tree as objectTree, Blob, BlobContent, Info, ObjectType, Tree};
pub mod person;
pub use person::Person;
pub mod revision;
pub use revision::Revision;
#[cfg(feature = "syntax")]
pub mod syntax;
#[cfg(feature = "syntax")]
pub use syntax::SYNTAX_SET;
// Private modules
mod nonempty;
mod tree;
@@ -15,6 +15,10 @@
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
//! Common definitions for git objects (blob and tree).
//! See git [doc](https://git-scm.com/book/en/v2/Git-Internals-Git-Objects) for more details.
#[cfg(feature = "serialize")]
use serde::{
ser::{SerializeStruct as _, Serializer},
Serialize,
@@ -26,7 +30,7 @@ pub use blob::{blob, Blob, BlobContent};
pub mod tree;
pub use tree::{tree, Tree, TreeEntry};
use crate::commit;
use crate::{commit, file_system, git};
/// Git object types.
///
@@ -39,6 +43,7 @@ pub enum ObjectType {
Blob,
}
#[cfg(feature = "serialize")]
impl Serialize for ObjectType {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
@@ -62,6 +67,7 @@ pub struct Info {
pub last_commit: Option<commit::Header>,
}
#[cfg(feature = "serialize")]
impl Serialize for Info {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
@@ -74,3 +80,19 @@ impl Serialize for Info {
state.end()
}
}
/// An error reported by object types.
#[derive(Debug, thiserror::Error)]
pub enum Error {
/// An error occurred during a file system operation.
#[error(transparent)]
FileSystem(#[from] file_system::Error),
/// An error occurred during a git operation.
#[error(transparent)]
Git(#[from] git::error::Error),
/// Trying to find a file path which could not be found.
#[error("the path '{0}' was not found")]
PathNotFound(file_system::Path),
}
@@ -15,26 +15,26 @@
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
//! Represents git object type 'blob', i.e. actual file contents.
//! See git [doc](https://git-scm.com/book/en/v2/Git-Internals-Git-Objects) for more details.
use std::{
convert::TryFrom as _,
str::{self, FromStr as _},
};
#[cfg(feature = "serialize")]
use serde::{
ser::{SerializeStruct as _, Serializer},
Serialize,
};
use radicle_surf::{
file_system,
vcs::git::{Browser, Rev},
};
use crate::{
commit,
error::Error,
object::{Info, ObjectType},
file_system,
object::{Error, Info, ObjectType},
revision::Revision,
vcs::git::{Browser, Rev},
};
#[cfg(feature = "syntax")]
@@ -64,6 +64,7 @@ impl Blob {
}
}
#[cfg(feature = "serialize")]
impl Serialize for Blob {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
@@ -94,6 +95,7 @@ pub enum BlobContent {
Binary(Vec<u8>),
}
#[cfg(feature = "serialize")]
impl Serialize for BlobContent {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
@@ -15,23 +15,23 @@
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
//! Represents git object type 'tree', i.e. like directory entries in Unix.
//! See git [doc](https://git-scm.com/book/en/v2/Git-Internals-Git-Objects) for more details.
use std::{convert::TryFrom as _, str::FromStr as _};
#[cfg(feature = "serialize")]
use serde::{
ser::{SerializeStruct as _, Serializer},
Serialize,
};
use radicle_surf::{
file_system,
vcs::git::{Browser, Rev},
};
use crate::{
commit,
error::Error,
object::{Info, ObjectType},
file_system,
object::{Error, Info, ObjectType},
revision::Revision,
vcs::git::{Browser, Rev},
};
/// Result of a directory listing, carries other trees and blobs.
@@ -44,6 +44,7 @@ pub struct Tree {
pub info: Info,
}
#[cfg(feature = "serialize")]
impl Serialize for Tree {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
@@ -66,6 +67,7 @@ pub struct TreeEntry {
pub path: String,
}
#[cfg(feature = "serialize")]
impl Serialize for TreeEntry {
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
@@ -15,11 +15,15 @@
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
//! Represents a person in a repo.
#[cfg(feature = "serialize")]
use serde::Serialize;
/// Representation of a person (e.g. committer, author, signer) from a
/// repository. Usually extracted from a signature.
#[derive(Clone, Debug, Serialize)]
#[cfg_attr(feature = "serialize", derive(Serialize))]
#[derive(Clone, Debug)]
pub struct Person {
/// Name part of the commit signature.
pub name: String,
@@ -15,37 +15,56 @@
// You should have received a copy of the GNU General Public License
// along with this program. If not, see <https://www.gnu.org/licenses/>.
//! Represents revisions
use std::convert::TryFrom;
use nonempty::NonEmpty;
#[cfg(feature = "serialize")]
use serde::{Deserialize, Serialize};
use radicle_surf::vcs::git::{self, Browser, RefScope, Rev};
use radicle_git_ext::Oid;
use crate::{
branch::{branches, Branch},
error::Error,
oid::Oid,
tag::{tags, Tag},
git::BranchName,
vcs::git::{self, error::Error, Browser, RefScope, Rev, TagName},
};
/// Types of a peer.
pub enum Category<P, U> {
Local { peer_id: P, user: U },
Remote { peer_id: P, user: U },
/// Local peer.
Local {
/// Peer Id
peer_id: P,
/// User name
user: U,
},
/// Remote peer.
Remote {
/// Peer Id
peer_id: P,
/// User name
user: U,
},
}
/// A revision selector for a `Browser`.
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "camelCase", tag = "type")]
#[cfg_attr(
feature = "serialize",
derive(Deserialize, Serialize),
serde(rename_all = "camelCase", tag = "type")
)]
#[derive(Debug, Clone)]
pub enum Revision<P> {
/// Select a tag under the name provided.
#[serde(rename_all = "camelCase")]
#[cfg_attr(feature = "serialize", serde(rename_all = "camelCase"))]
Tag {
/// Name of the tag.
name: String,
},
/// Select a branch under the name provided.
#[serde(rename_all = "camelCase")]
#[cfg_attr(feature = "serialize", serde(rename_all = "camelCase"))]
Branch {
/// Name of the branch.
name: String,
@@ -53,7 +72,7 @@ pub enum Revision<P> {
peer_id: Option<P>,
},
/// Select a SHA1 under the name provided.
#[serde(rename_all = "camelCase")]
#[cfg_attr(feature = "serialize", serde(rename_all = "camelCase"))]
Sha {
/// The SHA1 value.
sha: Oid,
@@ -83,18 +102,18 @@ where
}
}
/// Bundled response to retrieve both [`Branch`]es and [`Tag`]s for a user's
/// repo.
/// Bundled response to retrieve both [`BranchName`]es and [`TagName`]s for
/// a user's repo.
#[derive(Clone, Debug, PartialEq, Eq)]
pub struct Revisions<P, U> {
/// The peer peer_id for the user.
pub peer_id: P,
/// The user who owns these revisions.
pub user: U,
/// List of [`git::Branch`].
pub branches: NonEmpty<Branch>,
/// List of [`git::Tag`].
pub tags: Vec<Tag>,
/// List of [`git::BranchName`].
pub branches: NonEmpty<BranchName>,
/// List of [`git::TagName`].
pub tags: Vec<TagName>,
}
/// Provide the [`Revisions`] for the given `peer_id`, looking for the
@@ -113,7 +132,7 @@ pub fn remote<P, U>(
where
P: Clone + ToString,
{
let remote_branches = branches(browser, Some(peer_id.clone()).into())?;
let remote_branches = browser.branch_names(Some(peer_id.clone()).into())?;
Ok(
NonEmpty::from_vec(remote_branches).map(|branches| Revisions {
peer_id,
@@ -138,8 +157,8 @@ pub fn local<P, U>(browser: &Browser, peer_id: P, user: U) -> Result<Option<Revi
where
P: Clone + ToString,
{
let local_branches = branches(browser, RefScope::Local)?;
let tags = tags(browser)?;
let local_branches = browser.branch_names(RefScope::Local)?;
let tags = browser.tag_names()?;
Ok(
NonEmpty::from_vec(local_branches).map(|branches| Revisions {
peer_id,
+35
View File
@@ -616,6 +616,24 @@ impl<'a> Browser<'a> {
self.repository.list_branches(filter)
}
/// Given a project id to a repo returns the list of branches.
///
/// # Errors
///
/// Will return [`Error`] if the project doesn't exist or the surf
/// interaction fails.
pub fn branch_names(&self, filter: RefScope) -> Result<Vec<BranchName>, Error> {
let mut branches = self
.list_branches(filter)?
.into_iter()
.map(|b| b.name)
.collect::<Vec<BranchName>>();
branches.sort();
Ok(branches)
}
/// List the names of the _tags_ that are contained in the underlying
/// [`Repository`].
///
@@ -713,6 +731,23 @@ impl<'a> Browser<'a> {
self.repository.list_tags(scope)
}
/// Returns a sorted list of [`TagName`] from the browser.
///
/// # Errors
///
/// * [`error::Error::Git`]
pub fn tag_names(&self) -> Result<Vec<TagName>, Error> {
let tag_names = self.list_tags(RefScope::Local)?;
let mut tags: Vec<TagName> = tag_names
.into_iter()
.map(|tag_name| tag_name.name())
.collect();
tags.sort();
Ok(tags)
}
/// List the namespaces within a `Browser`, filtering out ones that do not
/// parse correctly.
///
+9 -5
View File
@@ -31,9 +31,12 @@ pub struct Author {
/// Email of the author.
pub email: String,
/// Time the action was taken, e.g. time of commit.
#[serde(
serialize_with = "serialize_time",
deserialize_with = "deserialize_time"
#[cfg_attr(
feature = "serialize",
serde(
serialize_with = "serialize_time",
deserialize_with = "deserialize_time"
)
)]
pub time: git2::Time,
}
@@ -91,7 +94,7 @@ impl<'repo> TryFrom<git2::Signature<'repo>> for Author {
pub struct Commit {
// TODO: Replace git2::Oid with git_ext::Oid (https://github.com/radicle-dev/radicle-git/issues/5)
/// Object ID of the Commit, i.e. the SHA1 digest.
#[serde(deserialize_with = "deserialize_oid")]
#[cfg_attr(feature = "serialize", serde(deserialize_with = "deserialize_oid"))]
pub id: Oid,
/// The author of the commit.
pub author: Author,
@@ -102,7 +105,7 @@ pub struct Commit {
/// The summary message of the commit.
pub summary: String,
/// The parents of this commit.
#[serde(deserialize_with = "deserialize_vec_oid")]
#[cfg_attr(feature = "serialize", serde(deserialize_with = "deserialize_vec_oid"))]
pub parents: Vec<Oid>,
}
@@ -193,6 +196,7 @@ impl<'repo> TryFrom<git2::Commit<'repo>> for Commit {
}
}
#[cfg(feature = "serialize")]
#[cfg(test)]
pub mod tests {
use git2::Oid;