From e5148e3ae1f6d459c0faeba6b6a78cf221f6f7ff Mon Sep 17 00:00:00 2001 From: orhun Date: Wed, 18 Aug 2021 03:19:06 +0300 Subject: [PATCH] feat(config): embed the default configuration file into the binary --- Cargo.lock | 102 ++++++++++++++++++++++++++++++++++-- git-cliff-core/Cargo.toml | 11 ++-- git-cliff-core/src/embed.rs | 37 +++++++++++++ git-cliff-core/src/error.rs | 6 +++ git-cliff-core/src/lib.rs | 2 + git-cliff/src/lib.rs | 11 +++- 6 files changed, 159 insertions(+), 10 deletions(-) create mode 100644 git-cliff-core/src/embed.rs diff --git a/Cargo.lock b/Cargo.lock index 95b2094a0a..5b5832271a 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -79,7 +79,16 @@ dependencies = [ "block-padding", "byte-tools", "byteorder", - "generic-array", + "generic-array 0.12.4", +] + +[[package]] +name = "block-buffer" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4152116fd6e9dadb291ae18fc1ec3575ed6d84c29642d97890f4b4a3417297e4" +dependencies = [ + "generic-array 0.14.4", ] [[package]] @@ -177,6 +186,15 @@ dependencies = [ "yaml-rust", ] +[[package]] +name = "cpufeatures" +version = "0.1.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "66c99696f6c9dd7f35d486b9d04d7e6e202aa3e8c40d553f2fdf5e7e0c6a71ef" +dependencies = [ + "libc", +] + [[package]] name = "crossbeam-utils" version = "0.8.5" @@ -215,7 +233,16 @@ version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f3d0c8c8752312f9713efd397ff63acb9f85585afbf179282e720e7704954dd5" dependencies = [ - "generic-array", + "generic-array 0.12.4", +] + +[[package]] +name = "digest" +version = "0.9.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "d3dd60d1080a57a05ab032377049e0591415d2b31afd7028356dbf3cc6dcb066" +dependencies = [ + "generic-array 0.14.4", ] [[package]] @@ -274,6 +301,16 @@ dependencies = [ "typenum", ] +[[package]] +name = "generic-array" +version = "0.14.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "501466ecc8a30d1d3b7fc9229b122b2ce8ed6e9d9223f1138d4babb253e51817" +dependencies = [ + "typenum", + "version_check", +] + [[package]] name = "getrandom" version = "0.2.3" @@ -306,11 +343,13 @@ dependencies = [ "indexmap", "pretty_assertions", "regex", + "rust-embed", "serde", "serde_derive", "serde_regex", "tera", "thiserror", + "toml", ] [[package]] @@ -592,6 +631,12 @@ version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "2839e79665f131bdb5782e51f2c6c9599c133c6098982a54c794358bf432529c" +[[package]] +name = "opaque-debug" +version = "0.3.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "624a8340c38c1b80fd549087862da4ba43e08858af025b236e509b6649fc13d5" + [[package]] name = "output_vt100" version = "0.1.2" @@ -804,6 +849,40 @@ version = "0.6.25" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f497285884f3fcff424ffc933e56d7cbca511def0c9831a7f9b5f6153e3cc89b" +[[package]] +name = "rust-embed" +version = "6.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3203eb498314cbc2c6671278c8da3c64a16476d79ad1442bc13e8629706f24f7" +dependencies = [ + "rust-embed-impl", + "rust-embed-utils", + "walkdir", +] + +[[package]] +name = "rust-embed-impl" +version = "6.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a1c03c7b7b780fdafde5055576641fd6b4d38095e3399cd0588552639aeff432" +dependencies = [ + "proc-macro2", + "quote", + "rust-embed-utils", + "syn", + "walkdir", +] + +[[package]] +name = "rust-embed-utils" +version = "6.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "5b5f2909061b856ce587f2496fc149a71d576cb2e0842c79f0dc82741622c6d0" +dependencies = [ + "sha2", + "walkdir", +] + [[package]] name = "ryu" version = "1.0.5" @@ -866,10 +945,23 @@ version = "0.8.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "f7d94d0bede923b3cea61f3f1ff57ff8cdfd77b400fb8f9998949e0cf04163df" dependencies = [ - "block-buffer", - "digest", + "block-buffer 0.7.3", + "digest 0.8.1", "fake-simd", - "opaque-debug", + "opaque-debug 0.2.3", +] + +[[package]] +name = "sha2" +version = "0.9.5" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b362ae5752fd2137731f9fa25fd4d9058af34666ca1966fb969119cc35719f12" +dependencies = [ + "block-buffer 0.9.0", + "cfg-if", + "cpufeatures", + "digest 0.9.0", + "opaque-debug 0.3.0", ] [[package]] diff --git a/git-cliff-core/Cargo.toml b/git-cliff-core/Cargo.toml index c01267b17a..bd33581778 100644 --- a/git-cliff-core/Cargo.toml +++ b/git-cliff-core/Cargo.toml @@ -17,6 +17,7 @@ tera = "1.12.1" regex = "1.5.4" serde_regex = "1.1.0" indexmap = "1.7.0" +toml = "0.5.8" [dependencies.git2] version = "0.13.21" @@ -27,9 +28,13 @@ version = "0.11.0" default-features = false features = ["toml", "yaml"] -[dev-dependencies] -pretty_assertions = "0.7" - [dependencies.git-conventional] version = "0.9.2" features = ["serde"] + +[dependencies.rust-embed] +version = "6.0.0" +features = ["debug-embed"] + +[dev-dependencies] +pretty_assertions = "0.7" diff --git a/git-cliff-core/src/embed.rs b/git-cliff-core/src/embed.rs new file mode 100644 index 0000000000..075299789f --- /dev/null +++ b/git-cliff-core/src/embed.rs @@ -0,0 +1,37 @@ +#![allow(missing_docs)] // RustEmbed generated functions does not have doc comments + +use crate::config::Config; +use crate::error::{ + Error, + Result, +}; +use rust_embed::RustEmbed; +use std::str; + +/// Configuration file embedder/extractor. +/// +/// Embeds `config/`[`DEFAULT_CONFIG`] into the binary. +/// +/// [`DEFAULT_CONFIG`]: crate::DEFAULT_CONFIG +#[derive(Debug, RustEmbed)] +#[folder = "../config/"] +pub struct EmbeddedConfig; + +impl EmbeddedConfig { + /// Extracts the embedded content. + pub fn get_config() -> Result { + match Self::get(crate::DEFAULT_CONFIG) { + Some(v) => Ok(str::from_utf8(&v.data.into_owned()).unwrap().to_string()), + None => Err(Error::EmbeddedError(String::from( + "Embedded config not found", + ))), + } + } + + /// Parses the extracted content into [`Config`]. + /// + /// [`Config`]: Config + pub fn parse() -> Result { + Ok(toml::from_str(&Self::get_config()?)?) + } +} diff --git a/git-cliff-core/src/error.rs b/git-cliff-core/src/error.rs index fbee13a4a5..29170fc19c 100644 --- a/git-cliff-core/src/error.rs +++ b/git-cliff-core/src/error.rs @@ -28,6 +28,12 @@ pub enum Error { /// Error that may occur while parsing the command line arguments. #[error("Argument error: `{0}`")] ArgumentError(String), + /// Error that may occur while extracting the embedded content. + #[error("Embedded error: `{0}`")] + EmbeddedError(String), + /// Errors that may occur when deserializing types from TOML format. + #[error("Cannot parse TOML: `{0}`")] + DeserializeError(#[from] toml::de::Error), } /// Result type of the core library. diff --git a/git-cliff-core/src/lib.rs b/git-cliff-core/src/lib.rs index c6140093b6..b25a2baaa9 100644 --- a/git-cliff-core/src/lib.rs +++ b/git-cliff-core/src/lib.rs @@ -7,6 +7,8 @@ pub use regex; pub mod commit; /// Config file parser. pub mod config; +/// Embedded file handler. +pub mod embed; /// Error handling. pub mod error; /// Common release type. diff --git a/git-cliff/src/lib.rs b/git-cliff/src/lib.rs index dd558bf89f..e361f53a4a 100644 --- a/git-cliff/src/lib.rs +++ b/git-cliff/src/lib.rs @@ -10,6 +10,7 @@ use args::Opt; use changelog::Changelog; use git_cliff_core::commit::Commit; use git_cliff_core::config::Config; +use git_cliff_core::embed::EmbeddedConfig; use git_cliff_core::error::{ Error, Result, @@ -38,13 +39,19 @@ pub fn run(mut args: Opt) -> Result<()> { } // Parse configuration file. - let mut config = Config::parse(match args.config.to_str() { + let path = match args.config.to_str() { Some(v) => Ok(v.to_string()), None => Err(Error::IoError(io::Error::new( io::ErrorKind::Other, "path contains invalid characters", ))), - }?)?; + }?; + let mut config = if fs::metadata(&path).is_ok() { + Config::parse(path)? + } else { + warn!("{:?} is not found, using the default configuration.", path); + EmbeddedConfig::parse()? + }; // Update the configuration based on command line arguments. match args.strip.as_deref() {