pub struct ZipWriter<W: Write + Seek> { /* private fields */ }
Expand description
ZIP archive generator
Handles the bookkeeping involved in building an archive, and provides an API to edit its contents.
use std::io::Write;
use zip::write::SimpleFileOptions;
// We use a buffer here, though you'd normally use a `File`
let mut buf = [0; 65536];
let mut zip = ZipWriter::new(std::io::Cursor::new(&mut buf[..]));
let options = SimpleFileOptions::default().compression_method(zip::CompressionMethod::Stored);
zip.start_file("hello_world.txt", options)?;
zip.write(b"Hello, World!")?;
// Apply the changes you've made.
// Dropping the `ZipWriter` will have the same effect, but may silently fail
zip.finish()?;
Implementations§
Source§impl<A: Read + Write + Seek> ZipWriter<A>
impl<A: Read + Write + Seek> ZipWriter<A>
Sourcepub fn new_append(readwriter: A) -> ZipResult<ZipWriter<A>>
pub fn new_append(readwriter: A) -> ZipResult<ZipWriter<A>>
Initializes the archive from an existing ZIP archive, making it ready for append.
This uses a default configuration to initially read the archive.
Sourcepub fn new_append_with_config(
config: Config,
readwriter: A,
) -> ZipResult<ZipWriter<A>>
pub fn new_append_with_config( config: Config, readwriter: A, ) -> ZipResult<ZipWriter<A>>
Initializes the archive from an existing ZIP archive, making it ready for append.
This uses the given read configuration to initially read the archive.
Sourcepub fn set_flush_on_finish_file(&mut self, flush_on_finish_file: bool)
pub fn set_flush_on_finish_file(&mut self, flush_on_finish_file: bool)
flush_on_finish_file
is designed to support a streaming inner
that may unload flushed
bytes. It flushes a file’s header and body once it starts writing another file. A ZipWriter
will not try to seek back into where a previous file was written unless
either ZipWriter::abort_file
is called while ZipWriter::is_writing_file
returns
false, or ZipWriter::deep_copy_file
is called. In the latter case, it will only need to
read previously-written files and not overwrite them.
Note: when using an inner
that cannot overwrite flushed bytes, do not wrap it in a
BufWriter, because that has a Seek::seek method that implicitly calls
BufWriter::flush, and ZipWriter needs to seek backward to update each file’s header with
the size and checksum after writing the body.
This setting is false by default.
Source§impl<A: Read + Write + Seek> ZipWriter<A>
impl<A: Read + Write + Seek> ZipWriter<A>
Sourcepub fn deep_copy_file(
&mut self,
src_name: &str,
dest_name: &str,
) -> ZipResult<()>
pub fn deep_copy_file( &mut self, src_name: &str, dest_name: &str, ) -> ZipResult<()>
Adds another copy of a file already in this archive. This will produce a larger but more widely-compatible archive compared to Self::shallow_copy_file. Does not copy alignment.
Sourcepub fn deep_copy_file_from_path<T: AsRef<Path>, U: AsRef<Path>>(
&mut self,
src_path: T,
dest_path: U,
) -> ZipResult<()>
pub fn deep_copy_file_from_path<T: AsRef<Path>, U: AsRef<Path>>( &mut self, src_path: T, dest_path: U, ) -> ZipResult<()>
Like deep_copy_file
, but uses Path arguments.
This function ensures that the ‘/’ path separator is used and normalizes .
and ..
. It
ignores any ..
or Windows drive letter that would produce a path outside the ZIP file’s
root.
Sourcepub fn finish_into_readable(self) -> ZipResult<ZipArchive<A>>
pub fn finish_into_readable(self) -> ZipResult<ZipArchive<A>>
Write the zip file into the backing stream, then produce a readable archive of that data.
This method avoids parsing the central directory records at the end of the stream for
a slight performance improvement over running ZipArchive::new()
on the output of
Self::finish()
.
use std::io::{Cursor, prelude::*};
use zip::{ZipArchive, ZipWriter, write::SimpleFileOptions};
let buf = Cursor::new(Vec::new());
let mut zip = ZipWriter::new(buf);
let options = SimpleFileOptions::default();
zip.start_file("a.txt", options)?;
zip.write_all(b"hello\n")?;
let mut zip = zip.finish_into_readable()?;
let mut s: String = String::new();
zip.by_name("a.txt")?.read_to_string(&mut s)?;
assert_eq!(s, "hello\n");
Source§impl<W: Write + Seek> ZipWriter<W>
impl<W: Write + Seek> ZipWriter<W>
Sourcepub fn new(inner: W) -> ZipWriter<W> ⓘ
pub fn new(inner: W) -> ZipWriter<W> ⓘ
Initializes the archive.
Before writing to this object, the ZipWriter::start_file
function should be called.
After a successful write, the file remains open for writing. After a failed write, call
ZipWriter::is_writing_file
to determine if the file remains open.
Sourcepub const fn is_writing_file(&self) -> bool
pub const fn is_writing_file(&self) -> bool
Returns true if a file is currently open for writing.
Sourcepub fn set_comment<S>(&mut self, comment: S)
pub fn set_comment<S>(&mut self, comment: S)
Set ZIP archive comment.
Sourcepub fn set_raw_comment(&mut self, comment: Box<[u8]>)
pub fn set_raw_comment(&mut self, comment: Box<[u8]>)
Set ZIP archive comment.
This sets the raw bytes of the comment. The comment is typically expected to be encoded in UTF-8.
Sourcepub fn get_comment(&mut self) -> Result<&str, Utf8Error>
pub fn get_comment(&mut self) -> Result<&str, Utf8Error>
Get ZIP archive comment.
Sourcepub const fn get_raw_comment(&self) -> &[u8] ⓘ
pub const fn get_raw_comment(&self) -> &[u8] ⓘ
Get ZIP archive comment.
This returns the raw bytes of the comment. The comment is typically expected to be encoded in UTF-8.
Sourcepub fn abort_file(&mut self) -> ZipResult<()>
pub fn abort_file(&mut self) -> ZipResult<()>
Removes the file currently being written from the archive if there is one, or else removes the file most recently written.
Sourcepub fn start_file<S: ToString, T: FileOptionExtension>(
&mut self,
name: S,
options: FileOptions<'_, T>,
) -> ZipResult<()>
pub fn start_file<S: ToString, T: FileOptionExtension>( &mut self, name: S, options: FileOptions<'_, T>, ) -> ZipResult<()>
Sourcepub fn merge_archive<R>(&mut self, source: ZipArchive<R>) -> ZipResult<()>
pub fn merge_archive<R>(&mut self, source: ZipArchive<R>) -> ZipResult<()>
Copy over the entire contents of another archive verbatim.
This method extracts file metadata from the source
archive, then simply performs a single
big io::copy()
to transfer all the actual file contents without any
decompression or decryption. This is more performant than the equivalent operation of
calling Self::raw_copy_file()
for each entry from the source
archive in sequence.
use std::io::{Cursor, prelude::*};
use zip::{ZipArchive, ZipWriter, write::SimpleFileOptions};
let buf = Cursor::new(Vec::new());
let mut zip = ZipWriter::new(buf);
zip.start_file("a.txt", SimpleFileOptions::default())?;
zip.write_all(b"hello\n")?;
let src = ZipArchive::new(zip.finish()?)?;
let buf = Cursor::new(Vec::new());
let mut zip = ZipWriter::new(buf);
zip.start_file("b.txt", SimpleFileOptions::default())?;
zip.write_all(b"hey\n")?;
let src2 = ZipArchive::new(zip.finish()?)?;
let buf = Cursor::new(Vec::new());
let mut zip = ZipWriter::new(buf);
zip.merge_archive(src)?;
zip.merge_archive(src2)?;
let mut result = ZipArchive::new(zip.finish()?)?;
let mut s: String = String::new();
result.by_name("a.txt")?.read_to_string(&mut s)?;
assert_eq!(s, "hello\n");
s.clear();
result.by_name("b.txt")?.read_to_string(&mut s)?;
assert_eq!(s, "hey\n");
Sourcepub fn start_file_from_path<E: FileOptionExtension, P: AsRef<Path>>(
&mut self,
path: P,
options: FileOptions<'_, E>,
) -> ZipResult<()>
pub fn start_file_from_path<E: FileOptionExtension, P: AsRef<Path>>( &mut self, path: P, options: FileOptions<'_, E>, ) -> ZipResult<()>
Starts a file, taking a Path as argument.
This function ensures that the ‘/’ path separator is used and normalizes .
and ..
. It
ignores any ..
or Windows drive letter that would produce a path outside the ZIP file’s
root.
Sourcepub fn raw_copy_file_rename<S: ToString>(
&mut self,
file: ZipFile<'_>,
name: S,
) -> ZipResult<()>
pub fn raw_copy_file_rename<S: ToString>( &mut self, file: ZipFile<'_>, name: S, ) -> ZipResult<()>
Add a new file using the already compressed data from a ZIP file being read and renames it, this
allows faster copies of the ZipFile
since there is no need to decompress and compress it again.
Any ZipFile
metadata is copied and not checked, for example the file CRC.
use std::fs::File;
use std::io::{Read, Seek, Write};
use zip::{ZipArchive, ZipWriter};
fn copy_rename<R, W>(
src: &mut ZipArchive<R>,
dst: &mut ZipWriter<W>,
) -> zip::result::ZipResult<()>
where
R: Read + Seek,
W: Write + Seek,
{
// Retrieve file entry by name
let file = src.by_name("src_file.txt")?;
// Copy and rename the previously obtained file entry to the destination zip archive
dst.raw_copy_file_rename(file, "new_name.txt")?;
Ok(())
}
Sourcepub fn raw_copy_file_to_path<P: AsRef<Path>>(
&mut self,
file: ZipFile<'_>,
path: P,
) -> ZipResult<()>
pub fn raw_copy_file_to_path<P: AsRef<Path>>( &mut self, file: ZipFile<'_>, path: P, ) -> ZipResult<()>
Like raw_copy_file_to_path
, but uses Path arguments.
This function ensures that the ‘/’ path separator is used and normalizes .
and ..
. It
ignores any ..
or Windows drive letter that would produce a path outside the ZIP file’s
root.
Sourcepub fn raw_copy_file(&mut self, file: ZipFile<'_>) -> ZipResult<()>
pub fn raw_copy_file(&mut self, file: ZipFile<'_>) -> ZipResult<()>
Add a new file using the already compressed data from a ZIP file being read, this allows faster
copies of the ZipFile
since there is no need to decompress and compress it again. Any ZipFile
metadata is copied and not checked, for example the file CRC.
use std::fs::File;
use std::io::{Read, Seek, Write};
use zip::{ZipArchive, ZipWriter};
fn copy<R, W>(src: &mut ZipArchive<R>, dst: &mut ZipWriter<W>) -> zip::result::ZipResult<()>
where
R: Read + Seek,
W: Write + Seek,
{
// Retrieve file entry by name
let file = src.by_name("src_file.txt")?;
// Copy the previously obtained file entry to the destination zip archive
dst.raw_copy_file(file)?;
Ok(())
}
Sourcepub fn raw_copy_file_touch(
&mut self,
file: ZipFile<'_>,
last_modified_time: DateTime,
unix_mode: Option<u32>,
) -> ZipResult<()>
pub fn raw_copy_file_touch( &mut self, file: ZipFile<'_>, last_modified_time: DateTime, unix_mode: Option<u32>, ) -> ZipResult<()>
Add a new file using the already compressed data from a ZIP file being read and set the last
modified date and unix mode. This allows faster copies of the ZipFile
since there is no need
to decompress and compress it again. Any ZipFile
metadata other than the last modified date
and the unix mode is copied and not checked, for example the file CRC.
use std::io::{Read, Seek, Write};
use zip::{DateTime, ZipArchive, ZipWriter};
fn copy<R, W>(src: &mut ZipArchive<R>, dst: &mut ZipWriter<W>) -> zip::result::ZipResult<()>
where
R: Read + Seek,
W: Write + Seek,
{
// Retrieve file entry by name
let file = src.by_name("src_file.txt")?;
// Copy the previously obtained file entry to the destination zip archive
dst.raw_copy_file_touch(file, DateTime::default(), Some(0o644))?;
Ok(())
}
Sourcepub fn add_directory<S, T: FileOptionExtension>(
&mut self,
name: S,
options: FileOptions<'_, T>,
) -> ZipResult<()>
pub fn add_directory<S, T: FileOptionExtension>( &mut self, name: S, options: FileOptions<'_, T>, ) -> ZipResult<()>
Add a directory entry.
As directories have no content, you must not call ZipWriter::write
before adding a new file.
Sourcepub fn add_directory_from_path<T: FileOptionExtension, P: AsRef<Path>>(
&mut self,
path: P,
options: FileOptions<'_, T>,
) -> ZipResult<()>
pub fn add_directory_from_path<T: FileOptionExtension, P: AsRef<Path>>( &mut self, path: P, options: FileOptions<'_, T>, ) -> ZipResult<()>
Add a directory entry, taking a Path as argument.
This function ensures that the ‘/’ path separator is used and normalizes .
and ..
. It
ignores any ..
or Windows drive letter that would produce a path outside the ZIP file’s
root.
Sourcepub fn finish(self) -> ZipResult<W>
pub fn finish(self) -> ZipResult<W>
Finish the last file and write all other zip-structures
This will return the writer, but one should normally not append any data to the end of the file. Note that the zipfile will also be finished on drop.
Sourcepub fn add_symlink<N: ToString, T: ToString, E: FileOptionExtension>(
&mut self,
name: N,
target: T,
options: FileOptions<'_, E>,
) -> ZipResult<()>
pub fn add_symlink<N: ToString, T: ToString, E: FileOptionExtension>( &mut self, name: N, target: T, options: FileOptions<'_, E>, ) -> ZipResult<()>
Add a symlink entry.
The zip archive will contain an entry for path name
which is a symlink to target
.
No validation or normalization of the paths is performed. For best results,
callers should normalize \
to /
and ensure symlinks are relative to other
paths within the zip archive.
WARNING: not all zip implementations preserve symlinks on extract. Some zip implementations may materialize a symlink as a regular file, possibly with the content incorrectly set to the symlink target. For maximum portability, consider storing a regular file instead.
Sourcepub fn add_symlink_from_path<P: AsRef<Path>, T: AsRef<Path>, E: FileOptionExtension>(
&mut self,
path: P,
target: T,
options: FileOptions<'_, E>,
) -> ZipResult<()>
pub fn add_symlink_from_path<P: AsRef<Path>, T: AsRef<Path>, E: FileOptionExtension>( &mut self, path: P, target: T, options: FileOptions<'_, E>, ) -> ZipResult<()>
Add a symlink entry, taking Paths to the location and target as arguments.
This function ensures that the ‘/’ path separator is used and normalizes .
and ..
. It
ignores any ..
or Windows drive letter that would produce a path outside the ZIP file’s
root.
Sourcepub fn shallow_copy_file(
&mut self,
src_name: &str,
dest_name: &str,
) -> ZipResult<()>
pub fn shallow_copy_file( &mut self, src_name: &str, dest_name: &str, ) -> ZipResult<()>
Adds another entry to the central directory referring to the same content as an existing entry. The file’s local-file header will still refer to it by its original name, so unzipping the file will technically be unspecified behavior. ZipArchive ignores the filename in the local-file header and treat the central directory as authoritative. However, some other software (e.g. Minecraft) will refuse to extract a file copied this way.
Sourcepub fn shallow_copy_file_from_path<T: AsRef<Path>, U: AsRef<Path>>(
&mut self,
src_path: T,
dest_path: U,
) -> ZipResult<()>
pub fn shallow_copy_file_from_path<T: AsRef<Path>, U: AsRef<Path>>( &mut self, src_path: T, dest_path: U, ) -> ZipResult<()>
Like shallow_copy_file
, but uses Path arguments.
This function ensures that the ‘/’ path separator is used and normalizes .
and ..
. It
ignores any ..
or Windows drive letter that would produce a path outside the ZIP file’s
root.
Trait Implementations§
Source§impl<W: Write + Seek> Write for ZipWriter<W>
impl<W: Write + Seek> Write for ZipWriter<W>
Source§fn write(&mut self, buf: &[u8]) -> Result<usize>
fn write(&mut self, buf: &[u8]) -> Result<usize>
Source§fn flush(&mut self) -> Result<()>
fn flush(&mut self) -> Result<()>
Source§fn is_write_vectored(&self) -> bool
fn is_write_vectored(&self) -> bool
can_vector
)1.0.0 · Source§fn write_all(&mut self, buf: &[u8]) -> Result<(), Error>
fn write_all(&mut self, buf: &[u8]) -> Result<(), Error>
Source§fn write_all_vectored(&mut self, bufs: &mut [IoSlice<'_>]) -> Result<(), Error>
fn write_all_vectored(&mut self, bufs: &mut [IoSlice<'_>]) -> Result<(), Error>
write_all_vectored
)