alibi_api/plugins/organization/hooks/
organization.rs1use crate::plugins::organization::types::CreatedOrganizationResponse;
2use alibi_core::AuthResult;
3use alibi_core::CreateMember;
4use alibi_core::CreateOrganization;
5use alibi_core::Member;
6use alibi_core::Organization;
7use alibi_core::UpdateOrganization;
8use alibi_core::utils::json::JsValue;
9use alibi_core::wire::UserView;
10use async_trait::async_trait;
11use indexmap::IndexMap;
12use serde_json::Map;
13use serde_json::Value;
14
15#[derive(Debug, Clone)]
17pub struct OrganizationDraftContext {
18 pub organization: CreateOrganization,
19 pub user: UserView,
20}
21
22#[derive(Debug, Clone)]
24pub struct OrganizationMemberDraftContext {
25 pub organization: Organization,
26 pub member: CreateMember,
27 pub user: UserView,
28}
29
30#[derive(Debug, Clone)]
33pub struct OrganizationCreatedContext {
34 pub organization: Organization,
35 pub member: Member,
36 pub user: UserView,
37}
38
39#[derive(Debug, Clone, Default)]
41pub struct OrganizationCreatePatch {
42 pub id: Option<String>,
43 pub name: Option<String>,
44 pub slug: Option<String>,
45 pub logo: Option<Option<String>>,
47 pub metadata: Option<Option<Map<String, Value>>>,
51}
52impl OrganizationCreatePatch {
53 pub(in crate::plugins) fn apply(self, data: &mut CreateOrganization) {
54 if let Some(id) = self.id {
55 data.id = Some(id);
56 }
57 if let Some(name) = self.name {
58 data.name = name;
59 }
60 if let Some(slug) = self.slug {
61 data.slug = slug;
62 }
63 if let Some(logo) = self.logo {
64 data.logo = logo;
65 }
66 if let Some(metadata) = self.metadata {
67 data.metadata = metadata.map(Value::Object);
68 }
69 }
70}
71
72#[derive(Debug, Clone, Default)]
74pub struct OrganizationMemberCreatePatch {
75 pub organization_id: Option<String>,
76 pub user_id: Option<String>,
77 pub role: Option<String>,
78}
79impl OrganizationMemberCreatePatch {
80 pub(in crate::plugins) fn apply(self, data: &mut CreateMember) {
81 if let Some(id) = self.organization_id {
82 data.organization_id = id;
83 }
84 if let Some(id) = self.user_id {
85 data.user_id = id;
86 }
87 if let Some(role) = self.role {
88 data.role = role;
89 }
90 }
91}
92
93#[async_trait]
101pub trait OrganizationCreationHooks: std::fmt::Debug + Send + Sync {
102 async fn before_create(
103 &self,
104 _context: &OrganizationDraftContext,
105 ) -> AuthResult<Option<OrganizationCreatePatch>> {
106 Ok(None)
107 }
108 async fn before_add_member(
109 &self,
110 _context: &OrganizationMemberDraftContext,
111 ) -> AuthResult<Option<OrganizationMemberCreatePatch>> {
112 Ok(None)
113 }
114 async fn after_add_member(&self, _context: &OrganizationCreatedContext) -> AuthResult<()> {
115 Ok(())
116 }
117 async fn after_create(&self, _context: &OrganizationCreatedContext) -> AuthResult<()> {
118 Ok(())
119 }
120}
121
122#[derive(Debug, Clone)]
127pub struct OrganizationDeleteContext {
128 pub organization: crate::plugins::organization::types::OrganizationResponse,
129 pub user: UserView,
130 pub session: alibi_core::wire::SessionView,
131 pub headers: std::collections::HashMap<String, String>,
133 pub request: Option<alibi_core::AuthRequest>,
136}
137
138pub(in crate::plugins) struct DeleteInvocation<'a> {
139 pub headers: &'a std::collections::HashMap<String, String>,
140 pub request: Option<&'a alibi_core::AuthRequest>,
141}
142
143#[async_trait]
150pub trait OrganizationDeletionHooks: std::fmt::Debug + Send + Sync {
151 async fn before_delete(&self, _context: &OrganizationDeleteContext) -> AuthResult<()> {
152 Ok(())
153 }
154 async fn after_delete(&self, _context: &OrganizationDeleteContext) -> AuthResult<()> {
155 Ok(())
156 }
157}
158
159#[derive(Debug, Clone)]
161pub struct OrganizationUpdateInput {
162 pub name: Option<String>,
163 pub slug: Option<String>,
164 pub logo: Option<Option<String>>,
165 pub metadata: Option<IndexMap<String, JsValue>>,
167}
168
169#[derive(Debug, Clone)]
171pub struct OrganizationUpdateContext {
172 pub organization: OrganizationUpdateInput,
173 pub user: UserView,
174 pub member: Member,
175}
176
177#[derive(Debug, Clone)]
180pub struct OrganizationUpdatedContext {
181 pub organization: Option<CreatedOrganizationResponse>,
182 pub user: UserView,
183 pub member: Member,
184}
185
186#[derive(Debug, Clone, Default)]
188pub struct OrganizationUpdatePatch {
189 pub name: Option<String>,
190 pub slug: Option<String>,
191 pub logo: Option<Option<String>>,
193 pub metadata: Option<Option<IndexMap<String, JsValue>>>,
196}
197impl OrganizationUpdatePatch {
198 pub(in crate::plugins) fn apply(self, data: &mut UpdateOrganization) -> AuthResult<()> {
202 if let Some(name) = self.name {
203 data.name = Some(name);
204 }
205 if let Some(slug) = self.slug {
206 data.slug = Some(slug);
207 }
208 if let Some(logo) = self.logo {
209 data.logo = Some(logo);
210 }
211 if let Some(metadata) = self.metadata {
212 data.metadata = Some(
213 metadata
214 .map_or(JsValue::Null, JsValue::Object)
215 .to_json_value()?,
216 );
217 }
218 Ok(())
219 }
220}
221
222#[async_trait]
229pub trait OrganizationUpdateHooks: std::fmt::Debug + Send + Sync {
230 async fn before_update(
231 &self,
232 _context: &OrganizationUpdateContext,
233 ) -> AuthResult<Option<OrganizationUpdatePatch>> {
234 Ok(None)
235 }
236 async fn after_update(&self, _context: &OrganizationUpdatedContext) -> AuthResult<()> {
237 Ok(())
238 }
239}