aboutsummaryrefslogtreecommitdiff
path: root/tools
diff options
context:
space:
mode:
Diffstat (limited to 'tools')
-rw-r--r--tools/src/bin/import.rs106
-rw-r--r--tools/src/tmdb.rs32
2 files changed, 101 insertions, 37 deletions
diff --git a/tools/src/bin/import.rs b/tools/src/bin/import.rs
index c771450..3050f71 100644
--- a/tools/src/bin/import.rs
+++ b/tools/src/bin/import.rs
@@ -5,7 +5,7 @@ Copyright (C) 2023 metamuffin <metamuffin.org>
*/
use anyhow::Context;
use clap::{Parser, Subcommand};
-use jellycommon::{CommmonInfo, ItemInfo};
+use jellycommon::{CommmonInfo, DirectoryInfo, ItemInfo};
use jellymatroska::read::EbmlReader;
use jellyremuxer::import::import_read;
use jellytools::tmdb::{tmdb_details, tmdb_image, tmdb_search};
@@ -13,7 +13,7 @@ use log::{info, warn};
use std::{
fs::File,
io::{stdin, Write},
- path::PathBuf,
+ path::{Path, PathBuf},
process::exit,
};
@@ -32,7 +32,15 @@ enum Action {
title: Option<String>,
#[arg(short = 'T', long)]
tmdb: Option<String>,
- #[arg(short = 'i', long)]
+ #[arg(short, long)]
+ input: Option<PathBuf>,
+ #[arg(short, long)]
+ series: bool,
+ },
+ Episode {
+ path: PathBuf,
+ index: usize,
+ title: String,
input: PathBuf,
},
Set {
@@ -66,23 +74,26 @@ fn main() -> anyhow::Result<()> {
title,
tmdb: id,
input,
+ series,
} => {
+ assert!(series || input.is_some(), "series or input required");
+ let kind = if series { "tv" } else { "movie" };
let key = std::env::var("TMDB_API_KEY").context("tmdb api key required")?;
let id = if let Some(id) = id {
id.parse().unwrap()
} else {
let title = title.unwrap();
- let results = tmdb_search(&title, &key)?;
+ let results = tmdb_search(kind, &title, &key)?;
info!("results:");
for (i, r) in results.results.iter().enumerate() {
info!(
"\t[{i}] {}: {} ({})",
r.id,
- r.title,
+ 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 {
+ let res_index = if results.results.len() > 1 {
stdin()
.lines()
.next()
@@ -96,8 +107,8 @@ fn main() -> anyhow::Result<()> {
results.results[res_index].id
};
- let details = tmdb_details(id, &key).context("fetching details")?;
- let ident = make_ident(&details.title);
+ let details = tmdb_details(kind, id, &key).context("fetching details")?;
+ let ident = make_ident(details.title.as_ref().or(details.name.as_ref()).unwrap());
let path = path.join(&ident);
std::fs::create_dir_all(&path)?;
@@ -125,36 +136,82 @@ fn main() -> anyhow::Result<()> {
backdrop,
description: Some(details.overview),
tagline: details.tagline,
- title: details.title,
+ title: details.title.clone().or(details.name.clone()).unwrap(),
+ index: None,
};
- let mut iteminfo = ItemInfo {
- common,
- duration: Default::default(),
- tracks: Default::default(),
- };
- info!("{iteminfo:#?}");
info!("is this correct? [y/n]");
if stdin().lines().next().unwrap().unwrap() != "y" {
exit(0)
}
+ let k = if let Some(input) = input {
+ let mut iteminfo = ItemInfo {
+ common,
+ duration: Default::default(),
+ tracks: Default::default(),
+ };
+ info!("{iteminfo:#?}");
+ let source_path = path.join(format!("source.mkv"));
+ // std::fs::rename(&input, &source_path)?;
+ // std::os::unix::fs::symlink(&input, &source_path)?;
+ std::fs::copy(&input, &source_path)?;
+ import_source(&mut iteminfo, &source_path)?;
+ serde_json::to_string_pretty(&iteminfo)?
+ } else {
+ serde_json::to_string_pretty(&DirectoryInfo {
+ common,
+ kind: jellycommon::DirectoryKind::Series,
+ })?
+ };
+
+ if args.dry {
+ println!("{k}")
+ } else {
+ let mut f = File::create(path.join(if series {
+ "directory.json".to_string()
+ } else {
+ format!("{ident}.jelly",)
+ }))?;
+ f.write_all(k.as_bytes())?;
+ }
+
+ Ok(())
+ }
+ Action::Episode {
+ path,
+ index,
+ title,
+ input,
+ } => {
+ let ident = make_ident(&title);
+ let common = CommmonInfo {
+ poster: None,
+ backdrop: None,
+ description: None,
+ tagline: None,
+ title,
+ index: Some(index),
+ };
+ let mut iteminfo = ItemInfo {
+ common,
+ duration: Default::default(),
+ tracks: Default::default(),
+ };
+ let path = path.join(&ident);
+ std::fs::create_dir_all(&path)?;
let source_path = path.join(format!("source.mkv"));
// std::fs::rename(&input, &source_path)?;
// std::os::unix::fs::symlink(&input, &source_path)?;
std::fs::copy(&input, &source_path)?;
- let input = File::open(&source_path).unwrap();
- let mut input = EbmlReader::new(input);
- import_read(&source_path, &mut input, &mut iteminfo)?;
-
+ import_source(&mut iteminfo, &source_path)?;
let k = serde_json::to_string_pretty(&iteminfo)?;
if args.dry {
println!("{k}")
} else {
- let mut f = File::create(path.join(format!("{ident}.jelly")))?;
+ let mut f = File::create(path.join(format!("{ident}.jelly",)))?;
f.write_all(k.as_bytes())?;
}
-
Ok(())
}
Action::Set {
@@ -178,6 +235,7 @@ fn main() -> anyhow::Result<()> {
tagline: None,
description: None,
title: item.to_str().unwrap().to_string(),
+ index: None,
},
duration: 0.0,
tracks: Default::default(),
@@ -231,3 +289,9 @@ fn make_ident(s: &str) -> String {
}
out
}
+fn import_source(iteminfo: &mut ItemInfo, source_path: &Path) -> anyhow::Result<()> {
+ let input = File::open(&source_path).unwrap();
+ let mut input = EbmlReader::new(input);
+ import_read(&source_path.to_path_buf(), &mut input, iteminfo)?;
+ Ok(())
+}
diff --git a/tools/src/tmdb.rs b/tools/src/tmdb.rs
index 6f8c341..5f21afd 100644
--- a/tools/src/tmdb.rs
+++ b/tools/src/tmdb.rs
@@ -21,14 +21,14 @@ pub struct TmdbQueryResult {
pub backdrop_path: Option<String>,
pub genre_ids: Vec<u64>,
pub id: u64,
- pub original_language: String,
- pub original_title: String,
+ pub original_language: Option<String>,
+ pub original_title: Option<String>,
pub overview: String,
pub popularity: f64,
pub poster_path: Option<String>,
- pub release_date: String,
- pub title: String,
- pub video: bool,
+ pub release_date: Option<String>,
+ pub title: Option<String>,
+ pub name: Option<String>,
pub vote_average: f64,
pub vote_count: usize,
}
@@ -39,21 +39,21 @@ pub struct TmdbDetails {
pub backdrop_path: Option<String>,
pub genres: Vec<TmdbGenre>,
pub id: u64,
- pub original_language: String,
- pub original_title: String,
+ pub original_language: Option<String>,
+ pub original_title: Option<String>,
pub overview: String,
pub popularity: f64,
pub poster_path: Option<String>,
- pub release_date: String,
- pub title: String,
- pub video: bool,
+ pub release_date: Option<String>,
+ pub title: Option<String>,
+ pub name: Option<String>,
pub vote_average: f64,
pub vote_count: usize,
- pub budget: usize,
+ pub budget: Option<usize>,
pub homepage: Option<String>,
pub imdb_id: Option<String>,
pub production_companies: Vec<TmdbProductionCompany>,
- pub revenue: usize,
+ pub revenue: Option<usize>,
pub tagline: Option<String>,
}
@@ -70,19 +70,19 @@ pub struct TmdbProductionCompany {
pub logo_path: Option<String>,
}
-pub fn tmdb_search(query: &str, key: &str) -> anyhow::Result<TmdbQuery> {
+pub fn tmdb_search(kind: &str, query: &str, key: &str) -> anyhow::Result<TmdbQuery> {
info!("searching tmdb: {query:?}");
Ok(reqwest::blocking::get(&format!(
- "https://api.themoviedb.org/3/search/movie?query={}&api_key={key}",
+ "https://api.themoviedb.org/3/search/{kind}?query={}&api_key={key}",
query.replace(" ", "+")
))?
.json::<TmdbQuery>()?)
}
-pub fn tmdb_details(id: u64, key: &str) -> anyhow::Result<TmdbDetails> {
+pub fn tmdb_details(kind: &str, id: u64, key: &str) -> anyhow::Result<TmdbDetails> {
info!("fetching details: {id:?}");
Ok(reqwest::blocking::get(&format!(
- "https://api.themoviedb.org/3/movie/{id}?api_key={key}"
+ "https://api.themoviedb.org/3/{kind}/{id}?api_key={key}"
))?
.json()?)
}