diff options
author | Keir Lawson <keirlawson@gmail.com> | 2019-05-18 02:45:24 +0100 |
---|---|---|
committer | Doug Tangren <d.tangren@gmail.com> | 2019-05-17 21:45:24 -0400 |
commit | e5258c8e63f09ef7aafc7e489bb62131eb34a74f (patch) | |
tree | 83e4d91889c8f300e2316d1529de3f0971690b12 | |
parent | e97bf7175ddf063788df2fa630b4dedcd19388a0 (diff) |
Add import functionality (#165)
-rw-r--r-- | examples/import.rs | 24 | ||||
-rw-r--r-- | src/lib.rs | 31 |
2 files changed, 51 insertions, 4 deletions
diff --git a/examples/import.rs b/examples/import.rs new file mode 100644 index 0000000..20c61e6 --- /dev/null +++ b/examples/import.rs @@ -0,0 +1,24 @@ +use shiplift::Docker; +use std::{env, fs::File}; +use tokio::prelude::{Future, Stream}; + +fn main() { + let docker = Docker::new(); + let path = env::args() + .nth(1) + .expect("You need to specify an image path"); + let f = File::open(path).expect("Unable to open file"); + + let reader = Box::from(f); + + let fut = docker + .images() + .import(reader) + .for_each(|output| { + println!("{:?}", output); + Ok(()) + }) + .map_err(|e| eprintln!("Error: {}", e)); + + tokio::run(fut); +} @@ -55,7 +55,7 @@ use mime::Mime; #[cfg(feature = "tls")] use openssl::ssl::{SslConnector, SslFiletype, SslMethod}; use serde_json::Value; -use std::{borrow::Cow, env, iter, path::Path, time::Duration}; +use std::{borrow::Cow, env, io::Read, iter, path::Path, time::Duration}; use tokio_codec::{FramedRead, LinesCodec}; use url::form_urlencoded; @@ -230,9 +230,32 @@ impl<'a> Images<'a> { .map(|c| c.to_vec()) } - // pub fn import(self, tarball: Box<Read>) -> Result<()> { - // self.docker.post - // } + /// imports an image or set of images from a given tarball source + /// source can be uncompressed on compressed via gzip, bzip2 or xz + pub fn import( + self, + mut tarball: Box<Read>, + ) -> impl Stream<Item = Value, Error = Error> { + let mut bytes = Vec::new(); + + match tarball.read_to_end(&mut bytes) { + Ok(_) => Box::new( + self.docker + .stream_post( + "/images/load", + Some((Body::from(bytes), tar())), + None::<iter::Empty<_>>, + ) + .and_then(|bytes| { + serde_json::from_slice::<'_, Value>(&bytes[..]) + .map_err(Error::from) + .into_future() + }), + ) as Box<Stream<Item = Value, Error = Error> + Send>, + Err(e) => Box::new(futures::future::err(Error::IO(e)).into_stream()) + as Box<Stream<Item = Value, Error = Error> + Send>, + } + } } /// Interface for accessing and manipulating a docker container |