source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe"
+[[package]]
+name = "anstream"
+version = "0.3.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "0ca84f3628370c59db74ee214b3263d58f9aadd9b4fe7e711fd87dc452b7f163"
+dependencies = [
+ "anstyle",
+ "anstyle-parse",
+ "anstyle-query",
+ "anstyle-wincon",
+ "colorchoice",
+ "is-terminal",
+ "utf8parse",
+]
+
+[[package]]
+name = "anstyle"
+version = "1.0.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "41ed9a86bf92ae6580e0a31281f65a1b1d867c0cc68d5346e2ae128dddfa6a7d"
+
+[[package]]
+name = "anstyle-parse"
+version = "0.2.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "e765fd216e48e067936442276d1d57399e37bce53c264d6fefbe298080cb57ee"
+dependencies = [
+ "utf8parse",
+]
+
+[[package]]
+name = "anstyle-query"
+version = "1.0.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "5ca11d4be1bab0c8bc8734a9aa7bf4ee8316d462a08c6ac5052f888fef5b494b"
+dependencies = [
+ "windows-sys",
+]
+
+[[package]]
+name = "anstyle-wincon"
+version = "1.0.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "180abfa45703aebe0093f79badacc01b8fd4ea2e35118747e5811127f926e188"
+dependencies = [
+ "anstyle",
+ "windows-sys",
+]
+
[[package]]
name = "backtrace"
version = "0.3.67"
"rustc-demangle",
]
+[[package]]
+name = "bitflags"
+version = "1.3.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"
+
[[package]]
name = "block-buffer"
version = "0.10.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd"
+[[package]]
+name = "clap"
+version = "4.2.7"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "34d21f9bf1b425d2968943631ec91202fe5e837264063503708b83013f8fc938"
+dependencies = [
+ "clap_builder",
+ "clap_derive",
+ "once_cell",
+]
+
+[[package]]
+name = "clap_builder"
+version = "4.2.7"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "914c8c79fb560f238ef6429439a30023c862f7a28e688c58f7203f12b29970bd"
+dependencies = [
+ "anstream",
+ "anstyle",
+ "bitflags",
+ "clap_lex",
+ "strsim",
+]
+
+[[package]]
+name = "clap_derive"
+version = "4.2.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "3f9644cd56d6b87dbe899ef8b053e331c0637664e9e21a33dfcdc36093f5c5c4"
+dependencies = [
+ "heck",
+ "proc-macro2",
+ "quote",
+ "syn 2.0.15",
+]
+
+[[package]]
+name = "clap_lex"
+version = "0.4.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "8a2dd5a6fe8c6e3502f568a6353e5273bbb15193ad9a89e457b9970798efbea1"
+
[[package]]
name = "color-eyre"
version = "0.5.11"
"owo-colors",
]
+[[package]]
+name = "colorchoice"
+version = "1.0.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "acbf1af155f9b9ef647e42cdc158db4b64a1b61f743629225fde6f3e0be2a7c7"
+
[[package]]
name = "cpufeatures"
version = "0.2.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7fcaabb2fef8c910e7f4c7ce9f67a1283a1715879a7c230ca9d6d1ae31f16d91"
+[[package]]
+name = "errno"
+version = "0.3.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "4bcfec3a70f97c962c307b2d2c56e358cf1d00b558d74262b5f929ee8cc7e73a"
+dependencies = [
+ "errno-dragonfly",
+ "libc",
+ "windows-sys",
+]
+
+[[package]]
+name = "errno-dragonfly"
+version = "0.1.2"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "aa68f1b12764fab894d2755d2518754e71b4fd80ecfb822714a1206c2aab39bf"
+dependencies = [
+ "cc",
+ "libc",
+]
+
[[package]]
name = "eyre"
version = "0.6.8"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ad0a93d233ebf96623465aad4046a8d3aa4da22d4f4beba5388838c8a434bbb4"
+[[package]]
+name = "heck"
+version = "0.4.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "95505c38b4572b2d910cecb0281560f54b440a19336cbbcb27bf6ce6adc6f5a8"
+
+[[package]]
+name = "hermit-abi"
+version = "0.3.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "fed44880c466736ef9a5c5b5facefb5ed0785676d0c02d612db14e54f0d84286"
+
[[package]]
name = "indenter"
version = "0.3.3"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ce23b50ad8242c51a442f3ff322d56b02f08852c77e4c0b4d3fd684abc89c683"
+[[package]]
+name = "io-lifetimes"
+version = "1.0.10"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "9c66c74d2ae7e79a5a8f7ac924adbe38ee42a859c6539ad869eb51f0b52dc220"
+dependencies = [
+ "hermit-abi",
+ "libc",
+ "windows-sys",
+]
+
+[[package]]
+name = "is-terminal"
+version = "0.4.7"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "adcf93614601c8129ddf72e2d5633df827ba6551541c6d8c59520a371475be1f"
+dependencies = [
+ "hermit-abi",
+ "io-lifetimes",
+ "rustix",
+ "windows-sys",
+]
+
[[package]]
name = "itertools"
version = "0.8.2"
[[package]]
name = "libc"
-version = "0.2.142"
+version = "0.2.144"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "2b00cc1c228a6782d0f076e7b232802e0c5689d41bb5df366f2a6b6621cfdfe1"
+
+[[package]]
+name = "linux-raw-sys"
+version = "0.3.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "6a987beff54b60ffa6d51982e1aa1146bc42f19bd26be28b0586f252fccf5317"
+checksum = "ece97ea872ece730aed82664c424eb4c8291e1ff2480247ccf7409044bc6479f"
[[package]]
name = "memchr"
name = "metaforge"
version = "0.1.1"
dependencies = [
+ "clap",
"color-eyre",
"pandoc",
"pest",
[[package]]
name = "quote"
-version = "1.0.26"
+version = "1.0.27"
source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "4424af4bf778aae2051a77b60283332f386554255d722233d09fbfc7e30da2fc"
+checksum = "8f4f29d145265ec1c483c7c654450edde0bfe043d3938d6972630663356d9500"
dependencies = [
"proc-macro2",
]
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "d626bb9dae77e28219937af045c257c28bfd3f69333c512553507f5f9798cb76"
+[[package]]
+name = "rustix"
+version = "0.37.19"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "acf8729d8542766f1b2cf77eb034d52f40d375bb8b615d0b147089946e16613d"
+dependencies = [
+ "bitflags",
+ "errno",
+ "io-lifetimes",
+ "libc",
+ "linux-raw-sys",
+ "windows-sys",
+]
+
[[package]]
name = "same-file"
version = "1.0.6"
"digest",
]
+[[package]]
+name = "strsim"
+version = "0.10.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "73473c0e59e6d5812c5dfe2a064a6444949f089e20eec9a2e5506596494e4623"
+
[[package]]
name = "syn"
version = "1.0.109"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "e5464a87b239f13a63a501f2701565754bae92d243d4bb7eb12f6d57d2269bf4"
+[[package]]
+name = "utf8parse"
+version = "0.2.1"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "711b9620af191e0cdc7468a8d14e709c3dcdb115b36f838e601583af800a370a"
+
[[package]]
name = "version_check"
version = "0.9.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f"
+[[package]]
+name = "windows-sys"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "677d2418bec65e3338edb076e806bc1ec15693c5d0104683f2efe857f61056a9"
+dependencies = [
+ "windows-targets",
+]
+
+[[package]]
+name = "windows-targets"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "7b1eb6f0cd7c80c79759c929114ef071b87354ce476d9d94271031c0497adfd5"
+dependencies = [
+ "windows_aarch64_gnullvm",
+ "windows_aarch64_msvc",
+ "windows_i686_gnu",
+ "windows_i686_msvc",
+ "windows_x86_64_gnu",
+ "windows_x86_64_gnullvm",
+ "windows_x86_64_msvc",
+]
+
+[[package]]
+name = "windows_aarch64_gnullvm"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "91ae572e1b79dba883e0d315474df7305d12f569b400fcf90581b06062f7e1bc"
+
+[[package]]
+name = "windows_aarch64_msvc"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "b2ef27e0d7bdfcfc7b868b317c1d32c641a6fe4629c171b8928c7b08d98d7cf3"
+
+[[package]]
+name = "windows_i686_gnu"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "622a1962a7db830d6fd0a69683c80a18fda201879f0f447f065a3b7467daa241"
+
+[[package]]
+name = "windows_i686_msvc"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "4542c6e364ce21bf45d69fdd2a8e455fa38d316158cfd43b3ac1c5b1b19f8e00"
+
+[[package]]
+name = "windows_x86_64_gnu"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "ca2b8a661f7628cbd23440e50b05d705db3686f894fc9580820623656af974b1"
+
+[[package]]
+name = "windows_x86_64_gnullvm"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "7896dbc1f41e08872e9d5e8f8baa8fdd2677f29468c4e156210174edc7f7b953"
+
+[[package]]
+name = "windows_x86_64_msvc"
+version = "0.48.0"
+source = "registry+https://github.com/rust-lang/crates.io-index"
+checksum = "1a515f5799fe4961cb532f983ce2b23082366b898e52ffbce459c86f67c8378a"
+
[[package]]
name = "yansi"
version = "0.5.1"
edition = "2021"
[dependencies]
+clap = { version = "4", features = ["derive"] }
pandoc = "0.8"
color-eyre = { version = "0.5", default-features = false }
walkdir = "2"
mod builder;
mod metafile;
-mod structs;
pub use builder::*;
pub use metafile::*;
-pub use structs::*;
-use crate::{parse_file, MetaFile, RootDirs, Source, Substitution};
+use crate::{parse_file, MetaFile, Options, Source, Substitution};
use color_eyre::{eyre::bail, Result};
use pandoc::{InputFormat, InputKind, OutputFormat, OutputKind, Pandoc, PandocOutput};
use std::{
path::{Path, PathBuf},
};
-pub fn build_metafile(path: &Path, dirs: &RootDirs) -> Result<()> {
+pub fn build_metafile(path: &Path, dirs: &Options) -> Result<()> {
let file = fs::read_to_string(path)?;
let file = parse_file(&file)?;
Ok(())
}
-pub fn metafile_to_string(file: &MetaFile, dirs: &RootDirs, name: Option<&str>) -> Result<String> {
+pub fn metafile_to_string(file: &MetaFile, dirs: &Options, name: Option<&str>) -> Result<String> {
let mut output = String::default();
let mut arrays = false;
}
}
-fn get_source_html(file: &MetaFile, dirs: &RootDirs) -> Result<String> {
+fn get_source_html(file: &MetaFile, dirs: &Options) -> Result<String> {
let file = metafile_to_string(file, dirs, Some("SOURCE"))?;
let mut pandoc = Pandoc::new();
}
}
-fn get_pattern(key: &str, file: &MetaFile, dirs: &RootDirs) -> Result<String> {
+fn get_pattern(key: &str, file: &MetaFile, dirs: &Options) -> Result<String> {
// SOURCE is already expanded in the initial build_metafile() call
// we just need to return that
if key == "SOURCE" {
metafile_to_string(&pattern, dirs, Some(key))
}
-fn find_dest(path: &Path, dirs: &RootDirs) -> Result<PathBuf> {
+fn find_dest(path: &Path, dirs: &Options) -> Result<PathBuf> {
let source = dirs.source.to_string_lossy().to_string();
let build = dirs.build.to_string_lossy().to_string();
-use crate::Source;
use std::collections::HashMap;
#[derive(Debug, Default, Clone)]
self.patterns.get(key).copied()
}
}
+
+#[macro_export]
+macro_rules! source (
+ (var($s:expr)) => { Source::Sub(Substitution::Variable($s))};
+ (arr($s:expr)) => { Source::Sub(Substitution::Array($s))};
+ (pat($s:expr)) => { Source::Sub(Substitution::Pattern($s))};
+ ($s:expr) => { Source::Str($s)};
+);
+
+#[derive(Debug, Clone, PartialEq)]
+pub enum Source<'a> {
+ Str(&'a str),
+ Sub(Substitution<'a>),
+}
+
+#[derive(Debug, Clone, PartialEq)]
+pub enum Substitution<'a> {
+ Variable(&'a str),
+ Array(&'a str),
+ Pattern(&'a str),
+}
-use std::path::PathBuf;
-#[macro_export]
-macro_rules! source (
- (var($s:expr)) => { Source::Sub(Substitution::Variable($s))};
- (arr($s:expr)) => { Source::Sub(Substitution::Array($s))};
- (pat($s:expr)) => { Source::Sub(Substitution::Pattern($s))};
- ($s:expr) => { Source::Str($s)};
-);
-#[derive(Debug, Clone, PartialEq)]
-pub enum Source<'a> {
- Str(&'a str),
- Sub(Substitution<'a>),
-}
-
-#[derive(Debug, Clone, PartialEq)]
-pub enum Substitution<'a> {
- Variable(&'a str),
- Array(&'a str),
- Pattern(&'a str),
-}
-
-#[derive(Debug, Clone, Default)]
-pub struct RootDirs {
- pub root: PathBuf,
- pub source: PathBuf,
- pub build: PathBuf,
- pub pattern: PathBuf,
-}
-
-impl RootDirs {
- pub fn new() -> Self {
- Self {
- root: PathBuf::new(),
- source: PathBuf::new(),
- build: PathBuf::new(),
- pattern: PathBuf::new(),
- }
- }
-}
extern crate pest_derive;
mod filetype;
+mod options;
mod parser;
pub use filetype::*;
+pub use options::*;
pub use parser::*;
#[cfg(test)]
-extern crate pest;
-extern crate pest_derive;
-
use color_eyre::Result;
+use metaforge::parse_opts;
fn main() -> Result<()> {
+ let opts = parse_opts()?;
+ println!("{:?}", opts);
Ok(())
}
--- /dev/null
+use clap::Parser;
+use color_eyre::Result;
+use std::path::PathBuf;
+
+#[derive(Parser, Debug)]
+#[command(author = "Huck Boles")]
+#[command(version = "0.1.1")]
+#[command(about = "A customizable template driven static site generator")]
+#[command(long_about = None)]
+pub struct Opts {
+ /// Root directory [CURRENT_DIR]
+ #[arg(short, long, value_name = "ROOT_DIR")]
+ pub root: Option<String>,
+ /// Source file directory [CURRENT_DIR/source]
+ #[arg(short, long, value_name = "SOURCE_DIR")]
+ source: Option<String>,
+ /// Build directory [CURRENT_DIR/build]
+ #[arg(short, long, value_name = "BUILD_DIR")]
+ build: Option<String>,
+ /// Pattern directory [CURRENT_DIR/pattern]
+ #[arg(short, long, value_name = "PATTERN_DIR")]
+ pattern: Option<String>,
+ /// Extra output [false]
+ #[arg(short, long, default_value_t = false)]
+ verbose: bool,
+ /// Minimal output [false]
+ #[arg(short, long, default_value_t = false)]
+ quiet: bool,
+ /// Don't stop if a single file fails [false]
+ #[arg(long, default_value_t = false)]
+ force: bool,
+ /// Stop on undefined variables, patterns, and arrays [false]
+ #[arg(long, default_value_t = false)]
+ undefined: bool,
+}
+
+#[derive(Debug, Clone, Default)]
+pub struct Options {
+ pub root: PathBuf,
+ pub source: PathBuf,
+ pub build: PathBuf,
+ pub pattern: PathBuf,
+ pub verbose: bool,
+ pub quiet: bool,
+ pub force: bool,
+ pub undefined: bool,
+}
+
+impl Options {
+ pub fn new() -> Self {
+ Self {
+ root: PathBuf::new(),
+ source: PathBuf::new(),
+ build: PathBuf::new(),
+ pattern: PathBuf::new(),
+ verbose: false,
+ quiet: false,
+ force: false,
+ undefined: false,
+ }
+ }
+}
+
+pub fn parse_opts() -> Result<Options> {
+ let opts = Opts::parse();
+
+ let mut options = Options::new();
+ options.verbose = opts.verbose;
+ options.quiet = opts.quiet;
+ options.force = opts.force;
+ options.undefined = opts.undefined;
+
+ if let Some(root) = opts.root.as_deref() {
+ options.root = PathBuf::from(root).canonicalize()?;
+ } else {
+ options.root = std::env::current_dir()?;
+ }
+
+ if let Some(source) = opts.source.as_deref() {
+ options.source = PathBuf::from(source).canonicalize()?;
+ } else {
+ options.source = options.root.join("source");
+ }
+
+ if let Some(build) = opts.build.as_deref() {
+ options.build = PathBuf::from(build).canonicalize()?;
+ } else {
+ options.build = options.root.join("build");
+ }
+
+ if let Some(pattern) = opts.pattern.as_deref() {
+ options.pattern = PathBuf::from(pattern).canonicalize()?;
+ } else {
+ options.pattern = options.root.join("pattern");
+ }
+
+ Ok(options)
+}
Ok(())
}
-#[ignore = "Need to rewrite pattern test file"]
#[test]
fn parse_pattern_file() -> Result<()> {
let mut pattern_src = parse_file(PATTERN)?.source.into_iter();
--- /dev/null
+<body>
+<h2 id="this-is-a-test">This is a test</h2>
+<p>
+Inline html
+</p>
+variable: GOOD pattern:
+<p>
+GOOD
+</p>
+<p>
+GOOD GOOD
+</p>
+
+</body>
-GOOD
+<h1>This is a test</h1>
+<p>${variable}</p>
+<ul>
+ @{array}
+</ul
+&{pattern}
+<footer>Other stuff</footer>
static POST_EXPAND: &str = include_str!("files/expanded");
#[test]
-#[ignore = "don't want to interfere with builder right now"]
fn test_metafile_to_str() -> Result<()> {
let metafile = parse_file(PRE_EXPAND)?;
- let dirs = build_rootdir()?;
+ let dirs = build_options()?;
let file = metafile_to_string(&metafile, &dirs, None)?;
#[test]
fn test_metafile_builder() -> Result<()> {
- let dirs = build_rootdir()?;
+ let dirs = build_options()?;
let path = PathBuf::from("test_site/source/expand_html.meta");
build_metafile(&path, &dirs)?;
- let source = fs::read_to_string("test_site/site/expand_html.html")?;
+ let source = fs::read_to_string("test_site/build/expand_html.html")?;
let html = fs::read_to_string("tests/files/expanded_html")?;
assert_eq!(source, html);
Ok(())
}
-fn build_rootdir() -> Result<RootDirs> {
+fn build_options() -> Result<Options> {
let dir = PathBuf::from("./test_site").canonicalize()?;
- let dirs = RootDirs {
+ let opts = Options {
root: dir.clone(),
source: dir.join("source"),
- build: dir.join("site"),
+ build: dir.join("build"),
pattern: dir.join("pattern"),
+ verbose: false,
+ quiet: false,
+ force: false,
+ undefined: false,
};
- if dirs.build.exists() {
- fs::remove_dir_all(&dirs.build)?;
+ if !opts.build.exists() {
+ fs::create_dir(&opts.build)?;
}
- fs::create_dir(&dirs.build)?;
- Ok(dirs)
+ Ok(opts)
}