rustpkg: Implement clean; replace boolean result flags with fail!()
1. Implemented the `clean` command 2. The methods implementing rustpkg commands all returned `bool`. Since most of not all of the error situations seem unrecoverable, I changed the methods to return unit (and also stubbed out several more methods that were assuming a package script existed, to be re-implemented in the future)
This commit is contained in:
parent
e6c3c371a5
commit
82765a0b48
2 changed files with 67 additions and 159 deletions
|
|
@ -33,7 +33,6 @@ use core::hashmap::HashMap;
|
|||
use core::io::WriterUtil;
|
||||
use rustc::driver::{driver, session};
|
||||
use rustc::metadata::filesearch;
|
||||
use std::net::url;
|
||||
use std::{getopts};
|
||||
use syntax::{ast, diagnostic};
|
||||
use util::*;
|
||||
|
|
@ -244,16 +243,21 @@ impl Ctx {
|
|||
src.build(&dst_dir, cfgs);
|
||||
}
|
||||
~"clean" => {
|
||||
self.clean();
|
||||
if args.len() < 1 {
|
||||
return usage::build();
|
||||
}
|
||||
// The package id is presumed to be the first command-line
|
||||
// argument
|
||||
let pkgid = PkgId::new(args[0]);
|
||||
|
||||
self.clean(pkgid);
|
||||
}
|
||||
~"do" => {
|
||||
if args.len() < 2 {
|
||||
return usage::do_cmd();
|
||||
}
|
||||
|
||||
if !self.do_cmd(args[0], args[1]) {
|
||||
fail!(~"a command failed!");
|
||||
}
|
||||
self.do_cmd(args[0], args[1]);
|
||||
}
|
||||
~"info" => {
|
||||
self.info();
|
||||
|
|
@ -298,12 +302,11 @@ impl Ctx {
|
|||
}
|
||||
}
|
||||
|
||||
fn do_cmd(&self, cmd: ~str, pkgname: ~str) -> bool {
|
||||
fn do_cmd(&self, cmd: ~str, pkgname: ~str) {
|
||||
match cmd {
|
||||
~"build" | ~"test" => {
|
||||
util::error(~"that command cannot be manually called");
|
||||
|
||||
return false;
|
||||
fail!(~"do_cmd");
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
|
|
@ -319,16 +322,15 @@ impl Ctx {
|
|||
Some(script_path) => {
|
||||
let script = PkgScript::parse(script_path, pkgid);
|
||||
let (_, status) = script.run_custom(cmd); // Ignore cfgs?
|
||||
if status == 42 { // ???
|
||||
if status == 42 {
|
||||
util::error(~"no fns are listening for that cmd");
|
||||
return false;
|
||||
fail!(~"do_cmd");
|
||||
}
|
||||
status == 0
|
||||
}
|
||||
None => {
|
||||
util::error(fmt!("invoked `do`, but there is no package script in %s",
|
||||
cwd.to_str()));
|
||||
false
|
||||
fail!(~"do_cmd");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -341,128 +343,44 @@ impl Ctx {
|
|||
}
|
||||
|
||||
fn compile(&self, _crate: &Path, _dir: &Path, _flags: ~[~str],
|
||||
_cfgs: ~[~str], _opt: bool, _test: bool) -> bool {
|
||||
_cfgs: ~[~str], _opt: bool, _test: bool) {
|
||||
// What's the difference between build and compile?
|
||||
fail!(~"compile not yet implemented");
|
||||
}
|
||||
|
||||
fn clean(&self) -> bool {
|
||||
// stub
|
||||
fail!();
|
||||
fn clean(&self, id: PkgId) {
|
||||
// Could also support a custom build hook in the pkg
|
||||
// script for cleaning files rustpkg doesn't know about.
|
||||
// Do something reasonable for now
|
||||
|
||||
let dir = dest_dir(id);
|
||||
util::note(fmt!("Cleaning package %s (removing directory %s)",
|
||||
id.to_str(), dir.to_str()));
|
||||
if os::path_exists(&dir) {
|
||||
util::remove_dir_r(&dir);
|
||||
util::note(fmt!("Removed directory %s", dir.to_str()));
|
||||
}
|
||||
|
||||
util::note(fmt!("Cleaned package %s", id.to_str()));
|
||||
}
|
||||
|
||||
fn info(&self) {
|
||||
// stub
|
||||
fail!();
|
||||
fail!(~"info not yet implemented");
|
||||
}
|
||||
|
||||
fn install(&self, url: Option<~str>,
|
||||
target: Option<~str>, cache: bool) -> bool {
|
||||
let dir = match url {
|
||||
None => {
|
||||
util::note(~"installing from the cwd");
|
||||
os::getcwd()
|
||||
}
|
||||
Some(url) => {
|
||||
let hash = util::hash(if !target.is_none() {
|
||||
url + target.get()
|
||||
}
|
||||
else { url });
|
||||
|
||||
if self.dep_cache.contains_key(&hash) {
|
||||
util::warn(~"already installed dep this run");
|
||||
return true;
|
||||
}
|
||||
|
||||
self.dep_cache.insert(hash, true);
|
||||
|
||||
let dir = util::root().push(~"tmp").push(hash);
|
||||
|
||||
if cache && os::path_exists(&dir) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if !self.fetch(&dir, url, target) {
|
||||
return false;
|
||||
}
|
||||
dir
|
||||
}
|
||||
};
|
||||
|
||||
let script = match self.build(&dir, false, true, false) {
|
||||
Some(script) => script,
|
||||
None => {
|
||||
return false;
|
||||
}
|
||||
};
|
||||
let work_dir = script.build_dir;
|
||||
let from_bin_dir = work_dir.push(~"bin");
|
||||
let from_lib_dir = work_dir.push(~"lib");
|
||||
let to_bin_dir = util::root().push(~"bin");
|
||||
let to_lib_dir = util::root().push(~"lib");
|
||||
let mut bins = ~[];
|
||||
let mut libs = ~[];
|
||||
|
||||
for os::walk_dir(&from_bin_dir) |bin| {
|
||||
let to = to_bin_dir.push_rel(&bin.file_path());
|
||||
|
||||
os::copy_file(bin, &to);
|
||||
bins.push(to.to_str());
|
||||
}
|
||||
|
||||
for os::walk_dir(&from_lib_dir) |lib| {
|
||||
let to = to_lib_dir.push_rel(&lib.file_path());
|
||||
|
||||
os::copy_file(lib, &to);
|
||||
libs.push(to.to_str());
|
||||
}
|
||||
|
||||
let package = Pkg {
|
||||
id: script.id,
|
||||
bins: bins,
|
||||
libs: libs
|
||||
};
|
||||
|
||||
util::note(fmt!("installed %s", script.id.to_str()));
|
||||
util::add_pkg(&package);
|
||||
|
||||
true
|
||||
fn install(&self, _url: Option<~str>,
|
||||
_target: Option<~str>, _cache: bool) {
|
||||
// stub
|
||||
fail!(~"install not yet implemented");
|
||||
}
|
||||
|
||||
fn fetch(&self, dir: &Path, url: ~str, target: Option<~str>) -> bool {
|
||||
let url = if str::find_str(url, "://").is_none() {
|
||||
~"http://" + url }
|
||||
else { url };
|
||||
let url = match url::from_str(url) {
|
||||
result::Ok(url) => url,
|
||||
result::Err(err) => {
|
||||
util::error(fmt!("failed parsing %s", err.to_lower()));
|
||||
|
||||
return false;
|
||||
}
|
||||
};
|
||||
let str = url.to_str();
|
||||
|
||||
match Path(url.path).filetype() {
|
||||
Some(ext) => {
|
||||
if ext == ~".git" {
|
||||
return self.fetch_git(dir, str, target);
|
||||
}
|
||||
}
|
||||
None => {}
|
||||
}
|
||||
|
||||
match url.scheme {
|
||||
~"git" => self.fetch_git(dir, str, target),
|
||||
~"http" | ~"ftp" | ~"file" => self.fetch_curl(dir, str),
|
||||
_ => {
|
||||
util::warn(~"unknown url scheme to fetch, using curl");
|
||||
self.fetch_curl(dir, str)
|
||||
}
|
||||
}
|
||||
fn fetch(&self, _dir: &Path, _url: ~str, _target: Option<~str>) {
|
||||
// stub
|
||||
fail!(~"fetch not yet implemented");
|
||||
}
|
||||
|
||||
fn fetch_curl(&self, dir: &Path, url: ~str) -> bool {
|
||||
fn fetch_curl(&self, dir: &Path, url: ~str) {
|
||||
util::note(fmt!("fetching from %s using curl", url));
|
||||
|
||||
let tar = dir.dir_path().push(&dir.file_path().to_str() + ~".tar");
|
||||
|
|
@ -472,7 +390,7 @@ impl Ctx {
|
|||
url]).status != 0 {
|
||||
util::error(~"fetching failed: downloading using curl failed");
|
||||
|
||||
return false;
|
||||
fail!();
|
||||
}
|
||||
|
||||
if run::program_output(~"tar", ~[~"-x", ~"--strip-components=1",
|
||||
|
|
@ -481,13 +399,11 @@ impl Ctx {
|
|||
util::error(~"fetching failed: extracting using tar failed" +
|
||||
~"(is it a valid tar archive?)");
|
||||
|
||||
return false;
|
||||
fail!();
|
||||
}
|
||||
|
||||
true
|
||||
}
|
||||
|
||||
fn fetch_git(&self, dir: &Path, url: ~str, target: Option<~str>) -> bool {
|
||||
fn fetch_git(&self, dir: &Path, url: ~str, target: Option<~str>) {
|
||||
util::note(fmt!("fetching from %s using git", url));
|
||||
|
||||
// Git can't clone into a non-empty directory
|
||||
|
|
@ -496,8 +412,7 @@ impl Ctx {
|
|||
if run::program_output(~"git", ~[~"clone", url,
|
||||
dir.to_str()]).status != 0 {
|
||||
util::error(~"fetching failed: can't clone repository");
|
||||
|
||||
return false;
|
||||
fail!();
|
||||
}
|
||||
|
||||
if !target.is_none() {
|
||||
|
|
@ -511,21 +426,17 @@ impl Ctx {
|
|||
|
||||
if !success {
|
||||
util::error(~"fetching failed: can't checkout target");
|
||||
|
||||
return false;
|
||||
fail!();
|
||||
}
|
||||
}
|
||||
|
||||
true
|
||||
}
|
||||
|
||||
fn prefer(&self, id: ~str, vers: Option<~str>) -> bool {
|
||||
fn prefer(&self, id: ~str, vers: Option<~str>) {
|
||||
let package = match util::get_pkg(id, vers) {
|
||||
result::Ok(package) => package,
|
||||
result::Err(err) => {
|
||||
util::error(err);
|
||||
|
||||
return false;
|
||||
fail!(); // Condition?
|
||||
}
|
||||
};
|
||||
let name = package.id.path.to_str(); // ???
|
||||
|
|
@ -548,29 +459,18 @@ impl Ctx {
|
|||
}
|
||||
|
||||
util::note(fmt!("preferred %s v%s", name, package.id.version.to_str()));
|
||||
|
||||
true
|
||||
}
|
||||
|
||||
fn test(&self) -> bool {
|
||||
let script = match self.build(&os::getcwd(), false, false, true) {
|
||||
Some(script) => script,
|
||||
None => {
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
// To do
|
||||
util::note(fmt!("Would test %s, but this is a dry run",
|
||||
script.id.to_str()));
|
||||
false
|
||||
fn test(&self) {
|
||||
// stub
|
||||
fail!(~"test not yet implemented");
|
||||
}
|
||||
|
||||
fn uninstall(&self, _id: ~str, _vers: Option<~str>) -> bool {
|
||||
fn uninstall(&self, _id: ~str, _vers: Option<~str>) {
|
||||
fail!(~"uninstall not yet implemented");
|
||||
}
|
||||
|
||||
fn unprefer(&self, _id: ~str, _vers: Option<~str>) -> bool {
|
||||
fn unprefer(&self, _id: ~str, _vers: Option<~str>) {
|
||||
fail!(~"unprefer not yet implemented");
|
||||
}
|
||||
}
|
||||
|
|
@ -839,14 +739,19 @@ impl PkgSrc {
|
|||
prefix, pth),
|
||||
Some(~"bench.rs") => push_crate(&mut self.benchs,
|
||||
prefix, pth),
|
||||
_ => {
|
||||
util::note(~"Couldn't infer any crates to build.\n\
|
||||
Try naming a crate `main.rs`, `lib.rs`, \
|
||||
`test.rs`, or `bench.rs`.");
|
||||
fail!(~"Failed to infer crates to build");
|
||||
}
|
||||
_ => ()
|
||||
}
|
||||
}
|
||||
|
||||
if self.libs.is_empty() && self.mains.is_empty()
|
||||
&& self.tests.is_empty() && self.benchs.is_empty() {
|
||||
|
||||
util::note(~"Couldn't infer any crates to build.\n\
|
||||
Try naming a crate `main.rs`, `lib.rs`, \
|
||||
`test.rs`, or `bench.rs`.");
|
||||
fail!(~"Failed to infer crates to build");
|
||||
}
|
||||
|
||||
debug!("found %u libs, %u mains, %u tests, %u benchs",
|
||||
self.libs.len(),
|
||||
self.mains.len(),
|
||||
|
|
|
|||
|
|
@ -10,9 +10,12 @@
|
|||
|
||||
/*
|
||||
The test runner should check that, after `rustpkg build hello-world`:
|
||||
* testsuite/hello-world/build/ exists
|
||||
* testsuite/hello-world/build/ contains an executable named hello-world
|
||||
* testsuite/hello-world/build/ does not contain a library
|
||||
* testsuite/pass/hello-world/build/ exists
|
||||
* testsuite/pass/hello-world/build/ contains an executable named hello-world
|
||||
* testsuite/pass/hello-world/build/ does not contain a library
|
||||
|
||||
It should also check that after `rustpkg clean hello-world`:
|
||||
* testsuite/pass/hello-world/build is empty
|
||||
*/
|
||||
|
||||
use core::io;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue