From 779ac244658d7641458ad669620c02f71037a8d3 Mon Sep 17 00:00:00 2001 From: MHamill98 <53518452+MHamill98@users.noreply.github.com> Date: Sat, 10 Aug 2019 23:12:06 +0100 Subject: Added function to tag an image (#187) * Added function to tag an image * Removed debug and println --- examples/imagetag.rs | 27 +++++++++++++++++++++++ src/builder.rs | 60 ++++++++++++++++++++++++++++++++++++++++++++++++++++ src/lib.rs | 14 +++++++++++- 3 files changed, 100 insertions(+), 1 deletion(-) create mode 100644 examples/imagetag.rs diff --git a/examples/imagetag.rs b/examples/imagetag.rs new file mode 100644 index 0000000..7ae78dd --- /dev/null +++ b/examples/imagetag.rs @@ -0,0 +1,27 @@ +// cargo run --example imagetag img repo tag + +use shiplift::{Docker, Image, TagOptions}; +use std::env; +use tokio::prelude::Future; + +fn main() { + env_logger::init(); + let docker = Docker::new(); + let img = env::args() + .nth(1) + .expect("You need to specify an image name"); + + let repo = env::args() + .nth(2) + .expect("You need to specify a repository name"); + + let tag = env::args().nth(3).expect("You need to specify a tag name"); + + let tag_opts = TagOptions::builder().repo(repo).tag(tag).build(); + + let image = Image::new(&docker, img); + + let fut = image.tag(&tag_opts).map_err(|e| eprintln!("Error: {}", e)); + + tokio::run(fut); +} diff --git a/src/builder.rs b/src/builder.rs index 58bca53..ea9bd32 100644 --- a/src/builder.rs +++ b/src/builder.rs @@ -118,6 +118,66 @@ impl RegistryAuthBuilder { } } +#[derive(Default, Debug)] +pub struct TagOptions { + pub params: HashMap<&'static str, String>, +} + +impl TagOptions { + /// return a new instance of a builder for options + pub fn builder() -> TagOptionsBuilder { + TagOptionsBuilder::default() + } + + /// serialize options as a string. returns None if no options are defined + pub fn serialize(&self) -> Option { + if self.params.is_empty() { + None + } else { + Some( + form_urlencoded::Serializer::new(String::new()) + .extend_pairs(&self.params) + .finish(), + ) + } + } +} + +#[derive(Default)] +pub struct TagOptionsBuilder { + params: HashMap<&'static str, String>, +} + +impl TagOptionsBuilder { + pub fn repo( + &mut self, + r: R, + ) -> &mut Self + where + R: Into, + { + self.params.insert("repo", r.into()); + self + } + + pub fn tag( + &mut self, + t: T, + ) -> &mut Self + where + T: Into, + { + self.params.insert("tag", t.into()); + self + } + + pub fn build(&self) -> TagOptions { + TagOptions { + params: self.params.clone(), + } + } +} + #[derive(Default, Debug)] pub struct PullOptions { auth: Option, diff --git a/src/lib.rs b/src/lib.rs index 669ac42..061b431 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -30,7 +30,7 @@ pub use crate::{ BuildOptions, ContainerConnectionOptions, ContainerFilter, ContainerListOptions, ContainerOptions, EventsOptions, ExecContainerOptions, ImageFilter, ImageListOptions, LogsOptions, NetworkCreateOptions, NetworkListOptions, PullOptions, RegistryAuth, - RmContainerOptions, VolumeCreateOptions, + RmContainerOptions, TagOptions, VolumeCreateOptions, }, errors::Error, }; @@ -113,6 +113,18 @@ impl<'a, 'b> Image<'a, 'b> { .stream_get(&format!("/images/{}/get", self.name)[..]) .map(|c| c.to_vec()) } + + /// Adds a tag to an image + pub fn tag( + &self, + opts: &TagOptions, + ) -> impl Future { + let mut path = vec![format!("/images/{}/tag", self.name)]; + if let Some(query) = opts.serialize() { + path.push(query) + } + self.docker.post::(&path.join("?"), None).map(|_| ()) + } } /// Interface for docker images -- cgit v1.2.3