panty 0.7.1

Fast gVim summoner
Documentation

use rustc_serialize::json;
use std::io::{Read, Write};
use unix_socket::{UnixListener, UnixStream};
use std::net::Shutdown;
use std::thread;

use summoner;
use collector;
use broadcaster;
use spell::Spell::*;
use gvim::SpawnOptions;



pub fn meditate(stocks: collector::Stocks, max_stocks: usize, socket_filepath: &str, spawn_options: SpawnOptions) {
    let listener = UnixListener::bind(socket_filepath).unwrap();

    for stream in listener.incoming() {
        let spawn_options = spawn_options.clone();

        match stream {
            Ok(mut stream) => {
                let mut buf: String = "".to_string();
                match stream.read_to_string(&mut buf).unwrap() {
                    _ => {
                        match json::decode(buf.as_str()).expect("Fail: json::decode") {
                            Summon {files, keys, expressions, role, nofork} =>
                                summon(
                                    stocks.clone(),
                                    summoner::SummonOptions {files: files, role: role, keys: keys, expressions: expressions},
                                    spawn_options,
                                    nofork,
                                    stream),
                            Broadcast {keys, expressions, conditions} => {
                                let stocks = stocks.clone();
                                thread::spawn(move || {
                                    let output = broadcaster::broadcast(stocks, conditions, keys, expressions);
                                    stream.write(output.as_bytes()).unwrap();
                                });
                            }
                            Renew =>
                                collector::renew(stocks.clone(), max_stocks, spawn_options),
                            Clean =>
                                collector::clean(stocks.clone())
                        }
                    }
                }
            }
            Err(err) => {
                error!("Error: {}", err);
                break;
            }
        }
    }

    drop(listener);
}


fn summon(stocks: collector::Stocks, summon_options: summoner::SummonOptions, spawn_options: SpawnOptions, nofork: bool, mut stream: UnixStream) {
    let stock = collector::emit(stocks.clone());
    let mut stdout_reader = stock.stdout_reader;
    let servername = stock.servername;

    summoner::summon(servername.clone(), stock.window, summon_options);
    collector::collect(stocks.clone(), 1, spawn_options);

    if nofork {
        thread::spawn(move || {
            let mut output = String::new();
            stdout_reader.read_to_string(&mut output).unwrap();
            stream.write_fmt(format_args!("{}\n", servername)).unwrap();
            stream.shutdown(Shutdown::Both).unwrap();
        });
    } else {
        stream.write_fmt(format_args!("{}\n", servername)).unwrap();
        stream.shutdown(Shutdown::Both).unwrap();
    }
}