mirror of
https://github.com/NLnetLabs/krill.git
synced 2026-09-20 08:27:49 +02:00
Parse options for publisher client.
This commit is contained in:
@@ -1,7 +0,0 @@
|
||||
# Speficy the directory where the CLI can find its state, i.e. the keypair used
|
||||
# for its identity, and the publication server xml response
|
||||
state_dir = "./client_state"
|
||||
|
||||
# Specify the directory that the client should synchronise to the server. Note
|
||||
# that this may be overridden with the "-d" command line option.
|
||||
data_dir = "./client_data"
|
||||
+8
-13
@@ -7,22 +7,17 @@
|
||||
|
||||
extern crate rpubd;
|
||||
|
||||
#[macro_use] extern crate lazy_static;
|
||||
|
||||
use rpubd::pubc::config::Config;
|
||||
|
||||
lazy_static! {
|
||||
static ref CONFIG: Config = {
|
||||
match Config::create() {
|
||||
Ok(c) => c,
|
||||
Err(e) => {
|
||||
eprintln!("{}", e);
|
||||
::std::process::exit(1);
|
||||
}
|
||||
fn main() {
|
||||
|
||||
let _c = match Config::create() {
|
||||
Ok(c) => c,
|
||||
Err(e) => {
|
||||
eprintln!("{}", e);
|
||||
::std::process::exit(1);
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
fn main() {
|
||||
println!("Data dir: {}", CONFIG.data_dir());
|
||||
println!("Goodbye cruel world");
|
||||
}
|
||||
+95
-57
@@ -1,6 +1,4 @@
|
||||
use std::fs::File;
|
||||
use std::io;
|
||||
use std::io::Read;
|
||||
use std::path::PathBuf;
|
||||
use clap::{App, Arg};
|
||||
use toml;
|
||||
@@ -15,14 +13,11 @@ use clap::SubCommand;
|
||||
#[derive(Debug, Deserialize)]
|
||||
pub struct Config {
|
||||
state_dir: PathBuf,
|
||||
data_dir: PathBuf,
|
||||
mode: RunMode
|
||||
}
|
||||
|
||||
/// # Accessors
|
||||
impl Config {
|
||||
pub fn data_dir(&self) -> String {
|
||||
self.data_dir.to_string_lossy().to_string()
|
||||
}
|
||||
pub fn state_dir(&self) -> String {
|
||||
self.state_dir.to_string_lossy().to_string()
|
||||
}
|
||||
@@ -32,71 +27,130 @@ impl Config {
|
||||
impl Config {
|
||||
/// Creates the config (at startup). Panics in case of issues.
|
||||
pub fn create() -> Result<Self, ConfigError> {
|
||||
let matches = App::new("NLnet Labs RRDP Client")
|
||||
let m = App::new("NLnet Labs RRDP Client")
|
||||
.version("0.1b")
|
||||
.arg(Arg::with_name("config")
|
||||
.short("c")
|
||||
.long("config")
|
||||
.arg(Arg::with_name("data")
|
||||
.short("d")
|
||||
.long("data")
|
||||
.value_name("FILE")
|
||||
.help("Specify non-default config file. If no file is \
|
||||
specified './defaults/client.toml' will be used to \
|
||||
determine default values for all settings. Note that you \
|
||||
can use any of the following options to override any of \
|
||||
these values..")
|
||||
.required(false))
|
||||
|
||||
.help("Specify the directory where this publication client \
|
||||
maintains its state.")
|
||||
.required(true))
|
||||
|
||||
.subcommand(SubCommand::with_name("init")
|
||||
.about("Initialise keypair and print client.xml.")
|
||||
.about("(Re-)Initialise the identity certificate and key \
|
||||
pair.")
|
||||
)
|
||||
|
||||
.subcommand(SubCommand::with_name("parent")
|
||||
.about("Process parent response")
|
||||
.subcommand(SubCommand::with_name("request")
|
||||
.about("Generate the publisher request XML")
|
||||
.arg(Arg::with_name("xml")
|
||||
.short("x")
|
||||
.long("xml")
|
||||
.value_name("FILE")
|
||||
.help("The server's parent.xml response.")
|
||||
.help("The name of the file to write the request to.")
|
||||
.required(true))
|
||||
)
|
||||
|
||||
.subcommand(SubCommand::with_name("response")
|
||||
.about("Process the repository response XML")
|
||||
.arg(Arg::with_name("xml")
|
||||
.short("x")
|
||||
.long("xml")
|
||||
.value_name("FILE")
|
||||
.help("The name of the file containing the response.")
|
||||
.required(true))
|
||||
)
|
||||
|
||||
.subcommand(SubCommand::with_name("sync")
|
||||
.about("Synchronise the configured directory. Use the '-d' \
|
||||
option to override the value set in the config file.")
|
||||
.about("Synchronise the directory specified by '-d'.")
|
||||
.arg(Arg::with_name("dir")
|
||||
.short("d")
|
||||
.long("directory")
|
||||
.value_name("FILE")
|
||||
.help("Override the directory to synchronise.")
|
||||
.required(false))
|
||||
.required(true))
|
||||
)
|
||||
|
||||
.get_matches();
|
||||
|
||||
let config_file = matches.value_of("config")
|
||||
.unwrap_or("./defaults/client.toml");
|
||||
|
||||
let mut c = Self::read_config(config_file.as_ref())?;
|
||||
|
||||
if let Some(matches) = matches.subcommand_matches("sync") {
|
||||
if let Some(data_dir) = matches.value_of("dir") {
|
||||
c.data_dir = PathBuf::from(data_dir)
|
||||
let mode = match m.subcommand_name() {
|
||||
Some("init") => {
|
||||
RunMode::Init
|
||||
},
|
||||
Some("request") => {
|
||||
if let Some(m) = m.subcommand_matches("request") {
|
||||
if let Some(xml) = m.value_of("xml") {
|
||||
let xml = PathBuf::from(xml);
|
||||
RunMode::PublisherRequest(xml)
|
||||
} else {
|
||||
Self::die(m.usage());
|
||||
unreachable!()
|
||||
}
|
||||
} else {
|
||||
Self::die(m.usage());
|
||||
unreachable!()
|
||||
}
|
||||
},
|
||||
Some("response") => {
|
||||
if let Some(m) = m.subcommand_matches("response") {
|
||||
if let Some(xml) = m.value_of("xml") {
|
||||
let xml = PathBuf::from(xml);
|
||||
RunMode::RepoResponse(xml)
|
||||
} else {
|
||||
Self::die(m.usage());
|
||||
unreachable!()
|
||||
}
|
||||
} else {
|
||||
Self::die(m.usage());
|
||||
unreachable!()
|
||||
}
|
||||
},
|
||||
Some("sync") => {
|
||||
if let Some(m) = m.subcommand_matches("sync") {
|
||||
if let Some(dir) = m.value_of("dir") {
|
||||
let dir = PathBuf::from(dir);
|
||||
RunMode::Sync(dir)
|
||||
} else {
|
||||
Self::die(m.usage());
|
||||
unreachable!()
|
||||
}
|
||||
} else {
|
||||
Self::die(m.usage());
|
||||
unreachable!()
|
||||
}
|
||||
},
|
||||
_ => {
|
||||
Self::die(
|
||||
"Expected subcommand (init, response, request, sync)"
|
||||
);
|
||||
unreachable!()
|
||||
}
|
||||
};
|
||||
|
||||
if let Some(data) = m.value_of("data") {
|
||||
let state_dir = PathBuf::from(data);
|
||||
Ok(Config {state_dir, mode})
|
||||
} else {
|
||||
Self::die(m.usage());
|
||||
unreachable!()
|
||||
}
|
||||
|
||||
Ok(c)
|
||||
}
|
||||
|
||||
fn read_config(file: &str) -> Result<Self, ConfigError> {
|
||||
let mut v = Vec::new();
|
||||
let mut f = File::open(file)?;
|
||||
f.read_to_end(&mut v)?;
|
||||
|
||||
let c: Config = toml::from_slice(v.as_slice())?;
|
||||
Ok(c)
|
||||
fn die(message: &str) {
|
||||
eprintln!("{}", message);
|
||||
::std::process::exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Deserialize)]
|
||||
pub enum RunMode {
|
||||
Init,
|
||||
PublisherRequest(PathBuf),
|
||||
RepoResponse(PathBuf),
|
||||
Sync(PathBuf)
|
||||
}
|
||||
|
||||
#[derive(Debug, Fail)]
|
||||
pub enum ConfigError {
|
||||
|
||||
@@ -119,19 +173,3 @@ impl From<toml::de::Error> for ConfigError {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//------------ Tests ---------------------------------------------------------
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn should_parse_default_config_file() {
|
||||
let c = Config::read_config("./defaults/client.toml").unwrap();
|
||||
assert_eq!(c.state_dir(), "./client_state".to_string());
|
||||
assert_eq!(c.data_dir(), "./client_data".to_string());
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user