Implement finding files by name

Resolves #2
This commit is contained in:
Mathijs van de Nes 2014-11-22 19:28:00 +01:00
parent ee6e830203
commit bdda4310e4
4 changed files with 45 additions and 3 deletions

View file

@ -1,7 +1,7 @@
[package]
name = "zip"
version = "0.0.2"
version = "0.0.3"
authors = ["Mathijs van de Nes <git@mathijs.vd-nes.nl>"]
license = "MIT"
repository = "https://github.com/mvdnes/zip-rs.git"
@ -19,6 +19,11 @@ name = "extract"
test = false
doc = false
[[bin]]
name = "extract_lorem"
test = false
doc = false
[[bin]]
name = "write_sample"
test = false

25
src/bin/extract_lorem.rs Normal file
View file

@ -0,0 +1,25 @@
extern crate zip;
fn main()
{
let args = std::os::args();
if args.len() < 2 {
println!("Usage: {} <filename>", args[0]);
std::os::set_exit_status(1);
return;
}
let fname = Path::new(args[1].as_slice());
let file = std::io::File::open(&fname).unwrap();
let zipcontainer = zip::ZipReader::new(file).unwrap();
let file = match zipcontainer.get("test/lorem_ipsum.txt")
{
Some(file) => file,
None => { println!("File test/lorem_ipsum.txt not found"); return }
};
let data = zipcontainer.read_file(file).unwrap().read_to_end().unwrap();
let contents = String::from_utf8(data).unwrap();
println!("{}", contents);
}

View file

@ -6,6 +6,7 @@ use reader_spec;
use result::{ZipResult, ZipError};
use std::io;
use std::cell::RefCell;
use std::collections::HashMap;
use flate2::FlateReader;
use bzip2::reader::BzDecompressor;
@ -37,6 +38,7 @@ pub struct ZipReader<T>
{
inner: RefCell<T>,
files: Vec<ZipFile>,
names_map: HashMap<String, uint>,
}
fn unsupported_zip_error<T>(detail: &'static str) -> ZipResult<T>
@ -57,14 +59,17 @@ impl<T: Reader+Seek> ZipReader<T>
let number_of_files = footer.number_of_files_on_this_disk as uint;
let mut files = Vec::with_capacity(number_of_files);
let mut names_map = HashMap::new();
try!(reader.seek(directory_start, io::SeekSet));
for _ in range(0, number_of_files)
{
files.push(try!(reader_spec::central_header_to_zip_file(&mut reader)));
let file = try!(reader_spec::central_header_to_zip_file(&mut reader));
names_map.insert(file.file_name.clone(), files.len());
files.push(file);
}
Ok(ZipReader { inner: RefCell::new(reader), files: files })
Ok(ZipReader { inner: RefCell::new(reader), files: files, names_map: names_map })
}
/// An iterator over the information of all contained files.
@ -73,6 +78,12 @@ impl<T: Reader+Seek> ZipReader<T>
self.files.as_slice().iter()
}
/// Search for a file entry by name
pub fn get(&self, name: &str) -> Option<&ZipFile>
{
self.names_map.get(name).map(|index| &self.files[*index])
}
/// Gets a reader for a contained zipfile.
///
/// May return `ReaderUnavailable` if there is another reader borrowed.

View file

@ -2,6 +2,7 @@
use time;
#[deriving(Clone)]
/// Structure representing a ZIP file.
pub struct ZipFile
{