bonsaidb_core/admin/
role.rs1use actionable::Permissions;
2use serde::{Deserialize, Serialize};
3
4use crate::admin::group;
5use crate::connection::{AsyncStorageConnection, Connection, IdentityReference, StorageConnection};
6use crate::define_basic_unique_mapped_view;
7use crate::document::{CollectionDocument, Emit};
8use crate::schema::{Collection, Nameable, NamedCollection, SerializedCollection};
9
10#[derive(Clone, Debug, Serialize, Deserialize, Collection)]
12#[collection(name = "role", authority="khonsulabs", views = [ByName], core = crate)]
13#[must_use]
14pub struct Role {
15 pub name: String,
17 pub groups: Vec<u64>,
19}
20
21impl Role {
22 pub fn named<S: Into<String>>(name: S) -> Self {
24 Self {
25 name: name.into(),
26 groups: Vec::new(),
27 }
28 }
29
30 pub fn with_group_ids<I: IntoIterator<Item = u64>>(mut self, ids: I) -> Self {
32 self.groups = ids.into_iter().collect();
33 self
34 }
35
36 pub fn assume_identity<'name, Storage: StorageConnection>(
37 name_or_id: impl Nameable<'name, u64>,
38 storage: &Storage,
39 ) -> Result<Storage::Authenticated, crate::Error> {
40 storage.assume_identity(IdentityReference::Role(name_or_id.name()?))
41 }
42
43 pub async fn assume_identity_async<'name, Storage: AsyncStorageConnection>(
44 name_or_id: impl Nameable<'name, u64> + Send,
45 storage: &Storage,
46 ) -> Result<Storage::Authenticated, crate::Error> {
47 storage
48 .assume_identity(IdentityReference::Role(name_or_id.name()?))
49 .await
50 }
51
52 pub fn effective_permissions<C: Connection>(
54 &self,
55 admin: &C,
56 inherit_permissions: &Permissions,
57 ) -> Result<Permissions, crate::Error> {
58 let groups = group::PermissionGroup::get_multiple(&self.groups, admin)?;
59
60 let merged_permissions = Permissions::merged(
62 groups
63 .into_iter()
64 .map(|group| Permissions::from(group.contents.statements))
65 .collect::<Vec<_>>()
66 .iter()
67 .chain(std::iter::once(inherit_permissions)),
68 );
69
70 Ok(merged_permissions)
71 }
72}
73
74impl NamedCollection for Role {
75 type ByNameView = ByName;
76}
77
78define_basic_unique_mapped_view!(
79 ByName,
80 Role,
81 1,
82 "by-name",
83 String,
84 |document: CollectionDocument<Role>| { document.header.emit_key(document.contents.name) }
85);