From 4a1f985cce3df022b0c688504f49773a25675067 Mon Sep 17 00:00:00 2001 From: Untone Date: Tue, 22 Oct 2024 00:11:33 +0300 Subject: [PATCH] 0.0.5-fixes --- Cargo.toml | 2 +- src/app_state.rs | 54 ++++++++++++++++++++++++++---------------------- src/handlers.rs | 12 +++++------ 3 files changed, 36 insertions(+), 32 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index aa3e468..4bb310b 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "discoursio-quoter" -version = "0.0.4" +version = "0.0.5" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/src/app_state.rs b/src/app_state.rs index c599242..83616aa 100644 --- a/src/app_state.rs +++ b/src/app_state.rs @@ -4,7 +4,7 @@ use aws_sdk_s3::{config::Credentials, Client as S3Client}; use redis::{aio::MultiplexedConnection, AsyncCommands, Client as RedisClient}; use std::{env, time::Duration}; use tokio::time::interval; - +use std::collections::HashMap; use crate::s3_utils::check_file_exists; #[derive(Clone)] @@ -110,12 +110,13 @@ impl AppState { for object in objects.iter() { if let Some(key) = &object.key { let parts: Vec<&str> = key.split('.').collect(); - if parts.len() > 1 && !parts.last().unwrap().contains('/') { - let filename = parts[0..parts.len()-1].join("."); - file_list.entry(filename).or_insert(key.clone()); - } else { - file_list.entry(key.to_string()).or_insert(key.clone()); + let filename = parts.first().unwrap_or(&""); + let ext = parts.get(1).unwrap_or(&""); + if ext.contains('/') { + continue; } + let filename_with_extension = format!("{}.{}", filename, ext); + file_list.insert(filename_with_extension, key.clone()); } } @@ -150,25 +151,25 @@ impl AppState { } /// Сохраняет маппинг старого пути из AWS S3 на новый путь в Storj S3. - async fn save_path_by_filekey( + async fn save_path_by_filename_with_extension( &self, - filekey: &str, + filename_with_extension: &str, path: &str, ) -> Result<(), actix_web::Error> { let mut redis = self.redis.clone(); // Храним маппинг в формате Hash: old_path -> new_path redis - .hset::<_, &str, &str, ()>(PATH_MAPPING_KEY, filekey, path) + .hset::<_, &str, &str, ()>(PATH_MAPPING_KEY, filename_with_extension, path) .await .map_err(|_| ErrorInternalServerError("Failed to save path mapping in Redis"))?; Ok(()) } /// Получает путь в хранилище из ключа (имени файла) в Redis. - pub async fn get_path(&self, filekey: &str) -> Result, actix_web::Error> { + pub async fn get_path(&self, filename_with_extension: &str) -> Result, actix_web::Error> { let mut redis = self.redis.clone(); let new_path: Option = redis - .hget(PATH_MAPPING_KEY, filekey) + .hget(PATH_MAPPING_KEY, filename_with_extension) .await .map_err(|_| ErrorInternalServerError("Failed to get path mapping from Redis"))?; Ok(new_path) @@ -186,35 +187,38 @@ impl AppState { for object in objects { if let Some(key) = object.key { // Получаем имя файла с расширением - let [filename, ext] = key.split('.').collect::>(); + let parts: Vec<&str> = key.split('.').collect(); + let filename = parts.first().unwrap_or(&""); + let ext = parts.get(1).unwrap_or(&""); + if ext.contains('/') { + continue; + } + let filename_with_extension = format!("{}.{}", filename, ext); if filename.is_empty() { - eprint!("Пустое имя файла {}", key); + eprint!("[ERROR] empty filename: {}", key); } else { // Проверяем, существует ли файл на Storj S3 - match check_file_exists(&self.s3_client, &self.s3_bucket, filename) + match check_file_exists(&self.s3_client, &self.s3_bucket, &filename_with_extension) .await { Ok(false) => { // Сохраняем маппинг пути if let Err(e) = - self.save_path_by_filekey(filename, &key).await + self.save_path_by_filename_with_extension(&filename_with_extension, &key).await { - eprintln!( - "[ОШИБКА СОХРАНЕНИЯ] {}: {:?}", - filename_with_extension, e - ); + eprintln!("[ERROR] save {}: {:?}", key, e); } else { - println!("{}", filename_with_extension); + println!("{}", key); } } Ok(true) => { - println!("Файл {} уже существует в Storj.", filename); + println!("Already exists in Storj: {}", filename_with_extension); } Err(e) => { eprintln!( - "Ошибка при проверке файла {} на Storj: {:?}", - filename, e + "[ERROR] check {}: {:?}", + filename_with_extension, e ); } } @@ -222,11 +226,11 @@ impl AppState { } } } else { - println!("Список файлов в AWS S3 пуст."); + println!("AWS S3 file list is empty."); } } Err(e) => { - eprintln!("Не удалось получить список файлов из AWS S3: {:?}", e); + eprintln!("[ERROR] get AWS S3 file list: {:?}", e); } } } diff --git a/src/handlers.rs b/src/handlers.rs index 4436b65..7862d11 100644 --- a/src/handlers.rs +++ b/src/handlers.rs @@ -17,14 +17,14 @@ use crate::thumbnail::{ pub const MAX_WEEK_BYTES: u64 = 2 * 1024 * 1024 * 1024; /// Функция для обслуживания файла по заданному пути. -async fn serve_file(file_key: &str, state: &AppState) -> Result { +async fn serve_file(filename_with_extension: &str, state: &AppState) -> Result { // Проверяем наличие файла в Storj S3 - if !check_file_exists(&state.s3_client, &state.s3_bucket, file_key).await? { - warn!("{}", file_key); + if !check_file_exists(&state.s3_client, &state.s3_bucket, filename_with_extension).await? { + warn!("{}", filename_with_extension); return Err(ErrorInternalServerError("File not found in S3")); } - let checked_filekey = state.get_path(file_key).await.unwrap().unwrap(); + let checked_filekey = state.get_path(filename_with_extension).await.unwrap().unwrap(); // Получаем объект из Storj S3 let get_object_output = state @@ -43,7 +43,7 @@ async fn serve_file(file_key: &str, state: &AppState) -> Result, state: web::Data, ) -> Result { - info!("proxy_handler вызван с путем: {}", path); + info!("proxy_handler: {}", path); let requested_path = match state.get_path(&path).await { Ok(Some(path)) => path,