mirror of
https://github.com/storytold/artcraft.git
synced 2026-11-09 11:31:27 +00:00
voice conversion result upload (WIP)
This commit is contained in:
1 parent
9e38b9a2fc
commit
08e8560499
5 files changed
+179
-6
No files matched your search
@@ -1,2 +1,3 @@
|
||||
pub mod media_uploads;
|
||||
pub mod public_path;
|
||||
pub mod public_path;
|
||||
pub mod voice_conversion_results;
|
||||
@@ -0,0 +1,63 @@
|
||||
use crate::public::public_path::PublicPath;
|
||||
use crate::util::hashed_directory_path_long_string::hashed_directory_path_long_string;
|
||||
|
||||
// TODO: Generate these from a macro.
|
||||
|
||||
// TODO: Use a central path registry for quick reference
|
||||
const DIRECTORY: &'static str = "/voice_conversion";
|
||||
|
||||
/// Directory for voice conversion results.
|
||||
/// Each result gets its own directory so that we can store the result
|
||||
/// alongside metadata and re-processed derivatives.
|
||||
#[derive(Clone)]
|
||||
pub struct VoiceConversionResultDirectory {
|
||||
object_hash: String,
|
||||
directory: String,
|
||||
}
|
||||
|
||||
impl PublicPath for VoiceConversionResultDirectory {}
|
||||
|
||||
impl VoiceConversionResultDirectory {
|
||||
|
||||
pub fn from_public_bucket_directory_hash(object_hash: &str) -> Self {
|
||||
// TODO: Path construction could be cleaner.
|
||||
let middle = hashed_directory_path_long_string(object_hash);
|
||||
let directory = format!("{}/{}{}", DIRECTORY, middle, object_hash);
|
||||
Self {
|
||||
object_hash: object_hash.to_string(),
|
||||
directory,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_directory_path_str(&self) -> &str {
|
||||
&self.directory
|
||||
}
|
||||
|
||||
pub fn get_object_hash(&self) -> &str {
|
||||
&self.object_hash
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use crate::public::voice_conversion_results::directory::VoiceConversionResultDirectory;
|
||||
|
||||
#[test]
|
||||
pub fn get_directory_path_str() {
|
||||
let directory = VoiceConversionResultDirectory::from_public_bucket_directory_hash("abcdefghijk");
|
||||
assert_eq!(directory.get_directory_path_str(), "/voice_conversion/a/b/c/d/e/abcdefghijk");
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn get_directory_path_str_short_name() {
|
||||
let directory = VoiceConversionResultDirectory::from_public_bucket_directory_hash("foo");
|
||||
assert_eq!(directory.get_directory_path_str(), "/voice_conversion/f/o/foo");
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn get_object_hash() {
|
||||
let hash = "abcdefghijk";
|
||||
let directory = VoiceConversionResultDirectory::from_public_bucket_directory_hash(hash);
|
||||
assert_eq!(directory.get_object_hash(), hash);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
pub mod directory;
|
||||
pub mod original_file;
|
||||
@@ -0,0 +1,105 @@
|
||||
use crate::public::media_uploads::directory::MediaUploadDirectory;
|
||||
use crate::public::public_path::PublicPath;
|
||||
use crockford::crockford_entropy_lower;
|
||||
use std::path::PathBuf;
|
||||
|
||||
const ORIGINAL_FILE_PREFIX : &'static str = "fakeyou_";
|
||||
const ORIGINAL_FILE_SUFFIX : &'static str = ".wav";
|
||||
|
||||
// TODO: Generate these from a macro.
|
||||
|
||||
/// The original user upload file.
|
||||
/// It may have derivative files (down samples, crops, etc.) that live alongside it.
|
||||
#[derive(Clone)]
|
||||
pub struct VoiceConversionResultOriginalFilePath {
|
||||
directory: MediaUploadDirectory,
|
||||
basename: String,
|
||||
full_object_path: String,
|
||||
}
|
||||
|
||||
impl PublicPath for VoiceConversionResultOriginalFilePath {}
|
||||
|
||||
impl VoiceConversionResultOriginalFilePath {
|
||||
|
||||
pub fn generate_new() -> Self {
|
||||
let entropy = crockford_entropy_lower(32);
|
||||
Self::from_object_hash(&entropy)
|
||||
}
|
||||
|
||||
pub fn from_object_hash(hash: &str) -> Self {
|
||||
// TODO: Path construction could be cleaner.
|
||||
let directory = MediaUploadDirectory::from_object_hash(hash);
|
||||
let basename = format!("{}{}{}", ORIGINAL_FILE_PREFIX, hash, ORIGINAL_FILE_SUFFIX);
|
||||
let full_object_path = format!("{}/{}{}{}", directory.get_directory_path_str(), ORIGINAL_FILE_PREFIX, hash, ORIGINAL_FILE_SUFFIX);
|
||||
Self {
|
||||
directory,
|
||||
basename,
|
||||
full_object_path,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_full_object_path_str(&self) -> &str {
|
||||
&self.full_object_path
|
||||
}
|
||||
|
||||
pub fn to_full_object_pathbuf(&self) -> PathBuf {
|
||||
PathBuf::from(&self.full_object_path)
|
||||
}
|
||||
|
||||
pub fn get_directory(&self) -> &MediaUploadDirectory {
|
||||
&self.directory
|
||||
}
|
||||
|
||||
pub fn get_object_hash(&self) -> &str {
|
||||
&self.directory.get_object_hash()
|
||||
}
|
||||
|
||||
pub fn get_basename(&self) -> &str {
|
||||
&self.basename
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use crate::public::voice_conversion_results::original_file::VoiceConversionResultOriginalFilePath;
|
||||
use std::path::PathBuf;
|
||||
|
||||
#[test]
|
||||
pub fn generate_new_entropy() {
|
||||
let file = VoiceConversionResultOriginalFilePath::generate_new();
|
||||
assert_eq!(file.get_object_hash().len(), 32);
|
||||
assert_eq!(file.get_directory().get_object_hash().len(), 32);
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn get_full_object_path_str() {
|
||||
let file = VoiceConversionResultOriginalFilePath::from_object_hash("abcdefghijk");
|
||||
assert_eq!(file.get_full_object_path_str(), "/media_upload/a/b/c/d/e/abcdefghijk/fakeyou_abcdefghijk.wav");
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn to_full_object_pathbuf() {
|
||||
let file = VoiceConversionResultOriginalFilePath::from_object_hash("abcdefghijk");
|
||||
assert_eq!(file.to_full_object_pathbuf(), PathBuf::from("/media_upload/a/b/c/d/e/abcdefghijk/fakeyou_abcdefghijk.wav"));
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn get_full_object_path_str_short_name() {
|
||||
let file = VoiceConversionResultOriginalFilePath::from_object_hash("foo");
|
||||
assert_eq!(file.get_full_object_path_str(), "/media_upload/f/o/foo/fakeyou_foo.wav");
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn get_full_object_path_str_starts_with_directory() {
|
||||
let file = VoiceConversionResultOriginalFilePath::from_object_hash("abcdefghijk");
|
||||
let full_path = file.get_full_object_path_str();
|
||||
assert!(full_path.starts_with(file.get_directory().get_directory_path_str()))
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn get_object_hash() {
|
||||
let hash = "abcdefghijk";
|
||||
let file = VoiceConversionResultOriginalFilePath::from_object_hash(hash);
|
||||
assert_eq!(file.get_object_hash(), hash);
|
||||
}
|
||||
}
|
||||
@@ -24,6 +24,7 @@ use std::path::{Path, PathBuf};
|
||||
use subprocess_common::docker_options::{DockerFilesystemMount, DockerGpu, DockerOptions};
|
||||
use tempdir::TempDir;
|
||||
use buckets::public::media_uploads::original_file::MediaUploadOriginalFilePath;
|
||||
use buckets::public::voice_conversion_results::original_file::VoiceConversionResultOriginalFilePath;
|
||||
use mysql_queries::queries::media_uploads::get_media_upload_for_inference::get_media_upload_for_inference;
|
||||
use tokens::files::media_upload::MediaUploadToken;
|
||||
use tts_common::clean_symbols::clean_symbols;
|
||||
@@ -192,15 +193,16 @@ pub async fn process_job(args: SoVitsSvcProcessJobArgs<'_>) -> Result<JobSuccess
|
||||
job_progress_reporter.log_status("uploading result")
|
||||
.map_err(|e| ProcessSingleJobError::Other(e))?;
|
||||
|
||||
let audio_result_object_path = args.job_dependencies.bucket_path_unifier.voice_conversion_inference_wav_audio_output_path(
|
||||
&job.uuid_idempotency_token); // TODO: Don't use this!
|
||||
let result_bucket_location = VoiceConversionResultOriginalFilePath::generate_new();
|
||||
|
||||
info!("Audio destination bucket path: {:?}", &audio_result_object_path);
|
||||
let result_bucket_object_pathbuf = result_bucket_location.to_full_object_pathbuf();
|
||||
|
||||
info!("Audio destination bucket path: {:?}", &result_bucket_object_pathbuf);
|
||||
|
||||
info!("Uploading audio...");
|
||||
|
||||
args.job_dependencies.public_bucket_client.upload_filename_with_content_type(
|
||||
&audio_result_object_path,
|
||||
&result_bucket_object_pathbuf,
|
||||
&output_audio_fs_path,
|
||||
"audio/wav")
|
||||
.await
|
||||
@@ -235,7 +237,7 @@ pub async fn process_job(args: SoVitsSvcProcessJobArgs<'_>) -> Result<JobSuccess
|
||||
|
||||
let worker_name = args.job_dependencies.get_worker_name();
|
||||
|
||||
info!("Saving tts inference record...");
|
||||
info!("Saving vc inference record...");
|
||||
|
||||
// NB: The stupid DB field for spectrograms is not nullable, so we'll just set empty string.
|
||||
let fake_spectrogram_path = PathBuf::from("");
|
||||
|
||||
Reference in new issue
Block a user