use miette::NamedSource;
use self::error::Error;
#[derive(Debug, Clone)]
pub(crate) struct ModuleInfo {
pub(crate) path: String,
pub(crate) name: String,
pub(crate) content: String,
}
impl From<ModuleInfo> for NamedSource {
fn from(m: ModuleInfo) -> Self {
Self::new(m.path, m.content)
}
}
impl From<&ModuleInfo> for NamedSource {
fn from(m: &ModuleInfo) -> Self {
Self::new(&m.path, m.content.clone())
}
}
pub(crate) fn read_query_modules(dir_path: &str) -> Result<Vec<ModuleInfo>, Error> {
let mut modules_info = Vec::new();
for entry_result in std::fs::read_dir(dir_path).map_err(|err| Error {
err,
path: String::from(dir_path),
})? {
let entry = entry_result.map_err(|err| Error {
err,
path: dir_path.to_owned(),
})?;
let path_buf = entry.path();
if path_buf
.extension()
.map(|extension| extension == "sql")
.unwrap_or_default()
{
let module_name = path_buf
.file_stem()
.expect("is a file")
.to_str()
.expect("file name is valid utf8")
.to_string();
let file_contents = std::fs::read_to_string(&path_buf).map_err(|err| Error {
err,
path: dir_path.to_owned(),
})?;
modules_info.push(ModuleInfo {
path: String::from(path_buf.to_string_lossy()),
name: module_name,
content: file_contents,
});
}
}
modules_info.sort_by(|a, b| a.name.cmp(&b.name));
Ok(modules_info)
}
pub(crate) mod error {
use miette::Diagnostic;
use thiserror::Error as ThisError;
#[derive(Debug, ThisError, Diagnostic)]
#[error("[{path}] : {err:#}")]
pub struct Error {
pub(crate) err: std::io::Error,
pub(crate) path: String,
}
}