You've already forked AstralRinth
forked from didirus/AstralRinth
@@ -13,17 +13,17 @@ use tokio::sync::RwLock;
|
|||||||
|
|
||||||
extern crate clickhouse as clickhouse_crate;
|
extern crate clickhouse as clickhouse_crate;
|
||||||
use clickhouse_crate::Client;
|
use clickhouse_crate::Client;
|
||||||
use governor::{Quota, RateLimiter};
|
|
||||||
use governor::middleware::StateInformationMiddleware;
|
use governor::middleware::StateInformationMiddleware;
|
||||||
|
use governor::{Quota, RateLimiter};
|
||||||
use util::cors::default_cors;
|
use util::cors::default_cors;
|
||||||
|
|
||||||
use crate::queue::moderation::AutomatedModerationQueue;
|
use crate::queue::moderation::AutomatedModerationQueue;
|
||||||
|
use crate::util::ratelimit::KeyedRateLimiter;
|
||||||
use crate::{
|
use crate::{
|
||||||
queue::payouts::process_payout,
|
queue::payouts::process_payout,
|
||||||
search::indexing::index_projects,
|
search::indexing::index_projects,
|
||||||
util::env::{parse_strings_from_var, parse_var},
|
util::env::{parse_strings_from_var, parse_var},
|
||||||
};
|
};
|
||||||
use crate::util::ratelimit::KeyedRateLimiter;
|
|
||||||
|
|
||||||
pub mod auth;
|
pub mod auth;
|
||||||
pub mod clickhouse;
|
pub mod clickhouse;
|
||||||
|
|||||||
@@ -1,17 +1,13 @@
|
|||||||
use actix_web::{App, HttpServer};
|
use actix_web::{App, HttpServer};
|
||||||
use actix_web_prom::PrometheusMetricsBuilder;
|
use actix_web_prom::PrometheusMetricsBuilder;
|
||||||
use env_logger::Env;
|
use env_logger::Env;
|
||||||
use governor::middleware::StateInformationMiddleware;
|
|
||||||
use governor::{Quota, RateLimiter};
|
|
||||||
use labrinth::database::redis::RedisPool;
|
use labrinth::database::redis::RedisPool;
|
||||||
use labrinth::file_hosting::S3Host;
|
use labrinth::file_hosting::S3Host;
|
||||||
use labrinth::search;
|
use labrinth::search;
|
||||||
use labrinth::util::ratelimit::{KeyedRateLimiter, RateLimit};
|
use labrinth::util::ratelimit::RateLimit;
|
||||||
use labrinth::{check_env_vars, clickhouse, database, file_hosting, queue};
|
use labrinth::{check_env_vars, clickhouse, database, file_hosting, queue};
|
||||||
use log::{error, info};
|
use log::{error, info};
|
||||||
use std::num::NonZeroU32;
|
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
use std::time::Duration;
|
|
||||||
|
|
||||||
#[cfg(feature = "jemalloc")]
|
#[cfg(feature = "jemalloc")]
|
||||||
#[global_allocator]
|
#[global_allocator]
|
||||||
@@ -98,7 +94,7 @@ async fn main() -> std::io::Result<()> {
|
|||||||
|
|
||||||
let search_config = search::SearchConfig::new(None);
|
let search_config = search::SearchConfig::new(None);
|
||||||
|
|
||||||
let mut labrinth_config = labrinth::app_setup(
|
let labrinth_config = labrinth::app_setup(
|
||||||
pool.clone(),
|
pool.clone(),
|
||||||
redis_pool.clone(),
|
redis_pool.clone(),
|
||||||
search_config.clone(),
|
search_config.clone(),
|
||||||
|
|||||||
@@ -453,7 +453,7 @@ pub async fn project_edit(
|
|||||||
old_status: project_item.inner.status,
|
old_status: project_item.inner.status,
|
||||||
},
|
},
|
||||||
thread_id: project_item.thread_id,
|
thread_id: project_item.thread_id,
|
||||||
hide_identity: true,
|
hide_identity: user.role.is_mod(),
|
||||||
}
|
}
|
||||||
.insert(&mut transaction)
|
.insert(&mut transaction)
|
||||||
.await?;
|
.await?;
|
||||||
|
|||||||
@@ -435,7 +435,7 @@ pub async fn report_edit(
|
|||||||
MessageBody::ThreadClosure
|
MessageBody::ThreadClosure
|
||||||
},
|
},
|
||||||
thread_id: report.thread_id,
|
thread_id: report.thread_id,
|
||||||
hide_identity: true,
|
hide_identity: user.role.is_mod(),
|
||||||
}
|
}
|
||||||
.insert(&mut transaction)
|
.insert(&mut transaction)
|
||||||
.await?;
|
.await?;
|
||||||
|
|||||||
@@ -569,6 +569,7 @@ pub async fn add_team_member(
|
|||||||
|
|
||||||
transaction.commit().await?;
|
transaction.commit().await?;
|
||||||
TeamMember::clear_cache(team_id, &redis).await?;
|
TeamMember::clear_cache(team_id, &redis).await?;
|
||||||
|
User::clear_project_cache(&[new_member.user_id.into()], &redis).await?;
|
||||||
|
|
||||||
Ok(HttpResponse::NoContent().body(""))
|
Ok(HttpResponse::NoContent().body(""))
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -19,9 +19,9 @@ impl Scheduler {
|
|||||||
}
|
}
|
||||||
|
|
||||||
pub fn run<F, R>(&mut self, interval: std::time::Duration, mut task: F)
|
pub fn run<F, R>(&mut self, interval: std::time::Duration, mut task: F)
|
||||||
where
|
where
|
||||||
F: FnMut() -> R + Send + 'static,
|
F: FnMut() -> R + Send + 'static,
|
||||||
R: std::future::Future<Output = ()> + Send + 'static,
|
R: std::future::Future<Output = ()> + Send + 'static,
|
||||||
{
|
{
|
||||||
let future = IntervalStream::new(actix_rt::time::interval(interval))
|
let future = IntervalStream::new(actix_rt::time::interval(interval))
|
||||||
.for_each_concurrent(2, move |_| task());
|
.for_each_concurrent(2, move |_| task());
|
||||||
@@ -207,4 +207,4 @@ async fn update_versions(
|
|||||||
}
|
}
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,10 +9,6 @@ impl super::Validator for DataPackValidator {
|
|||||||
&["zip"]
|
&["zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["datapack"]
|
&["datapack"]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,10 +10,6 @@ impl super::Validator for FabricValidator {
|
|||||||
&["jar", "zip"]
|
&["jar", "zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["fabric"]
|
&["fabric"]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,10 +10,6 @@ impl super::Validator for ForgeValidator {
|
|||||||
&["jar", "zip"]
|
&["jar", "zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["forge"]
|
&["forge"]
|
||||||
}
|
}
|
||||||
@@ -47,10 +43,6 @@ impl super::Validator for LegacyForgeValidator {
|
|||||||
&["jar", "zip"]
|
&["jar", "zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["forge"]
|
&["forge"]
|
||||||
}
|
}
|
||||||
@@ -71,15 +63,13 @@ impl super::Validator for LegacyForgeValidator {
|
|||||||
|
|
||||||
fn validate(
|
fn validate(
|
||||||
&self,
|
&self,
|
||||||
archive: &mut ZipArchive<Cursor<bytes::Bytes>>,
|
_archive: &mut ZipArchive<Cursor<bytes::Bytes>>,
|
||||||
) -> Result<ValidationResult, ValidationError> {
|
) -> Result<ValidationResult, ValidationError> {
|
||||||
if archive.by_name("mcmod.info").is_err() {
|
// if archive.by_name("mcmod.info").is_err() {
|
||||||
return Ok(ValidationResult::Warning(
|
// return Ok(ValidationResult::Warning(
|
||||||
"Forge mod file does not contain mcmod.info!",
|
// "Forge mod file does not contain mcmod.info!",
|
||||||
));
|
// ));
|
||||||
};
|
// };
|
||||||
|
|
||||||
//TODO: Check if file is a dev JAR?
|
|
||||||
|
|
||||||
Ok(ValidationResult::Pass)
|
Ok(ValidationResult::Pass)
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,10 +9,6 @@ impl super::Validator for LiteLoaderValidator {
|
|||||||
&["litemod", "jar"]
|
&["litemod", "jar"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["liteloader"]
|
&["liteloader"]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -77,7 +77,6 @@ pub enum SupportedGameVersions {
|
|||||||
|
|
||||||
pub trait Validator: Sync {
|
pub trait Validator: Sync {
|
||||||
fn get_file_extensions(&self) -> &[&str];
|
fn get_file_extensions(&self) -> &[&str];
|
||||||
fn get_project_types(&self) -> &[&str];
|
|
||||||
fn get_supported_loaders(&self) -> &[&str];
|
fn get_supported_loaders(&self) -> &[&str];
|
||||||
fn get_supported_game_versions(&self) -> SupportedGameVersions;
|
fn get_supported_game_versions(&self) -> SupportedGameVersions;
|
||||||
fn validate(
|
fn validate(
|
||||||
@@ -118,41 +117,28 @@ pub async fn validate_file(
|
|||||||
transaction: &mut sqlx::Transaction<'_, sqlx::Postgres>,
|
transaction: &mut sqlx::Transaction<'_, sqlx::Postgres>,
|
||||||
redis: &RedisPool,
|
redis: &RedisPool,
|
||||||
) -> Result<ValidationResult, ValidationError> {
|
) -> Result<ValidationResult, ValidationError> {
|
||||||
// TODO: This needs to be revisited or removed with v3.
|
let game_versions = version_fields
|
||||||
// Currently, it checks if the loader is the modpack loader, and extracts the pack data from it.
|
.into_iter()
|
||||||
// This (and the funnction that calls this) should be refactored such that
|
.find_map(|v| MinecraftGameVersion::try_from_version_field(&v).ok())
|
||||||
// - validators are removed (or altogether reworked)
|
.unwrap_or_default();
|
||||||
// - if a mrpack is uploaded, the pack data is extracted and usable to extract dependencies automatically
|
let all_game_versions =
|
||||||
|
MinecraftGameVersion::list(None, None, &mut *transaction, redis).await?;
|
||||||
|
|
||||||
// TODO: A test needs to be written for this.
|
validate_minecraft_file(
|
||||||
match loaders {
|
data,
|
||||||
loaders if loaders == vec![Loader("mrpack".to_string())] => {
|
file_extension,
|
||||||
let game_versions = version_fields
|
loaders,
|
||||||
.into_iter()
|
game_versions,
|
||||||
.find_map(|v| MinecraftGameVersion::try_from_version_field(&v).ok())
|
all_game_versions,
|
||||||
.unwrap_or_default();
|
file_type,
|
||||||
let all_game_versions =
|
)
|
||||||
MinecraftGameVersion::list(None, None, &mut *transaction, redis).await?;
|
.await
|
||||||
validate_minecraft_file(
|
|
||||||
data,
|
|
||||||
file_extension,
|
|
||||||
"modpack".to_string(),
|
|
||||||
loaders,
|
|
||||||
game_versions,
|
|
||||||
all_game_versions,
|
|
||||||
file_type,
|
|
||||||
)
|
|
||||||
.await
|
|
||||||
}
|
|
||||||
_ => Ok(ValidationResult::Pass),
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
async fn validate_minecraft_file(
|
async fn validate_minecraft_file(
|
||||||
data: bytes::Bytes,
|
data: bytes::Bytes,
|
||||||
file_extension: String,
|
file_extension: String,
|
||||||
mut project_type: String,
|
loaders: Vec<Loader>,
|
||||||
mut loaders: Vec<Loader>,
|
|
||||||
game_versions: Vec<MinecraftGameVersion>,
|
game_versions: Vec<MinecraftGameVersion>,
|
||||||
all_game_versions: Vec<MinecraftGameVersion>,
|
all_game_versions: Vec<MinecraftGameVersion>,
|
||||||
file_type: Option<FileType>,
|
file_type: Option<FileType>,
|
||||||
@@ -164,19 +150,18 @@ async fn validate_minecraft_file(
|
|||||||
if let Some(file_type) = file_type {
|
if let Some(file_type) = file_type {
|
||||||
match file_type {
|
match file_type {
|
||||||
FileType::RequiredResourcePack | FileType::OptionalResourcePack => {
|
FileType::RequiredResourcePack | FileType::OptionalResourcePack => {
|
||||||
project_type = "resourcepack".to_string();
|
return PackValidator.validate(&mut zip);
|
||||||
loaders = vec![Loader("minecraft".to_string())];
|
|
||||||
}
|
}
|
||||||
FileType::Unknown => {}
|
FileType::Unknown => {}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let mut visited = false;
|
let mut visited = false;
|
||||||
|
let mut saved_result = None;
|
||||||
for validator in VALIDATORS {
|
for validator in VALIDATORS {
|
||||||
if validator.get_project_types().contains(&&*project_type)
|
if loaders
|
||||||
&& loaders
|
.iter()
|
||||||
.iter()
|
.any(|x| validator.get_supported_loaders().contains(&&*x.0))
|
||||||
.any(|x| validator.get_supported_loaders().contains(&&*x.0))
|
|
||||||
&& game_version_supported(
|
&& game_version_supported(
|
||||||
&game_versions,
|
&game_versions,
|
||||||
&all_game_versions,
|
&all_game_versions,
|
||||||
@@ -184,13 +169,30 @@ async fn validate_minecraft_file(
|
|||||||
)
|
)
|
||||||
{
|
{
|
||||||
if validator.get_file_extensions().contains(&&*file_extension) {
|
if validator.get_file_extensions().contains(&&*file_extension) {
|
||||||
return validator.validate(&mut zip);
|
let result = validator.validate(&mut zip)?;
|
||||||
|
match result {
|
||||||
|
ValidationResult::PassWithPackDataAndFiles { .. } => {
|
||||||
|
saved_result = Some(result);
|
||||||
|
}
|
||||||
|
ValidationResult::Pass => {
|
||||||
|
if saved_result.is_none() {
|
||||||
|
saved_result = Some(result);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
ValidationResult::Warning(_) => {
|
||||||
|
return Ok(result);
|
||||||
|
}
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
visited = true;
|
visited = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if let Some(result) = saved_result {
|
||||||
|
return Ok(result);
|
||||||
|
}
|
||||||
|
|
||||||
if visited {
|
if visited {
|
||||||
if ALWAYS_ALLOWED_EXT.contains(&&*file_extension) {
|
if ALWAYS_ALLOWED_EXT.contains(&&*file_extension) {
|
||||||
Ok(ValidationResult::Warning(
|
Ok(ValidationResult::Warning(
|
||||||
|
|||||||
@@ -13,12 +13,8 @@ impl super::Validator for ModpackValidator {
|
|||||||
&["mrpack"]
|
&["mrpack"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["modpack"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["forge", "fabric", "quilt", "mrpack"]
|
&["mrpack"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_supported_game_versions(&self) -> SupportedGameVersions {
|
fn get_supported_game_versions(&self) -> SupportedGameVersions {
|
||||||
|
|||||||
@@ -9,10 +9,6 @@ impl super::Validator for PluginYmlValidator {
|
|||||||
&["zip", "jar"]
|
&["zip", "jar"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["bukkit", "spigot", "paper", "purpur"]
|
&["bukkit", "spigot", "paper", "purpur"]
|
||||||
}
|
}
|
||||||
@@ -45,10 +41,6 @@ impl super::Validator for BungeeCordValidator {
|
|||||||
&["zip", "jar"]
|
&["zip", "jar"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["bungeecord", "waterfall"]
|
&["bungeecord", "waterfall"]
|
||||||
}
|
}
|
||||||
@@ -81,10 +73,6 @@ impl super::Validator for VelocityValidator {
|
|||||||
&["zip", "jar"]
|
&["zip", "jar"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["velocity"]
|
&["velocity"]
|
||||||
}
|
}
|
||||||
@@ -114,10 +102,6 @@ impl super::Validator for SpongeValidator {
|
|||||||
&["zip", "jar"]
|
&["zip", "jar"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["sponge"]
|
&["sponge"]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,10 +10,6 @@ impl super::Validator for QuiltValidator {
|
|||||||
&["jar", "zip"]
|
&["jar", "zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["mod"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["quilt"]
|
&["quilt"]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,10 +10,6 @@ impl super::Validator for PackValidator {
|
|||||||
&["zip"]
|
&["zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["resourcepack"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["minecraft"]
|
&["minecraft"]
|
||||||
}
|
}
|
||||||
@@ -47,10 +43,6 @@ impl super::Validator for TexturePackValidator {
|
|||||||
&["zip"]
|
&["zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["resourcepack"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["minecraft"]
|
&["minecraft"]
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -9,10 +9,6 @@ impl super::Validator for ShaderValidator {
|
|||||||
&["zip"]
|
&["zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["shader"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["optifine", "iris"]
|
&["optifine", "iris"]
|
||||||
}
|
}
|
||||||
@@ -42,10 +38,6 @@ impl super::Validator for CanvasShaderValidator {
|
|||||||
&["zip"]
|
&["zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["shader"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["canvas"]
|
&["canvas"]
|
||||||
}
|
}
|
||||||
@@ -81,10 +73,6 @@ impl super::Validator for CoreShaderValidator {
|
|||||||
&["zip"]
|
&["zip"]
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_project_types(&self) -> &[&str] {
|
|
||||||
&["shader"]
|
|
||||||
}
|
|
||||||
|
|
||||||
fn get_supported_loaders(&self) -> &[&str] {
|
fn get_supported_loaders(&self) -> &[&str] {
|
||||||
&["vanilla"]
|
&["vanilla"]
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user