Addd flag to list used template variables

This commit is contained in:
2021-05-27 23:34:46 +02:00
parent 8d9937e44e
commit ce84eac3c3
4 changed files with 121 additions and 21 deletions

View File

@ -3,21 +3,13 @@ use crate::Config;
use async_recursion::async_recursion;
use blueprint::{parse_template, Env, Value};
use futures::future::join_all;
use serde::Serialize;
use std::ffi::OsStr;
use std::io::ErrorKind;
use std::path::PathBuf;
use tokio::fs::{copy, create_dir, read_dir, read_to_string, write};
use tokio::join;
#[derive(Serialize)]
struct TemplateContext<'a> {
hostname: &'a str,
lightmode: bool,
darkmode: bool,
}
const TEMPLATE_EXTENSION: &str = "tpl";
pub const TEMPLATE_EXTENSION: &str = "tpl";
pub async fn build_tree(cfg: &Config) -> Result<(), Errors> {
let hostname_path: PathBuf = "/etc/hostname".into();

View File

@ -4,11 +4,13 @@ extern crate log;
mod builder;
mod error;
mod linker;
mod peeker;
use builder::build_tree;
use error::Errors;
use linker::link_tree;
use log::LevelFilter;
use peeker::peek_tree;
use std::env;
use std::path::PathBuf;
use structopt::StructOpt;
@ -24,6 +26,9 @@ struct Opt {
#[structopt(short, long)]
link_dir: Option<PathBuf>,
#[structopt(short, long)]
print_variables: bool,
#[structopt(short, parse(from_occurrences))]
verbosity: u8,
@ -75,11 +80,16 @@ async fn run() -> Result<(), Errors> {
flags: opt.flags,
};
info!("building tree");
build_tree(&cfg).await?;
if opt.print_variables {
info!("peeking tree");
peek_tree(&cfg).await?;
} else {
info!("building tree");
build_tree(&cfg).await?;
info!("linking tree");
link_tree(&cfg).await?;
info!("linking tree");
link_tree(&cfg).await?;
}
Ok(())
}

98
manager/src/peeker.rs Normal file
View File

@ -0,0 +1,98 @@
use crate::builder::TEMPLATE_EXTENSION;
use crate::error::{Error, ErrorLocation, Errors};
use crate::Config;
use async_recursion::async_recursion;
use blueprint::parse_template;
use futures::future::join_all;
use std::ffi::OsStr;
use std::path::PathBuf;
use tokio::fs::{read_dir, read_to_string};
use tokio::join;
pub async fn peek_tree(cfg: &Config) -> Result<(), Errors> {
for var in dir(cfg, PathBuf::new()).await? {
println!("{}", var);
}
Ok(())
}
#[async_recursion]
async fn dir(cfg: &Config, relative: PathBuf) -> Result<Vec<String>, Errors> {
let template_path = cfg.template_dir.join(&relative);
info!("traversing {:?}", template_path);
let mut walker = read_dir(&template_path)
.await
.with_location(&template_path)?;
let mut dir_tasks = vec![];
let mut file_tasks = vec![];
while let Some(entry) = walker.next_entry().await.with_location(&&template_path)? {
let meta = entry.metadata().await.with_location(&entry.path())?;
let new_relative = relative.join(entry.file_name());
if meta.is_dir() {
dir_tasks.push(dir(cfg, new_relative));
} else if meta.is_file() {
file_tasks.push(file(cfg, new_relative));
}
}
let dirs = async { join_all(dir_tasks).await.into_iter().collect::<Vec<_>>() };
let files = async { join_all(file_tasks).await.into_iter().collect::<Vec<_>>() };
let (dirs, files) = join!(dirs, files);
let mut vars = vec![];
let mut errors = vec![];
for result in files.into_iter() {
match result {
Ok(mut more_vars) => vars.append(&mut more_vars),
Err(error) => errors.push(error),
}
}
let mut errors: Errors = errors.into();
for result in dirs.into_iter() {
match result {
Ok(mut more_vars) => vars.append(&mut more_vars),
Err(error) => errors.join(error),
}
}
if errors.is_empty() {
vars.sort_unstable();
vars.dedup();
Ok(vars)
} else {
Err(errors)
}
}
async fn file(cfg: &Config, relative: PathBuf) -> Result<Vec<String>, Error> {
let template_path = cfg.template_dir.join(&relative);
if template_path.extension() != Some(OsStr::new(TEMPLATE_EXTENSION)) {
return Ok(vec![]);
}
debug!("reading {:?}", template_path);
// parse template
let file_str = read_to_string(&template_path)
.await
.with_location(&template_path)?;
let vars = parse_template(&file_str)
.with_location(&template_path)?
.list_variables()
.into_iter()
.map(|s| s.to_string())
.collect();
Ok(vars)
}