mirror of
https://github.com/rustmailer/bichon.git
synced 2026-08-03 07:48:34 +02:00
refactor: replace native_db with memdb and add tests
This commit is contained in:
@@ -38,11 +38,9 @@ impl AccessTokenApi {
|
||||
&self,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Vec<AccessTokenResp>>> {
|
||||
context
|
||||
.require_permission(None, Permission::TOKEN_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(None, Permission::TOKEN_MANAGE)?;
|
||||
|
||||
Ok(Json(AccessTokenModel::list_all_api_tokens().await?))
|
||||
Ok(Json(AccessTokenModel::list_all_api_tokens()?))
|
||||
}
|
||||
|
||||
/// Deletes a specific access token.
|
||||
@@ -58,14 +56,12 @@ impl AccessTokenApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let token = token.0.trim();
|
||||
let token = AccessTokenModel::get_token(token).await?;
|
||||
let token = AccessTokenModel::get_token(token)?;
|
||||
if context.user.id != token.user_id {
|
||||
context
|
||||
.require_permission(None, Permission::TOKEN_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(None, Permission::TOKEN_MANAGE)?;
|
||||
}
|
||||
|
||||
Ok(AccessTokenModel::delete(&token.token).await?)
|
||||
Ok(AccessTokenModel::delete(&token.token)?)
|
||||
}
|
||||
|
||||
/// Creates a new api token.
|
||||
@@ -83,12 +79,10 @@ impl AccessTokenApi {
|
||||
let current_user_id = context.user.id;
|
||||
let target_user_id = payload.0.user_id.unwrap_or(current_user_id);
|
||||
if target_user_id != current_user_id {
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
}
|
||||
|
||||
let token_string = AccessTokenModel::create_api_token(target_user_id, payload.0).await?;
|
||||
let token_string = AccessTokenModel::create_api_token(target_user_id, payload.0)?;
|
||||
Ok(PlainText(token_string))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -56,10 +56,8 @@ impl AccountApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<AccountModel>> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)
|
||||
.await?;
|
||||
Ok(Json(AccountModel::async_get(account_id).await?))
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)?;
|
||||
Ok(Json(AccountModel::get(account_id)?))
|
||||
}
|
||||
|
||||
/// Delete an account by ID - WARNING: This permanently removes the account and all associated resources
|
||||
@@ -75,10 +73,9 @@ impl AccountApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)
|
||||
.await?;
|
||||
Ok(AccountModel::delete(account_id).await?)
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)?;
|
||||
AccountModel::delete(account_id).await?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// Create a new account
|
||||
@@ -89,9 +86,7 @@ impl AccountApi {
|
||||
payload: Json<AccountCreateRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<AccountModel>> {
|
||||
context
|
||||
.require_permission(None, Permission::ACCOUNT_CREATE)
|
||||
.await?;
|
||||
context.require_permission(None, Permission::ACCOUNT_CREATE)?;
|
||||
let account = AccountModel::create_account(context.user.id, payload.0).await?;
|
||||
Ok(Json(account))
|
||||
}
|
||||
@@ -111,10 +106,8 @@ impl AccountApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)
|
||||
.await?;
|
||||
Ok(AccountModel::update(account_id, payload.0, true).await?)
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)?;
|
||||
Ok(AccountModel::update(account_id, payload.0, true)?)
|
||||
}
|
||||
|
||||
/// List accounts with optional pagination parameters
|
||||
@@ -129,16 +122,15 @@ impl AccountApi {
|
||||
desc: Query<Option<bool>>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<DataPage<AccountResp>>> {
|
||||
let is_admin = context.user.is_admin().await;
|
||||
let is_admin = context.user.is_admin();
|
||||
let sort_desc = desc.0.unwrap_or(true);
|
||||
|
||||
let user_map: HashMap<u64, UserModel> = UserModel::list_all()
|
||||
.await?
|
||||
let user_map: HashMap<u64, UserModel> = UserModel::list_all()?
|
||||
.into_iter()
|
||||
.map(|u| (u.id, u))
|
||||
.collect();
|
||||
let page_data: DataPage<AccountModel> = if is_admin {
|
||||
AccountModel::paginate_list(page.0, page_size.0, desc.0).await?
|
||||
AccountModel::paginate_list(page.0, page_size.0, desc.0)?
|
||||
} else {
|
||||
let authorized_ids: HashSet<u64> =
|
||||
context.user.account_access_map.keys().cloned().collect();
|
||||
@@ -153,8 +145,7 @@ impl AccountApi {
|
||||
}));
|
||||
}
|
||||
|
||||
let mut accounts: Vec<AccountModel> = AccountModel::list_all()
|
||||
.await?
|
||||
let mut accounts: Vec<AccountModel> = AccountModel::list_all()?
|
||||
.into_iter()
|
||||
.filter(|acct| authorized_ids.contains(&acct.id))
|
||||
.collect();
|
||||
@@ -198,11 +189,9 @@ impl AccountApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<DownloadState>> {
|
||||
let account_id = account_id.0;
|
||||
AccountModel::check_account_exists(account_id).await?;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)
|
||||
.await?;
|
||||
let state = DownloadState::get(account_id).await?;
|
||||
AccountModel::check_account_exists(account_id)?;
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)?;
|
||||
let state = DownloadState::get(account_id)?;
|
||||
let state = state.unwrap_or(DownloadState::empty(account_id));
|
||||
Ok(Json(state))
|
||||
}
|
||||
@@ -220,16 +209,14 @@ impl AccountApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let account_id = account_id.0;
|
||||
let account = AccountModel::check_account_exists(account_id).await?;
|
||||
let account = AccountModel::check_account_exists(account_id)?;
|
||||
if !matches!(account.account_type, AccountType::IMAP) {
|
||||
return Err(raise_error!(
|
||||
format!("Manual download is not supported for '{:#?}' accounts. Only IMAP accounts are supported.", account.account_type),
|
||||
ErrorCode::InvalidParameter
|
||||
))?;
|
||||
}
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)?;
|
||||
SYNC_TASKS.start_manual_task(account_id).await?;
|
||||
Ok(())
|
||||
}
|
||||
@@ -247,7 +234,7 @@ impl AccountApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let account_id = account_id.0;
|
||||
let account = AccountModel::check_account_exists(account_id).await?;
|
||||
let account = AccountModel::check_account_exists(account_id)?;
|
||||
|
||||
if !matches!(account.account_type, AccountType::IMAP) {
|
||||
return Err(raise_error!(
|
||||
@@ -255,9 +242,7 @@ impl AccountApi {
|
||||
ErrorCode::InvalidParameter
|
||||
))?;
|
||||
}
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)?;
|
||||
|
||||
if !SYNC_TASKS.is_manual_running(account_id).await {
|
||||
return Err(raise_error!(
|
||||
@@ -282,11 +267,9 @@ impl AccountApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<AccountStats>> {
|
||||
let account_id = account_id.0;
|
||||
AccountModel::check_account_exists(account_id).await?;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)
|
||||
.await?;
|
||||
let state = ENVELOPE_MANAGER.get_account_stats(account_id).await?;
|
||||
AccountModel::check_account_exists(account_id)?;
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)?;
|
||||
let state = ENVELOPE_MANAGER.get_account_stats(account_id)?;
|
||||
Ok(Json(state))
|
||||
}
|
||||
|
||||
@@ -304,10 +287,10 @@ impl AccountApi {
|
||||
only_nosync: Query<Option<bool>>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Vec<MinimalAccount>>> {
|
||||
let is_admin = context.user.is_admin().await;
|
||||
let is_admin = context.user.is_admin();
|
||||
let only_nosync = only_nosync.0.unwrap_or_default();
|
||||
|
||||
let minimal_list = AccountModel::minimal_list(only_nosync).await?;
|
||||
let minimal_list = AccountModel::minimal_list(only_nosync)?;
|
||||
if is_admin {
|
||||
return Ok(Json(minimal_list));
|
||||
}
|
||||
@@ -323,8 +306,8 @@ impl AccountApi {
|
||||
req: Json<BatchAccountRoleRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
req.validate_existence().await?;
|
||||
req.0.do_assign(&context).await?;
|
||||
req.validate_existence()?;
|
||||
req.0.do_assign(&context)?;
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -52,17 +52,13 @@ impl AttachmentApi {
|
||||
payload: Json<AttachmentSearchRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<DataPage<AttachmentModel>>> {
|
||||
let authorized_ids: Option<HashSet<u64>> = if context
|
||||
.has_permission(None, Permission::DATA_READ_ALL)
|
||||
.await
|
||||
{
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(
|
||||
search_attachment_impl(authorized_ids, payload.0).await?,
|
||||
))
|
||||
let authorized_ids: Option<HashSet<u64>> =
|
||||
if context.has_permission(None, Permission::DATA_READ_ALL) {
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(search_attachment_impl(authorized_ids, payload.0)?))
|
||||
}
|
||||
|
||||
/// Retrieves the attachment (metadata) of a specific message.
|
||||
@@ -80,13 +76,10 @@ impl AttachmentApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<AttachmentModel>> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_READ)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_READ)?;
|
||||
let attachment_id = attachment_id.0;
|
||||
let a = ATTACHMENT_MANAGER
|
||||
.get_attachment_by_id(account_id, &attachment_id)
|
||||
.await?
|
||||
.get_attachment_by_id(account_id, &attachment_id)?
|
||||
.ok_or_else(|| {
|
||||
raise_error!(
|
||||
format!(
|
||||
@@ -109,15 +102,13 @@ impl AttachmentApi {
|
||||
&self,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Vec<TagCount>>> {
|
||||
let authorized_ids: Option<HashSet<u64>> = if context
|
||||
.has_permission(None, Permission::DATA_READ_ALL)
|
||||
.await
|
||||
{
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(ATTACHMENT_MANAGER.get_all_tags(authorized_ids).await?))
|
||||
let authorized_ids: Option<HashSet<u64>> =
|
||||
if context.has_permission(None, Permission::DATA_READ_ALL) {
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(ATTACHMENT_MANAGER.get_all_tags(authorized_ids)?))
|
||||
}
|
||||
|
||||
/// Adds or removes facet tags for multiple emails across accounts.
|
||||
@@ -137,9 +128,7 @@ impl AttachmentApi {
|
||||
}
|
||||
|
||||
for account_id in req.updates.keys() {
|
||||
context
|
||||
.require_permission(Some(*account_id), Permission::DATA_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(Some(*account_id), Permission::DATA_MANAGE)?;
|
||||
}
|
||||
|
||||
ATTACHMENT_MANAGER.update_attachment_tags(req).await?;
|
||||
@@ -156,17 +145,13 @@ impl AttachmentApi {
|
||||
&self,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<HashSet<String>>> {
|
||||
let authorized_ids: Option<HashSet<u64>> = if context
|
||||
.has_permission(None, Permission::DATA_READ_ALL)
|
||||
.await
|
||||
{
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(
|
||||
ATTACHMENT_MANAGER.get_all_senders(authorized_ids).await?,
|
||||
))
|
||||
let authorized_ids: Option<HashSet<u64>> =
|
||||
if context.has_permission(None, Permission::DATA_READ_ALL) {
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(ATTACHMENT_MANAGER.get_all_senders(authorized_ids)?))
|
||||
}
|
||||
|
||||
/// Retrieves unique metadata for all attachments across authorized accounts.
|
||||
@@ -179,14 +164,12 @@ impl AttachmentApi {
|
||||
&self,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<AttachmentMetadata>> {
|
||||
let authorized_ids: Option<HashSet<u64>> = if context
|
||||
.has_permission(None, Permission::DATA_READ_ALL)
|
||||
.await
|
||||
{
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
let authorized_ids: Option<HashSet<u64>> =
|
||||
if context.has_permission(None, Permission::DATA_READ_ALL) {
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(
|
||||
ATTACHMENT_MANAGER.collect_attachment_metadata(authorized_ids)?,
|
||||
))
|
||||
|
||||
@@ -44,10 +44,7 @@ impl AutoConfigApi {
|
||||
email_address: Path<String>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<MailServerConfig>> {
|
||||
context
|
||||
.require_permission(None, Permission::ACCOUNT_CREATE)
|
||||
.await?;
|
||||
|
||||
context.require_permission(None, Permission::ACCOUNT_CREATE)?;
|
||||
let result = resolve_autoconfig(email_address.0.trim())
|
||||
.await?
|
||||
.ok_or_else(|| {
|
||||
|
||||
@@ -44,9 +44,7 @@ impl ImportApi {
|
||||
payload: Json<BatchEmlRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<BatchEmlResult>> {
|
||||
context
|
||||
.require_permission(Some(payload.0.account_id), Permission::DATA_IMPORT_BATCH)
|
||||
.await?;
|
||||
context.require_permission(Some(payload.0.account_id), Permission::DATA_IMPORT_BATCH)?;
|
||||
Ok(Json(ImportEmls::do_import(payload.0).await?))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -53,9 +53,7 @@ impl MailBoxApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Vec<MailBox>>> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_READ_DETAILS)?;
|
||||
let remote = remote.0.unwrap_or(false);
|
||||
Ok(Json(get_account_mailboxes(account_id, remote).await?))
|
||||
}
|
||||
@@ -82,9 +80,7 @@ impl MailBoxApi {
|
||||
) -> ApiResult<()> {
|
||||
let account_id = account_id.0;
|
||||
let mailbox_id = mailbox_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_DELETE)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_DELETE)?;
|
||||
Ok(delete_mailbox_impl(account_id, mailbox_id).await?)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -35,8 +35,8 @@ use bichon_core::message::search::{search_messages_impl, EmailSearchRequest};
|
||||
use bichon_core::message::tags::TagCount;
|
||||
use bichon_core::message::tags::TagsRequest;
|
||||
use bichon_core::raise_error;
|
||||
use bichon_core::store::envelope::Envelope;
|
||||
use bichon_core::store::blob::get_reader;
|
||||
use bichon_core::store::envelope::Envelope;
|
||||
use bichon_core::store::tantivy::envelope::ENVELOPE_MANAGER;
|
||||
use bichon_core::store::tantivy::validate_facet;
|
||||
use bichon_core::users::permissions::Permission;
|
||||
@@ -65,9 +65,7 @@ impl MessageApi {
|
||||
) -> ApiResult<()> {
|
||||
let request = payload.0;
|
||||
for account_id in request.keys() {
|
||||
context
|
||||
.require_permission(Some(*account_id), Permission::DATA_DELETE)
|
||||
.await?;
|
||||
context.require_permission(Some(*account_id), Permission::DATA_DELETE)?;
|
||||
}
|
||||
Ok(delete_messages_impl(request).await?)
|
||||
}
|
||||
@@ -84,15 +82,13 @@ impl MessageApi {
|
||||
payload: Json<EmailSearchRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<DataPage<Envelope>>> {
|
||||
let authorized_ids: Option<HashSet<u64>> = if context
|
||||
.has_permission(None, Permission::DATA_READ_ALL)
|
||||
.await
|
||||
{
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(search_messages_impl(authorized_ids, payload.0).await?))
|
||||
let authorized_ids: Option<HashSet<u64>> =
|
||||
if context.has_permission(None, Permission::DATA_READ_ALL) {
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(search_messages_impl(authorized_ids, payload.0)?))
|
||||
}
|
||||
|
||||
/// Retrieves all messages belonging to a specific thread. Requires `thread_id`, `page`, and `page_size` query parameters.
|
||||
@@ -115,12 +111,13 @@ impl MessageApi {
|
||||
) -> ApiResult<Json<DataPage<Envelope>>> {
|
||||
let account_id = account_id.0;
|
||||
let thread_id = thread_id.0.trim();
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_READ)
|
||||
.await?;
|
||||
Ok(Json(
|
||||
get_thread_messages(account_id, thread_id, page.0, page_size.0).await?,
|
||||
))
|
||||
context.require_permission(Some(account_id), Permission::DATA_READ)?;
|
||||
Ok(Json(get_thread_messages(
|
||||
account_id,
|
||||
thread_id,
|
||||
page.0,
|
||||
page_size.0,
|
||||
)?))
|
||||
}
|
||||
|
||||
/// Fetches the content of a specific email.
|
||||
@@ -138,12 +135,8 @@ impl MessageApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<FullMessageContent>> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_READ)
|
||||
.await?;
|
||||
Ok(Json(
|
||||
retrieve_email_content(account_id, envelope_id.0).await?,
|
||||
))
|
||||
context.require_permission(Some(account_id), Permission::DATA_READ)?;
|
||||
Ok(Json(retrieve_email_content(account_id, envelope_id.0)?))
|
||||
}
|
||||
|
||||
/// Retrieves the content of an email embedded as an attachment.
|
||||
@@ -162,13 +155,13 @@ impl MessageApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<FullNestedMessageContent>> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_READ)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_READ)?;
|
||||
let content_hash = content_hash.0.trim();
|
||||
Ok(Json(
|
||||
retrieve_nested_eml_content(account_id, envelope_id.0, content_hash).await?,
|
||||
))
|
||||
Ok(Json(retrieve_nested_eml_content(
|
||||
account_id,
|
||||
envelope_id.0,
|
||||
content_hash,
|
||||
)?))
|
||||
}
|
||||
|
||||
/// Retrieves the envelope (metadata) of a specific message.
|
||||
@@ -186,13 +179,10 @@ impl MessageApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Envelope>> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_READ)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_READ)?;
|
||||
let envelope_id = envelope_id.0;
|
||||
let e = ENVELOPE_MANAGER
|
||||
.get_envelope_by_id(account_id, &envelope_id)
|
||||
.await?
|
||||
.get_envelope_by_id(account_id, &envelope_id)?
|
||||
.ok_or_else(|| {
|
||||
raise_error!(
|
||||
format!(
|
||||
@@ -220,12 +210,10 @@ impl MessageApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Attachment<Body>> {
|
||||
let account_id = account_id.0;
|
||||
AccountModel::check_account_exists(account_id).await?;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_RAW_DOWNLOAD)
|
||||
.await?;
|
||||
AccountModel::check_account_exists(account_id)?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_RAW_DOWNLOAD)?;
|
||||
let envelope_id = envelope_id.0;
|
||||
let reader = get_reader(account_id, envelope_id.clone()).await?;
|
||||
let reader = get_reader(account_id, envelope_id.clone())?;
|
||||
let body = Body::from_async_read(reader);
|
||||
let attachment = Attachment::new(body)
|
||||
.attachment_type(AttachmentType::Attachment)
|
||||
@@ -247,9 +235,7 @@ impl MessageApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let account_id = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_EXPORT_BATCH)
|
||||
.await?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_EXPORT_BATCH)?;
|
||||
Ok(restore_emails(account_id, payload.0.envelope_ids).await?)
|
||||
}
|
||||
|
||||
@@ -271,12 +257,10 @@ impl MessageApi {
|
||||
) -> ApiResult<Attachment<Body>> {
|
||||
let account_id = account_id.0;
|
||||
let envelope_id = envelope_id.0.trim().to_string();
|
||||
AccountModel::check_account_exists(account_id).await?;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_READ)
|
||||
.await?;
|
||||
AccountModel::check_account_exists(account_id)?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_READ)?;
|
||||
let content_hash = content_hash.0.trim();
|
||||
let reader = retrieve_attachment_content(account_id, envelope_id, content_hash).await?;
|
||||
let reader = retrieve_attachment_content(account_id, envelope_id, content_hash)?;
|
||||
let body = Body::from_async_read(reader);
|
||||
let attachment = Attachment::new(body)
|
||||
.attachment_type(AttachmentType::Attachment)
|
||||
@@ -303,10 +287,8 @@ impl MessageApi {
|
||||
) -> ApiResult<Attachment<Body>> {
|
||||
let account_id = account_id.0;
|
||||
let envelope_id = envelope_id.0.trim().to_string();
|
||||
AccountModel::check_account_exists(account_id).await?;
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::DATA_READ)
|
||||
.await?;
|
||||
AccountModel::check_account_exists(account_id)?;
|
||||
context.require_permission(Some(account_id), Permission::DATA_READ)?;
|
||||
let content_hash = content_hash.0.trim();
|
||||
let nested_content_hash = nested_content_hash.0.trim();
|
||||
let reader = retrieve_nested_attachment_content(
|
||||
@@ -314,8 +296,7 @@ impl MessageApi {
|
||||
envelope_id,
|
||||
content_hash,
|
||||
nested_content_hash,
|
||||
)
|
||||
.await?;
|
||||
)?;
|
||||
let body = Body::from_async_read(reader);
|
||||
let attachment = Attachment::new(body)
|
||||
.attachment_type(AttachmentType::Attachment)
|
||||
@@ -326,15 +307,13 @@ impl MessageApi {
|
||||
/// Returns all facets in the index along with their document counts.
|
||||
#[oai(path = "/all-tags", method = "get", operation_id = "get_all_tags")]
|
||||
async fn get_all_tags(&self, context: WrappedContext) -> ApiResult<Json<Vec<TagCount>>> {
|
||||
let authorized_ids: Option<HashSet<u64>> = if context
|
||||
.has_permission(None, Permission::DATA_READ_ALL)
|
||||
.await
|
||||
{
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(ENVELOPE_MANAGER.get_all_tags(authorized_ids).await?))
|
||||
let authorized_ids: Option<HashSet<u64>> =
|
||||
if context.has_permission(None, Permission::DATA_READ_ALL) {
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(ENVELOPE_MANAGER.get_all_tags(authorized_ids)?))
|
||||
}
|
||||
|
||||
/// Adds or removes facet tags for multiple emails across accounts.
|
||||
@@ -354,9 +333,7 @@ impl MessageApi {
|
||||
}
|
||||
|
||||
for account_id in req.updates.keys() {
|
||||
context
|
||||
.require_permission(Some(*account_id), Permission::DATA_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(Some(*account_id), Permission::DATA_MANAGE)?;
|
||||
}
|
||||
|
||||
ENVELOPE_MANAGER.update_envelope_tags(req).await?;
|
||||
@@ -370,16 +347,12 @@ impl MessageApi {
|
||||
operation_id = "get_all_contacts"
|
||||
)]
|
||||
async fn get_all_contacts(&self, context: WrappedContext) -> ApiResult<Json<HashSet<String>>> {
|
||||
let authorized_ids: Option<HashSet<u64>> = if context
|
||||
.has_permission(None, Permission::DATA_READ_ALL)
|
||||
.await
|
||||
{
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(
|
||||
ENVELOPE_MANAGER.get_all_contacts(authorized_ids).await?,
|
||||
))
|
||||
let authorized_ids: Option<HashSet<u64>> =
|
||||
if context.has_permission(None, Permission::DATA_READ_ALL) {
|
||||
None
|
||||
} else {
|
||||
Some(context.user.account_access_map.keys().cloned().collect())
|
||||
};
|
||||
Ok(Json(ENVELOPE_MANAGER.get_all_contacts(authorized_ids)?))
|
||||
}
|
||||
}
|
||||
|
||||
@@ -52,13 +52,13 @@ impl OAuth2Api {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<OAuth2>> {
|
||||
let id = id.0;
|
||||
let mut oauth2 = OAuth2::get(id).await?.ok_or_else(|| {
|
||||
let mut oauth2 = OAuth2::get(id)?.ok_or_else(|| {
|
||||
raise_error!(
|
||||
format!("OAuth2 configuration id='{id}' not found"),
|
||||
ErrorCode::ResourceNotFound
|
||||
)
|
||||
})?;
|
||||
if context.has_permission(None, Permission::ROOT).await {
|
||||
if context.has_permission(None, Permission::ROOT) {
|
||||
return Ok(Json(oauth2));
|
||||
}
|
||||
oauth2.scrub_sensitive_fields();
|
||||
@@ -80,8 +80,8 @@ impl OAuth2Api {
|
||||
id: Path<u64>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
Ok(OAuth2::delete(id.0).await?)
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
Ok(OAuth2::delete(id.0)?)
|
||||
}
|
||||
|
||||
/// Creates a new OAuth2 configuration.
|
||||
@@ -99,9 +99,9 @@ impl OAuth2Api {
|
||||
request: Json<OAuth2CreateRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
let entity = OAuth2::new(request.0)?;
|
||||
Ok(entity.save().await?)
|
||||
Ok(entity.save()?)
|
||||
}
|
||||
|
||||
/// Updates an existing OAuth2 configuration.
|
||||
@@ -121,8 +121,8 @@ impl OAuth2Api {
|
||||
payload: Json<OAuth2UpdateRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
Ok(OAuth2::update(id.0, payload.0).await?)
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
Ok(OAuth2::update(id.0, payload.0)?)
|
||||
}
|
||||
|
||||
/// Lists OAuth2 configurations with pagination and sorting options.
|
||||
@@ -144,8 +144,8 @@ impl OAuth2Api {
|
||||
desc: Query<Option<bool>>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<DataPage<OAuth2>>> {
|
||||
let mut list = OAuth2::paginate_list(page.0, page_size.0, desc.0).await?;
|
||||
if context.has_permission(None, Permission::ROOT).await {
|
||||
let mut list = OAuth2::paginate_list(page.0, page_size.0, desc.0)?;
|
||||
if context.has_permission(None, Permission::ROOT) {
|
||||
return Ok(Json(list));
|
||||
}
|
||||
//Non-root users can only view masked data.
|
||||
@@ -172,15 +172,13 @@ impl OAuth2Api {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<PlainText<String>> {
|
||||
let request = request.0;
|
||||
context
|
||||
.require_any_permission(vec![
|
||||
(None, Permission::ACCOUNT_CREATE),
|
||||
(Some(request.account_id), Permission::ACCOUNT_MANAGE),
|
||||
])
|
||||
.await?;
|
||||
context.require_any_permission(vec![
|
||||
(None, Permission::ACCOUNT_CREATE),
|
||||
(Some(request.account_id), Permission::ACCOUNT_MANAGE),
|
||||
])?;
|
||||
|
||||
let flow = OAuth2Flow::new(request.oauth2_id);
|
||||
Ok(PlainText(flow.authorize_url(request.account_id).await?))
|
||||
Ok(PlainText(flow.authorize_url(request.account_id)?))
|
||||
}
|
||||
|
||||
/// Retrieves OAuth2 access tokens for a specified account.
|
||||
@@ -198,17 +196,13 @@ impl OAuth2Api {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<OAuth2AccessToken>> {
|
||||
let account = account_id.0;
|
||||
context
|
||||
.require_permission(Some(account), Permission::ACCOUNT_MANAGE)
|
||||
.await?;
|
||||
Ok(Json(OAuth2AccessToken::get(account).await?.ok_or_else(
|
||||
|| {
|
||||
raise_error!(
|
||||
"OAuth2 access tokens not found".into(),
|
||||
ErrorCode::ResourceNotFound
|
||||
)
|
||||
},
|
||||
)?))
|
||||
context.require_permission(Some(account), Permission::ACCOUNT_MANAGE)?;
|
||||
Ok(Json(OAuth2AccessToken::get(account)?.ok_or_else(|| {
|
||||
raise_error!(
|
||||
"OAuth2 access tokens not found".into(),
|
||||
ErrorCode::ResourceNotFound
|
||||
)
|
||||
})?))
|
||||
}
|
||||
|
||||
/// Configures an external OAuth2 token for a specified account.
|
||||
@@ -239,12 +233,10 @@ impl OAuth2Api {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let account_id = account_id.0;
|
||||
AccountModel::check_account_exists(account_id).await?;
|
||||
AccountModel::check_account_exists(account_id)?;
|
||||
// Check account access permissions
|
||||
context
|
||||
.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)
|
||||
.await?;
|
||||
OAuth2AccessToken::upsert_external_oauth_token(account_id, request.0).await?;
|
||||
context.require_permission(Some(account_id), Permission::ACCOUNT_MANAGE)?;
|
||||
OAuth2AccessToken::upsert_external_oauth_token(account_id, request.0)?;
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
@@ -75,7 +75,6 @@ impl SystemApi {
|
||||
async fn list_proxy(&self, _context: WrappedContext) -> ApiResult<Json<Vec<Proxy>>> {
|
||||
//The proxy list is visible to all users.
|
||||
let proxies = Proxy::list_all()
|
||||
.await
|
||||
.map_err(|e| raise_error!(format!("{:#?}", e), ErrorCode::InternalError))?;
|
||||
Ok(Json(proxies))
|
||||
}
|
||||
@@ -88,8 +87,8 @@ impl SystemApi {
|
||||
id: Path<u64>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
Ok(Proxy::delete(id.0).await?)
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
Ok(Proxy::delete(id.0)?)
|
||||
}
|
||||
|
||||
/// Retrieve a specific proxy configuration by ID. Requires root permission.
|
||||
@@ -100,16 +99,16 @@ impl SystemApi {
|
||||
id: Path<u64>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Proxy>> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
Ok(Json(Proxy::get(id.0).await?))
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
Ok(Json(Proxy::get(id.0)?))
|
||||
}
|
||||
|
||||
/// Create a new proxy configuration. Requires root permission.
|
||||
#[oai(path = "/proxy", method = "post", operation_id = "create_proxy")]
|
||||
async fn create_proxy(&self, url: PlainText<String>, context: WrappedContext) -> ApiResult<()> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
let entity = Proxy::new(url.0);
|
||||
Ok(entity.save().await?)
|
||||
Ok(entity.save()?)
|
||||
}
|
||||
|
||||
/// Update the URL of a specific proxy by ID. Requires root permission.
|
||||
@@ -120,8 +119,8 @@ impl SystemApi {
|
||||
url: PlainText<String>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
Ok(Proxy::update(id.0, url.0).await?)
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
Ok(Proxy::update(id.0, url.0)?)
|
||||
}
|
||||
/// Get system configurations.
|
||||
///
|
||||
@@ -136,7 +135,7 @@ impl SystemApi {
|
||||
&self,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<SystemConfigurations>> {
|
||||
context.require_permission(None, Permission::ROOT).await?;
|
||||
context.require_permission(None, Permission::ROOT)?;
|
||||
let config: SystemConfigurations = SystemConfigurations::from(&*SETTINGS);
|
||||
Ok(Json(config))
|
||||
}
|
||||
|
||||
@@ -40,11 +40,8 @@ pub struct UsersApi;
|
||||
impl UsersApi {
|
||||
#[oai(path = "/list-roles", method = "get", operation_id = "list_roles")]
|
||||
async fn list_roles(&self, context: WrappedContext) -> ApiResult<Json<Vec<UserRole>>> {
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
|
||||
Ok(Json(UserRole::list_all().await?))
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
Ok(Json(UserRole::list_all()?))
|
||||
}
|
||||
|
||||
#[oai(path = "/roles/:id", method = "delete", operation_id = "remove_role")]
|
||||
@@ -55,10 +52,8 @@ impl UsersApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let id = id.0;
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
Ok(UserRole::delete(id).await?)
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
Ok(UserRole::delete(id)?)
|
||||
}
|
||||
|
||||
/// Create a new account
|
||||
@@ -69,10 +64,8 @@ impl UsersApi {
|
||||
payload: Json<RoleCreateRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<UserRole>> {
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
let role = UserRole::create(payload.0).await?;
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
let role = UserRole::create(payload.0)?;
|
||||
Ok(Json(role))
|
||||
}
|
||||
|
||||
@@ -87,20 +80,16 @@ impl UsersApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let id = id.0;
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
Ok(UserRole::update(id, payload.0).await?)
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
Ok(UserRole::update(id, payload.0)?)
|
||||
}
|
||||
|
||||
#[oai(path = "/list-users", method = "get", operation_id = "list_users")]
|
||||
async fn list_users(&self, context: WrappedContext) -> ApiResult<Json<Vec<UserView>>> {
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
let roles = UserRole::list_all().await?;
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
let roles = UserRole::list_all()?;
|
||||
let role_lookup: BTreeMap<u64, UserRole> = roles.into_iter().map(|r| (r.id, r)).collect();
|
||||
let users = UserModel::list_all().await?;
|
||||
let users = UserModel::list_all()?;
|
||||
let users = users.into_iter().map(|u| u.to_view(&role_lookup)).collect();
|
||||
Ok(Json(users))
|
||||
}
|
||||
@@ -116,13 +105,11 @@ impl UsersApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Vec<AccessTokenModel>>> {
|
||||
let target_user_id = id.0;
|
||||
let tokens = AccessTokenModel::get_user_api_tokens(target_user_id).await?;
|
||||
let tokens = AccessTokenModel::get_user_api_tokens(target_user_id)?;
|
||||
if context.user.id == target_user_id {
|
||||
return Ok(Json(tokens));
|
||||
}
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
Ok(Json(tokens))
|
||||
}
|
||||
|
||||
@@ -134,10 +121,8 @@ impl UsersApi {
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<()> {
|
||||
let id = id.0;
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
Ok(UserModel::remove(id).await?)
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
Ok(UserModel::remove(id)?)
|
||||
}
|
||||
|
||||
#[oai(path = "/users", method = "post", operation_id = "create_user")]
|
||||
@@ -146,11 +131,9 @@ impl UsersApi {
|
||||
payload: Json<UserCreateRequest>,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<UserView>> {
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
let user = UserModel::create(payload.0).await?;
|
||||
let roles = UserRole::list_all().await?;
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
let user = UserModel::create(payload.0)?;
|
||||
let roles = UserRole::list_all()?;
|
||||
let role_lookup: BTreeMap<u64, UserRole> = roles.into_iter().map(|r| (r.id, r)).collect();
|
||||
Ok(Json(user.to_view(&role_lookup)))
|
||||
}
|
||||
@@ -165,19 +148,15 @@ impl UsersApi {
|
||||
let target_id = id.0;
|
||||
let current_user_id = context.user.id;
|
||||
if current_user_id != target_id {
|
||||
context
|
||||
.require_permission(None, Permission::USER_MANAGE)
|
||||
.await?;
|
||||
context.require_permission(None, Permission::USER_MANAGE)?;
|
||||
}
|
||||
let mut update_data = payload.0;
|
||||
if current_user_id == target_id
|
||||
&& !context.has_permission(None, Permission::USER_MANAGE).await
|
||||
{
|
||||
if current_user_id == target_id && !context.has_permission(None, Permission::USER_MANAGE) {
|
||||
update_data.global_roles = None;
|
||||
update_data.account_access_map = None;
|
||||
update_data.acl = None;
|
||||
}
|
||||
Ok(UserModel::update(target_id, update_data).await?)
|
||||
Ok(UserModel::update(target_id, update_data)?)
|
||||
}
|
||||
|
||||
#[oai(
|
||||
@@ -186,7 +165,7 @@ impl UsersApi {
|
||||
operation_id = "get_current_user"
|
||||
)]
|
||||
async fn get_current_user(&self, context: WrappedContext) -> ApiResult<Json<UserView>> {
|
||||
let roles = UserRole::list_all().await?;
|
||||
let roles = UserRole::list_all()?;
|
||||
let role_lookup: BTreeMap<u64, UserRole> = roles.into_iter().map(|r| (r.id, r)).collect();
|
||||
Ok(Json(context.0.user.to_view(&role_lookup)))
|
||||
}
|
||||
@@ -200,15 +179,12 @@ impl UsersApi {
|
||||
&self,
|
||||
context: WrappedContext,
|
||||
) -> ApiResult<Json<Vec<MinimalUser>>> {
|
||||
let is_admin = context.user.is_admin().await;
|
||||
let minimal_list = MinimalUser::list_all().await?;
|
||||
let is_admin = context.user.is_admin();
|
||||
let minimal_list = MinimalUser::list_all()?;
|
||||
if is_admin {
|
||||
return Ok(Json(minimal_list));
|
||||
}
|
||||
context
|
||||
.require_permission(None, Permission::USER_VIEW)
|
||||
.await?;
|
||||
|
||||
context.require_permission(None, Permission::USER_VIEW)?;
|
||||
Ok(Json(minimal_list))
|
||||
}
|
||||
|
||||
@@ -218,10 +194,8 @@ impl UsersApi {
|
||||
operation_id = "list_account_roles"
|
||||
)]
|
||||
async fn list_account_roles(&self, context: WrappedContext) -> ApiResult<Json<Vec<UserRole>>> {
|
||||
context
|
||||
.require_permission(None, Permission::USER_VIEW)
|
||||
.await?;
|
||||
let all = UserRole::list_all().await?;
|
||||
context.require_permission(None, Permission::USER_VIEW)?;
|
||||
let all = UserRole::list_all()?;
|
||||
Ok(Json(
|
||||
all.into_iter()
|
||||
.filter(|r| matches!(r.role_type, RoleType::Account))
|
||||
|
||||
@@ -32,9 +32,9 @@ pub struct LoginPayload {
|
||||
/// Accepts a plain text password and returns the `root_token`
|
||||
/// on successful authentication.
|
||||
#[handler]
|
||||
pub async fn login(payload: Json<LoginPayload>) -> Response {
|
||||
pub fn login(payload: Json<LoginPayload>) -> Response {
|
||||
let payload = payload.0;
|
||||
match UserModel::authenticate_user(payload.username, payload.password).await {
|
||||
match UserModel::authenticate_user(payload.username, payload.password) {
|
||||
Ok(result) => match serde_json::to_string(&result) {
|
||||
Ok(json_string) => Response::builder()
|
||||
.status(http::StatusCode::OK)
|
||||
|
||||
@@ -16,7 +16,6 @@
|
||||
// You should have received a copy of the GNU Affero General Public License
|
||||
// along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
|
||||
use bichon_core::oauth2::{flow::OAuth2Flow, pending::OAuth2PendingEntity};
|
||||
use poem::{
|
||||
handler,
|
||||
@@ -56,7 +55,7 @@ pub async fn oauth2_callback(
|
||||
}
|
||||
};
|
||||
|
||||
let pending = match OAuth2PendingEntity::get(state).await {
|
||||
let pending = match OAuth2PendingEntity::get(state) {
|
||||
Ok(Some(pending)) => pending,
|
||||
_ => {
|
||||
let message =
|
||||
@@ -86,7 +85,7 @@ pub async fn oauth2_callback(
|
||||
.into_response());
|
||||
}
|
||||
|
||||
if let Err(e) = OAuth2PendingEntity::delete(state).await {
|
||||
if let Err(e) = OAuth2PendingEntity::delete(state) {
|
||||
error!("Failed to delete pending OAuth2 entity: {}", e);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user