ref-format: improve Qualified/NamespacedPattern API

Some elements of the `QaulifiedPattern` and `NamespacedPattern` API
were missing:

  - `From` implementations
  - `Display` implementations
  - `Serialize` and `Deserialize` implementations
  - `qualified_pattern` macro

This also requires bumping versions:

  - `git-ref-format`: 0.3.1
  - `git-ref-core`: 0.3.1
  - `git-ref-format-macro`: 0.3.1
  - `radicle-git-ext`: 0.8.1
  - `radicle-surf`: 0.22.1

Signed-off-by: Fintan Halpenny <fintan.halpenny@gmail.com>
X-Clacks-Overhead: GNU Terry Pratchett
This commit is contained in:
Fintan Halpenny
2024-09-02 13:16:38 +01:00
parent 9d3af5fa43
commit d1cc777cfb
10 changed files with 122 additions and 18 deletions
Generated
+5 -5
View File
@@ -260,7 +260,7 @@ dependencies = [
[[package]]
name = "git-ref-format"
version = "0.3.0"
version = "0.3.1"
dependencies = [
"git-ref-format-core",
"git-ref-format-macro",
@@ -268,7 +268,7 @@ dependencies = [
[[package]]
name = "git-ref-format-core"
version = "0.3.0"
version = "0.3.1"
dependencies = [
"bstr",
"minicbor",
@@ -279,7 +279,7 @@ dependencies = [
[[package]]
name = "git-ref-format-macro"
version = "0.3.0"
version = "0.3.1"
dependencies = [
"git-ref-format-core",
"proc-macro-error",
@@ -641,7 +641,7 @@ dependencies = [
[[package]]
name = "radicle-git-ext"
version = "0.8.0"
version = "0.8.1"
dependencies = [
"git-ref-format",
"git2",
@@ -671,7 +671,7 @@ version = "0.1.0"
[[package]]
name = "radicle-surf"
version = "0.22.0"
version = "0.22.1"
dependencies = [
"anyhow",
"base64",
+2 -2
View File
@@ -1,6 +1,6 @@
[package]
name = "radicle-git-ext"
version = "0.8.0"
version = "0.8.1"
authors = [
"Alexis Sellier <alexis@radicle.xyz>",
"Kim Altintop <kim@eagain.st>",
@@ -31,7 +31,7 @@ default-features = false
features = ["vendored-libgit2"]
[dependencies.git-ref-format]
version = "0.3.0"
version = "0.3.1"
path = "./git-ref-format"
features = ["macro", "serde"]
+3 -3
View File
@@ -1,6 +1,6 @@
[package]
name = "git-ref-format"
version = "0.3.0"
version = "0.3.1"
authors = [
"Kim Altintop <kim@eagain.st>",
"Fintan Halpenny <fintan.halpenny@gmail.com>",
@@ -22,10 +22,10 @@ percent-encoding = ["git-ref-format-core/percent-encoding"]
serde = ["git-ref-format-core/serde"]
[dependencies.git-ref-format-core]
version = "0.3.0"
version = "0.3.1"
path = "./core"
[dependencies.git-ref-format-macro]
version = "0.3.0"
version = "0.3.1"
path = "./macro"
optional = true
@@ -1,6 +1,6 @@
[package]
name = "git-ref-format-core"
version = "0.3.0"
version = "0.3.1"
authors = ["Kim Altintop <kim@eagain.st>"]
edition = "2018"
license = "GPL-3.0-or-later"
@@ -13,7 +13,7 @@ use std::{
use thiserror::Error;
use crate::{check, lit, RefStr, RefString};
use crate::{check, lit, Namespaced, Qualified, RefStr, RefString};
mod iter;
pub use iter::{component, Component, Components, Iter};
@@ -430,6 +430,20 @@ impl AsRef<Self> for QualifiedPattern<'_> {
}
}
impl Display for QualifiedPattern<'_> {
#[inline]
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
self.0.fmt(f)
}
}
impl<'a> From<Qualified<'a>> for QualifiedPattern<'a> {
#[inline]
fn from(q: Qualified<'a>) -> Self {
Self(Cow::Owned(q.into_refstring().into()))
}
}
impl<'a> From<QualifiedPattern<'a>> for Cow<'a, PatternStr> {
#[inline]
fn from(q: QualifiedPattern<'a>) -> Self {
@@ -534,6 +548,13 @@ impl Borrow<PatternStr> for NamespacedPattern<'_> {
}
}
impl<'a> From<Namespaced<'a>> for NamespacedPattern<'a> {
#[inline]
fn from(ns: Namespaced<'a>) -> Self {
NamespacedPattern(Cow::Owned(ns.to_ref_string().into()))
}
}
impl<'a> From<NamespacedPattern<'a>> for QualifiedPattern<'a> {
#[inline]
fn from(ns: NamespacedPattern<'a>) -> Self {
@@ -5,10 +5,10 @@
use std::convert::TryFrom;
use ::serde::{de, Deserialize, Deserializer, Serialize, Serializer};
use serde::{de, Deserialize, Deserializer, Serialize, Serializer};
use crate::{
refspec::{PatternStr, PatternString},
refspec::{NamespacedPattern, PatternStr, PatternString, QualifiedPattern},
Namespaced, Qualified, RefStr, RefString,
};
@@ -145,3 +145,51 @@ impl Serialize for Namespaced<'_> {
serializer.serialize_str(self.as_str())
}
}
impl<'de> Deserialize<'de> for QualifiedPattern<'_> {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: Deserializer<'de>,
{
Deserialize::deserialize(deserializer).and_then(|s: String| {
let s = PatternString::try_from(s).map_err(de::Error::custom)?;
s.qualified()
.ok_or_else(|| de::Error::custom("not a qualified ref"))
.map(|q| q.into_owned())
})
}
}
impl Serialize for QualifiedPattern<'_> {
#[inline]
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
serializer.serialize_str(self.as_str())
}
}
impl<'de> Deserialize<'de> for NamespacedPattern<'_> {
fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
where
D: Deserializer<'de>,
{
Deserialize::deserialize(deserializer).and_then(|s: String| {
let s = PatternString::try_from(s).map_err(de::Error::custom)?;
s.to_namespaced()
.ok_or_else(|| de::Error::custom("not a qualified ref"))
.map(|q| q.into_owned())
})
}
}
impl Serialize for NamespacedPattern<'_> {
#[inline]
fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
where
S: Serializer,
{
serializer.serialize_str(self.as_str())
}
}
@@ -1,6 +1,6 @@
[package]
name = "git-ref-format-macro"
version = "0.3.0"
version = "0.3.1"
authors = ["Kim Altintop <kim@eagain.st>"]
edition = "2018"
license = "GPL-3.0-or-later"
@@ -18,5 +18,5 @@ quote = "1"
syn = "2"
[dependencies.git-ref-format-core]
version = "0.3.0"
version = "0.3.1"
path = "../core"
@@ -166,3 +166,35 @@ pub fn pattern(input: TokenStream) -> TokenStream {
}
}
}
/// Create a [`git_ref_format_core::refspec::QualifiedPattern`] from a string
/// literal.
///
/// The string is validated at compile time, and an unsafe conversion is
/// emitted.
#[proc_macro_error]
#[proc_macro]
pub fn qualified_pattern(input: TokenStream) -> TokenStream {
let lit = parse_macro_input!(input as LitStr);
let val = lit.value();
let parsed: Result<&PatternStr, Error> = val.as_str().try_into();
match parsed {
Ok(safe) => {
let safe: &str = safe.as_str();
let expand = quote! {
unsafe {
use ::std::mem::transmute;
use ::radicle_git_ext::ref_format::refspec::QualifiedPattern;
transmute::<_, QualifiedPattern>(#safe.to_owned())
}
};
TokenStream::from(expand)
}
Err(e) => {
abort!(lit.span(), "invalid refspec pattern literal: {}", e);
}
}
}
@@ -145,4 +145,7 @@ pub mod refspec {
#[cfg(any(feature = "macro", feature = "git-ref-format-macro"))]
pub use git_ref_format_macro::pattern;
#[cfg(any(feature = "macro", feature = "git-ref-format-macro"))]
pub use git_ref_format_macro::qualified_pattern;
}
+2 -2
View File
@@ -2,7 +2,7 @@
name = "radicle-surf"
description = "A code surfing library for Git repositories"
readme = "README.md"
version = "0.22.0"
version = "0.22.1"
authors = ["The Radicle Team <dev@radicle.xyz>"]
edition = "2021"
homepage = "https://github.com/radicle-dev/radicle-git/blob/main/radicle-surf/README.md"
@@ -41,7 +41,7 @@ default-features = false
features = ["vendored-libgit2"]
[dependencies.radicle-git-ext]
version = "0.8.0"
version = "0.8.1"
path = "../radicle-git-ext"
features = ["serde"]