Commit 26ec0bd5 authored by Jeremy Soller's avatar Jeremy Soller Committed by GitHub
Browse files

Merge pull request #9 from ids1024/package

Refactor with a Package class
parents 3c89b49c 0b9d1fa9
......@@ -2,7 +2,7 @@
extern crate pkgutils;
use pkgutils::Repo;
use pkgutils::{Repo, Package};
use std::{env, process};
use std::io::{self, Write};
......@@ -85,8 +85,8 @@ fn main() {
if ! packages.is_empty() {
for package in packages.iter() {
match repo.fetch(package) {
Ok(tarfile) => {
let _ = write!(io::stderr(), "pkg: fetch: {}: fetched {}\n", package, tarfile);
Ok(pkg) => {
let _ = write!(io::stderr(), "pkg: fetch: {}: fetched {}\n", package, pkg.path().display());
},
Err(err) => {
let _ = write!(io::stderr(), "pkg: fetch: {}: failed: {}\n", package, err);
......@@ -105,14 +105,14 @@ fn main() {
let packages: Vec<String> = args.collect();
if ! packages.is_empty() {
for package in packages.iter() {
let result = if package.ends_with(".tar") {
let pkg = if package.ends_with(".tar") {
let path = format!("{}/{}", env::current_dir().unwrap().to_string_lossy(), package);
repo.install_file(&path)
Package::from_path(&path)
} else {
repo.install(package)
repo.fetch(package)
};
if let Err(err) = result {
if let Err(err) = pkg.and_then(|mut p| p.install("/")) {
let _ = write!(io::stderr(), "pkg: install: {}: failed: {}\n", package, err);
} else {
let _ = write!(io::stderr(), "pkg: install: {}: succeeded\n", package);
......@@ -127,7 +127,7 @@ fn main() {
let packages: Vec<String> = args.collect();
if ! packages.is_empty() {
for package in packages.iter() {
if let Err(err) = repo.list(package) {
if let Err(err) = repo.fetch(package).and_then(|mut p| p.list()) {
let _ = write!(io::stderr(), "pkg: list: {}: failed: {}\n", package, err);
} else {
let _ = write!(io::stderr(), "pkg: list: {}: succeeded\n", package);
......
......@@ -10,7 +10,6 @@ extern crate toml;
use octavo::octavo_digest::Digest;
use octavo::octavo_digest::sha3::Sha512;
use tar::Archive;
use std::str;
use std::fs::{self, File};
use std::io::{self, stderr, Read, Write};
......@@ -18,14 +17,15 @@ use std::path::Path;
pub use download::download;
pub use packagemeta::PackageMeta;
pub use package::Package;
mod download;
mod packagemeta;
mod package;
pub struct Repo {
local: String,
remotes: Vec<String>,
dest: String,
target: String,
}
......@@ -68,7 +68,6 @@ impl Repo {
Repo {
local: format!("/tmp/pkg"),
remotes: remotes,
dest: "/".to_string(),
target: target.to_string()
}
}
......@@ -141,7 +140,7 @@ impl Repo {
Ok(tarfile)
}
pub fn fetch(&self, package: &str) -> io::Result<String> {
pub fn fetch(&self, package: &str) -> io::Result<Package> {
let sigfile = self.sync(&format!("{}.sig", package))?;
let tarfile = self.sync(&format!("{}.tar", package))?;
......@@ -151,48 +150,16 @@ impl Repo {
return Err(io::Error::new(io::ErrorKind::InvalidData, format!("{} not valid", package)));
}
Ok(tarfile)
Package::from_path(tarfile)
}
pub fn extract(&self, package: &str) -> io::Result<String> {
let tarfile = self.fetch(package)?;
let tardir = format!("{}/{}", self.local, package);
fs::create_dir_all(&tardir)?;
let mut ar = Archive::new(File::open(&tarfile)?);
ar.set_preserve_permissions(true);
ar.unpack(&tardir)?;
self.fetch(package)?.install(&tardir)?;
Ok(tardir)
}
pub fn install_file(&self, path: &str)-> io::Result<()> {
let mut ar = Archive::new(File::open(path)?);
ar.set_preserve_permissions(true);
ar.unpack(&self.dest)?;
Ok(())
}
pub fn install(&self, package: &str) -> io::Result<()> {
let tarfile = self.fetch(package)?;
self.install_file(&tarfile)
}
pub fn list(&self, package: &str) -> io::Result<()> {
let tarfile = self.fetch(package)?;
let mut ar = Archive::new(File::open(tarfile)?);
for i in ar.entries()? {
println!("{}", i?.path()?.display());
}
Ok(())
}
pub fn set_dest(&mut self, dest: &str) {
self.dest = dest.to_string();
}
pub fn add_remote(&mut self, remote: &str) {
self.remotes.push(remote.to_string());
}
......
use std::fs::File;
use std::path::Path;
use std::path::PathBuf;
use std::io::{self, Error, ErrorKind, Read};
use tar::{Archive, EntryType};
use packagemeta::PackageMeta;
pub struct Package {
archive: Archive<File>,
path: PathBuf,
meta: Option<PackageMeta>,
}
impl Package {
pub fn from_path<P: AsRef<Path>>(path: P) -> io::Result<Self> {
let mut ar = Archive::new(File::open(&path)?);
ar.set_preserve_permissions(true);
Ok(Package{archive: ar, path: path.as_ref().to_path_buf(), meta: None})
}
pub fn install(&mut self, dest: &str)-> io::Result<()> {
self.archive.unpack(dest)?;
Ok(())
}
pub fn list(&mut self) -> io::Result<()> {
for i in self.archive.entries()? {
println!("{}", i?.path()?.display());
}
Ok(())
}
pub fn path(&self) -> &Path {
&self.path
}
pub fn meta(&mut self) -> io::Result<&PackageMeta> {
if self.meta.is_none() {
let mut toml = None;
for entry in self.archive.entries()? {
let mut entry = entry?;
if entry.header().entry_type() != EntryType::Directory && entry.path()?.starts_with("pkg") {
if toml.is_none() {
let mut text = String::new();
entry.read_to_string(&mut text)?;
toml = Some(text);
} else {
return Err(Error::new(ErrorKind::Other, "Multiple metadata files in package"));
}
}
}
if let Some(toml) = toml {
self.meta = Some(PackageMeta::from_toml(&toml).map_err(|e| Error::new(ErrorKind::Other, e))?);
} else {
return Err(Error::new(ErrorKind::NotFound, "Package metadata not found"));
}
}
Ok(self.meta.as_ref().unwrap())
}
}
......@@ -2,9 +2,9 @@ use toml::{self, to_string, from_str};
#[derive(Serialize, Deserialize)]
pub struct PackageMeta {
name: String,
version: String,
target: String,
pub name: String,
pub version: String,
pub target: String,
}
impl PackageMeta {
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment