readded game_profile to ClientOptions, added creation of libraries folder

This commit is contained in:
Quentin Legot 2023-04-24 02:47:14 +02:00
parent 6869f97eea
commit c0990b3fe8
3 changed files with 48 additions and 11 deletions

View File

@ -69,7 +69,7 @@ pub struct Library {
#[derive(Serialize, Deserialize)] #[derive(Serialize, Deserialize)]
pub struct LibraryDownload { pub struct LibraryDownload {
artifact: LibraryArtifact pub artifact: LibraryArtifact
} }
#[derive(Serialize, Deserialize)] #[derive(Serialize, Deserialize)]
@ -93,11 +93,11 @@ pub enum OSName {
} }
#[derive(Serialize, Deserialize)] #[derive(Serialize, Deserialize)]
struct LibraryArtifact { pub struct LibraryArtifact {
path: String, pub path: String,
sha1: String, pub sha1: String,
size: i64, pub size: i64,
url: String, pub url: String,
} }
pub async fn get_version_detail(reqwest: &Client, version : &Version) -> Result<VersionDetail> { pub async fn get_version_detail(reqwest: &Client, version : &Version) -> Result<VersionDetail> {

View File

@ -1,11 +1,13 @@
mod manifest; mod manifest;
use std::path::Path; use std::path::{Path, self};
use anyhow::Result; use anyhow::{Result, bail};
use reqwest::Client; use reqwest::Client;
use serde::{Serialize, Deserialize}; use serde::{Serialize, Deserialize};
use tokio::fs; use tokio::{fs, io::AsyncWriteExt};
use crate::authentification::GameProfile;
use self::manifest::{VersionDetail, get_version_manifest, get_version_from_manifest, get_version_detail, Library, OSName}; use self::manifest::{VersionDetail, get_version_manifest, get_version_from_manifest, get_version_detail, Library, OSName};
@ -18,6 +20,7 @@ const ACTUAL_OS: OSName = OSName::Linux;
const ACTUAL_OS: OSName = OSName::MacOsX; const ACTUAL_OS: OSName = OSName::MacOsX;
pub struct ClientOptions<'a> { pub struct ClientOptions<'a> {
pub authorization: GameProfile,
pub root_path: &'a Path, pub root_path: &'a Path,
pub java_path: &'a Path, pub java_path: &'a Path,
pub version_number: String, pub version_number: String,
@ -57,11 +60,41 @@ impl<'a> MinecraftClient<'_> {
if !self.opts.root_path.exists() { if !self.opts.root_path.exists() {
fs::create_dir_all(self.opts.root_path).await?; fs::create_dir_all(self.opts.root_path).await?;
} }
let lib = self.opts.root_path.join("librairies"); let lib = &self.opts.root_path.join("libraries");
if !lib.exists() { if !lib.exists() {
fs::create_dir(lib).await?; fs::create_dir(lib).await?;
} }
self.filter_non_necessary_librairies(); self.filter_non_necessary_librairies();
for (_, i) in self.details.libraries.iter().enumerate() {
let p = i.downloads.artifact.path.clone();
let mut splited = p.split("/").collect::<Vec<&str>>();
splited.pop(); // remove last element
let p = splited.join(path::MAIN_SEPARATOR_STR);
let p = &lib.join(p);
fs::create_dir_all(p).await?;
let url = i.downloads.artifact.url.clone();
let mut sha = url.clone();
sha.push_str(".sha1");
let sha1 = self.reqwest_client
.get(sha)
.send()
.await?
.text()
.await?;
if sha1 != i.downloads.artifact.sha1 {
bail!("Sha1 hash of a library is invalid, a malicious file might be present on the remote server")
}
let content = self.reqwest_client
.get(url)
.send()
.await?
.bytes()
.await?;
let mut file = fs::File::create(p).await?;
file.write_all(&content).await?;
println!("{} downloaded", i.name);
}
Ok(()) Ok(())
} }

View File

@ -9,7 +9,7 @@ pub mod launcher;
use std::sync::Mutex; use std::sync::Mutex;
use authentification::{Authentification, Prompt, GameProfile}; use authentification::{Authentification, Prompt, GameProfile};
use anyhow::{Result, bail}; use anyhow::Result;
use directories::BaseDirs; use directories::BaseDirs;
use launcher::{MinecraftClient, ClientOptions}; use launcher::{MinecraftClient, ClientOptions};
@ -51,7 +51,11 @@ async fn download(state: tauri::State<'_, Mutex<CustomState>>) -> Result<String,
Ok(res) => Ok(res.0.clone()), Ok(res) => Ok(res.0.clone()),
Err(err) => Err(err.to_string()) Err(err) => Err(err.to_string())
}?; }?;
if game_profile.is_none() {
return Err("You're not connected".to_string());
}
let opts = ClientOptions { let opts = ClientOptions {
authorization: game_profile.unwrap(),
root_path, root_path,
java_path: &java_path.as_path(), java_path: &java_path.as_path(),
version_number: "1.19.4".to_string(), version_number: "1.19.4".to_string(),