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