From 72ddd7b7704f2087a52c9c0552446682918c513b Mon Sep 17 00:00:00 2001 From: Filip Wandzio Date: Thu, 22 Jan 2026 23:14:08 +0100 Subject: Implement basic game files download logic Implement core clap arguments Respect XDG_BASE_DIR Currently library extraction is broken because it assumes every instace has it's own library folder. This should be refactored so instances share libraries Signed-off-by: Filip Wandzio --- src/minecraft/downloads.rs | 66 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 66 insertions(+) create mode 100644 src/minecraft/downloads.rs (limited to 'src/minecraft/downloads.rs') diff --git a/src/minecraft/downloads.rs b/src/minecraft/downloads.rs new file mode 100644 index 0000000..5be5a05 --- /dev/null +++ b/src/minecraft/downloads.rs @@ -0,0 +1,66 @@ +use log::{debug, info}; +use tokio::{fs, io::AsyncWriteExt}; + +use crate::{ + config::Config, + errors::McError, + minecraft::manifests::{Library, Version}, + platform::paths, +}; + +/// Download everything required to launch: +/// - client jar +/// - libraries +pub async fn download_all(config: &Config, version: &Version) -> Result<(), McError> { + download_client(config, version).await?; + download_libraries(config, &version.libraries).await?; + Ok(()) +} + +async fn download_client(config: &Config, version: &Version) -> Result<(), McError> { + let jar_path = paths::client_jar(config, &version.id)?; + + if jar_path.exists() { + debug!("Client jar already exists"); + return Ok(()); + } + + info!("Downloading client {}", version.id); + + download_file(&version.downloads.client.url, &jar_path).await +} + +async fn download_libraries(config: &Config, libraries: &[Library]) -> Result<(), McError> { + for lib in libraries { + let Some(artifact) = &lib.downloads.artifact else { + continue; + }; + + let lib_path = paths::library_file(config, &artifact.path)?; + + if lib_path.exists() { + continue; + } + + info!("Downloading library {}", artifact.path); + download_file(&artifact.url, &lib_path).await?; + } + + Ok(()) +} + +/* ---------------- helper ---------------- */ + +async fn download_file(url: &str, path: &std::path::Path) -> Result<(), McError> { + if let Some(parent) = path.parent() { + fs::create_dir_all(parent).await?; + } + + let response = reqwest::get(url).await?; + let bytes = response.bytes().await?; + + let mut file = fs::File::create(path).await?; + file.write_all(&bytes).await?; + + Ok(()) +} -- cgit v1.2.3