Skip to content

Commit 95577e2

Browse files
committed
feat: A shared permission::Error type (#301)
1 parent 97e53f6 commit 95577e2

File tree

1 file changed

+29
-11
lines changed

1 file changed

+29
-11
lines changed

git-sec/src/lib.rs

Lines changed: 29 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -79,19 +79,19 @@ pub mod permission {
7979
use std::fmt::{Debug, Display};
8080

8181
/// A marker trait to signal tags for permissions.
82-
pub trait Tag: Debug {}
82+
pub trait Tag: Debug + Clone {}
8383

8484
/// A tag indicating that a permission is applying to the contents of a configuration file.
85-
#[derive(Debug)]
85+
#[derive(Debug, Clone)]
8686
pub struct Config;
8787
impl Tag for Config {}
8888

8989
/// A tag indicating that a permission is applying to the resource itself.
90-
#[derive(Debug)]
90+
#[derive(Debug, Clone)]
9191
pub struct Resource;
9292
impl Tag for Resource {}
9393

94-
impl<P: Debug + Display> Access<Config, P> {
94+
impl<P: Debug + Display + Clone> Access<Config, P> {
9595
/// Create a permission for values contained in git configuration files.
9696
///
9797
/// This applies permissions to values contained inside of these files.
@@ -103,7 +103,7 @@ pub mod permission {
103103
}
104104
}
105105

106-
impl<P: Debug + Display> Access<Resource, P> {
106+
impl<P: Debug + Display + Clone> Access<Resource, P> {
107107
/// Create a permission a file or directory itself.
108108
///
109109
/// This applies permissions to a configuration file itself and whether it can be used at all, or to a directory
@@ -124,8 +124,10 @@ pub mod permission {
124124
#[derive(Debug, thiserror::Error)]
125125
#[error("Not allowed to handle resource {:?}: permission {}", .resource, .permission)]
126126
pub struct Error<R: Debug, P: Debug + Display> {
127-
resource: R,
128-
permission: P,
127+
/// The resource which cannot be used.
128+
pub resource: R,
129+
/// The permission causing it to be disallowed.
130+
pub permission: P,
129131
}
130132
}
131133

@@ -141,6 +143,22 @@ pub enum Permission {
141143
Allow,
142144
}
143145

146+
impl Permission {
147+
/// Check this permissions and produce a reply to indicate if the `resource` can be used and in which way.
148+
///
149+
/// Only if this permission is set to `Allow` will the resource be usable.
150+
pub fn check<R: Debug>(&self, resource: R) -> Result<Option<R>, permission::Error<R, Self>> {
151+
match self {
152+
Permission::Allow => Ok(Some(resource)),
153+
Permission::Deny => Ok(None),
154+
Permission::Forbid => Err(permission::Error {
155+
resource,
156+
permission: self.clone(),
157+
}),
158+
}
159+
}
160+
}
161+
144162
impl Display for Permission {
145163
fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
146164
Display::fmt(
@@ -172,20 +190,20 @@ impl Display for ReadWrite {
172190
}
173191

174192
/// A container to define tagged access permissions, rendering the permission read-only.
175-
#[derive(Debug)]
176-
pub struct Access<T: permission::Tag, P: Debug + Display> {
193+
#[derive(Debug, Clone)]
194+
pub struct Access<T: permission::Tag, P: Debug + Display + Clone> {
177195
/// The access permission itself.
178196
permission: P,
179197
_data: PhantomData<T>,
180198
}
181199

182-
impl<T: permission::Tag, P: Debug + Display> Display for Access<T, P> {
200+
impl<T: permission::Tag, P: Debug + Display + Clone> Display for Access<T, P> {
183201
fn fmt(&self, f: &mut Formatter<'_>) -> std::fmt::Result {
184202
Display::fmt(&self.permission, f)
185203
}
186204
}
187205

188-
impl<T: permission::Tag, P: Debug + Display> Deref for Access<T, P> {
206+
impl<T: permission::Tag, P: Debug + Display + Clone> Deref for Access<T, P> {
189207
type Target = P;
190208

191209
fn deref(&self) -> &Self::Target {

0 commit comments

Comments
 (0)