aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md2
-rw-r--r--codegen/src/lib.rs41
-rw-r--r--example/Cargo.toml6
-rw-r--r--example/build.rs13
-rw-r--r--lib/src/lib.rs13
5 files changed, 58 insertions, 17 deletions
diff --git a/README.md b/README.md
index 77f6fbf..3070360 100644
--- a/README.md
+++ b/README.md
@@ -13,7 +13,7 @@ Include a directory in your Rust binary, e.g. static files for your web server o
* [x] Use [rust-phf](https://github.com/sfackler/rust-phf) for efficient lookup
* [x] Wrapping API around the phf map, to abstract away additional features
* [x] Compression, with optional crate "flate2"
-* [ ] Reading from source files for debug builds
+* [x] Reading from source files for debug builds
## Example
diff --git a/codegen/src/lib.rs b/codegen/src/lib.rs
index e8a6475..2cd9392 100644
--- a/codegen/src/lib.rs
+++ b/codegen/src/lib.rs
@@ -2,7 +2,7 @@ extern crate walkdir;
extern crate phf_codegen;
extern crate flate2;
-use std::{fmt, env, io};
+use std::{env, fmt, io};
use std::borrow::{Borrow, Cow};
use std::collections::HashMap;
use std::fs::{self, File};
@@ -13,10 +13,11 @@ use walkdir::WalkDir;
use flate2::FlateWriteExt;
-#[derive(Copy, Clone, Debug)]
+#[derive(Copy, Clone, PartialEq, Eq, Debug)]
pub enum Compression {
None,
Gzip,
+ Passthrough,
}
impl fmt::Display for Compression {
@@ -24,6 +25,7 @@ impl fmt::Display for Compression {
match *self {
Compression::None => fmt.write_str("None"),
Compression::Gzip => fmt.write_str("Gzip"),
+ Compression::Passthrough => panic!("Should not be called"),
}
}
}
@@ -31,12 +33,14 @@ impl fmt::Display for Compression {
pub struct IncludeDir {
files: HashMap<String, (Compression, PathBuf)>,
name: String,
+ passthrough: bool,
}
pub fn start(static_name: &str) -> IncludeDir {
IncludeDir {
files: HashMap::new(),
name: static_name.to_owned(),
+ passthrough: false,
}
}
@@ -51,6 +55,12 @@ fn as_key(path: &str) -> Cow<str> {
}
impl IncludeDir {
+ /// Don't include any data, but read from the source directory instead.
+ pub fn passthrough(&mut self) -> &mut IncludeDir {
+ self.passthrough = true;
+ self
+ }
+
/// Add a single file to the binary.
/// With Gzip compression, the file will be encoded to OUT_DIR first.
/// For chaining, it's not sensible to return a Result. If any to-be-included
@@ -65,7 +75,13 @@ impl IncludeDir {
/// This function panics when CARGO_MANIFEST_DIR or OUT_DIR are not defined.
pub fn add_file<P: AsRef<Path>>(&mut self, path: P, comp: Compression) -> io::Result<()> {
let key = path.as_ref().to_string_lossy();
+
match comp {
+ c if self.passthrough || c == Compression::Passthrough => {
+ self.files.insert(as_key(key.borrow()).into_owned(),
+ (Compression::Passthrough, PathBuf::new()));
+
+ }
Compression::None => {
self.files.insert(as_key(key.borrow()).into_owned(),
(comp, path.as_ref().clone().to_owned()));
@@ -85,6 +101,7 @@ impl IncludeDir {
self.files.insert(as_key(key.borrow()).into_owned(),
(comp, out_path.to_owned()));
}
+ _ => unreachable!(),
}
Ok(())
}
@@ -122,17 +139,23 @@ impl IncludeDir {
\tfiles: ",
self.name));
- let entries: Vec<_> = self.files //accumulate_entries()
+ let entries: Vec<_> = self.files
.iter()
.map(|(name, &(ref comp, ref path))| {
let include_path = format!("{}",
base_path.join(path).display());
- let code = format!("(Compression::{}, \
- include_bytes!(\"{}\") as &'static \
- [u8])",
- comp,
- as_key(&include_path));
- (as_key(&name).into_owned(), code)
+ if comp == &Compression::Passthrough {
+ (as_key(&name).into_owned(),
+ "(Compression::Passthrough, &[] as &'static [u8])"
+ .to_owned())
+ } else {
+ let code = format!("(Compression::{}, \
+ include_bytes!(\"{}\") as &'static \
+ [u8])",
+ comp,
+ as_key(&include_path));
+ (as_key(&name).into_owned(), code)
+ }
})
.collect();
let mut map: phf_codegen::Map<&str> = phf_codegen::Map::new();
diff --git a/example/Cargo.toml b/example/Cargo.toml
index c7c6496..3d3cbd5 100644
--- a/example/Cargo.toml
+++ b/example/Cargo.toml
@@ -8,7 +8,9 @@ publish = false
[dependencies]
phf = "0.7.12"
-includedir = "0.2.0"
+# includedir = "0.2.0"
+includedir = { path = "../lib" }
[build-dependencies]
-includedir_codegen = "0.2.0"
+# includedir_codegen = "0.2.0"
+includedir_codegen = { path = "../codegen" }
diff --git a/example/build.rs b/example/build.rs
index fb23001..c13f035 100644
--- a/example/build.rs
+++ b/example/build.rs
@@ -1,10 +1,15 @@
extern crate includedir_codegen;
+use std::env;
+
use includedir_codegen::Compression;
fn main() {
- includedir_codegen::start("FILES")
- .dir("data", Compression::Gzip)
- .build("data.rs")
- .unwrap();
+ let mut cg = includedir_codegen::start("FILES");
+ if env::var("PASSTHROUGH").is_ok() {
+ cg.passthrough();
+ }
+ cg.dir("data", Compression::Gzip)
+ .build("data.rs")
+ .unwrap();
}
diff --git a/lib/src/lib.rs b/lib/src/lib.rs
index 20078a2..ce1e2ec 100644
--- a/lib/src/lib.rs
+++ b/lib/src/lib.rs
@@ -4,7 +4,8 @@ extern crate phf;
extern crate flate2;
use std::borrow::{Borrow, Cow};
-use std::io::{self, Cursor, Error, ErrorKind, Read};
+use std::io::{self, BufReader, Cursor, Error, ErrorKind, Read};
+use std::fs::File;
#[cfg(feature = "flate2")]
use flate2::FlateReadExt;
@@ -12,6 +13,7 @@ use flate2::FlateReadExt;
pub enum Compression {
None,
Gzip,
+ Passthrough,
}
/// Runtime access to the included files
@@ -50,6 +52,12 @@ impl Files {
}
#[cfg(not(feature = "flate2"))]
Compression::Gzip => panic!("Feature 'flate2' not enabled"),
+ Compression::Passthrough => {
+ let mut r = BufReader::new(try!(File::open(path)));
+ let mut v = Vec::new();
+ try!(r.read_to_end(&mut v));
+ Ok(Cow::Owned(v))
+ }
}
}
None => Err(Error::new(ErrorKind::NotFound, "Key not found")),
@@ -66,6 +74,9 @@ impl Files {
Compression::Gzip => Ok(Box::new(try!(Cursor::new(b.1).gz_decode()))),
#[cfg(not(feature = "flate2"))]
Compression::Gzip => panic!("Feature 'flate2' not enabled"),
+ Compression::Passthrough => {
+ Ok(Box::new(BufReader::new(try!(File::open(path)))))
+ }
}
}
None => Err(Error::new(ErrorKind::NotFound, "Key not found")),