drizzle_types/postgres/ddl/
privilege.rs1use crate::alloc_prelude::*;
6
7#[cfg(feature = "serde")]
8use crate::serde_helpers::cow_from_string;
9
10#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash, Default)]
16#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
17#[cfg_attr(feature = "serde", serde(rename_all = "SCREAMING_SNAKE_CASE"))]
18pub enum PrivilegeType {
19 #[default]
21 All,
22 Select,
24 Insert,
26 Update,
28 Delete,
30 Truncate,
32 References,
34 Trigger,
36}
37
38impl PrivilegeType {
39 #[must_use]
41 pub const fn as_sql(&self) -> &'static str {
42 match self {
43 Self::All => "ALL",
44 Self::Select => "SELECT",
45 Self::Insert => "INSERT",
46 Self::Update => "UPDATE",
47 Self::Delete => "DELETE",
48 Self::Truncate => "TRUNCATE",
49 Self::References => "REFERENCES",
50 Self::Trigger => "TRIGGER",
51 }
52 }
53
54 #[must_use]
56 pub fn from_sql(s: &str) -> Option<Self> {
57 match s.to_uppercase().as_str() {
58 "ALL" => Some(Self::All),
59 "SELECT" => Some(Self::Select),
60 "INSERT" => Some(Self::Insert),
61 "UPDATE" => Some(Self::Update),
62 "DELETE" => Some(Self::Delete),
63 "TRUNCATE" => Some(Self::Truncate),
64 "REFERENCES" => Some(Self::References),
65 "TRIGGER" => Some(Self::Trigger),
66 _ => None,
67 }
68 }
69}
70
71#[derive(Clone, Copy, Debug, PartialEq, Eq, Hash)]
77pub struct PrivilegeDef {
78 pub grantor: &'static str,
80 pub grantee: &'static str,
82 pub schema: &'static str,
84 pub table: &'static str,
86 pub privilege_type: PrivilegeType,
88 pub is_grantable: bool,
90}
91
92impl PrivilegeDef {
93 #[must_use]
95 pub const fn new(
96 schema: &'static str,
97 table: &'static str,
98 grantee: &'static str,
99 privilege_type: PrivilegeType,
100 ) -> Self {
101 Self {
102 grantor: "",
103 grantee,
104 schema,
105 table,
106 privilege_type,
107 is_grantable: false,
108 }
109 }
110
111 #[must_use]
113 pub const fn grantor(self, grantor: &'static str) -> Self {
114 Self { grantor, ..self }
115 }
116
117 #[must_use]
119 pub const fn grantable(self) -> Self {
120 Self {
121 is_grantable: true,
122 ..self
123 }
124 }
125
126 #[must_use]
128 pub const fn into_privilege(self) -> Privilege {
129 Privilege {
130 grantor: Cow::Borrowed(self.grantor),
131 grantee: Cow::Borrowed(self.grantee),
132 schema: Cow::Borrowed(self.schema),
133 table: Cow::Borrowed(self.table),
134 privilege_type: self.privilege_type,
135 is_grantable: self.is_grantable,
136 }
137 }
138}
139
140impl Default for PrivilegeDef {
141 fn default() -> Self {
142 Self::new("public", "", "", PrivilegeType::All)
143 }
144}
145
146#[derive(Clone, Debug, PartialEq, Eq)]
152#[cfg_attr(feature = "serde", derive(serde::Serialize, serde::Deserialize))]
153#[cfg_attr(feature = "serde", serde(rename_all = "camelCase"))]
154pub struct Privilege {
155 #[cfg_attr(feature = "serde", serde(deserialize_with = "cow_from_string"))]
157 pub grantor: Cow<'static, str>,
158
159 #[cfg_attr(feature = "serde", serde(deserialize_with = "cow_from_string"))]
161 pub grantee: Cow<'static, str>,
162
163 #[cfg_attr(feature = "serde", serde(deserialize_with = "cow_from_string"))]
165 pub schema: Cow<'static, str>,
166
167 #[cfg_attr(feature = "serde", serde(deserialize_with = "cow_from_string"))]
169 pub table: Cow<'static, str>,
170
171 #[cfg_attr(feature = "serde", serde(rename = "type"))]
173 pub privilege_type: PrivilegeType,
174
175 #[cfg_attr(feature = "serde", serde(default))]
177 pub is_grantable: bool,
178}
179
180impl Privilege {
181 #[must_use]
183 pub fn new(
184 schema: impl Into<Cow<'static, str>>,
185 table: impl Into<Cow<'static, str>>,
186 grantee: impl Into<Cow<'static, str>>,
187 privilege_type: PrivilegeType,
188 ) -> Self {
189 Self {
190 grantor: Cow::Borrowed(""),
191 grantee: grantee.into(),
192 schema: schema.into(),
193 table: table.into(),
194 privilege_type,
195 is_grantable: false,
196 }
197 }
198
199 #[inline]
201 #[must_use]
202 pub fn schema(&self) -> &str {
203 &self.schema
204 }
205
206 #[inline]
208 #[must_use]
209 pub fn table(&self) -> &str {
210 &self.table
211 }
212
213 #[inline]
215 #[must_use]
216 pub fn grantee(&self) -> &str {
217 &self.grantee
218 }
219
220 #[inline]
222 #[must_use]
223 pub fn grantor(&self) -> &str {
224 &self.grantor
225 }
226}
227
228impl Default for Privilege {
229 fn default() -> Self {
230 Self::new("public", "", "", PrivilegeType::All)
231 }
232}
233
234impl From<PrivilegeDef> for Privilege {
235 fn from(def: PrivilegeDef) -> Self {
236 def.into_privilege()
237 }
238}
239
240#[cfg(test)]
241mod tests {
242 use super::*;
243
244 #[test]
245 fn test_const_privilege_def() {
246 const PRIV: PrivilegeDef =
247 PrivilegeDef::new("public", "users", "app_user", PrivilegeType::Select)
248 .grantor("admin")
249 .grantable();
250
251 assert_eq!(PRIV.schema, "public");
252 assert_eq!(PRIV.table, "users");
253 assert_eq!(PRIV.grantee, "app_user");
254 assert_eq!(PRIV.grantor, "admin");
255 assert_eq!(PRIV.privilege_type, PrivilegeType::Select);
256 const {
257 assert!(PRIV.is_grantable);
258 }
259 }
260
261 #[test]
262 fn test_privilege_def_to_privilege() {
263 const DEF: PrivilegeDef =
264 PrivilegeDef::new("public", "users", "reader", PrivilegeType::Select);
265 let priv_ = DEF.into_privilege();
266 assert_eq!(priv_.schema(), "public");
267 assert_eq!(priv_.table(), "users");
268 assert_eq!(priv_.grantee(), "reader");
269 }
270
271 #[test]
272 fn test_privilege_type_sql() {
273 assert_eq!(PrivilegeType::Select.as_sql(), "SELECT");
274 assert_eq!(PrivilegeType::All.as_sql(), "ALL");
275 assert_eq!(PrivilegeType::Truncate.as_sql(), "TRUNCATE");
276 }
277}