mirror of
https://github.com/RGBCube/uutils-coreutils
synced 2025-07-28 11:37:44 +00:00
Merge pull request #3586 from jfinkels/mktemp-multiple-x-sequences
mktemp: only replace last contiguous block of Xs
This commit is contained in:
commit
3f203c7ab1
2 changed files with 60 additions and 4 deletions
|
@ -6,7 +6,7 @@
|
||||||
// For the full copyright and license information, please view the LICENSE
|
// For the full copyright and license information, please view the LICENSE
|
||||||
// file that was distributed with this source code.
|
// file that was distributed with this source code.
|
||||||
|
|
||||||
// spell-checker:ignore (paths) GPGHome
|
// spell-checker:ignore (paths) GPGHome findxs
|
||||||
|
|
||||||
use clap::{crate_version, Arg, ArgMatches, Command};
|
use clap::{crate_version, Arg, ArgMatches, Command};
|
||||||
use uucore::display::{println_verbatim, Quotable};
|
use uucore::display::{println_verbatim, Quotable};
|
||||||
|
@ -205,12 +205,29 @@ struct Params {
|
||||||
suffix: String,
|
suffix: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Find the start and end indices of the last contiguous block of Xs.
|
||||||
|
///
|
||||||
|
/// If no contiguous block of at least three Xs could be found, this
|
||||||
|
/// function returns `None`.
|
||||||
|
///
|
||||||
|
/// # Examples
|
||||||
|
///
|
||||||
|
/// ```rust,ignore
|
||||||
|
/// assert_eq!(find_last_contiguous_block_of_xs("XXX_XXX"), Some((4, 7)));
|
||||||
|
/// assert_eq!(find_last_contiguous_block_of_xs("aXbXcX"), None);
|
||||||
|
/// ```
|
||||||
|
fn find_last_contiguous_block_of_xs(s: &str) -> Option<(usize, usize)> {
|
||||||
|
let j = s.rfind("XXX")? + 3;
|
||||||
|
let i = s[..j].rfind(|c| c != 'X').map_or(0, |i| i + 1);
|
||||||
|
Some((i, j))
|
||||||
|
}
|
||||||
|
|
||||||
impl Params {
|
impl Params {
|
||||||
fn from(options: Options) -> Result<Self, MkTempError> {
|
fn from(options: Options) -> Result<Self, MkTempError> {
|
||||||
// Get the start and end indices of the randomized part of the template.
|
// Get the start and end indices of the randomized part of the template.
|
||||||
//
|
//
|
||||||
// For example, if the template is "abcXXXXyz", then `i` is 3 and `j` is 7.
|
// For example, if the template is "abcXXXXyz", then `i` is 3 and `j` is 7.
|
||||||
let i = match options.template.find("XXX") {
|
let (i, j) = match find_last_contiguous_block_of_xs(&options.template) {
|
||||||
None => {
|
None => {
|
||||||
let s = match options.suffix {
|
let s = match options.suffix {
|
||||||
None => options.template,
|
None => options.template,
|
||||||
|
@ -218,9 +235,8 @@ impl Params {
|
||||||
};
|
};
|
||||||
return Err(MkTempError::TooFewXs(s));
|
return Err(MkTempError::TooFewXs(s));
|
||||||
}
|
}
|
||||||
Some(i) => i,
|
Some(indices) => indices,
|
||||||
};
|
};
|
||||||
let j = options.template.rfind("XXX").unwrap() + 3;
|
|
||||||
|
|
||||||
// Combine the directory given as an option and the prefix of the template.
|
// Combine the directory given as an option and the prefix of the template.
|
||||||
//
|
//
|
||||||
|
@ -450,3 +466,21 @@ fn exec(dir: &str, prefix: &str, rand: usize, suffix: &str, make_dir: bool) -> U
|
||||||
|
|
||||||
println_verbatim(path).map_err_context(|| "failed to print directory name".to_owned())
|
println_verbatim(path).map_err_context(|| "failed to print directory name".to_owned())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use crate::find_last_contiguous_block_of_xs as findxs;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_find_last_contiguous_block_of_xs() {
|
||||||
|
assert_eq!(findxs("XXX"), Some((0, 3)));
|
||||||
|
assert_eq!(findxs("XXX_XXX"), Some((4, 7)));
|
||||||
|
assert_eq!(findxs("XXX_XXX_XXX"), Some((8, 11)));
|
||||||
|
assert_eq!(findxs("aaXXXbb"), Some((2, 5)));
|
||||||
|
assert_eq!(findxs(""), None);
|
||||||
|
assert_eq!(findxs("X"), None);
|
||||||
|
assert_eq!(findxs("XX"), None);
|
||||||
|
assert_eq!(findxs("aXbXcX"), None);
|
||||||
|
assert_eq!(findxs("aXXbXXcXX"), None);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -597,3 +597,25 @@ fn test_too_few_xs_suffix_directory() {
|
||||||
fn test_too_many_arguments() {
|
fn test_too_many_arguments() {
|
||||||
new_ucmd!().args(&["-q", "a", "b"]).fails().code_is(1);
|
new_ucmd!().args(&["-q", "a", "b"]).fails().code_is(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_two_contiguous_wildcard_blocks() {
|
||||||
|
let (at, mut ucmd) = at_and_ucmd!();
|
||||||
|
let template = "XXX_XXX";
|
||||||
|
let result = ucmd.arg(template).succeeds();
|
||||||
|
let filename = result.no_stderr().stdout_str().trim_end();
|
||||||
|
assert_eq!(&filename[..4], "XXX_");
|
||||||
|
assert_matches_template!(template, filename);
|
||||||
|
assert!(at.file_exists(filename));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_three_contiguous_wildcard_blocks() {
|
||||||
|
let (at, mut ucmd) = at_and_ucmd!();
|
||||||
|
let template = "XXX_XXX_XXX";
|
||||||
|
let result = ucmd.arg(template).succeeds();
|
||||||
|
let filename = result.no_stderr().stdout_str().trim_end();
|
||||||
|
assert_eq!(&filename[..8], "XXX_XXX_");
|
||||||
|
assert_matches_template!(template, filename);
|
||||||
|
assert!(at.file_exists(filename));
|
||||||
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue