feat: added command functionality to install

This commit is contained in:
Strix 2023-10-14 22:39:43 +02:00
parent 3a21d12c07
commit 092c616ca4
No known key found for this signature in database
GPG key ID: 49B2E37B8915B774
20 changed files with 464 additions and 76 deletions

View file

@ -0,0 +1,71 @@
use libc::fork;
use log::{debug, trace};
use manifest::Manifest;
use pkgfile::PKGFile;
use crate::tmp::TempDir;
#[derive(Debug)]
pub enum InstallType {
Build,
Bin
}
#[derive(Debug)]
pub enum InstallError {
BuildError(String),
BinError(String),
InstallError
}
impl ToString for InstallError {
fn to_string(&self) -> String {
match self {
InstallError::BuildError(e) => format!("Build error: {}", e),
InstallError::BinError(e) => format!("Bin error: {}", e),
InstallError::InstallError => "Install error".to_string(),
}
}
}
#[derive(Debug)]
pub struct PackageInstaller {
manifest: Manifest,
pkgfile: PKGFile,
install_type: InstallType
}
impl PackageInstaller {
pub fn new(m: Manifest, p: PKGFile, i: InstallType) -> PackageInstaller {
PackageInstaller {
manifest: m,
pkgfile: p,
install_type: i
}
}
fn extract_to<S: Into<String>>(&self, path: S) -> Result<(), String> {
tar::Archive::new(self.pkgfile.data.as_slice())
.unpack(path.into())
.map_err(|e| e.to_string())
}
fn bin(&self) -> Result<(), String> {
let mut tmpdir = TempDir::default();
tmpdir.push(&self.manifest.package.name);
trace!("extracting package into: {}", tmpdir.to_string());
self.extract_to(tmpdir.to_string())?;
debug!("extracted package in: {}", tmpdir.to_string());
Ok(())
}
fn build(&self) -> Result<(), String> {
Ok(())
}
pub fn install(&self) -> Result<(), InstallError> {
match self.install_type {
InstallType::Bin => self.bin().map_err(|e| InstallError::BinError(e)),
InstallType::Build => self.build().map_err(|e| InstallError::BuildError(e))
}
}
}

59
pkgr/src/package/fetch.rs Normal file
View file

@ -0,0 +1,59 @@
use std::error::Error;
use std::fmt::Display;
use std::fs::File;
use std::io::Read;
use log::warn;
use pkgfile::PKGFile;
use crate::package::identifier::PackageIdentifier;
use reqwest::blocking::get;
#[derive(Debug)]
pub enum FetchError {
HTTPError(reqwest::Error),
IOError(std::io::Error),
ParseError,
}
impl Display for FetchError {
fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
match self {
FetchError::HTTPError(e) => write!(f, "HTTP Error: {}", e),
FetchError::IOError(e) => write!(f, "IO Error: {}", e),
FetchError::ParseError => write!(f, "Parse Error"),
}
}
}
impl Error for FetchError {}
pub fn fetch_package(package_identifier: PackageIdentifier) -> Result<PKGFile, FetchError> {
match package_identifier {
PackageIdentifier::Path(path) => {
std::fs::read(path)
.map_err(|e| FetchError::IOError(e)).and_then(|bytes| {
PKGFile::try_from(bytes).map_err(|_| FetchError::ParseError)
})
}
PackageIdentifier::URI(uri) => {
// get file contents as bytes
let mut bytes = Vec::new();
match get(&uri) {
Ok(mut response) => {
match response.take(1024 * 1024).read_to_end(&mut bytes) {
Ok(_) => (),
Err(e) => return Err(FetchError::IOError(e)),
};
}
Err(e) => return Err(FetchError::HTTPError(e)),
};
// parse bytes as PKGFile
match PKGFile::try_from(bytes) {
Ok(pkgfile) => Ok(pkgfile),
Err(e) => Err(FetchError::ParseError),
}
}
PackageIdentifier::PackageLocator(package_locator) => {
Ok(PKGFile::default())
}
}
}

View file

@ -26,6 +26,7 @@ impl Error for PackageIdentifierError {}
pub enum PackageIdentifier {
PackageLocator(PackageLocator),
URI(String),
Path(String),
}
impl std::fmt::Display for PackageIdentifier {
@ -33,6 +34,7 @@ impl std::fmt::Display for PackageIdentifier {
match self {
PackageIdentifier::PackageLocator(pl) => write!(f, "{}", pl),
PackageIdentifier::URI(uri) => write!(f, "{}", uri),
PackageIdentifier::Path(path) => write!(f, "{}", path),
}
}
}
@ -61,7 +63,7 @@ impl FromStr for PackageIdentifier {
type Err = PackageIdentifierError;
fn from_str(s: &str) -> Result<Self, Self::Err> {
let uri_re = regex::Regex::new(r"^[a-zA-Z0-9]+://").unwrap();
let uri_re = Regex::new(r"^[a-zA-Z0-9]+://").unwrap();
if uri_re.is_match(s) {
// there needs to be stuff after the protocol
let split = s.split("://").collect::<Vec<&str>>();
@ -69,6 +71,8 @@ impl FromStr for PackageIdentifier {
return Err(PackageIdentifierError::InvalidURI(s.to_string()));
}
Ok(PackageIdentifier::URI(s.to_string()))
} else if std::path::Path::new(s).exists() {
return Ok(PackageIdentifier::Path(s.to_string()));
} else {
let pl = match PackageLocator::from_str(s) {
Ok(pl) => pl,
@ -84,7 +88,7 @@ impl FromStr for PackageLocator {
fn from_str(s: &str) -> Result<Self, Self::Err> {
#[allow(unused_assignments)] // false positive
let mut name = None;
let mut name = None;
let mut version = None;
let mut tags = None;

View file

@ -1 +1,3 @@
pub mod identifier;
pub mod builder;
pub mod fetch;