From cd366dfdfad18b38c4e542e6db61ced3929d42f9 Mon Sep 17 00:00:00 2001 From: metamuffin Date: Sun, 6 Aug 2023 11:49:09 +0200 Subject: quick setup command --- import/Cargo.toml | 2 ++ import/src/main.rs | 79 ++++++++++++++++++++++++++++++++++++++++++++++++++++-- 2 files changed, 79 insertions(+), 2 deletions(-) (limited to 'import') diff --git a/import/Cargo.toml b/import/Cargo.toml index 4e351c6..2e35e18 100644 --- a/import/Cargo.toml +++ b/import/Cargo.toml @@ -17,3 +17,5 @@ reqwest = { version = "0.11.18", features = ["blocking", "json"] } serde = { version = "1.0.180", features = ["derive"] } serde_json = "1.0.104" bincode = { version = "2.0.0-rc.3", features = ["serde"] } +base64 = "0.21.2" +rand = "0.8.5" diff --git a/import/src/main.rs b/import/src/main.rs index 2d66221..26899bb 100644 --- a/import/src/main.rs +++ b/import/src/main.rs @@ -3,19 +3,23 @@ which is licensed under the GNU Affero General Public License (version 3); see /COPYING. Copyright (C) 2023 metamuffin */ +#![feature(file_create_new)] + pub mod infojson; pub mod tmdb; use anyhow::Context; +use base64::Engine; use clap::{Parser, Subcommand}; use infojson::YVideo; use jellycommon::{ - AssetLocation, LocalTrack, MediaInfo, MediaSource, Node, NodeKind, NodePrivate, NodePublic, - Rating, + config::GlobalConfig, AssetLocation, LocalTrack, MediaInfo, MediaSource, Node, NodeKind, + NodePrivate, NodePublic, Rating, }; use jellymatroska::read::EbmlReader; use jellyremuxer::import::{import_metadata, seek_index}; use log::{info, warn}; +use rand::random; use std::{ fs::{remove_file, File}, io::{stdin, Write}, @@ -34,22 +38,39 @@ struct Args { #[derive(Subcommand)] enum Action { + /// Initialize a new jellything instance + Init { + /// Base path of the instance, must either be absolute or relative to the servers pwd + base_path: PathBuf, + #[arg(short, long)] + brand: String, + }, + /// Imports a movie, video or series given media and metadata sources New { + /// Relative path to the node's parent(!). path: PathBuf, + /// Search the node by title on TMDB #[arg(short = 't', long)] tmdb_search: Option, + /// Search the node by id on TMDB #[arg(short = 'T', long)] tmdb_id: Option, #[arg(long)] + /// Prefix the inferred id with something to avoid collisions ident_prefix: Option, + /// Copies media into the library #[arg(long)] copy: bool, + /// Moves media into the library (potentially destructive operation) #[arg(long)] r#move: bool, + /// Marks node as a video #[arg(long)] video: bool, + /// Path to the media of the node, required for non-series #[arg(short, long)] input: Option, + /// Marks node as a series #[arg(short, long)] series: bool, }, @@ -63,6 +84,56 @@ fn main() -> anyhow::Result<()> { let args = Args::parse(); match args.action { + Action::Init { + base_path: path, + brand, + } => { + info!("creating new instance..."); + std::fs::create_dir_all(path.join("library"))?; + std::fs::create_dir_all(path.join("cache"))?; + std::fs::create_dir_all(path.join("assets"))?; + File::create_new(path.join("assets/front.htm"))? + .write_fmt(format_args!("

My very own jellything instance

"))?; + serde_json::to_writer( + File::create_new(path.join("config.json"))?, + &GlobalConfig { + brand: brand.clone(), + slogan: "Creative slogan here".to_string(), + asset_path: path.join("assets"), + cache_path: path.join("cache"), + library_path: path.join("library"), + database_path: path.join("database"), + cookie_key: Some( + base64::engine::general_purpose::STANDARD + .encode([(); 32].map(|_| random())), + ), + session_key: Some( + base64::engine::general_purpose::STANDARD + .encode([(); 32].map(|_| random())), + ), + admin_username: "admin".to_string(), + admin_password: "hackme".to_string(), + login_expire: 10, + ..Default::default() + }, + )?; + serde_json::to_writer( + File::create_new(path.join("library/directory.json"))?, + &Node { + public: NodePublic { + kind: NodeKind::Collection, + title: "My Library".to_string(), + ..Default::default() + }, + private: NodePrivate { + ..Default::default() + }, + }, + )?; + info!("{brand:?} is ready!"); + warn!("please change the admin password."); + Ok(()) + } Action::New { path, tmdb_id, @@ -74,6 +145,10 @@ fn main() -> anyhow::Result<()> { video, r#move, } => { + if std::env::current_dir().unwrap().file_name().unwrap() != "library" { + warn!("new command can only be used in the library directory; what you are doing right now probably wont work.") + } + let tmdb_kind = if series { "tv" } else { "movie" }; let tmdb_id = if let Some(id) = tmdb_id { Some(id.parse().unwrap()) -- cgit v1.2.3-70-g09d2