nexus_common/media/processors/
mod.rs1use crate::{media::FileVariant, models::file::FileDetails, types::DynError};
2use async_trait::async_trait;
3use std::path::PathBuf;
4
5mod image;
6mod video;
7
8pub use image::*;
9pub use video::*;
10
11pub trait BaseProcessingOptions: Send + Sync {
12 fn content_type(&self) -> String;
13}
14
15#[async_trait]
16pub trait VariantProcessor {
17 type ProcessingOptions: BaseProcessingOptions;
18
19 fn get_valid_variants_for_content_type(content_type: &str) -> Vec<FileVariant>;
22
23 fn get_content_type_for_variant(file: &FileDetails, variant: &FileVariant) -> String;
25
26 fn get_options_for_variant(
29 file: &FileDetails,
30 variant: &FileVariant,
31 ) -> Result<Self::ProcessingOptions, DynError>;
32
33 async fn process(
36 origin_file_path: &str,
37 output_file_path: &str,
38 options: &Self::ProcessingOptions,
39 ) -> Result<String, DynError>;
40
41 async fn create_variant(
44 file: &FileDetails,
45 variant: &FileVariant,
46 file_path: PathBuf,
47 ) -> Result<String, DynError> {
48 let options = match Self::get_options_for_variant(file, variant) {
50 Ok(options) => options,
51 Err(_) => return Ok(file.content_type.clone()),
52 };
53
54 let origin_path = file_path
55 .join(file.owner_id.as_str())
56 .join(file.id.as_str());
57
58 let origin_file = origin_path.join(FileVariant::Main.to_string());
59
60 let origin_file_path = match origin_file.to_str() {
61 Some(path) => path,
62 None => return Err("Invalid original file path".into()),
63 };
64
65 let output = origin_path.join(variant.to_string());
66 let output_path = match output.to_str() {
67 Some(path) => path,
68 None => return Err("Invalid output path".into()),
69 };
70
71 Self::process(origin_file_path, output_path, &options).await?;
72
73 Ok(options.content_type())
74 }
75}