use std::{
fs,
io::{self, Write},
path::{Path, PathBuf},
};
use snipdoc::{
cli::CmdExit,
config::Config,
db::{self, Db},
parser::{
collector::Collector,
injector::{InjectedContent, Injector, InjectorResult},
},
walk,
};
use crate::Format;
pub fn exec(
config: &Config,
inject_folder: &Path,
db_file: Option<PathBuf>,
dry_run: bool,
format: &Format,
) -> CmdExit {
let span = tracing::span!(tracing::Level::INFO, "run");
let _guard = span.enter();
let injector = match run(config, inject_folder, db_file) {
Ok(i) => i,
Err(err) => {
return CmdExit::error_with_message(&format!("could not init walk instance: {err}"));
}
};
if !dry_run {
for (path, status) in injector.results.iter() {
if let InjectedContent::Injected(summary) = status {
write_content(path.as_path(), &summary.content).unwrap();
}
}
}
format.reporter().inject(inject_folder, &injector.results);
CmdExit::ok()
}
pub fn run(
config: &Config,
inject_folder: &Path,
db_file: Option<PathBuf>,
) -> io::Result<InjectorResult> {
let walk = match walk::Walk::from_config(inject_folder, &config.walk) {
Ok(walk) => walk,
Err(err) => {
return Err(err);
}
};
let mut db_data = db::Code::new(Collector::walk(&walk).snippets)
.load()
.unwrap();
let maybe_yaml_file = {
db_file.map_or_else(
|| db::Yaml::try_from_default_file(inject_folder),
|db_file| Some(db::Yaml::new(db_file.as_path())),
)
};
if let Some(yaml_db) = &maybe_yaml_file {
let snippets_from_yaml = yaml_db.load().unwrap();
db_data.snippets.extend(snippets_from_yaml.snippets);
db_data.templates = snippets_from_yaml.templates;
tracing::debug!(
snippet_count = db_data.snippets.len(),
template_count = db_data.templates.len(),
"yaml file loaded successfully"
);
}
let walk = match walk::Walk::from_config(inject_folder, &config.walk) {
Ok(walk) => walk,
Err(err) => {
return Err(err);
}
};
Ok(Injector::walk(&walk, &db_data, &config.inject))
}
fn write_content(path: &Path, content: &str) -> std::io::Result<()> {
let mut file = fs::File::create(path)?;
file.write_all(content.as_bytes())?;
Ok(())
}