Skip to content
This repository has been archived by the owner on Oct 19, 2024. It is now read-only.

Commit

Permalink
Fix duplicate file names
Browse files Browse the repository at this point in the history
  • Loading branch information
Geometrically committed Jun 13, 2024
1 parent beaaed6 commit a6ce29c
Show file tree
Hide file tree
Showing 9 changed files with 36 additions and 98 deletions.

This file was deleted.

This file was deleted.

This file was deleted.

3 changes: 3 additions & 0 deletions src/routes/v2/version_creation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ use crate::models::projects::{
Dependency, FileType, Loader, ProjectId, Version, VersionId, VersionStatus, VersionType,
};
use crate::models::v2::projects::LegacyVersion;
use crate::queue::moderation::AutomatedModerationQueue;
use crate::queue::session::AuthQueue;
use crate::routes::v3::project_creation::CreateError;
use crate::routes::v3::version_creation;
Expand Down Expand Up @@ -87,6 +88,7 @@ pub async fn version_create(
redis: Data<RedisPool>,
file_host: Data<Arc<dyn FileHost + Send + Sync>>,
session_queue: Data<AuthQueue>,
moderation_queue: Data<AutomatedModerationQueue>,
) -> Result<HttpResponse, CreateError> {
let payload = v2_reroute::alter_actix_multipart(
payload,
Expand Down Expand Up @@ -233,6 +235,7 @@ pub async fn version_create(
redis.clone(),
file_host,
session_queue,
moderation_queue,
)
.await?;

Expand Down
2 changes: 0 additions & 2 deletions src/routes/v2/versions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -211,7 +211,6 @@ pub struct EditVersion {
pub game_versions: Option<Vec<String>>,
pub loaders: Option<Vec<models::projects::Loader>>,
pub featured: Option<bool>,
pub primary_file: Option<(String, String)>,
pub downloads: Option<u32>,
pub status: Option<VersionStatus>,
pub file_types: Option<Vec<EditVersionFileType>>,
Expand Down Expand Up @@ -278,7 +277,6 @@ pub async fn version_edit(
dependencies: new_version.dependencies,
loaders,
featured: new_version.featured,
primary_file: new_version.primary_file,
downloads: new_version.downloads,
status: new_version.status,
file_types: new_version.file_types.map(|v| {
Expand Down
6 changes: 6 additions & 0 deletions src/routes/v3/project_creation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -538,6 +538,11 @@ async fn project_create_inner(
let version_data = project_create_data.initial_versions.get(index).unwrap();
// TODO: maybe redundant is this calculation done elsewhere?

let existing_file_names = created_version
.files
.iter()
.map(|x| x.filename.clone())
.collect();
// Upload the new jar file
super::version_creation::upload_file(
&mut field,
Expand All @@ -555,6 +560,7 @@ async fn project_create_inner(
version_data.primary_file.is_some(),
version_data.primary_file.as_deref() == Some(name),
None,
existing_file_names,
transaction,
redis,
)
Expand Down
23 changes: 22 additions & 1 deletion src/routes/v3/version_creation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,13 @@ use crate::models::images::{Image, ImageContext, ImageId};
use crate::models::notifications::NotificationBody;
use crate::models::pack::PackFileHash;
use crate::models::pats::Scopes;
use crate::models::projects::{skip_nulls, DependencyType};
use crate::models::projects::{skip_nulls, DependencyType, ProjectStatus};
use crate::models::projects::{
Dependency, FileType, Loader, ProjectId, Version, VersionFile, VersionId, VersionStatus,
VersionType,
};
use crate::models::teams::ProjectPermissions;
use crate::queue::moderation::AutomatedModerationQueue;
use crate::queue::session::AuthQueue;
use crate::util::routes::read_from_field;
use crate::util::validate::validation_errors_to_string;
Expand Down Expand Up @@ -102,6 +103,7 @@ pub async fn version_create(
redis: Data<RedisPool>,
file_host: Data<Arc<dyn FileHost + Send + Sync>>,
session_queue: Data<AuthQueue>,
moderation_queue: web::Data<AutomatedModerationQueue>,
) -> Result<HttpResponse, CreateError> {
let mut transaction = client.begin().await?;
let mut uploaded_files = Vec::new();
Expand All @@ -115,6 +117,7 @@ pub async fn version_create(
&mut uploaded_files,
&client,
&session_queue,
&moderation_queue,
)
.await;

Expand Down Expand Up @@ -144,6 +147,7 @@ async fn version_create_inner(
uploaded_files: &mut Vec<UploadedFile>,
pool: &PgPool,
session_queue: &AuthQueue,
moderation_queue: &AutomatedModerationQueue,
) -> Result<HttpResponse, CreateError> {
let cdn_url = dotenvy::var("CDN_URL")?;

Expand Down Expand Up @@ -333,6 +337,8 @@ async fn version_create_inner(
.clone()
.ok_or_else(|| CreateError::InvalidInput("`data` field is required".to_string()))?;

let existing_file_names = version.files.iter().map(|x| x.filename.clone()).collect();

upload_file(
&mut field,
file_host,
Expand All @@ -349,6 +355,7 @@ async fn version_create_inner(
version_data.primary_file.is_some(),
version_data.primary_file.as_deref() == Some(name),
version_data.file_types.get(name).copied().flatten(),
existing_file_names,
transaction,
redis,
)
Expand Down Expand Up @@ -498,6 +505,12 @@ async fn version_create_inner(

models::Project::clear_cache(project_id, None, Some(true), redis).await?;

if let Some(project) = models::Project::get_id(project_id, &*pool, &redis).await? {

Check warning on line 508 in src/routes/v3/version_creation.rs

View workflow job for this annotation

GitHub Actions / clippy

this expression creates a reference which is immediately dereferenced by the compiler

warning: this expression creates a reference which is immediately dereferenced by the compiler --> src/routes/v3/version_creation.rs:508:72 | 508 | if let Some(project) = models::Project::get_id(project_id, &*pool, &redis).await? { | ^^^^^^ help: change this to: `redis` | = help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#needless_borrow = note: `#[warn(clippy::needless_borrow)]` on by default

Check warning on line 508 in src/routes/v3/version_creation.rs

View workflow job for this annotation

GitHub Actions / clippy

deref on an immutable reference

warning: deref on an immutable reference --> src/routes/v3/version_creation.rs:508:64 | 508 | if let Some(project) = models::Project::get_id(project_id, &*pool, &redis).await? { | ^^^^^^ help: if you would like to reborrow, try removing `&*`: `pool` | = help: for further information visit https://rust-lang.github.io/rust-clippy/master/index.html#borrow_deref_ref = note: `#[warn(clippy::borrow_deref_ref)]` on by default
if project.inner.status == ProjectStatus::Processing {
moderation_queue.projects.insert(project_id.into());
}
}

Ok(HttpResponse::Ok().json(response))
}

Expand Down Expand Up @@ -706,6 +719,7 @@ async fn upload_file_to_version_inner(
true,
false,
file_data.file_types.get(name).copied().flatten(),
version.files.iter().map(|x| x.filename.clone()).collect(),
transaction,
&redis,
)
Expand Down Expand Up @@ -759,11 +773,18 @@ pub async fn upload_file(
ignore_primary: bool,
force_primary: bool,
file_type: Option<FileType>,
other_file_names: Vec<String>,
transaction: &mut sqlx::Transaction<'_, sqlx::Postgres>,
redis: &RedisPool,
) -> Result<(), CreateError> {
let (file_name, file_extension) = get_name_ext(content_disposition)?;

if other_file_names.contains(&format!("{}.{}", file_name, file_extension)) {
return Err(CreateError::InvalidInput(
"Duplicate files are not allowed to be uploaded to Modrinth!".to_string(),
));
}

if file_name.contains('/') {
return Err(CreateError::InvalidInput(
"File names must not contain slashes!".to_string(),
Expand Down
43 changes: 0 additions & 43 deletions src/routes/v3/versions.rs
Original file line number Diff line number Diff line change
Expand Up @@ -198,7 +198,6 @@ pub struct EditVersion {
pub dependencies: Option<Vec<Dependency>>,
pub loaders: Option<Vec<Loader>>,
pub featured: Option<bool>,
pub primary_file: Option<(String, String)>,
pub downloads: Option<u32>,
pub status: Option<VersionStatus>,
pub file_types: Option<Vec<EditVersionFileType>>,
Expand Down Expand Up @@ -490,48 +489,6 @@ pub async fn version_edit_helper(
.await?;
}

if let Some(primary_file) = &new_version.primary_file {
let result = sqlx::query!(
"
SELECT f.id id FROM hashes h
INNER JOIN files f ON h.file_id = f.id
WHERE h.algorithm = $2 AND h.hash = $1
",
primary_file.1.as_bytes(),
primary_file.0
)
.fetch_optional(&**pool)
.await?
.ok_or_else(|| {
ApiError::InvalidInput(format!(
"Specified file with hash {} does not exist.",
primary_file.1.clone()
))
})?;

sqlx::query!(
"
UPDATE files
SET is_primary = FALSE
WHERE (version_id = $1)
",
id as database::models::ids::VersionId,
)
.execute(&mut *transaction)
.await?;

sqlx::query!(
"
UPDATE files
SET is_primary = TRUE
WHERE (id = $1)
",
result.id,
)
.execute(&mut *transaction)
.await?;
}

if let Some(body) = &new_version.changelog {
sqlx::query!(
"
Expand Down
6 changes: 5 additions & 1 deletion src/validate/modpack.rs
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,11 @@ impl super::Validator for ModpackValidator {
(x.ends_with("jar") || x.ends_with("zip"))
&& (x.starts_with("overrides/mods")
|| x.starts_with("client-overrides/mods")
|| x.starts_with("server-overrides/mods"))
|| x.starts_with("server-overrides/mods")
|| x.starts_with("overrides/resourcepacks")
|| x.starts_with("server-overrides/resourcepacks")
|| x.starts_with("overrides/shaderpacks")
|| x.starts_with("client-overrides/shaderpacks"))
})
.flat_map(|x| x.rsplit('/').next().map(|x| x.to_string()))
.collect::<Vec<String>>(),
Expand Down

0 comments on commit a6ce29c

Please sign in to comment.