Skip to content

Commit

Permalink
fix(cli): deprecate input:output syntax
Browse files Browse the repository at this point in the history
  • Loading branch information
loichyan committed Oct 2, 2024
1 parent b424be4 commit 0680464
Show file tree
Hide file tree
Showing 4 changed files with 54 additions and 24 deletions.
30 changes: 19 additions & 11 deletions src/cli.rs
Original file line number Diff line number Diff line change
Expand Up @@ -126,12 +126,17 @@ pub enum Command {
/// Set the file size limit (0 to disable it).
#[arg(long, value_name= V_SIZE, default_value = DEFAULT_SIZE)]
size_limit: ByteSize,
/// Path tuple(s) of files to read from and write to.
/// Save fixed files to different paths.
///
/// Each tuple is an input path followed by an optional output path,
/// e.g. `nerdfix fix /input/as/ouput /read/from:/write/to`.
/// Each path should be paired with its corresponding source path. Use
/// empty strings to save output directly to the source path. For
/// example, `nerdfix fix -o output1 -o "" input1 input2` will save
/// `input1` to `output1` and save `input2` to its original path.
#[arg(short, long, value_name = V_PATH)]
output: Vec<Outpath>,
/// Path(s) of files to check.
#[arg(value_name = V_SOURCE)]
source: Vec<Source>,
source: Vec<IoPath>,
},
/// Fuzzy search for an icon.
Search {},
Expand Down Expand Up @@ -249,16 +254,19 @@ impl fmt::Display for OutputFormat {
}

#[derive(Clone, Debug)]
pub struct Source(pub IoPath, pub Option<IoPath>);
pub struct Outpath(pub Option<IoPath>);

impl FromStr for Source {
type Err = &'static str;
impl FromStr for Outpath {
type Err = <IoPath as FromStr>::Err;

fn from_str(s: &str) -> Result<Self, Self::Err> {
Ok(if let Some((input, output)) = s.split_once(':') {
Source(input.parse()?, Some(output.parse()?))
if s.is_empty() {
Ok(Self(None))
} else {
Source(s.parse()?, None)
})
s.parse().map(Some).map(Self)
}
}
}

#[derive(Debug)]
pub struct Source(pub IoPath, pub Option<IoPath>);
2 changes: 2 additions & 0 deletions src/error.rs
Original file line number Diff line number Diff line change
Expand Up @@ -52,6 +52,8 @@ pub enum Error {
InvalidCodepoint,
#[error("Operation was interrupted by the user")]
Interrupted,
#[error("Number of output paths mismatch with source paths")]
OutputMismatched,
#[error(transparent)]
Any(Box<dyn Send + Sync + std::error::Error>),
}
Expand Down
37 changes: 27 additions & 10 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -12,29 +12,31 @@ mod runtime;
shadow_rs::shadow!(shadow);

use clap::Parser;
use cli::{Command, IoPath, Source};
use prompt::YesOrNo;
use runtime::{CheckerContext, Runtime};
use thisctx::WithContext;
use thisctx::{IntoError, WithContext};
use tracing::{error, info, warn, Level};
use tracing_subscriber::prelude::*;
use util::{LogStatus, ResultExt as _};
use walkdir::WalkDir;

use self::cli::{Command, IoPath, Source};
use self::prompt::YesOrNo;
use self::runtime::{CheckerContext, Runtime};
use self::util::{LogStatus, ResultExt as _};

static ICONS: &str = include_str!("./icons.json");
static SUBSTITUTIONS: &str = include_str!("./substitutions.json");

fn walk<'a>(
paths: impl 'a + IntoIterator<Item = Source>,
paths: impl 'a + IntoIterator<Item = (IoPath, Option<IoPath>)>,
recursive: bool,
) -> impl 'a + Iterator<Item = error::Result<Source>> {
if !recursive {
Box::new(paths.into_iter().map(Ok)) as Box<dyn Iterator<Item = _>>
Box::new(paths.into_iter().map(|(i, o)| Source(i, o)).map(Ok))
as Box<dyn Iterator<Item = _>>
} else {
Box::new(
paths
.into_iter()
.flat_map(|Source(input, output)| {
.flat_map(|(input, output)| {
if let Some(output) = output {
warn!("Output path is ignored when `--recursive`: {}", output);
}
Expand Down Expand Up @@ -119,7 +121,7 @@ fn main_impl() -> error::Result<()> {
size_limit: size_limit.as_u64(),
..Default::default()
};
for source in walk(source.into_iter().map(|p| Source(p, None)), recursive) {
for source in walk(source.into_iter().map(|p| (p, None)), recursive) {
tri!({
let source = source?;
rt.check(&mut context, &source.0, None)
Expand All @@ -135,11 +137,23 @@ fn main_impl() -> error::Result<()> {
recursive,
include_binary,
size_limit,
output,
source,
} => {
if yes {
warn!("`--yes` is deprecated, use `--write` instead");
}
if !output.is_empty() && output.len() != source.len() {
return Err(error::OutputMismatched.build());
}
if cfg!(unix) {
// Colon in `C:\Path` should not be considered as separators.
for p in source.iter() {
if matches!(p, IoPath::Path(p) if p.as_str().contains(':')) {
warn!("`input:output` syntax is deprecated, use `--output` instead");
}
}
}
let rt = rt.build();
let mut context = CheckerContext {
write,
Expand All @@ -149,7 +163,10 @@ fn main_impl() -> error::Result<()> {
..Default::default()
};
let mut buffer = String::new();
for source in walk(source, recursive) {
for source in walk(
source.into_iter().zip(output.into_iter().map(|p| p.0)),
recursive,
) {
tri!({
let source = source?;
let Source(input, output) = &source;
Expand Down
9 changes: 6 additions & 3 deletions tests/cli.rs
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,8 @@ fn fix() {
"fix",
"--select-first",
"--write",
"tests/test-data.txt:-"
"-o-",
"tests/test-data.txt"
);
}

Expand All @@ -144,7 +145,8 @@ fn fix_with_exact_subs() {
"--write",
"-i=src/icons.json",
"-i=tests/test-substitutions.json",
"tests/test-data.txt:-"
"-o-",
"tests/test-data.txt"
);
}

Expand All @@ -157,6 +159,7 @@ fn fix_with_prefix_subs() {
"--write",
"-i=src/icons.json",
"--sub=prefix:mdi-/md-",
"tests/test-data.txt:-"
"-o-",
"tests/test-data.txt"
);
}

0 comments on commit 0680464

Please sign in to comment.