From 06f933dac333d58b2cc3ae7ab0c285e5015a0257 Mon Sep 17 00:00:00 2001 From: fxqnlr Date: Sun, 30 Apr 2023 19:20:29 +0200 Subject: fixed config directories, moved to own folder --- src/config.rs | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/src/config.rs b/src/config.rs index 61db1c7..9064548 100644 --- a/src/config.rs +++ b/src/config.rs @@ -26,7 +26,8 @@ impl Cfg { Some(p) => String::from(p), None => dirs::config_dir() .unwrap() - .join("modlist.toml") + .join("modlist") + .join("config.toml") .to_string_lossy() .to_string(), }; @@ -50,7 +51,6 @@ impl Cfg { create_cache(&config.cache)?; }; //Check database - //TODO check file let datafile = format!("{}/data.db", config.data); match File::open(&datafile) { Ok(..) => (), @@ -64,14 +64,19 @@ fn create_config(path: &str) -> MLE<()> { print!("No config file found, create default"); //Force flush of stdout, else print! doesn't print instantly std::io::stdout().flush()?; + let cache_dir = dirs::cache_dir() + .unwrap() + .join("modlist") + .to_string_lossy() + .to_string(); let default_cfg = Cfg { - //TODO get home dir - data: String::from("$HOME/.cache/modlist/"), - cache: String::from("$HOME/.cache/modlist/cache"), + data: cache_dir.clone(), + cache: format!("{}/cache", cache_dir), apis: Apis { modrinth: String::from("https://api.modrinth.com/v2/"), }, }; + create_dir_all(path.split("config.toml").collect::>()[0])?; let mut file = File::create(path)?; file.write_all(toml::to_string(&default_cfg)?.as_bytes())?; println!(" ✓"); -- cgit v1.2.3 From e8cac6786bc2e91382316ef1023a494c3e812013 Mon Sep 17 00:00:00 2001 From: fxqnlr Date: Sun, 30 Apr 2023 20:11:10 +0200 Subject: added modloader default to config --- src/config.rs | 11 ++++++++++- src/lib.rs | 41 +++++++++++++++++++++++++++++++++++++++++ src/main.rs | 3 +-- 3 files changed, 52 insertions(+), 3 deletions(-) diff --git a/src/config.rs b/src/config.rs index 9064548..cf27257 100644 --- a/src/config.rs +++ b/src/config.rs @@ -6,12 +6,13 @@ use std::{ use serde::{Deserialize, Serialize}; -use crate::{db::db_setup, error::MLE}; +use crate::{db::db_setup, error::MLE, Modloader}; #[derive(Debug, Clone, Serialize, Deserialize)] pub struct Cfg { pub data: String, pub cache: String, + pub defaults: Defaults, pub apis: Apis, } @@ -20,6 +21,11 @@ pub struct Apis { pub modrinth: String, } +#[derive(Debug, Clone, Serialize, Deserialize)] +pub struct Defaults { + pub modloader: Modloader, +} + impl Cfg { pub fn init(path: Option) -> MLE { let configfile = match path.clone() { @@ -72,6 +78,9 @@ fn create_config(path: &str) -> MLE<()> { let default_cfg = Cfg { data: cache_dir.clone(), cache: format!("{}/cache", cache_dir), + defaults: Defaults { + modloader: Modloader::Fabric + }, apis: Apis { modrinth: String::from("https://api.modrinth.com/v2/"), }, diff --git a/src/lib.rs b/src/lib.rs index 185edd7..05d74db 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -11,6 +11,7 @@ use std::fmt::Display; pub use apis::*; pub use commands::*; use error::{ErrorType, MLError, MLE}; +use serde::{Deserialize, Serialize, de::Visitor}; #[derive(Debug, Clone, PartialEq, Eq)] pub enum Modloader { @@ -36,3 +37,43 @@ impl Display for Modloader { } } } + +impl Serialize for Modloader { + fn serialize(&self, serializer: S) -> Result + where + S: serde::Serializer { + match self { + Modloader::Fabric => serializer.serialize_str("fabric"), + Modloader::Forge => serializer.serialize_str("forge"), + } + } +} + +impl<'de> Deserialize<'de> for Modloader { + fn deserialize(deserializer: D) -> Result + where + D: serde::Deserializer<'de>, + { + struct FieldVisitor; + + impl<'de> Visitor<'de> for FieldVisitor { + type Value = Modloader; + + fn expecting(&self, formatter: &mut std::fmt::Formatter) -> std::fmt::Result { + formatter.write_str("`fabric`, `forge` or `quilt`") + } + + fn visit_str(self, v: &str) -> Result + where + E: serde::de::Error, { + match v { + "fabric" => Ok(Modloader::Fabric), + "forge" => Ok(Modloader::Forge), + _ => Err(serde::de::Error::unknown_field(v, &["fabric", "forge", "quilt"])) + } + } + } + + deserializer.deserialize_identifier(FieldVisitor) + } +} diff --git a/src/main.rs b/src/main.rs index 53cbe71..82c0ade 100644 --- a/src/main.rs +++ b/src/main.rs @@ -201,8 +201,7 @@ async fn main() { } => { let ml = match modloader { Some(ml) => Modloader::from(&ml).unwrap(), - //TODO add default modloader to config - None => Modloader::Fabric, + None => config.clone().defaults.modloader, }; let ver = match version { -- cgit v1.2.3 From 202ed4fcaa69e7de23e83fab0bae4ced6209eee4 Mon Sep 17 00:00:00 2001 From: fxqnlr Date: Tue, 2 May 2023 20:37:23 +0200 Subject: added config option for default mc version changed version input system --- Cargo.lock | 2 +- Cargo.toml | 2 +- src/apis/modrinth.rs | 66 ++++++++++++------------------ src/commands/io.rs | 2 +- src/config.rs | 29 ++++++++++++-- src/error.rs | 9 +++++ src/lib.rs | 111 ++++++++++++++++++++++++++++++++++++++++++++++++++- src/main.rs | 18 ++++++--- 8 files changed, 186 insertions(+), 53 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index f25b161..0e93641 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -798,7 +798,7 @@ dependencies = [ [[package]] name = "modlist" -version = "0.13.1" +version = "0.14.0" dependencies = [ "chrono", "clap", diff --git a/Cargo.toml b/Cargo.toml index 7b6466f..736831d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "modlist" -version = "0.13.1" +version = "0.14.0" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/src/apis/modrinth.rs b/src/apis/modrinth.rs index 9afe7f3..13e7a6d 100644 --- a/src/apis/modrinth.rs +++ b/src/apis/modrinth.rs @@ -1,6 +1,6 @@ use chrono::{DateTime, FixedOffset}; use reqwest::Client; -use serde::Deserialize; +use serde::{Deserialize, Serialize}; use crate::{ error::{ErrorType, MLError, MLE}, @@ -113,7 +113,24 @@ pub struct Hash { pub sha1: String, } -async fn get(api: &str, path: String) -> Result>, Box> { +#[derive(Debug, Clone, Serialize, Deserialize)] +pub struct GameVersion { + pub version: String, + pub version_type: GameVersionType, + pub date: String, + pub major: bool, +} + +#[allow(non_camel_case_types)] +#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)] +pub enum GameVersionType { + release, + snapshot, + alpha, + beta +} + +async fn get(api: &str, path: &str) -> Result>, Box> { let url = format!(r#"{}{}"#, api, path); let client = Client::builder() @@ -135,7 +152,7 @@ async fn get(api: &str, path: String) -> Result>, Box Project { let url = format!("project/{}", name); - let data = get(api, url).await.unwrap().unwrap(); + let data = get(api, &url).await.unwrap().unwrap(); serde_json::from_slice(&data).unwrap() } @@ -144,7 +161,7 @@ pub async fn projects(api: &str, ids: Vec) -> Vec { let all = ids.join(r#"",""#); let url = format!(r#"projects?ids=["{}"]"#, all); - let data = get(api, url).await.unwrap().unwrap(); + let data = get(api, &url).await.unwrap().unwrap(); serde_json::from_slice(&data).unwrap() } @@ -161,7 +178,7 @@ pub async fn versions(api: &str, id: String, list: List) -> Vec { id, loaderstr, list.mc_version ); - let data = get(api, url).await.unwrap(); + let data = get(api, &url).await.unwrap(); match data { Some(data) => serde_json::from_slice(&data).unwrap(), @@ -173,7 +190,7 @@ pub async fn versions(api: &str, id: String, list: List) -> Vec { pub async fn get_raw_versions(api: &str, versions: Vec) -> Vec { let url = format!(r#"versions?ids=["{}"]"#, versions.join(r#"",""#)); - let data = get(api, url).await.unwrap().unwrap(); + let data = get(api, &url).await.unwrap().unwrap(); serde_json::from_slice(&data).unwrap() } @@ -195,39 +212,8 @@ pub fn extract_current_version(versions: Vec) -> MLE { } } -pub enum MCVersionType { - Release, - Latest, - Specific, -} +pub async fn get_game_versions() -> Vec { + let data = get("https://api.modrinth.com/v2/", "tag/game_version").await.unwrap().unwrap(); -#[derive(Debug, Deserialize)] -pub struct MCVersion { - pub version: String, - pub version_type: String, - pub date: String, - pub major: bool, -} - -pub async fn get_minecraft_version(api: &str, version: MCVersionType) -> String { - let data = get(api, String::from("tag/game_version")) - .await - .unwrap() - .unwrap(); - let mc_versions: Vec = serde_json::from_slice(&data).unwrap(); - let ver = match version { - MCVersionType::Release => { - let mut i = 0; - while !mc_versions[i].major { - i += 1; - } - &mc_versions[i] - } - MCVersionType::Latest => &mc_versions[0], - MCVersionType::Specific => { - println!("Not inplemented"); - &mc_versions[0] - } - }; - String::from(&ver.version) + serde_json::from_slice(&data).unwrap() } diff --git a/src/commands/io.rs b/src/commands/io.rs index 82b30ce..e072f00 100644 --- a/src/commands/io.rs +++ b/src/commands/io.rs @@ -92,7 +92,7 @@ pub async fn import(config: Cfg, file_str: String, direct_download: bool) -> MLE mod_ids.push(IDSelector::ModificationID(String::from(mod_id))); } //TODO impl set_version and good direct download - //TODO impl all at once, dafuck + //TODO impl all at once, dafuck ?done? mod_add(config.clone(), mod_ids, list, direct_download, false).await?; } Ok(()) diff --git a/src/config.rs b/src/config.rs index cf27257..e1049d1 100644 --- a/src/config.rs +++ b/src/config.rs @@ -6,12 +6,13 @@ use std::{ use serde::{Deserialize, Serialize}; -use crate::{db::db_setup, error::MLE, Modloader}; +use crate::{db::db_setup, error::MLE, Modloader, VersionLevel, check_game_versions}; #[derive(Debug, Clone, Serialize, Deserialize)] pub struct Cfg { pub data: String, pub cache: String, + pub versions: String, pub defaults: Defaults, pub apis: Apis, } @@ -24,10 +25,11 @@ pub struct Apis { #[derive(Debug, Clone, Serialize, Deserialize)] pub struct Defaults { pub modloader: Modloader, + pub version: VersionLevel, } impl Cfg { - pub fn init(path: Option) -> MLE { + pub async fn init(path: Option) -> MLE { let configfile = match path.clone() { Some(p) => String::from(p), None => dirs::config_dir() @@ -62,6 +64,15 @@ impl Cfg { Ok(..) => (), Err(..) => create_database(&datafile)?, }; + //Check versions + let versionfile = format!("{}/versions.json", config.versions); + match File::open(&versionfile) { + Ok(..) => (), + Err(..) => { + create_versions_dummy(&versionfile).await?; + check_game_versions(&versionfile, true).await?; + }, + } Ok(config) } } @@ -78,8 +89,10 @@ fn create_config(path: &str) -> MLE<()> { let default_cfg = Cfg { data: cache_dir.clone(), cache: format!("{}/cache", cache_dir), + versions: cache_dir.clone(), defaults: Defaults { - modloader: Modloader::Fabric + modloader: Modloader::Fabric, + version: VersionLevel::Release }, apis: Apis { modrinth: String::from("https://api.modrinth.com/v2/"), @@ -112,3 +125,13 @@ fn create_cache(path: &str) -> MLE<()> { println!(" ✓"); Ok(()) } + +async fn create_versions_dummy(path: &str) -> MLE<()> { + print!("No version file found, create dummy"); + //Force flush of stdout, else print! doesn't print instantly + std::io::stdout().flush()?; + + File::create(path)?; + println!(" ✓"); + Ok(()) +} diff --git a/src/error.rs b/src/error.rs index bd6e3da..e6afeaa 100644 --- a/src/error.rs +++ b/src/error.rs @@ -20,6 +20,7 @@ pub enum ErrorType { LibSql, LibReq, LibChrono, + LibJson, IoError, Other, } @@ -42,6 +43,7 @@ impl fmt::Display for MLError { ErrorType::LibSql => write!(f, "SQL: {}", self.message), ErrorType::LibReq => write!(f, "REQWEST"), ErrorType::LibChrono => write!(f, "Chrono error: {}", self.message), + ErrorType::LibJson => write!(f, "JSON: {}", self.message), ErrorType::IoError => write!(f, "IO"), ErrorType::Other => write!(f, "OTHER"), } @@ -102,6 +104,13 @@ impl From for MLError { } } +impl From for MLError { + fn from(value: serde_json::error::Error) -> Self { + Self { etype: ErrorType::LibJson, message: value.to_string() } + } + +} + impl MLError { pub fn new(etype: ErrorType, message: &str) -> Self { Self { diff --git a/src/lib.rs b/src/lib.rs index 05d74db..73b5697 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -6,9 +6,10 @@ pub mod db; pub mod error; pub mod files; -use std::fmt::Display; +use std::{fmt::Display, fs::{File, remove_file, self}, io::{Write, Read}, time::Duration}; pub use apis::*; +use apis::modrinth::{get_game_versions, GameVersion, GameVersionType}; pub use commands::*; use error::{ErrorType, MLError, MLE}; use serde::{Deserialize, Serialize, de::Visitor}; @@ -77,3 +78,111 @@ impl<'de> Deserialize<'de> for Modloader { deserializer.deserialize_identifier(FieldVisitor) } } + +#[derive(Debug, Clone)] +pub enum VersionLevel { + Release, + Snapshot, + Version(String) +} + +/// Checks if update needed (time) +/// if yes: get versions, update +pub async fn check_game_versions(path: &str, force: bool) -> MLE<()> { + let creation_time = fs::metadata(path)?.created()?; + if !force && creation_time.elapsed().unwrap() < Duration::from_secs(60 * 60 * 24) { return Ok(()); } + print!("Update minecraft versions"); + std::io::stdout().flush()?; + let versions = get_game_versions().await; + remove_file(path)?; + let mut file = File::create(path)?; + file.write_all(&serde_json::to_string_pretty(&versions)?.as_bytes())?; + println!(" ✓"); + Ok(()) +} + +/// Loads game versions +pub fn load_game_versions(path: &str) -> MLE> { + let mut file = File::open(path)?; + let mut data = String::new(); + file.read_to_string(&mut data)?; + let versions: Vec = serde_json::from_str(&data)?; + Ok(versions) +} + +impl VersionLevel { + + pub fn from(str: &str) -> Self { + match str { + "release" => VersionLevel::Release, + "snapshot" => VersionLevel::Snapshot, + _ => VersionLevel::Version(String::from(str)), + } + } + + pub fn get(self, versions_path: &str) -> MLE { + let path = format!("{}/versions.json", versions_path); + let mut versions = load_game_versions(&path)?.into_iter(); + + match self { + VersionLevel::Release => { + let release = versions.find(|ver| ver.version_type == GameVersionType::release).unwrap(); + println!("{:?}", release); + Ok(release.version) + }, + VersionLevel::Snapshot => { + let snapshot = versions.find(|ver| ver.version_type == GameVersionType::snapshot).unwrap(); + println!("{:?}", snapshot); + Ok(snapshot.version) + }, + VersionLevel::Version(v) => { + if versions.find(|ver| ver.version == v).is_some() { + Ok(v) + } else { + Err(MLError::new(ErrorType::ConfigError, "unknown minecraft version")) + } + }, + } + } +} + +impl Serialize for VersionLevel { + fn serialize(&self, serializer: S) -> Result + where + S: serde::Serializer { + match self { + VersionLevel::Release => serializer.serialize_str("release"), + VersionLevel::Snapshot => serializer.serialize_str("snapshot"), + VersionLevel::Version(v) => serializer.serialize_str(v), + } + } +} + +impl<'de> Deserialize<'de> for VersionLevel { + fn deserialize(deserializer: D) -> Result + where + D: serde::Deserializer<'de>, + { + struct FieldVisitor; + + impl<'de> Visitor<'de> for FieldVisitor { + type Value = VersionLevel; + + fn expecting(&self, formatter: &mut std::fmt::Formatter) -> std::fmt::Result { + formatter.write_str("`fabric`, `forge` or `quilt`") + } + + fn visit_str(self, v: &str) -> Result + where + E: serde::de::Error, { + match v { + "release" => Ok(VersionLevel::Release), + "snapshot" => Ok(VersionLevel::Snapshot), + _ => Ok(VersionLevel::Version(String::from(v))) + } + } + } + + deserializer.deserialize_identifier(FieldVisitor) + } +} diff --git a/src/main.rs b/src/main.rs index 82c0ade..93da718 100644 --- a/src/main.rs +++ b/src/main.rs @@ -3,7 +3,7 @@ use modlist::{ config::Cfg, db::{config_get_current_list, lists_get, lists_get_all_ids}, download, export, get_current_list, import, list_add, list_change, list_remove, list_version, - mod_add, mod_remove, update, IDSelector, List, Modloader, + mod_add, mod_remove, update, IDSelector, List, Modloader, check_game_versions, VersionLevel, }; //TODO implement remote sql db @@ -18,6 +18,10 @@ struct Cli { /// config file path #[arg(short, long)] config: Option, + + /// Force GameVersion update + #[arg(long)] + force_gameupdate: bool, } #[derive(Subcommand)] @@ -72,6 +76,7 @@ enum Commands { /// the list you want to export list: Option, }, + Test } #[derive(Subcommand)] @@ -147,7 +152,8 @@ enum ListCommands { async fn main() { let cli = Cli::parse(); - let config = Cfg::init(cli.config).unwrap(); + let config = Cfg::init(cli.config).await.unwrap(); + check_game_versions(format!("{}/versions.json", config.versions).as_str(), cli.force_gameupdate).await.unwrap(); match cli.command { Commands::Mod { command } => { @@ -204,11 +210,10 @@ async fn main() { None => config.clone().defaults.modloader, }; + let versions_path = &config.versions; let ver = match version { - Some(ver) => ver, - //TODO get latest version - //TODO impl config for specific version or latest or latest snap - None => "1.19.4".to_string(), + Some(ver) => VersionLevel::from(&ver).get(versions_path).unwrap(), + None => config.clone().defaults.version.get(versions_path).unwrap(), }; list_add(config, id, ver, ml, directory) @@ -262,6 +267,7 @@ async fn main() { import(config, filestr, download).await } Commands::Export { list } => export(config, list), + Commands::Test => Ok(()), } .unwrap(); } -- cgit v1.2.3 From 245b6b9926033acd750503ab4947c9514c5e1aa6 Mon Sep 17 00:00:00 2001 From: fxqnlr Date: Wed, 3 May 2023 08:01:51 +0200 Subject: fuck serde, plus maybe added quilt --- Cargo.lock | 2 +- Cargo.toml | 2 +- src/apis/modrinth.rs | 9 ++--- src/lib.rs | 96 ++++++---------------------------------------------- 4 files changed, 15 insertions(+), 94 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 0e93641..7422038 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -798,7 +798,7 @@ dependencies = [ [[package]] name = "modlist" -version = "0.14.0" +version = "0.14.1" dependencies = [ "chrono", "clap", diff --git a/Cargo.toml b/Cargo.toml index 736831d..bd41811 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,6 +1,6 @@ [package] name = "modlist" -version = "0.14.0" +version = "0.14.1" edition = "2021" # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html diff --git a/src/apis/modrinth.rs b/src/apis/modrinth.rs index 13e7a6d..525cc0d 100644 --- a/src/apis/modrinth.rs +++ b/src/apis/modrinth.rs @@ -4,7 +4,7 @@ use serde::{Deserialize, Serialize}; use crate::{ error::{ErrorType, MLError, MLE}, - List, Modloader, + List, }; #[derive(Debug, Deserialize, Clone)] @@ -168,14 +168,9 @@ pub async fn projects(api: &str, ids: Vec) -> Vec { ///Get applicable versions from mod_id with list context pub async fn versions(api: &str, id: String, list: List) -> Vec { - let loaderstr = match list.modloader { - Modloader::Forge => String::from("forge"), - Modloader::Fabric => String::from("fabric"), - }; - let url = format!( r#"project/{}/version?loaders=["{}"]&game_versions=["{}"]"#, - id, loaderstr, list.mc_version + id, list.modloader.to_string(), list.mc_version ); let data = get(api, &url).await.unwrap(); diff --git a/src/lib.rs b/src/lib.rs index 73b5697..b48bf61 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -12,12 +12,16 @@ pub use apis::*; use apis::modrinth::{get_game_versions, GameVersion, GameVersionType}; pub use commands::*; use error::{ErrorType, MLError, MLE}; -use serde::{Deserialize, Serialize, de::Visitor}; +use serde::{Deserialize, Serialize}; -#[derive(Debug, Clone, PartialEq, Eq)] +#[derive(Debug, Clone, PartialEq, Eq, Deserialize, Serialize)] pub enum Modloader { + #[serde(rename(serialize = "fabric", deserialize = "fabric"))] Fabric, + #[serde(rename(serialize = "forge", deserialize = "forge"))] Forge, + #[serde(rename(serialize = "quilt", deserialize = "quilt"))] + Quilt, } impl Modloader { @@ -35,53 +39,16 @@ impl Display for Modloader { match self { Modloader::Fabric => write!(f, "fabric"), Modloader::Forge => write!(f, "forge"), + Modloader::Quilt => write!(f, "quilt"), } } } -impl Serialize for Modloader { - fn serialize(&self, serializer: S) -> Result - where - S: serde::Serializer { - match self { - Modloader::Fabric => serializer.serialize_str("fabric"), - Modloader::Forge => serializer.serialize_str("forge"), - } - } -} - -impl<'de> Deserialize<'de> for Modloader { - fn deserialize(deserializer: D) -> Result - where - D: serde::Deserializer<'de>, - { - struct FieldVisitor; - - impl<'de> Visitor<'de> for FieldVisitor { - type Value = Modloader; - - fn expecting(&self, formatter: &mut std::fmt::Formatter) -> std::fmt::Result { - formatter.write_str("`fabric`, `forge` or `quilt`") - } - - fn visit_str(self, v: &str) -> Result - where - E: serde::de::Error, { - match v { - "fabric" => Ok(Modloader::Fabric), - "forge" => Ok(Modloader::Forge), - _ => Err(serde::de::Error::unknown_field(v, &["fabric", "forge", "quilt"])) - } - } - } - - deserializer.deserialize_identifier(FieldVisitor) - } -} - -#[derive(Debug, Clone)] +#[derive(Debug, Clone, Deserialize, Serialize)] pub enum VersionLevel { + #[serde(rename(serialize = "release", deserialize = "release"))] Release, + #[serde(rename(serialize = "snapshot", deserialize = "snapshot"))] Snapshot, Version(String) } @@ -101,7 +68,7 @@ pub async fn check_game_versions(path: &str, force: bool) -> MLE<()> { Ok(()) } -/// Loads game versions +/// Loads game versions from file pub fn load_game_versions(path: &str) -> MLE> { let mut file = File::open(path)?; let mut data = String::new(); @@ -145,44 +112,3 @@ impl VersionLevel { } } } - -impl Serialize for VersionLevel { - fn serialize(&self, serializer: S) -> Result - where - S: serde::Serializer { - match self { - VersionLevel::Release => serializer.serialize_str("release"), - VersionLevel::Snapshot => serializer.serialize_str("snapshot"), - VersionLevel::Version(v) => serializer.serialize_str(v), - } - } -} - -impl<'de> Deserialize<'de> for VersionLevel { - fn deserialize(deserializer: D) -> Result - where - D: serde::Deserializer<'de>, - { - struct FieldVisitor; - - impl<'de> Visitor<'de> for FieldVisitor { - type Value = VersionLevel; - - fn expecting(&self, formatter: &mut std::fmt::Formatter) -> std::fmt::Result { - formatter.write_str("`fabric`, `forge` or `quilt`") - } - - fn visit_str(self, v: &str) -> Result - where - E: serde::de::Error, { - match v { - "release" => Ok(VersionLevel::Release), - "snapshot" => Ok(VersionLevel::Snapshot), - _ => Ok(VersionLevel::Version(String::from(v))) - } - } - } - - deserializer.deserialize_identifier(FieldVisitor) - } -} -- cgit v1.2.3 From 87947ce38476e7a5fb8d4db1bc9e0b584aa965ca Mon Sep 17 00:00:00 2001 From: fxqnlr Date: Wed, 3 May 2023 08:29:31 +0200 Subject: added async trait? WHY --- src/lib.rs | 5 +++-- src/main.rs | 7 +++---- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/lib.rs b/src/lib.rs index b48bf61..f18bdfb 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -76,7 +76,7 @@ pub fn load_game_versions(path: &str) -> MLE> { let versions: Vec = serde_json::from_str(&data)?; Ok(versions) } - + impl VersionLevel { pub fn from(str: &str) -> Self { @@ -87,8 +87,9 @@ impl VersionLevel { } } - pub fn get(self, versions_path: &str) -> MLE { + pub async fn get(self, versions_path: &str, force_update: bool) -> MLE { let path = format!("{}/versions.json", versions_path); + check_game_versions(&path, force_update).await?; let mut versions = load_game_versions(&path)?.into_iter(); match self { diff --git a/src/main.rs b/src/main.rs index 93da718..b12e3e4 100644 --- a/src/main.rs +++ b/src/main.rs @@ -3,7 +3,7 @@ use modlist::{ config::Cfg, db::{config_get_current_list, lists_get, lists_get_all_ids}, download, export, get_current_list, import, list_add, list_change, list_remove, list_version, - mod_add, mod_remove, update, IDSelector, List, Modloader, check_game_versions, VersionLevel, + mod_add, mod_remove, update, IDSelector, List, Modloader, VersionLevel, }; //TODO implement remote sql db @@ -153,7 +153,6 @@ async fn main() { let cli = Cli::parse(); let config = Cfg::init(cli.config).await.unwrap(); - check_game_versions(format!("{}/versions.json", config.versions).as_str(), cli.force_gameupdate).await.unwrap(); match cli.command { Commands::Mod { command } => { @@ -212,8 +211,8 @@ async fn main() { let versions_path = &config.versions; let ver = match version { - Some(ver) => VersionLevel::from(&ver).get(versions_path).unwrap(), - None => config.clone().defaults.version.get(versions_path).unwrap(), + Some(ver) => VersionLevel::from(&ver).get(versions_path, cli.force_gameupdate).await.unwrap(), + None => config.clone().defaults.version.get(versions_path, cli.force_gameupdate).await.unwrap(), }; list_add(config, id, ver, ml, directory) -- cgit v1.2.3 From 5a1196c3c98a48028bf70576b5f946f7a0475e07 Mon Sep 17 00:00:00 2001 From: fxqnlr Date: Wed, 3 May 2023 11:56:17 +0200 Subject: added id to db lookup --- src/db.rs | 11 +++++++++-- 1 file changed, 9 insertions(+), 2 deletions(-) diff --git a/src/db.rs b/src/db.rs index abfe1dd..6c7e4f8 100644 --- a/src/db.rs +++ b/src/db.rs @@ -50,8 +50,6 @@ pub fn mods_get_all_ids(config: Cfg) -> Result, Box MLE { - //TODO check if "slug" is id - let data = format!("{}/data.db", data); let connection = Connection::open(data)?; @@ -64,6 +62,15 @@ pub fn mods_get_id(data: &str, slug: &str) -> MLE { for id in id_iter { mod_id = id?; } + //get from id if no slug found + if mod_id.is_empty() { + let mut stmt = connection.prepare("SELECT id FROM mods WHERE id = ?")?; + let id_iter = stmt.query_map([slug], |row| row.get::(0))?; + + for id in id_iter { + mod_id = id?; + } + } //get from title if no id found from slug if mod_id.is_empty() { let mut stmt = connection.prepare("SELECT id FROM mods WHERE title = ?")?; -- cgit v1.2.3 From 59d539f756375719f7ff71822c72afa00c3bd3c4 Mon Sep 17 00:00:00 2001 From: fxqnlr Date: Thu, 4 May 2023 14:31:52 +0200 Subject: removed todo --- src/main.rs | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/main.rs b/src/main.rs index b12e3e4..3bc2ba0 100644 --- a/src/main.rs +++ b/src/main.rs @@ -6,8 +6,6 @@ use modlist::{ mod_add, mod_remove, update, IDSelector, List, Modloader, VersionLevel, }; -//TODO implement remote sql db - //TODO make default list optional #[derive(Parser)] #[command(author, version, about)] -- cgit v1.2.3