kubernetes 0.2.0

A Kubernetes client library for Rust
Documentation
extern crate failure;
extern crate futures;
extern crate hyper;
extern crate hyper_tls;
extern crate kubernetes;
extern crate serde_json;
#[macro_use]
extern crate log;
extern crate pretty_env_logger;

use failure::Error;
use futures::prelude::*;
use hyper::rt;
use std::result::Result;

use kubernetes::api;
use kubernetes::api::core::v1::{ContainerState, Pod, PodList};
use kubernetes::api::meta::v1::{EventType, ListOptions};
use kubernetes::client::Client;

fn print_pod_state(p: &Pod) {
    println!(
        "pod {} - {:?}",
        p.metadata
            .name
            .as_ref()
            .map(String::as_str)
            .unwrap_or("(no name)"),
        p.status.phase.unwrap_or(api::core::v1::PodPhase::Unknown)
    );
    let c_statuses = p
        .status
        .init_container_statuses
        .iter()
        .chain(p.status.container_statuses.iter());
    for c in c_statuses {
        print!("  -> {}: ", c.name);
        match c.state {
            None => println!("state unknown"),
            Some(ContainerState::Waiting(ref s)) => {
                println!(
                    "waiting: {}",
                    s.message
                        .as_ref()
                        .or(s.reason.as_ref())
                        .map(String::as_str)
                        .unwrap_or("waiting")
                );
            }
            Some(ContainerState::Running(ref s)) => {
                print!("running");
                if let Some(ref t) = s.started_at {
                    print!(" since {}", t);
                }
                println!("");
            }
            Some(ContainerState::Terminated(ref s)) => {
                if let Some(ref msg) = s.message {
                    println!("terminated: {}", msg);
                } else {
                    print!("exited with code {}", s.exit_code);
                    if let Some(ref t) = s.finished_at {
                        print!(" at {}", t);
                    }
                    println!("");
                }
            }
        }
    }
}

fn main_() -> Result<(), Error> {
    let client = Client::new()?;

    let pods = api::core::v1::GROUP_VERSION.with_resource("pods");
    let namespace = Some("kube-system");

    let work = client
        .list(&pods, namespace, Default::default())
        .inspect(|podlist: &PodList| {
            podlist.items.iter().for_each(print_pod_state);
        })
        .and_then(move |podlist: PodList| {
            debug!(
                "Starting at resource version {}",
                podlist.metadata.resource_version
            );

            let listopts = ListOptions {
                resource_version: podlist.metadata.resource_version,
                ..Default::default()
            };
            client
                .watch_list(&pods, namespace, listopts)
                .for_each(|event| {
                    match event.typ {
                        EventType::Added | EventType::Modified => {
                            let p: Pod = serde_json::from_value(event.object)?;
                            print_pod_state(&p);
                        }
                        EventType::Deleted => {
                            let p: Pod = serde_json::from_value(event.object)?;
                            println!("deleted {}", p.metadata.name.unwrap_or("(no name)".into()));
                        }
                        EventType::Error => debug!("Ignoring error event {:#?}", event.object),
                    }
                    Ok(())
                })
        });

    rt::run(work.map_err(|err| panic!("Error: {}", err)));

    Ok(())
}

fn main() {
    pretty_env_logger::init();
    let status = match main_() {
        Ok(_) => 0,
        Err(e) => {
            eprintln!("Error: {}", e);
            for c in e.iter_chain().skip(1) {
                eprintln!(" Caused by {}", c);
            }
            debug!("Backtrace: {}", e.backtrace());
            1
        }
    };
    ::std::process::exit(status);
}