X-Git-Url: http://these/git/?a=blobdiff_plain;f=crates%2Fapi_crud%2Fsrc%2Fsite%2Fupdate.rs;h=83f746429fa02892b79abb806684ff1338efcd11;hb=HEAD;hp=d1820d177b654ad5ef5a6b16a147b3ae3ca49d8c;hpb=ef9dc5d0b6f727cc78ab4df214e6e65ec77c3b9e;p=lemmy.git diff --git a/crates/api_crud/src/site/update.rs b/crates/api_crud/src/site/update.rs index d1820d17..83f74642 100644 --- a/crates/api_crud/src/site/update.rs +++ b/crates/api_crud/src/site/update.rs @@ -1,12 +1,12 @@ -use crate::{ - site::{application_question_check, site_default_post_listing_type_check}, - PerformCrud, -}; -use actix_web::web::Data; +use crate::site::{application_question_check, site_default_post_listing_type_check}; +use actix_web::web::{Data, Json}; use lemmy_api_common::{ context::LemmyContext, site::{EditSite, SiteResponse}, - utils::{is_admin, local_site_rate_limit_to_rate_limit_config, local_user_view_from_jwt}, + utils::{ + is_admin, local_site_rate_limit_to_rate_limit_config, local_user_view_from_jwt, + sanitize_html_opt, + }, }; use lemmy_db_schema::{ source::{ @@ -29,148 +29,152 @@ use lemmy_utils::{ utils::{ slurs::check_slurs_opt, validation::{ - build_and_check_regex, - check_site_visibility_valid, - is_valid_body_field, - site_description_length_check, - site_name_length_check, + build_and_check_regex, check_site_visibility_valid, is_valid_body_field, + site_description_length_check, site_name_length_check, }, }, }; -#[async_trait::async_trait(?Send)] -impl PerformCrud for EditSite { - type Response = SiteResponse; +#[tracing::instrument(skip(context))] +pub async fn update_site( + data: Json, + context: Data, +) -> Result, LemmyError> { + let local_user_view = local_user_view_from_jwt(&data.auth, &context).await?; + let site_view = SiteView::read_local(&mut context.pool()).await?; + let local_site = site_view.local_site; + let site = site_view.site; - #[tracing::instrument(skip(context))] - async fn perform(&self, context: &Data) -> Result { - let data: &EditSite = self; - let local_user_view = local_user_view_from_jwt(&data.auth, context).await?; - let site_view = SiteView::read_local(context.pool()).await?; - let local_site = site_view.local_site; - let site = site_view.site; + // Make sure user is an admin; other types of users should not update site data... + is_admin(&local_user_view)?; - // Make sure user is an admin; other types of users should not update site data... - is_admin(&local_user_view)?; + validate_update_payload(&local_site, &data)?; - validate_update_payload(&local_site, data)?; - - if let Some(discussion_languages) = data.discussion_languages.clone() { - SiteLanguage::update(context.pool(), discussion_languages.clone(), &site).await?; - } - - let site_form = SiteUpdateForm::builder() - .name(data.name.clone()) - .sidebar(diesel_option_overwrite(&data.sidebar)) - .description(diesel_option_overwrite(&data.description)) - .icon(diesel_option_overwrite_to_url(&data.icon)?) - .banner(diesel_option_overwrite_to_url(&data.banner)?) - .updated(Some(Some(naive_now()))) - .build(); + if let Some(discussion_languages) = data.discussion_languages.clone() { + SiteLanguage::update(&mut context.pool(), discussion_languages.clone(), &site).await?; + } - Site::update(context.pool(), site.id, &site_form) - .await - // Ignore errors for all these, so as to not throw errors if no update occurs - // Diesel will throw an error for empty update forms - .ok(); - - let local_site_form = LocalSiteUpdateForm::builder() - .enable_downvotes(data.enable_downvotes) - .registration_mode(data.registration_mode) - .enable_nsfw(data.enable_nsfw) - .community_creation_admin_only(data.community_creation_admin_only) - .require_email_verification(data.require_email_verification) - .application_question(diesel_option_overwrite(&data.application_question)) - .private_instance(data.private_instance) - .default_theme(data.default_theme.clone()) - .default_post_listing_type(data.default_post_listing_type) - .legal_information(diesel_option_overwrite(&data.legal_information)) - .application_email_admins(data.application_email_admins) - .hide_modlog_mod_names(data.hide_modlog_mod_names) - .updated(Some(Some(naive_now()))) - .slur_filter_regex(diesel_option_overwrite(&data.slur_filter_regex)) - .actor_name_max_length(data.actor_name_max_length) - .federation_enabled(data.federation_enabled) - .captcha_enabled(data.captcha_enabled) - .captcha_difficulty(data.captcha_difficulty.clone()) - .reports_email_admins(data.reports_email_admins) - .build(); - - let update_local_site = LocalSite::update(context.pool(), &local_site_form) - .await - .ok(); - - let local_site_rate_limit_form = LocalSiteRateLimitUpdateForm::builder() - .message(data.rate_limit_message) - .message_per_second(data.rate_limit_message_per_second) - .post(data.rate_limit_post) - .post_per_second(data.rate_limit_post_per_second) - .register(data.rate_limit_register) - .register_per_second(data.rate_limit_register_per_second) - .image(data.rate_limit_image) - .image_per_second(data.rate_limit_image_per_second) - .comment(data.rate_limit_comment) - .comment_per_second(data.rate_limit_comment_per_second) - .search(data.rate_limit_search) - .search_per_second(data.rate_limit_search_per_second) - .build(); - - LocalSiteRateLimit::update(context.pool(), &local_site_rate_limit_form) + let name = sanitize_html_opt(&data.name); + let sidebar = sanitize_html_opt(&data.sidebar); + let description = sanitize_html_opt(&data.description); + + let site_form = SiteUpdateForm { + name, + sidebar: diesel_option_overwrite(sidebar), + description: diesel_option_overwrite(description), + icon: diesel_option_overwrite_to_url(&data.icon)?, + banner: diesel_option_overwrite_to_url(&data.banner)?, + updated: Some(Some(naive_now())), + ..Default::default() + }; + + Site::update(&mut context.pool(), site.id, &site_form) + .await + // Ignore errors for all these, so as to not throw errors if no update occurs + // Diesel will throw an error for empty update forms + .ok(); + + let application_question = sanitize_html_opt(&data.application_question); + let default_theme = sanitize_html_opt(&data.default_theme); + let legal_information = sanitize_html_opt(&data.legal_information); + + let local_site_form = LocalSiteUpdateForm { + enable_downvotes: data.enable_downvotes, + enable_federated_downvotes: data.enable_federated_downvotes, + registration_mode: data.registration_mode, + enable_nsfw: data.enable_nsfw, + community_creation_admin_only: data.community_creation_admin_only, + require_email_verification: data.require_email_verification, + application_question: diesel_option_overwrite(application_question), + private_instance: data.private_instance, + default_theme, + default_post_listing_type: data.default_post_listing_type, + legal_information: diesel_option_overwrite(legal_information), + application_email_admins: data.application_email_admins, + hide_modlog_mod_names: data.hide_modlog_mod_names, + updated: Some(Some(naive_now())), + slur_filter_regex: diesel_option_overwrite(data.slur_filter_regex.clone()), + actor_name_max_length: data.actor_name_max_length, + federation_enabled: data.federation_enabled, + captcha_enabled: data.captcha_enabled, + captcha_difficulty: data.captcha_difficulty.clone(), + reports_email_admins: data.reports_email_admins, + ..Default::default() + }; + + let update_local_site = LocalSite::update(&mut context.pool(), &local_site_form) + .await + .ok(); + + let local_site_rate_limit_form = LocalSiteRateLimitUpdateForm { + message: data.rate_limit_message, + message_per_second: data.rate_limit_message_per_second, + post: data.rate_limit_post, + post_per_second: data.rate_limit_post_per_second, + register: data.rate_limit_register, + register_per_second: data.rate_limit_register_per_second, + image: data.rate_limit_image, + image_per_second: data.rate_limit_image_per_second, + comment: data.rate_limit_comment, + comment_per_second: data.rate_limit_comment_per_second, + search: data.rate_limit_search, + search_per_second: data.rate_limit_search_per_second, + ..Default::default() + }; + + LocalSiteRateLimit::update(&mut context.pool(), &local_site_rate_limit_form) + .await + .ok(); + + // Replace the blocked and allowed instances + let allowed = data.allowed_instances.clone(); + FederationAllowList::replace(&mut context.pool(), allowed).await?; + let blocked = data.blocked_instances.clone(); + FederationBlockList::replace(&mut context.pool(), blocked).await?; + + // TODO can't think of a better way to do this. + // If the server suddenly requires email verification, or required applications, no old users + // will be able to log in. It really only wants this to be a requirement for NEW signups. + // So if it was set from false, to true, you need to update all current users columns to be verified. + + let old_require_application = + local_site.registration_mode == RegistrationMode::RequireApplication; + let new_require_application = update_local_site + .as_ref() + .map(|ols| ols.registration_mode == RegistrationMode::RequireApplication) + .unwrap_or(false); + if !old_require_application && new_require_application { + LocalUser::set_all_users_registration_applications_accepted(&mut context.pool()) .await - .ok(); - - // Replace the blocked and allowed instances - let allowed = data.allowed_instances.clone(); - FederationAllowList::replace(context.pool(), allowed).await?; - let blocked = data.blocked_instances.clone(); - FederationBlockList::replace(context.pool(), blocked).await?; - - // TODO can't think of a better way to do this. - // If the server suddenly requires email verification, or required applications, no old users - // will be able to log in. It really only wants this to be a requirement for NEW signups. - // So if it was set from false, to true, you need to update all current users columns to be verified. - - let old_require_application = - local_site.registration_mode == RegistrationMode::RequireApplication; - let new_require_application = update_local_site - .as_ref() - .map(|ols| ols.registration_mode == RegistrationMode::RequireApplication) - .unwrap_or(false); - if !old_require_application && new_require_application { - LocalUser::set_all_users_registration_applications_accepted(context.pool()) - .await - .with_lemmy_type(LemmyErrorType::CouldntSetAllRegistrationsAccepted)?; - } - - let new_require_email_verification = update_local_site - .as_ref() - .map(|ols| ols.require_email_verification) - .unwrap_or(false); - if !local_site.require_email_verification && new_require_email_verification { - LocalUser::set_all_users_email_verified(context.pool()) - .await - .with_lemmy_type(LemmyErrorType::CouldntSetAllEmailVerified)?; - } + .with_lemmy_type(LemmyErrorType::CouldntSetAllRegistrationsAccepted)?; + } - let new_taglines = data.taglines.clone(); - let taglines = Tagline::replace(context.pool(), local_site.id, new_taglines).await?; + let new_require_email_verification = update_local_site + .as_ref() + .map(|ols| ols.require_email_verification) + .unwrap_or(false); + if !local_site.require_email_verification && new_require_email_verification { + LocalUser::set_all_users_email_verified(&mut context.pool()) + .await + .with_lemmy_type(LemmyErrorType::CouldntSetAllEmailVerified)?; + } - let site_view = SiteView::read_local(context.pool()).await?; + let new_taglines = data.taglines.clone(); + let taglines = Tagline::replace(&mut context.pool(), local_site.id, new_taglines).await?; - let rate_limit_config = - local_site_rate_limit_to_rate_limit_config(&site_view.local_site_rate_limit); - context - .settings_updated_channel() - .send(rate_limit_config) - .await?; + let site_view = SiteView::read_local(&mut context.pool()).await?; - let res = SiteResponse { - site_view, - taglines, - }; + let rate_limit_config = + local_site_rate_limit_to_rate_limit_config(&site_view.local_site_rate_limit); + context + .settings_updated_channel() + .send(rate_limit_config) + .await?; - Ok(res) - } + Ok(Json(SiteResponse { + site_view, + taglines, + })) } fn validate_update_payload(local_site: &LocalSite, edit_site: &EditSite) -> LemmyResult<()> { @@ -217,6 +221,9 @@ fn validate_update_payload(local_site: &LocalSite, edit_site: &EditSite) -> Lemm #[cfg(test)] mod tests { + #![allow(clippy::unwrap_used)] + #![allow(clippy::indexing_slicing)] + use crate::site::update::validate_update_payload; use lemmy_api_common::site::EditSite; use lemmy_db_schema::{source::local_site::LocalSite, ListingType, RegistrationMode}; @@ -500,6 +507,7 @@ mod tests { site_id: Default::default(), site_setup: true, enable_downvotes: false, + enable_federated_downvotes: false, enable_nsfw: false, community_creation_admin_only: false, require_email_verification: false, @@ -543,6 +551,7 @@ mod tests { icon: None, banner: None, enable_downvotes: None, + enable_federated_downvotes: None, enable_nsfw: None, community_creation_admin_only: None, require_email_verification: None,