mirror of
https://github.com/LemmyNet/lemmy.git
synced 2025-01-03 16:51:35 +00:00
Merge branch 'LemmyNet:main' into migration-runner
This commit is contained in:
commit
277524298b
26 changed files with 475 additions and 121 deletions
28
Cargo.lock
generated
28
Cargo.lock
generated
|
@ -2582,13 +2582,13 @@ checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646"
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_api"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"activitypub_federation",
|
||||
"actix-web",
|
||||
"actix-web-httpauth",
|
||||
"anyhow",
|
||||
"base64 0.21.7",
|
||||
"base64 0.22.0",
|
||||
"bcrypt",
|
||||
"captcha",
|
||||
"chrono",
|
||||
|
@ -2611,7 +2611,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_api_common"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"activitypub_federation",
|
||||
"actix-web",
|
||||
|
@ -2649,7 +2649,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_api_crud"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"accept-language",
|
||||
"activitypub_federation",
|
||||
|
@ -2672,7 +2672,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_apub"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"activitypub_federation",
|
||||
"actix-web",
|
||||
|
@ -2710,7 +2710,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_db_perf"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"clap",
|
||||
|
@ -2725,7 +2725,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_db_schema"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"activitypub_federation",
|
||||
"anyhow",
|
||||
|
@ -2765,7 +2765,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_db_views"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"actix-web",
|
||||
"chrono",
|
||||
|
@ -2787,7 +2787,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_db_views_actor"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"chrono",
|
||||
"diesel",
|
||||
|
@ -2807,7 +2807,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_db_views_moderator"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"diesel",
|
||||
"diesel-async",
|
||||
|
@ -2819,7 +2819,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_federate"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"activitypub_federation",
|
||||
"anyhow",
|
||||
|
@ -2842,7 +2842,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_routes"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"activitypub_federation",
|
||||
"actix-web",
|
||||
|
@ -2867,7 +2867,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_server"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"activitypub_federation",
|
||||
"actix-cors",
|
||||
|
@ -2910,7 +2910,7 @@ dependencies = [
|
|||
|
||||
[[package]]
|
||||
name = "lemmy_utils"
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
dependencies = [
|
||||
"actix-web",
|
||||
"anyhow",
|
||||
|
|
24
Cargo.toml
24
Cargo.toml
|
@ -1,5 +1,5 @@
|
|||
[workspace.package]
|
||||
version = "0.19.4-beta.4"
|
||||
version = "0.19.4-beta.5"
|
||||
edition = "2021"
|
||||
description = "A link aggregator for the fediverse"
|
||||
license = "AGPL-3.0"
|
||||
|
@ -88,17 +88,17 @@ unused_self = "deny"
|
|||
unwrap_used = "deny"
|
||||
|
||||
[workspace.dependencies]
|
||||
lemmy_api = { version = "=0.19.4-beta.4", path = "./crates/api" }
|
||||
lemmy_api_crud = { version = "=0.19.4-beta.4", path = "./crates/api_crud" }
|
||||
lemmy_apub = { version = "=0.19.4-beta.4", path = "./crates/apub" }
|
||||
lemmy_utils = { version = "=0.19.4-beta.4", path = "./crates/utils", default-features = false }
|
||||
lemmy_db_schema = { version = "=0.19.4-beta.4", path = "./crates/db_schema" }
|
||||
lemmy_api_common = { version = "=0.19.4-beta.4", path = "./crates/api_common" }
|
||||
lemmy_routes = { version = "=0.19.4-beta.4", path = "./crates/routes" }
|
||||
lemmy_db_views = { version = "=0.19.4-beta.4", path = "./crates/db_views" }
|
||||
lemmy_db_views_actor = { version = "=0.19.4-beta.4", path = "./crates/db_views_actor" }
|
||||
lemmy_db_views_moderator = { version = "=0.19.4-beta.4", path = "./crates/db_views_moderator" }
|
||||
lemmy_federate = { version = "=0.19.4-beta.4", path = "./crates/federate" }
|
||||
lemmy_api = { version = "=0.19.4-beta.5", path = "./crates/api" }
|
||||
lemmy_api_crud = { version = "=0.19.4-beta.5", path = "./crates/api_crud" }
|
||||
lemmy_apub = { version = "=0.19.4-beta.5", path = "./crates/apub" }
|
||||
lemmy_utils = { version = "=0.19.4-beta.5", path = "./crates/utils", default-features = false }
|
||||
lemmy_db_schema = { version = "=0.19.4-beta.5", path = "./crates/db_schema" }
|
||||
lemmy_api_common = { version = "=0.19.4-beta.5", path = "./crates/api_common" }
|
||||
lemmy_routes = { version = "=0.19.4-beta.5", path = "./crates/routes" }
|
||||
lemmy_db_views = { version = "=0.19.4-beta.5", path = "./crates/db_views" }
|
||||
lemmy_db_views_actor = { version = "=0.19.4-beta.5", path = "./crates/db_views_actor" }
|
||||
lemmy_db_views_moderator = { version = "=0.19.4-beta.5", path = "./crates/db_views_moderator" }
|
||||
lemmy_federate = { version = "=0.19.4-beta.5", path = "./crates/federate" }
|
||||
activitypub_federation = { version = "0.5.4", default-features = false, features = [
|
||||
"actix-web",
|
||||
] }
|
||||
|
|
|
@ -36,8 +36,20 @@ pub async fn add_mod_to_community(
|
|||
let community = Community::read(&mut context.pool(), community_id)
|
||||
.await?
|
||||
.ok_or(LemmyErrorType::CouldntFindCommunity)?;
|
||||
|
||||
// If user is admin and community is remote, explicitly check that he is a
|
||||
// moderator. This is necessary because otherwise the action would be rejected
|
||||
// by the community's home instance.
|
||||
if local_user_view.local_user.admin && !community.local {
|
||||
Err(LemmyErrorType::NotAModerator)?
|
||||
let is_mod = CommunityModeratorView::is_community_moderator(
|
||||
&mut context.pool(),
|
||||
community.id,
|
||||
local_user_view.person.id,
|
||||
)
|
||||
.await?;
|
||||
if !is_mod {
|
||||
Err(LemmyErrorType::NotAModerator)?
|
||||
}
|
||||
}
|
||||
|
||||
// Update in local database
|
||||
|
|
|
@ -105,7 +105,11 @@ pub fn generate_post_link_metadata(
|
|||
}
|
||||
// Generate local thumbnail if allowed
|
||||
else if allow_generate_thumbnail {
|
||||
match post.url.or(metadata.opengraph_data.image) {
|
||||
match post
|
||||
.url
|
||||
.filter(|_| is_image_post)
|
||||
.or(metadata.opengraph_data.image)
|
||||
{
|
||||
Some(url) => generate_pictrs_thumbnail(&url, &context).await.ok(),
|
||||
None => None,
|
||||
}
|
||||
|
|
|
@ -536,25 +536,8 @@ pub async fn get_url_blocklist(context: &LemmyContext) -> LemmyResult<RegexSet>
|
|||
.try_get_with::<_, LemmyError>((), async {
|
||||
let urls = LocalSiteUrlBlocklist::get_all(&mut context.pool()).await?;
|
||||
|
||||
let regexes = urls.iter().map(|url| {
|
||||
let url = &url.url;
|
||||
let parsed = Url::parse(url).expect("Coundln't parse URL.");
|
||||
if url.ends_with('/') {
|
||||
format!(
|
||||
"({}://)?{}{}?",
|
||||
parsed.scheme(),
|
||||
escape(parsed.domain().expect("No domain.")),
|
||||
escape(parsed.path())
|
||||
)
|
||||
} else {
|
||||
format!(
|
||||
"({}://)?{}{}",
|
||||
parsed.scheme(),
|
||||
escape(parsed.domain().expect("No domain.")),
|
||||
escape(parsed.path())
|
||||
)
|
||||
}
|
||||
});
|
||||
// The urls are already validated on saving, so just escape them.
|
||||
let regexes = urls.iter().map(|url| escape(&url.url));
|
||||
|
||||
let set = RegexSet::new(regexes)?;
|
||||
Ok(set)
|
||||
|
|
|
@ -43,20 +43,13 @@ impl LocalUserLanguage {
|
|||
};
|
||||
let conn = &mut get_conn(pool).await?;
|
||||
|
||||
conn
|
||||
.build_transaction()
|
||||
.run(|conn| {
|
||||
Box::pin(async move {
|
||||
let langs = local_user_language
|
||||
.filter(local_user_id.eq(for_local_user_id))
|
||||
.order(language_id)
|
||||
.select(language_id)
|
||||
.get_results(conn)
|
||||
.await?;
|
||||
convert_read_languages(conn, langs).await
|
||||
}) as _
|
||||
})
|
||||
.await
|
||||
let langs = local_user_language
|
||||
.filter(local_user_id.eq(for_local_user_id))
|
||||
.order(language_id)
|
||||
.select(language_id)
|
||||
.get_results(conn)
|
||||
.await?;
|
||||
convert_read_languages(conn, langs).await
|
||||
}
|
||||
|
||||
/// Update the user's languages.
|
||||
|
@ -90,24 +83,33 @@ impl LocalUserLanguage {
|
|||
.build_transaction()
|
||||
.run(|conn| {
|
||||
Box::pin(async move {
|
||||
use crate::schema::local_user_language::dsl::{local_user_id, local_user_language};
|
||||
// Clear the current user languages
|
||||
delete(local_user_language.filter(local_user_id.eq(for_local_user_id)))
|
||||
.execute(conn)
|
||||
.await?;
|
||||
use crate::schema::local_user_language::dsl::{
|
||||
language_id,
|
||||
local_user_id,
|
||||
local_user_language,
|
||||
};
|
||||
// Delete old languages, not including new languages
|
||||
let delete_old = delete(local_user_language)
|
||||
.filter(local_user_id.eq(for_local_user_id))
|
||||
.filter(language_id.ne_all(&lang_ids))
|
||||
.execute(conn);
|
||||
|
||||
let forms = lang_ids
|
||||
.into_iter()
|
||||
.map(|l| LocalUserLanguageForm {
|
||||
.iter()
|
||||
.map(|&l| LocalUserLanguageForm {
|
||||
local_user_id: for_local_user_id,
|
||||
language_id: l,
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
insert_into(local_user_language)
|
||||
// Insert new languages
|
||||
let insert_new = insert_into(local_user_language)
|
||||
.values(forms)
|
||||
.execute(conn)
|
||||
.await?;
|
||||
.on_conflict((language_id, local_user_id))
|
||||
.do_nothing()
|
||||
.execute(conn);
|
||||
|
||||
tokio::try_join!(delete_old, insert_new)?;
|
||||
Ok(())
|
||||
}) as _
|
||||
})
|
||||
|
@ -159,25 +161,30 @@ impl SiteLanguage {
|
|||
.build_transaction()
|
||||
.run(|conn| {
|
||||
Box::pin(async move {
|
||||
use crate::schema::site_language::dsl::{site_id, site_language};
|
||||
use crate::schema::site_language::dsl::{language_id, site_id, site_language};
|
||||
|
||||
// Clear the current languages
|
||||
delete(site_language.filter(site_id.eq(for_site_id)))
|
||||
.execute(conn)
|
||||
.await?;
|
||||
// Delete old languages, not including new languages
|
||||
let delete_old = delete(site_language)
|
||||
.filter(site_id.eq(for_site_id))
|
||||
.filter(language_id.ne_all(&lang_ids))
|
||||
.execute(conn);
|
||||
|
||||
let forms = lang_ids
|
||||
.into_iter()
|
||||
.map(|l| SiteLanguageForm {
|
||||
.iter()
|
||||
.map(|&l| SiteLanguageForm {
|
||||
site_id: for_site_id,
|
||||
language_id: l,
|
||||
})
|
||||
.collect::<Vec<_>>();
|
||||
|
||||
insert_into(site_language)
|
||||
// Insert new languages
|
||||
let insert_new = insert_into(site_language)
|
||||
.values(forms)
|
||||
.get_result::<Self>(conn)
|
||||
.await?;
|
||||
.on_conflict((site_id, language_id))
|
||||
.do_nothing()
|
||||
.execute(conn);
|
||||
|
||||
tokio::try_join!(delete_old, insert_new)?;
|
||||
|
||||
CommunityLanguage::limit_languages(conn, instance_id).await?;
|
||||
|
||||
|
@ -278,8 +285,8 @@ impl CommunityLanguage {
|
|||
}
|
||||
|
||||
let form = lang_ids
|
||||
.into_iter()
|
||||
.map(|language_id| CommunityLanguageForm {
|
||||
.iter()
|
||||
.map(|&language_id| CommunityLanguageForm {
|
||||
community_id: for_community_id,
|
||||
language_id,
|
||||
})
|
||||
|
@ -289,25 +296,25 @@ impl CommunityLanguage {
|
|||
.build_transaction()
|
||||
.run(|conn| {
|
||||
Box::pin(async move {
|
||||
use crate::schema::community_language::dsl::{community_id, community_language};
|
||||
use diesel::result::DatabaseErrorKind::UniqueViolation;
|
||||
// Clear the current languages
|
||||
delete(community_language.filter(community_id.eq(for_community_id)))
|
||||
.execute(conn)
|
||||
.await?;
|
||||
use crate::schema::community_language::dsl::{
|
||||
community_id,
|
||||
community_language,
|
||||
language_id,
|
||||
};
|
||||
// Delete old languages, not including new languages
|
||||
let delete_old = delete(community_language)
|
||||
.filter(community_id.eq(for_community_id))
|
||||
.filter(language_id.ne_all(&lang_ids))
|
||||
.execute(conn);
|
||||
|
||||
let insert_res = insert_into(community_language)
|
||||
// Insert new languages
|
||||
let insert_new = insert_into(community_language)
|
||||
.values(form)
|
||||
.get_result::<Self>(conn)
|
||||
.await;
|
||||
.on_conflict((community_id, language_id))
|
||||
.do_nothing()
|
||||
.execute(conn);
|
||||
|
||||
if let Err(Error::DatabaseError(UniqueViolation, _info)) = insert_res {
|
||||
// race condition: this function was probably called simultaneously from another caller. ignore error
|
||||
// tracing::warn!("unique error: {_info:#?}");
|
||||
// _info.constraint_name() should be = "community_language_community_id_language_id_key"
|
||||
return Ok(());
|
||||
}
|
||||
insert_res?;
|
||||
tokio::try_join!(delete_old, insert_new)?;
|
||||
|
||||
Ok(())
|
||||
}) as _
|
||||
|
|
|
@ -215,9 +215,14 @@ fn queries<'a>() -> Queries<
|
|||
if let Some(parent_path) = options.parent_path.as_ref() {
|
||||
query = query.filter(comment::path.contained_by(parent_path));
|
||||
};
|
||||
|
||||
//filtering out removed and deleted comments from search
|
||||
if let Some(search_term) = options.search_term {
|
||||
query = query.filter(comment::content.ilike(fuzzy_search(&search_term)));
|
||||
query = query.filter(
|
||||
comment::content
|
||||
.ilike(fuzzy_search(&search_term))
|
||||
.and(comment::removed.eq(false))
|
||||
.and(comment::deleted.eq(false)),
|
||||
);
|
||||
};
|
||||
|
||||
if let Some(community_id) = options.community_id {
|
||||
|
|
|
@ -40,6 +40,11 @@ impl AdminPurgeCommentView {
|
|||
query = query.filter(admin_purge_comment::admin_person_id.eq(admin_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -38,6 +38,11 @@ impl AdminPurgeCommunityView {
|
|||
query = query.filter(admin_purge_community::admin_person_id.eq(admin_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -38,6 +38,11 @@ impl AdminPurgePersonView {
|
|||
query = query.filter(admin_purge_person::admin_person_id.eq(admin_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -40,6 +40,11 @@ impl AdminPurgePostView {
|
|||
query = query.filter(admin_purge_post::admin_person_id.eq(admin_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -52,6 +52,11 @@ impl ModAddCommunityView {
|
|||
query = query.filter(person_alias_1.field(person::id).eq(other_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -44,6 +44,11 @@ impl ModAddView {
|
|||
query = query.filter(person_alias_1.field(person::id).eq(other_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -54,6 +54,11 @@ impl ModBanFromCommunityView {
|
|||
query = query.filter(mod_ban_from_community::other_person_id.eq(other_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -44,6 +44,11 @@ impl ModBanView {
|
|||
query = query.filter(person_alias_1.field(person::id).eq(other_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -55,6 +55,11 @@ impl ModFeaturePostView {
|
|||
query = query.filter(post::id.eq(post_id));
|
||||
}
|
||||
|
||||
// If a comment ID is given, then don't find any results
|
||||
if params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -45,6 +45,11 @@ impl ModHideCommunityView {
|
|||
query = query.filter(mod_hide_community::mod_person_id.eq(admin_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -56,6 +56,11 @@ impl ModLockPostView {
|
|||
query = query.filter(post::id.eq(post_id));
|
||||
}
|
||||
|
||||
// If a comment ID is given, then don't find any results
|
||||
if params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -58,6 +58,11 @@ impl ModRemoveCommentView {
|
|||
query = query.filter(comment::id.eq(comment_id));
|
||||
}
|
||||
|
||||
// If a post ID is given, then don't find any results
|
||||
if params.post_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -39,6 +39,11 @@ impl ModRemoveCommunityView {
|
|||
query = query.filter(mod_remove_community::mod_person_id.eq(mod_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -56,6 +56,11 @@ impl ModRemovePostView {
|
|||
query = query.filter(post::id.eq(post_id));
|
||||
}
|
||||
|
||||
// If a comment ID is given, then don't find any results
|
||||
if params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -54,6 +54,11 @@ impl ModTransferCommunityView {
|
|||
query = query.filter(person_alias_1.field(person::id).eq(other_person_id));
|
||||
};
|
||||
|
||||
// If a post or comment ID is given, then don't find any results
|
||||
if params.post_id.is_some() || params.comment_id.is_some() {
|
||||
return Ok(vec![]);
|
||||
}
|
||||
|
||||
let (limit, offset) = limit_and_offset(params.page, params.limit)?;
|
||||
|
||||
query
|
||||
|
|
|
@ -309,21 +309,44 @@ pub fn is_url_blocked(url: &Option<Url>, blocklist: &RegexSet) -> LemmyResult<()
|
|||
Ok(())
|
||||
}
|
||||
|
||||
/// Check that urls are valid, and also remove the scheme, and uniques
|
||||
pub fn check_urls_are_valid(urls: &Vec<String>) -> LemmyResult<Vec<String>> {
|
||||
let mut parsed_urls = vec![];
|
||||
for url in urls {
|
||||
let url = Url::parse(url).or_else(|e| {
|
||||
if e == ParseError::RelativeUrlWithoutBase {
|
||||
Url::parse(&format!("https://{url}"))
|
||||
} else {
|
||||
Err(e)
|
||||
}
|
||||
})?;
|
||||
|
||||
parsed_urls.push(url.to_string());
|
||||
parsed_urls.push(build_url_str_without_scheme(url)?);
|
||||
}
|
||||
|
||||
Ok(parsed_urls)
|
||||
let unique_urls = parsed_urls.into_iter().unique().collect();
|
||||
Ok(unique_urls)
|
||||
}
|
||||
|
||||
pub fn build_url_str_without_scheme(url_str: &str) -> LemmyResult<String> {
|
||||
// Parse and check for errors
|
||||
let mut url = Url::parse(url_str).or_else(|e| {
|
||||
if e == ParseError::RelativeUrlWithoutBase {
|
||||
Url::parse(&format!("http://{url_str}"))
|
||||
} else {
|
||||
Err(e)
|
||||
}
|
||||
})?;
|
||||
|
||||
// Set the scheme to http, then remove the http:// part
|
||||
url
|
||||
.set_scheme("http")
|
||||
.map_err(|_| LemmyErrorType::InvalidUrl)?;
|
||||
|
||||
let mut out = url
|
||||
.to_string()
|
||||
.get(7..)
|
||||
.ok_or(LemmyErrorType::InvalidUrl)?
|
||||
.to_string();
|
||||
|
||||
// Remove trailing / if necessary
|
||||
if out.ends_with('/') {
|
||||
out.pop();
|
||||
}
|
||||
|
||||
Ok(out)
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
@ -600,17 +623,21 @@ mod tests {
|
|||
|
||||
#[test]
|
||||
fn test_url_parsed() {
|
||||
// Make sure the scheme is removed, and uniques also
|
||||
assert_eq!(
|
||||
vec![String::from("https://example.com/")],
|
||||
check_urls_are_valid(&vec![String::from("example.com")]).unwrap()
|
||||
&check_urls_are_valid(&vec![
|
||||
"example.com".to_string(),
|
||||
"http://example.com".to_string(),
|
||||
"https://example.com".to_string(),
|
||||
"https://example.com/test?q=test2&q2=test3#test4".to_string(),
|
||||
])
|
||||
.unwrap(),
|
||||
&vec![
|
||||
"example.com".to_string(),
|
||||
"example.com/test?q=test2&q2=test3#test4".to_string()
|
||||
],
|
||||
);
|
||||
|
||||
assert!(check_urls_are_valid(&vec![
|
||||
String::from("example.com"),
|
||||
String::from("https://example.blog")
|
||||
])
|
||||
.is_ok());
|
||||
|
||||
assert!(check_urls_are_valid(&vec![String::from("https://example .com"),]).is_err());
|
||||
assert!(check_urls_are_valid(&vec!["https://example .com".to_string()]).is_err());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1 +1 @@
|
|||
Subproject commit c88dd1e3b36ee1617f1b86acf94c1b7946e97cd4
|
||||
Subproject commit 866e4056656755f7b31e20094b46391e6931e3e7
|
120
migrations/2024-04-23-020604_add_post_id_index/down.sql
Normal file
120
migrations/2024-04-23-020604_add_post_id_index/down.sql
Normal file
|
@ -0,0 +1,120 @@
|
|||
DROP INDEX idx_post_aggregates_community_active;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_controversy;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_hot;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_most_comments;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_newest_comment_time;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_newest_comment_time_necro;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_published;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_published_asc;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_scaled;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_score;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_active;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_controversy;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_hot;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_most_comments;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_newest_comment_time;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_newest_comment_time_necr;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_published;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_published_asc;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_scaled;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_score;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_active;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_controversy;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_hot;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_most_comments;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_newest_comment_time;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_newest_comment_time_necro;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_published;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_published_asc;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_scaled;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_score;
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_active ON public.post_aggregates USING btree (community_id, featured_local DESC, hot_rank_active DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_controversy ON public.post_aggregates USING btree (community_id, featured_local DESC, controversy_rank DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_hot ON public.post_aggregates USING btree (community_id, featured_local DESC, hot_rank DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_most_comments ON public.post_aggregates USING btree (community_id, featured_local DESC, comments DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_newest_comment_time ON public.post_aggregates USING btree (community_id, featured_local DESC, newest_comment_time DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_newest_comment_time_necro ON public.post_aggregates USING btree (community_id, featured_local DESC, newest_comment_time_necro DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_published ON public.post_aggregates USING btree (community_id, featured_local DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_published_asc ON public.post_aggregates USING btree (community_id, featured_local DESC, public.reverse_timestamp_sort (published) DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_scaled ON public.post_aggregates USING btree (community_id, featured_local DESC, scaled_rank DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_score ON public.post_aggregates USING btree (community_id, featured_local DESC, score DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_active ON public.post_aggregates USING btree (community_id, featured_community DESC, hot_rank_active DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_controversy ON public.post_aggregates USING btree (community_id, featured_community DESC, controversy_rank DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_hot ON public.post_aggregates USING btree (community_id, featured_community DESC, hot_rank DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_most_comments ON public.post_aggregates USING btree (community_id, featured_community DESC, comments DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_newest_comment_time ON public.post_aggregates USING btree (community_id, featured_community DESC, newest_comment_time DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_newest_comment_time_necr ON public.post_aggregates USING btree (community_id, featured_community DESC, newest_comment_time_necro DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_published ON public.post_aggregates USING btree (community_id, featured_community DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_published_asc ON public.post_aggregates USING btree (community_id, featured_community DESC, public.reverse_timestamp_sort (published) DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_scaled ON public.post_aggregates USING btree (community_id, featured_community DESC, scaled_rank DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_score ON public.post_aggregates USING btree (community_id, featured_community DESC, score DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_active ON public.post_aggregates USING btree (featured_local DESC, hot_rank_active DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_controversy ON public.post_aggregates USING btree (featured_local DESC, controversy_rank DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_hot ON public.post_aggregates USING btree (featured_local DESC, hot_rank DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_most_comments ON public.post_aggregates USING btree (featured_local DESC, comments DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_newest_comment_time ON public.post_aggregates USING btree (featured_local DESC, newest_comment_time DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_newest_comment_time_necro ON public.post_aggregates USING btree (featured_local DESC, newest_comment_time_necro DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_published ON public.post_aggregates USING btree (featured_local DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_published_asc ON public.post_aggregates USING btree (featured_local DESC, public.reverse_timestamp_sort (published) DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_scaled ON public.post_aggregates USING btree (featured_local DESC, scaled_rank DESC, published DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_score ON public.post_aggregates USING btree (featured_local DESC, score DESC, published DESC);
|
||||
|
121
migrations/2024-04-23-020604_add_post_id_index/up.sql
Normal file
121
migrations/2024-04-23-020604_add_post_id_index/up.sql
Normal file
|
@ -0,0 +1,121 @@
|
|||
-- Add , post_id DESC to all these
|
||||
DROP INDEX idx_post_aggregates_community_active;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_controversy;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_hot;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_most_comments;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_newest_comment_time;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_newest_comment_time_necro;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_published;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_published_asc;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_scaled;
|
||||
|
||||
DROP INDEX idx_post_aggregates_community_score;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_active;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_controversy;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_hot;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_most_comments;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_newest_comment_time;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_newest_comment_time_necr;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_published;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_published_asc;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_scaled;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_community_score;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_active;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_controversy;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_hot;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_most_comments;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_newest_comment_time;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_newest_comment_time_necro;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_published;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_published_asc;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_scaled;
|
||||
|
||||
DROP INDEX idx_post_aggregates_featured_local_score;
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_active ON public.post_aggregates USING btree (community_id, featured_local DESC, hot_rank_active DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_controversy ON public.post_aggregates USING btree (community_id, featured_local DESC, controversy_rank DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_hot ON public.post_aggregates USING btree (community_id, featured_local DESC, hot_rank DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_most_comments ON public.post_aggregates USING btree (community_id, featured_local DESC, comments DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_newest_comment_time ON public.post_aggregates USING btree (community_id, featured_local DESC, newest_comment_time DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_newest_comment_time_necro ON public.post_aggregates USING btree (community_id, featured_local DESC, newest_comment_time_necro DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_published ON public.post_aggregates USING btree (community_id, featured_local DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_published_asc ON public.post_aggregates USING btree (community_id, featured_local DESC, public.reverse_timestamp_sort (published) DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_scaled ON public.post_aggregates USING btree (community_id, featured_local DESC, scaled_rank DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_community_score ON public.post_aggregates USING btree (community_id, featured_local DESC, score DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_active ON public.post_aggregates USING btree (community_id, featured_community DESC, hot_rank_active DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_controversy ON public.post_aggregates USING btree (community_id, featured_community DESC, controversy_rank DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_hot ON public.post_aggregates USING btree (community_id, featured_community DESC, hot_rank DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_most_comments ON public.post_aggregates USING btree (community_id, featured_community DESC, comments DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_newest_comment_time ON public.post_aggregates USING btree (community_id, featured_community DESC, newest_comment_time DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_newest_comment_time_necr ON public.post_aggregates USING btree (community_id, featured_community DESC, newest_comment_time_necro DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_published ON public.post_aggregates USING btree (community_id, featured_community DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_published_asc ON public.post_aggregates USING btree (community_id, featured_community DESC, public.reverse_timestamp_sort (published) DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_scaled ON public.post_aggregates USING btree (community_id, featured_community DESC, scaled_rank DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_community_score ON public.post_aggregates USING btree (community_id, featured_community DESC, score DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_active ON public.post_aggregates USING btree (featured_local DESC, hot_rank_active DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_controversy ON public.post_aggregates USING btree (featured_local DESC, controversy_rank DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_hot ON public.post_aggregates USING btree (featured_local DESC, hot_rank DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_most_comments ON public.post_aggregates USING btree (featured_local DESC, comments DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_newest_comment_time ON public.post_aggregates USING btree (featured_local DESC, newest_comment_time DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_newest_comment_time_necro ON public.post_aggregates USING btree (featured_local DESC, newest_comment_time_necro DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_published ON public.post_aggregates USING btree (featured_local DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_published_asc ON public.post_aggregates USING btree (featured_local DESC, public.reverse_timestamp_sort (published) DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_scaled ON public.post_aggregates USING btree (featured_local DESC, scaled_rank DESC, published DESC, post_id DESC);
|
||||
|
||||
CREATE INDEX idx_post_aggregates_featured_local_score ON public.post_aggregates USING btree (featured_local DESC, score DESC, published DESC, post_id DESC);
|
||||
|
Loading…
Reference in a new issue