diff options
Diffstat (limited to 'tools/src/bin')
| -rw-r--r-- | tools/src/bin/import.rs | 322 | 
1 files changed, 0 insertions, 322 deletions
| diff --git a/tools/src/bin/import.rs b/tools/src/bin/import.rs deleted file mode 100644 index eada6ad..0000000 --- a/tools/src/bin/import.rs +++ /dev/null @@ -1,322 +0,0 @@ -/* -    This file is part of jellything (https://codeberg.org/metamuffin/jellything) -    which is licensed under the GNU Affero General Public License (version 3); see /COPYING. -    Copyright (C) 2023 metamuffin <metamuffin.org> -*/ -use anyhow::Context; -use clap::{Parser, Subcommand}; -use jellycommon::{AssetLocation, MediaInfo, MediaSource, Node, NodeKind, NodePrivate, NodePublic}; -use jellymatroska::read::EbmlReader; -use jellyremuxer::import::{import_metadata, seek_index::import_seek_index}; -use jellytools::tmdb::{tmdb_details, tmdb_image, tmdb_search}; -use log::info; -use std::{ -    collections::BTreeMap, -    fs::{remove_file, File}, -    io::stdin, -    path::PathBuf, -    process::exit, -}; - -#[derive(Parser)] -struct Args { -    #[arg(short = 'N', long)] -    dry: bool, -    #[clap(subcommand)] -    action: Action, -} - -#[derive(Subcommand)] -enum Action { -    Create { -        path: PathBuf, -        #[arg(short = 't', long)] -        tmdb_search: Option<String>, -        #[arg(short = 'T', long)] -        tmdb_id: Option<String>, -        #[arg(long)] -        copy: bool, -        #[arg(long)] -        r#move: bool, -        #[arg(short, long)] -        input: Option<PathBuf>, -        #[arg(short, long)] -        series: bool, -    }, -    Set { -        #[arg(short = 'I', long)] -        item: PathBuf, -        #[arg(short, long)] -        poster: Option<PathBuf>, -        #[arg(short, long)] -        title: Option<String>, -        #[arg(short = 'D', long)] -        tagline: Option<String>, -        #[arg(short = 'd', long)] -        description: Option<String>, -        #[arg(short = 'c', long)] -        clear_inputs: bool, -        #[arg(short = 'i', long, num_args(0..))] -        input: Vec<PathBuf>, -    }, -} - -fn main() -> anyhow::Result<()> { -    env_logger::builder() -        .filter_level(log::LevelFilter::Info) -        .parse_env("LOG") -        .init(); -    let args = Args::parse(); - -    match args.action { -        Action::Create { -            path, -            tmdb_id, -            tmdb_search, -            input, -            series, -            copy, -            r#move, -        } => { -            let tmdb_kind = if series { "tv" } else { "movie" }; -            let tmdb_key = std::env::var("TMDB_API_KEY").context("tmdb api key required")?; -            let tmdb_id = if let Some(id) = tmdb_id { -                Some(id.parse().unwrap()) -            } else { -                let title = tmdb_search.as_ref().unwrap(); -                let results = crate::tmdb_search(tmdb_kind, title, &tmdb_key)?; -                info!("results:"); -                for (i, r) in results.results.iter().enumerate() { -                    info!( -                        "\t[{i}] {}: {} ({})", -                        r.id, -                        r.title.as_ref().or(r.name.as_ref()).unwrap(), -                        r.overview.chars().take(100).collect::<String>() -                    ); -                } -                let res_index = if results.results.len() > 1 { -                    stdin() -                        .lines() -                        .next() -                        .unwrap() -                        .unwrap() -                        .parse::<usize>() -                        .unwrap() -                } else { -                    0 -                }; -                Some(results.results[res_index].id) -            }; - -            let tmdb_details = tmdb_id.map(|id| { -                let td = tmdb_details(tmdb_kind, id, &tmdb_key) -                    .context("fetching details") -                    .unwrap(); -                if td.title.is_some() { -                    info!("is this correct? [y/n]"); -                    if stdin().lines().next().unwrap().unwrap() != "y" { -                        exit(0) -                    } -                } -                td -            }); - -            let title = tmdb_details -                .as_ref() -                .map(|d| d.title.clone().or(d.name.clone())) -                .flatten() -                .unwrap(); -            let ident = make_ident(&title); -            let path = path.join(&ident); - -            let poster = tmdb_details -                .as_ref() -                .map(|d| { -                    d.poster_path -                        .as_ref() -                        .map(|p| { -                            let pu = path.join("poster.jpeg"); -                            let mut f = File::create(&pu)?; -                            tmdb_image(&p, &mut f)?; -                            Ok::<_, anyhow::Error>(pu) -                        }) -                        .transpose() -                }) -                .transpose()? -                .flatten(); - -            let backdrop = tmdb_details -                .as_ref() -                .map(|d| { -                    d.backdrop_path -                        .as_ref() -                        .map(|p| { -                            let pu = path.join("backdrop.jpeg"); -                            let mut f = File::create(&pu)?; -                            tmdb_image(&p, &mut f)?; -                            Ok::<_, anyhow::Error>(pu) -                        }) -                        .transpose() -                }) -                .transpose()? -                .flatten(); - -            let kind; -            let media; -            let source; -            let mut seek_index = BTreeMap::new(); -            let mut source_path_e = None; - -            if let Some(input) = input { -                let source_path = path.join(format!("source.mkv")); -                if r#move { -                    std::fs::rename(&input, &source_path)?; -                } else if copy { -                    std::fs::copy(&input, &source_path)?; -                } else { -                    if source_path.is_symlink() { -                        remove_file(&source_path)?; -                    } -                    std::os::unix::fs::symlink(&input, &source_path)?; -                } - -                let (tracks, local_tracks, duration) = { -                    let input = File::open(&source_path).unwrap(); -                    let mut input = EbmlReader::new(input); -                    import_metadata(&source_path.to_path_buf(), &mut input)? -                }; -                seek_index = { -                    let input = File::open(&source_path).unwrap(); -                    let mut input = EbmlReader::new(input); -                    import_seek_index(&mut input)? -                }; - -                kind = NodeKind::Movie; -                media = Some(MediaInfo { duration, tracks }); -                source = Some(MediaSource::Local { -                    tracks: local_tracks, -                }); -                source_path_e = Some(source_path) -            } else { -                kind = NodeKind::Series; -                media = None; -                source = None; -            }; - -            let node = Node { -                private: NodePrivate { -                    import: None, -                    backdrop: backdrop.clone().map(AssetLocation::Library), -                    poster: poster.clone().map(AssetLocation::Library), -                    source, -                }, -                public: NodePublic { -                    parent: None, -                    federated: None, -                    description: tmdb_details.as_ref().map(|d| d.overview.to_owned()), -                    tagline: tmdb_details -                        .as_ref() -                        .map(|d| d.tagline.to_owned()) -                        .flatten(), -                    title, -                    index: None, -                    kind, -                    children: Vec::new(), -                    media, -                }, -            }; - -            if args.dry { -                println!("{node:?}") -            } else { -                std::fs::create_dir_all(&path)?; -                for (tn, index) in seek_index { -                    info!("writing index {tn} with {} blocks", index.blocks.len()); -                    bincode::encode_into_std_write( -                        index, -                        &mut File::create( -                            source_path_e -                                .as_ref() -                                .unwrap() -                                .with_extension(&format!("si.{tn}")), -                        )?, -                        bincode::config::standard(), -                    )?; -                } -                let f = File::create(path.join(if series { -                    "directory.json".to_string() -                } else { -                    format!("{ident}.jelly") -                }))?; -                serde_json::to_writer_pretty(f, &node)?; -            } - -            Ok(()) -        } -        Action::Set { .. } => { -            // let mut iteminfo: ItemInfo = match File::open(item.clone()) { -            //     Ok(f) => serde_json::from_reader(f)?, -            //     Err(e) => { -            //         warn!("could not load item info: {e}"); -            //         warn!("using the default instead"); -            //         ItemInfo { -            //             common: CommmonInfo { -            //                 poster: None, -            //                 backdrop: None, -            //                 tagline: None, -            //                 description: None, -            //                 title: item.to_str().unwrap().to_string(), -            //                 index: None, -            //             }, -            //             duration: 0.0, -            //             tracks: Default::default(), -            //         } -            //     } -            // }; - -            // if let Some(title) = title { -            //     iteminfo.title = title; -            // } -            // if let Some(poster) = poster { -            //     iteminfo.poster = Some(poster); -            // } -            // if let Some(d) = description { -            //     iteminfo.description = Some(d); -            // } -            // if let Some(d) = tagline { -            //     iteminfo.tagline = Some(d); -            // } -            // if clear_inputs { -            //     iteminfo.tracks = Default::default() -            // } - -            // // for input_path in input { -            // //     let input = File::open(input_path.clone()).unwrap(); -            // //     let mut input = EbmlReader::new(input); -            // //     import_read(&input_path, &mut input, &mut iteminfo)?; -            // // } - -            // let k = serde_json::to_string_pretty(&iteminfo)?; -            // if args.dry { -            //     println!("{k}") -            // } else { -            //     let mut f = File::create(item)?; -            //     f.write_all(k.as_bytes())?; -            // } -            Ok(()) -        } -    } -} - -fn make_ident(s: &str) -> String { -    let mut out = String::new(); -    for s in s.chars() { -        match s { -            'a'..='z' => out.push(s), -            'A'..='Z' => out.push(s.to_ascii_lowercase()), -            '-' | ' ' | '_' => out.push('-'), -            _ => (), -        } -    } -    out -} | 
