Support nested paths in git and path sources

This commit is contained in:
Yehuda Katz + Carl Lerche 2014-06-17 17:40:22 -07:00 committed by Tim Carey-Smith
parent 9224a5ae61
commit bcf9028749
7 changed files with 109 additions and 81 deletions

View file

@ -89,29 +89,9 @@ impl SourceId {
}
}
/*
let git_sources: Vec<Box<Source>> = try!(result::collect(package.get_sources().iter().map(|source_id: &SourceId| {
match source_id.kind {
GitKind(ref reference) => {
let remote = GitRemote::new(source_id.url.clone(), false);
let home = try!(os::homedir().require(simple_human("Cargo couldn't find a home directory")));
let git = home.join(".cargo").join("git");
let ident = url_to_path_ident(&source_id.url);
// .cargo/git/db
// .cargo/git/checkouts
let db_path = git.join("db").join(ident.as_slice());
let checkout_path = git.join("checkouts").join(ident.as_slice()).join(reference.as_slice());
Ok(box GitSource::new(remote, reference.clone(), db_path, checkout_path) as Box<Source>)
},
ref PathKind => fail!("Cannot occur")
}
})));
*/
pub fn load(&self, config: &Config) -> Box<Source> {
match self.kind {
GitKind(ref reference) => {
GitKind(..) => {
box GitSource::new(self, config) as Box<Source>
},
PathKind => box PathSource::new(self) as Box<Source>,

View file

@ -1,6 +1,5 @@
use std::io::File;
use util;
use url::Url;
use core::{Package,Manifest,SourceId};
use util::{CargoResult,io_error};
@ -16,3 +15,14 @@ pub fn read_package(path: &Path, source_id: &SourceId) -> CargoResult<(Package,
Ok((Package::new(manifest, path), nested))
}
pub fn read_packages(path: &Path, source_id: &SourceId) -> CargoResult<Vec<Package>> {
let (pkg, nested) = try!(read_package(&path.join("Cargo.toml"), source_id));
let mut ret = vec!(pkg);
for p in nested.iter() {
ret.push_all(try!(read_packages(&path.join(p), source_id)).as_slice());
}
Ok(ret)
}

View file

@ -1,5 +1,5 @@
pub use self::cargo_compile::compile;
pub use self::cargo_read_manifest::{read_manifest,read_package};
pub use self::cargo_read_manifest::{read_manifest,read_package,read_packages};
pub use self::cargo_rustc::compile_packages;
mod cargo_compile;

View file

@ -13,6 +13,8 @@ use core::{Package,PackageId,Summary};
use util::{CargoResult,Config};
use sources::git::utils::{GitReference,GitRemote,Master,Other};
/* TODO: Refactor GitSource to delegate to a PathSource
*/
pub struct GitSource {
id: SourceId,
remote: GitRemote,
@ -52,6 +54,9 @@ impl GitSource {
self.remote.get_url()
}
fn packages(&self) -> CargoResult<Vec<Package>> {
ops::read_packages(&self.checkout_path, &self.id)
}
}
fn ident(url: &Url) -> String {
@ -97,34 +102,27 @@ impl Source for GitSource {
fn list(&self) -> CargoResult<Vec<Summary>> {
log!(5, "listing summaries in git source `{}`", self.remote);
let pkg = try!(read_manifest(&self.checkout_path, &self.id));
Ok(vec!(pkg.get_summary().clone()))
let pkgs = try!(self.packages());
Ok(pkgs.iter().map(|p| p.get_summary().clone()).collect())
}
fn download(&self, _: &[PackageId]) -> CargoResult<()> {
Ok(())
}
fn get(&self, package_ids: &[PackageId]) -> CargoResult<Vec<Package>> {
log!(5, "getting packages for package ids `{}` from `{}`", package_ids, self.remote);
fn get(&self, ids: &[PackageId]) -> CargoResult<Vec<Package>> {
log!(5, "getting packages for package ids `{}` from `{}`", ids, self.remote);
// TODO: Support multiple manifests per repo
let pkg = try!(read_manifest(&self.checkout_path, &self.id));
let pkgs = try!(self.packages());
if package_ids.iter().any(|pkg_id| pkg_id == pkg.get_package_id()) {
Ok(vec!(pkg))
} else {
Ok(vec!())
}
Ok(pkgs.iter()
.filter(|pkg| ids.iter().any(|id| pkg.get_package_id() == id))
.map(|pkg| pkg.clone())
.collect())
}
}
fn read_manifest(path: &Path, source_id: &SourceId) -> CargoResult<Package> {
let path = path.join("Cargo.toml");
// TODO: recurse
let (pkg, _) = try!(ops::read_package(&path, source_id));
Ok(pkg)
}
#[cfg(test)]
mod test {
use url;

View file

@ -2,8 +2,7 @@ use std::fmt;
use std::fmt::{Show,Formatter};
use core::{Package,PackageId,Summary,SourceId,Source};
use ops;
use url;
use util::{CargoResult,simple_human,io_error,realpath};
use util::{CargoResult,simple_human};
pub struct PathSource {
id: SourceId,
@ -33,12 +32,6 @@ impl PathSource {
}
}
/*
pub fn get_path<'a>(&'a self) -> &'a Path {
&self.path
}
*/
pub fn get_root_package(&self) -> CargoResult<Package> {
log!(5, "get_root_package; source={}", self);
@ -49,14 +42,8 @@ impl PathSource {
}
fn packages(&self) -> CargoResult<Vec<Package>> {
find_packages(&self.path, &self.id)
ops::read_packages(&self.path, &self.id)
}
/*
fn get_root_manifest_path(&self) -> Path {
self.path.join("Cargo.toml")
}
*/
}
impl Show for PathSource {
@ -91,20 +78,3 @@ impl Source for PathSource {
.collect())
}
}
fn find_packages(path: &Path, source_id: &SourceId) -> CargoResult<Vec<Package>> {
let (pkg, nested) = try!(ops::read_package(&path.join("Cargo.toml"), source_id));
let mut ret = vec!(pkg);
for path in nested.iter() {
ret.push_all(try!(find_packages(path, source_id)).as_slice());
}
Ok(ret)
}
fn namespace(path: &Path) -> CargoResult<url::Url> {
let real = try!(realpath(path).map_err(io_error));
url::from_str(format!("file://{}", real.display()).as_slice()).map_err(|err|
simple_human(err.as_slice()))
}

View file

@ -77,3 +77,77 @@ test!(cargo_compile_simple_git_dep {
cargo::util::process("foo").extra_path(project.root().join("target")),
execs().with_stdout("hello world\n"));
})
test!(cargo_compile_with_nested_paths {
let git_project = git_repo("dep1", |project| {
project
.file("Cargo.toml", r#"
[project]
name = "dep1"
version = "0.5.0"
authors = ["carlhuda@example.com"]
[dependencies.dep2]
version = "0.5.0"
path = "vendor/dep2"
[[lib]]
name = "dep1"
"#)
.file("src/dep1.rs", r#"
extern crate dep2;
pub fn hello() -> &'static str {
dep2::hello()
}
"#)
.file("vendor/dep2/Cargo.toml", r#"
[project]
name = "dep2"
version = "0.5.0"
authors = ["carlhuda@example.com"]
[[lib]]
name = "dep2"
"#)
.file("vendor/dep2/src/dep2.rs", r#"
pub fn hello() -> &'static str {
"hello world"
}
"#)
}).assert();
let p = project("parent")
.file("Cargo.toml", format!(r#"
[project]
name = "parent"
version = "0.5.0"
authors = ["wycats@example.com"]
[dependencies.dep1]
version = "0.5.0"
git = "file://{}"
[[bin]]
name = "parent"
"#, git_project.root().display()))
.file("src/parent.rs", main_file(r#""{}", dep1::hello()"#, ["dep1"]).as_slice());
p.cargo_process("cargo-compile")
.exec_with_output()
.assert();
assert_that(&p.root().join("target/parent"), existing_file());
assert_that(
cargo::util::process("parent").extra_path(p.root().join("target")),
execs().with_stdout("hello world\n"));
})

View file

@ -1,17 +1,13 @@
use support::{ProjectBuilder,ResultTest,project,execs,main_file};
use support::{ResultTest,project,execs,main_file};
use hamcrest::{assert_that,existing_file};
use cargo;
use cargo::util::{CargoResult,process};
use cargo::util::{process};
fn setup() {
}
test!(cargo_compile_with_nested_deps_shorthand {
let mut p = project("foo");
let bar = p.root().join("bar");
let baz = p.root().join("baz");
p = p
let p = project("foo")
.file("Cargo.toml", r#"
[project]
@ -52,7 +48,7 @@ test!(cargo_compile_with_nested_deps_shorthand {
baz::gimme()
}
"#)
.file("baz/Cargo.toml", r#"
.file("bar/baz/Cargo.toml", r#"
[project]
name = "baz"
@ -63,7 +59,7 @@ test!(cargo_compile_with_nested_deps_shorthand {
name = "baz"
"#)
.file("baz/src/baz.rs", r#"
.file("bar/baz/src/baz.rs", r#"
pub fn gimme() -> String {
"test passed".to_str()
}