use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, Copy, Default, PartialEq, Eq, Serialize, Deserialize)]
pub struct SchemaPrivileges {
#[serde(default)]
pub usage: bool,
#[serde(default)]
pub create: bool,
}
impl SchemaPrivileges {
pub const ALL: Self = Self {
usage: true,
create: true,
};
#[must_use]
pub const fn is_empty(self) -> bool {
!self.usage && !self.create
}
#[must_use]
pub const fn intersects(self, other: Self) -> bool {
self.usage && other.usage || self.create && other.create
}
pub fn insert(&mut self, other: Self) {
self.usage |= other.usage;
self.create |= other.create;
}
pub fn remove(&mut self, other: Self) {
self.usage &= !other.usage;
self.create &= !other.create;
}
}
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
pub struct SchemaAclEntry {
pub role: String,
#[serde(default, skip_serializing_if = "Option::is_none")]
pub grantor: Option<String>,
#[serde(default)]
pub privileges: SchemaPrivileges,
#[serde(default)]
pub grant_options: SchemaPrivileges,
}
#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
pub struct SchemaRow {
pub name: String,
#[serde(default = "default_schema_role_owner")]
pub role_owner: String,
#[serde(default, skip_serializing_if = "Option::is_none")]
pub acl: Option<Vec<SchemaAclEntry>>,
}
impl SchemaRow {
#[must_use]
pub fn legacy(name: impl Into<String>) -> Self {
let name = name.into();
let acl = (name == "public").then(|| {
vec![
SchemaAclEntry {
role: "uqa".into(),
grantor: Some("uqa".into()),
privileges: SchemaPrivileges::ALL,
grant_options: SchemaPrivileges::default(),
},
SchemaAclEntry {
role: "PUBLIC".into(),
grantor: Some("uqa".into()),
privileges: SchemaPrivileges {
usage: true,
create: false,
},
grant_options: SchemaPrivileges::default(),
},
]
});
Self {
name,
role_owner: default_schema_role_owner(),
acl,
}
}
}
fn default_schema_role_owner() -> String {
"uqa".into()
}