mirror of
https://github.com/RGBCube/uutils-coreutils
synced 2025-07-28 11:37:44 +00:00
l10n: port tr for translation + add french
This commit is contained in:
parent
a769fc7904
commit
aba6128fc1
5 changed files with 173 additions and 46 deletions
|
@ -1,3 +1,41 @@
|
||||||
tr-about = Translate or delete characters
|
tr-about = Translate or delete characters
|
||||||
tr-usage = tr [OPTION]... SET1 [SET2]
|
tr-usage = tr [OPTION]... SET1 [SET2]
|
||||||
tr-after-help = Translate, squeeze, and/or delete characters from standard input, writing to standard output.
|
tr-after-help = Translate, squeeze, and/or delete characters from standard input, writing to standard output.
|
||||||
|
|
||||||
|
# Help messages
|
||||||
|
tr-help-complement = use the complement of SET1
|
||||||
|
tr-help-delete = delete characters in SET1, do not translate
|
||||||
|
tr-help-squeeze = replace each sequence of a repeated character that is listed in the last specified SET, with a single occurrence of that character
|
||||||
|
tr-help-truncate-set1 = first truncate SET1 to length of SET2
|
||||||
|
|
||||||
|
# Error messages
|
||||||
|
tr-error-missing-operand = missing operand
|
||||||
|
tr-error-missing-operand-translating = missing operand after { $set }
|
||||||
|
Two strings must be given when translating.
|
||||||
|
tr-error-missing-operand-deleting-squeezing = missing operand after { $set }
|
||||||
|
Two strings must be given when deleting and squeezing.
|
||||||
|
tr-error-extra-operand-deleting-without-squeezing = extra operand { $operand }
|
||||||
|
Only one string may be given when deleting without squeezing repeats.
|
||||||
|
tr-error-extra-operand-simple = extra operand { $operand }
|
||||||
|
tr-error-read-directory = read error: Is a directory
|
||||||
|
tr-error-write-error = write error
|
||||||
|
|
||||||
|
# Warning messages
|
||||||
|
tr-warning-unescaped-backslash = warning: an unescaped backslash at end of string is not portable
|
||||||
|
tr-warning-ambiguous-octal-escape = the ambiguous octal escape \{ $origin_octal } is being interpreted as the 2-byte sequence \0{ $actual_octal_tail }, { $outstand_char }
|
||||||
|
|
||||||
|
# Sequence parsing error messages
|
||||||
|
tr-error-missing-char-class-name = missing character class name '[::]'
|
||||||
|
tr-error-missing-equivalence-class-char = missing equivalence class character '[==]'
|
||||||
|
tr-error-multiple-char-repeat-in-set2 = only one [c*] repeat construct may appear in string2
|
||||||
|
tr-error-char-repeat-in-set1 = the [c*] repeat construct may not appear in string1
|
||||||
|
tr-error-invalid-repeat-count = invalid repeat count { $count } in [c*n] construct
|
||||||
|
tr-error-empty-set2-when-not-truncating = when not truncating set1, string2 must be non-empty
|
||||||
|
tr-error-class-except-lower-upper-in-set2 = when translating, the only character classes that may appear in set2 are 'upper' and 'lower'
|
||||||
|
tr-error-class-in-set2-not-matched = when translating, every 'upper'/'lower' in set2 must be matched by a 'upper'/'lower' in the same position in set1
|
||||||
|
tr-error-set1-longer-set2-ends-in-class = when translating with string1 longer than string2,
|
||||||
|
the latter string must not end with a character class
|
||||||
|
tr-error-complement-more-than-one-unique = when translating with complemented character classes,
|
||||||
|
string2 must map all characters in the domain to one
|
||||||
|
tr-error-backwards-range = range-endpoints of '{ $start }-{ $end }' are in reverse collating sequence order
|
||||||
|
tr-error-multiple-char-in-equivalence = { $chars }: equivalence class operand must be a single character
|
||||||
|
|
42
src/uu/tr/locales/fr-FR.ftl
Normal file
42
src/uu/tr/locales/fr-FR.ftl
Normal file
|
@ -0,0 +1,42 @@
|
||||||
|
tr-about = Traduire ou supprimer des caractères
|
||||||
|
tr-usage = tr [OPTION]... ENSEMBLE1 [ENSEMBLE2]
|
||||||
|
tr-after-help = Traduire, compresser et/ou supprimer des caractères de l'entrée standard, en écrivant vers la sortie standard.
|
||||||
|
|
||||||
|
# Messages d'aide
|
||||||
|
tr-help-complement = utiliser le complément d'ENSEMBLE1
|
||||||
|
tr-help-delete = supprimer les caractères dans ENSEMBLE1, ne pas traduire
|
||||||
|
tr-help-squeeze = remplacer chaque séquence d'un caractère répété qui est listé dans le dernier ENSEMBLE spécifié, avec une seule occurrence de ce caractère
|
||||||
|
tr-help-truncate-set1 = d'abord tronquer ENSEMBLE1 à la longueur d'ENSEMBLE2
|
||||||
|
|
||||||
|
# Messages d'erreur
|
||||||
|
tr-error-missing-operand = opérande manquant
|
||||||
|
tr-error-missing-operand-translating = opérande manquant après { $set }
|
||||||
|
Deux chaînes doivent être données lors de la traduction.
|
||||||
|
tr-error-missing-operand-deleting-squeezing = opérande manquant après { $set }
|
||||||
|
Deux chaînes doivent être données lors de la suppression et compression.
|
||||||
|
tr-error-extra-operand-deleting-without-squeezing = opérande supplémentaire { $operand }
|
||||||
|
Une seule chaîne peut être donnée lors de la suppression sans compression des répétitions.
|
||||||
|
tr-error-extra-operand-simple = opérande supplémentaire { $operand }
|
||||||
|
tr-error-read-directory = erreur de lecture : Est un répertoire
|
||||||
|
tr-error-write-error = erreur d'écriture
|
||||||
|
|
||||||
|
# Messages d'avertissement
|
||||||
|
tr-warning-unescaped-backslash = avertissement : une barre oblique inverse non échappée à la fin de la chaîne n'est pas portable
|
||||||
|
tr-warning-ambiguous-octal-escape = l'échappement octal ambigu \{ $origin_octal } est en cours
|
||||||
|
d'interprétation comme la séquence de 2 octets \0{ $actual_octal_tail }, { $outstand_char }
|
||||||
|
|
||||||
|
# Messages d'erreur d'analyse de séquence
|
||||||
|
tr-error-missing-char-class-name = nom de classe de caractères manquant '[::]'
|
||||||
|
tr-error-missing-equivalence-class-char = caractère de classe d'équivalence manquant '[==]'
|
||||||
|
tr-error-multiple-char-repeat-in-set2 = seule une construction de répétition [c*] peut apparaître dans string2
|
||||||
|
tr-error-char-repeat-in-set1 = la construction de répétition [c*] ne peut pas apparaître dans string1
|
||||||
|
tr-error-invalid-repeat-count = nombre de répétitions invalide { $count } dans la construction [c*n]
|
||||||
|
tr-error-empty-set2-when-not-truncating = quand on ne tronque pas set1, string2 doit être non-vide
|
||||||
|
tr-error-class-except-lower-upper-in-set2 = lors de la traduction, les seules classes de caractères qui peuvent apparaître dans set2 sont 'upper' et 'lower'
|
||||||
|
tr-error-class-in-set2-not-matched = lors de la traduction, chaque 'upper'/'lower' dans set2 doit être associé à un 'upper'/'lower' à la même position dans set1
|
||||||
|
tr-error-set1-longer-set2-ends-in-class = lors de la traduction avec string1 plus long que string2,
|
||||||
|
cette dernière chaîne ne doit pas se terminer par une classe de caractères
|
||||||
|
tr-error-complement-more-than-one-unique = lors de la traduction avec des classes de caractères complémentées,
|
||||||
|
string2 doit mapper tous les caractères du domaine vers un seul
|
||||||
|
tr-error-backwards-range = les points de fin de plage de '{ $start }-{ $end }' sont dans l'ordre inverse de la séquence de collation
|
||||||
|
tr-error-multiple-char-in-equivalence = { $chars } : l'opérande de classe d'équivalence doit être un seul caractère
|
|
@ -24,6 +24,7 @@ use std::{
|
||||||
ops::Not,
|
ops::Not,
|
||||||
};
|
};
|
||||||
use uucore::error::{FromIo, UError, UResult};
|
use uucore::error::{FromIo, UError, UResult};
|
||||||
|
use uucore::locale::{get_message, get_message_with_args};
|
||||||
use uucore::show_warning;
|
use uucore::show_warning;
|
||||||
|
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
|
@ -45,44 +46,65 @@ pub enum BadSequence {
|
||||||
impl Display for BadSequence {
|
impl Display for BadSequence {
|
||||||
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
||||||
match self {
|
match self {
|
||||||
Self::MissingCharClassName => write!(f, "missing character class name '[::]'"),
|
Self::MissingCharClassName => {
|
||||||
|
write!(f, "{}", get_message("tr-error-missing-char-class-name"))
|
||||||
|
}
|
||||||
Self::MissingEquivalentClassChar => {
|
Self::MissingEquivalentClassChar => {
|
||||||
write!(f, "missing equivalence class character '[==]'")
|
write!(
|
||||||
|
f,
|
||||||
|
"{}",
|
||||||
|
get_message("tr-error-missing-equivalence-class-char")
|
||||||
|
)
|
||||||
}
|
}
|
||||||
Self::MultipleCharRepeatInSet2 => {
|
Self::MultipleCharRepeatInSet2 => {
|
||||||
write!(f, "only one [c*] repeat construct may appear in string2")
|
write!(
|
||||||
|
f,
|
||||||
|
"{}",
|
||||||
|
get_message("tr-error-multiple-char-repeat-in-set2")
|
||||||
|
)
|
||||||
}
|
}
|
||||||
Self::CharRepeatInSet1 => {
|
Self::CharRepeatInSet1 => {
|
||||||
write!(f, "the [c*] repeat construct may not appear in string1")
|
write!(f, "{}", get_message("tr-error-char-repeat-in-set1"))
|
||||||
}
|
}
|
||||||
Self::InvalidRepeatCount(count) => {
|
Self::InvalidRepeatCount(count) => {
|
||||||
write!(f, "invalid repeat count '{count}' in [c*n] construct")
|
write!(
|
||||||
|
f,
|
||||||
|
"{}",
|
||||||
|
get_message_with_args(
|
||||||
|
"tr-error-invalid-repeat-count",
|
||||||
|
HashMap::from([("count".to_string(), format!("'{}'", count))])
|
||||||
|
)
|
||||||
|
)
|
||||||
}
|
}
|
||||||
Self::EmptySet2WhenNotTruncatingSet1 => {
|
Self::EmptySet2WhenNotTruncatingSet1 => {
|
||||||
write!(f, "when not truncating set1, string2 must be non-empty")
|
write!(
|
||||||
|
f,
|
||||||
|
"{}",
|
||||||
|
get_message("tr-error-empty-set2-when-not-truncating")
|
||||||
|
)
|
||||||
}
|
}
|
||||||
Self::ClassExceptLowerUpperInSet2 => {
|
Self::ClassExceptLowerUpperInSet2 => {
|
||||||
write!(
|
write!(
|
||||||
f,
|
f,
|
||||||
"when translating, the only character classes that may appear in set2 are 'upper' and 'lower'"
|
"{}",
|
||||||
|
get_message("tr-error-class-except-lower-upper-in-set2")
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Self::ClassInSet2NotMatchedBySet1 => {
|
Self::ClassInSet2NotMatchedBySet1 => {
|
||||||
write!(
|
write!(f, "{}", get_message("tr-error-class-in-set2-not-matched"))
|
||||||
f,
|
|
||||||
"when translating, every 'upper'/'lower' in set2 must be matched by a 'upper'/'lower' in the same position in set1"
|
|
||||||
)
|
|
||||||
}
|
}
|
||||||
Self::Set1LongerSet2EndsInClass => {
|
Self::Set1LongerSet2EndsInClass => {
|
||||||
write!(
|
write!(
|
||||||
f,
|
f,
|
||||||
"when translating with string1 longer than string2,\nthe latter string must not end with a character class"
|
"{}",
|
||||||
|
get_message("tr-error-set1-longer-set2-ends-in-class")
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Self::ComplementMoreThanOneUniqueInSet2 => {
|
Self::ComplementMoreThanOneUniqueInSet2 => {
|
||||||
write!(
|
write!(
|
||||||
f,
|
f,
|
||||||
"when translating with complemented character classes,\nstring2 must map all characters in the domain to one"
|
"{}",
|
||||||
|
get_message("tr-error-complement-more-than-one-unique")
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Self::BackwardsRange { end, start } => {
|
Self::BackwardsRange { end, start } => {
|
||||||
|
@ -94,17 +116,25 @@ impl Display for BadSequence {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
write!(
|
write!(
|
||||||
f,
|
f,
|
||||||
"range-endpoints of '{}-{}' are in reverse collating sequence order",
|
"{}",
|
||||||
end_or_start_to_string(start),
|
get_message_with_args(
|
||||||
end_or_start_to_string(end)
|
"tr-error-backwards-range",
|
||||||
|
HashMap::from([
|
||||||
|
("start".to_string(), end_or_start_to_string(start)),
|
||||||
|
("end".to_string(), end_or_start_to_string(end))
|
||||||
|
])
|
||||||
|
)
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
Self::MultipleCharInEquivalence(s) => write!(
|
Self::MultipleCharInEquivalence(s) => write!(
|
||||||
f,
|
f,
|
||||||
"{s}: equivalence class operand must be a single character"
|
"{}",
|
||||||
|
get_message_with_args(
|
||||||
|
"tr-error-multiple-char-in-equivalence",
|
||||||
|
HashMap::from([("chars".to_string(), s.clone())])
|
||||||
|
)
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -364,11 +394,25 @@ impl Sequence {
|
||||||
let origin_octal: &str = std::str::from_utf8(input).unwrap();
|
let origin_octal: &str = std::str::from_utf8(input).unwrap();
|
||||||
let actual_octal_tail: &str = std::str::from_utf8(&input[0..2]).unwrap();
|
let actual_octal_tail: &str = std::str::from_utf8(&input[0..2]).unwrap();
|
||||||
let outstand_char: char = char::from_u32(input[2] as u32).unwrap();
|
let outstand_char: char = char::from_u32(input[2] as u32).unwrap();
|
||||||
show_warning!("the ambiguous octal escape \\{origin_octal} is being\n interpreted as the 2-byte sequence \\0{actual_octal_tail}, {outstand_char}");
|
show_warning!(
|
||||||
|
"{}",
|
||||||
|
get_message_with_args(
|
||||||
|
"tr-warning-ambiguous-octal-escape",
|
||||||
|
HashMap::from([
|
||||||
|
("origin_octal".to_string(), origin_octal.to_string()),
|
||||||
|
(
|
||||||
|
"actual_octal_tail".to_string(),
|
||||||
|
actual_octal_tail.to_string()
|
||||||
|
),
|
||||||
|
("outstand_char".to_string(), outstand_char.to_string())
|
||||||
|
])
|
||||||
|
)
|
||||||
|
);
|
||||||
}
|
}
|
||||||
result
|
result
|
||||||
},
|
},
|
||||||
).parse(input)
|
)
|
||||||
|
.parse(input)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn parse_octal_two_digits(input: &[u8]) -> IResult<&[u8], u8> {
|
fn parse_octal_two_digits(input: &[u8]) -> IResult<&[u8], u8> {
|
||||||
|
@ -666,7 +710,7 @@ where
|
||||||
|
|
||||||
output
|
output
|
||||||
.write_all(&output_buf)
|
.write_all(&output_buf)
|
||||||
.map_err_context(|| "write error".into())?;
|
.map_err_context(|| get_message("tr-error-write-error"))?;
|
||||||
|
|
||||||
buf.clear();
|
buf.clear();
|
||||||
output_buf.clear();
|
output_buf.clear();
|
||||||
|
|
|
@ -13,6 +13,7 @@ use clap::{Arg, ArgAction, Command, value_parser};
|
||||||
use operation::{
|
use operation::{
|
||||||
Sequence, SqueezeOperation, SymbolTranslator, TranslateOperation, translate_input,
|
Sequence, SqueezeOperation, SymbolTranslator, TranslateOperation, translate_input,
|
||||||
};
|
};
|
||||||
|
use std::collections::HashMap;
|
||||||
use std::ffi::OsString;
|
use std::ffi::OsString;
|
||||||
use std::io::{BufWriter, Write, stdin, stdout};
|
use std::io::{BufWriter, Write, stdin, stdout};
|
||||||
use uucore::display::Quotable;
|
use uucore::display::Quotable;
|
||||||
|
@ -20,7 +21,7 @@ use uucore::error::{FromIo, UResult, USimpleError, UUsageError};
|
||||||
use uucore::fs::is_stdin_directory;
|
use uucore::fs::is_stdin_directory;
|
||||||
use uucore::{format_usage, os_str_as_bytes, show};
|
use uucore::{format_usage, os_str_as_bytes, show};
|
||||||
|
|
||||||
use uucore::locale::get_message;
|
use uucore::locale::{get_message, get_message_with_args};
|
||||||
|
|
||||||
mod options {
|
mod options {
|
||||||
pub const COMPLEMENT: &str = "complement";
|
pub const COMPLEMENT: &str = "complement";
|
||||||
|
@ -53,15 +54,15 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||||
let sets_len = sets.len();
|
let sets_len = sets.len();
|
||||||
|
|
||||||
if sets.is_empty() {
|
if sets.is_empty() {
|
||||||
return Err(UUsageError::new(1, "missing operand"));
|
return Err(UUsageError::new(1, get_message("tr-error-missing-operand")));
|
||||||
}
|
}
|
||||||
|
|
||||||
if !(delete_flag || squeeze_flag) && sets_len < 2 {
|
if !(delete_flag || squeeze_flag) && sets_len < 2 {
|
||||||
return Err(UUsageError::new(
|
return Err(UUsageError::new(
|
||||||
1,
|
1,
|
||||||
format!(
|
get_message_with_args(
|
||||||
"missing operand after {}\nTwo strings must be given when translating.",
|
"tr-error-missing-operand-translating",
|
||||||
sets[0].quote()
|
HashMap::from([("set".to_string(), sets[0].quote().to_string())]),
|
||||||
),
|
),
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
@ -69,29 +70,35 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||||
if delete_flag & squeeze_flag && sets_len < 2 {
|
if delete_flag & squeeze_flag && sets_len < 2 {
|
||||||
return Err(UUsageError::new(
|
return Err(UUsageError::new(
|
||||||
1,
|
1,
|
||||||
format!(
|
get_message_with_args(
|
||||||
"missing operand after {}\nTwo strings must be given when deleting and squeezing.",
|
"tr-error-missing-operand-deleting-squeezing",
|
||||||
sets[0].quote()
|
HashMap::from([("set".to_string(), sets[0].quote().to_string())]),
|
||||||
),
|
),
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
if sets_len > 1 {
|
if sets_len > 1 {
|
||||||
let start = "extra operand";
|
|
||||||
if delete_flag && !squeeze_flag {
|
if delete_flag && !squeeze_flag {
|
||||||
let op = sets[1].quote();
|
let op = sets[1].quote();
|
||||||
let msg = if sets_len == 2 {
|
let msg = if sets_len == 2 {
|
||||||
format!(
|
get_message_with_args(
|
||||||
"{start} {op}\nOnly one string may be given when deleting without squeezing repeats.",
|
"tr-error-extra-operand-deleting-without-squeezing",
|
||||||
|
HashMap::from([("operand".to_string(), op.to_string())]),
|
||||||
)
|
)
|
||||||
} else {
|
} else {
|
||||||
format!("{start} {op}")
|
get_message_with_args(
|
||||||
|
"tr-error-extra-operand-simple",
|
||||||
|
HashMap::from([("operand".to_string(), op.to_string())]),
|
||||||
|
)
|
||||||
};
|
};
|
||||||
return Err(UUsageError::new(1, msg));
|
return Err(UUsageError::new(1, msg));
|
||||||
}
|
}
|
||||||
if sets_len > 2 {
|
if sets_len > 2 {
|
||||||
let op = sets[2].quote();
|
let op = sets[2].quote();
|
||||||
let msg = format!("{start} {op}");
|
let msg = get_message_with_args(
|
||||||
|
"tr-error-extra-operand-simple",
|
||||||
|
HashMap::from([("operand".to_string(), op.to_string())]),
|
||||||
|
);
|
||||||
return Err(UUsageError::new(1, msg));
|
return Err(UUsageError::new(1, msg));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -103,7 +110,7 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||||
// The trailing backslash has a non-backslash character before it.
|
// The trailing backslash has a non-backslash character before it.
|
||||||
show!(USimpleError::new(
|
show!(USimpleError::new(
|
||||||
0,
|
0,
|
||||||
"warning: an unescaped backslash at end of string is not portable"
|
get_message("tr-warning-unescaped-backslash")
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -125,7 +132,7 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||||
)?;
|
)?;
|
||||||
|
|
||||||
if is_stdin_directory(&stdin) {
|
if is_stdin_directory(&stdin) {
|
||||||
return Err(USimpleError::new(1, "read error: Is a directory"));
|
return Err(USimpleError::new(1, get_message("tr-error-read-directory")));
|
||||||
}
|
}
|
||||||
|
|
||||||
// '*_op' are the operations that need to be applied, in order.
|
// '*_op' are the operations that need to be applied, in order.
|
||||||
|
@ -156,7 +163,7 @@ pub fn uumain(args: impl uucore::Args) -> UResult<()> {
|
||||||
|
|
||||||
buffered_stdout
|
buffered_stdout
|
||||||
.flush()
|
.flush()
|
||||||
.map_err_context(|| "write error".into())?;
|
.map_err_context(|| get_message("tr-error-write-error"))?;
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
@ -173,7 +180,7 @@ pub fn uu_app() -> Command {
|
||||||
.visible_short_alias('C')
|
.visible_short_alias('C')
|
||||||
.short('c')
|
.short('c')
|
||||||
.long(options::COMPLEMENT)
|
.long(options::COMPLEMENT)
|
||||||
.help("use the complement of SET1")
|
.help(get_message("tr-help-complement"))
|
||||||
.action(ArgAction::SetTrue)
|
.action(ArgAction::SetTrue)
|
||||||
.overrides_with(options::COMPLEMENT),
|
.overrides_with(options::COMPLEMENT),
|
||||||
)
|
)
|
||||||
|
@ -181,7 +188,7 @@ pub fn uu_app() -> Command {
|
||||||
Arg::new(options::DELETE)
|
Arg::new(options::DELETE)
|
||||||
.short('d')
|
.short('d')
|
||||||
.long(options::DELETE)
|
.long(options::DELETE)
|
||||||
.help("delete characters in SET1, do not translate")
|
.help(get_message("tr-help-delete"))
|
||||||
.action(ArgAction::SetTrue)
|
.action(ArgAction::SetTrue)
|
||||||
.overrides_with(options::DELETE),
|
.overrides_with(options::DELETE),
|
||||||
)
|
)
|
||||||
|
@ -189,11 +196,7 @@ pub fn uu_app() -> Command {
|
||||||
Arg::new(options::SQUEEZE)
|
Arg::new(options::SQUEEZE)
|
||||||
.long(options::SQUEEZE)
|
.long(options::SQUEEZE)
|
||||||
.short('s')
|
.short('s')
|
||||||
.help(
|
.help(get_message("tr-help-squeeze"))
|
||||||
"replace each sequence of a repeated character that is \
|
|
||||||
listed in the last specified SET, with a single occurrence \
|
|
||||||
of that character",
|
|
||||||
)
|
|
||||||
.action(ArgAction::SetTrue)
|
.action(ArgAction::SetTrue)
|
||||||
.overrides_with(options::SQUEEZE),
|
.overrides_with(options::SQUEEZE),
|
||||||
)
|
)
|
||||||
|
@ -201,7 +204,7 @@ pub fn uu_app() -> Command {
|
||||||
Arg::new(options::TRUNCATE_SET1)
|
Arg::new(options::TRUNCATE_SET1)
|
||||||
.long(options::TRUNCATE_SET1)
|
.long(options::TRUNCATE_SET1)
|
||||||
.short('t')
|
.short('t')
|
||||||
.help("first truncate SET1 to length of SET2")
|
.help(get_message("tr-help-truncate-set1"))
|
||||||
.action(ArgAction::SetTrue)
|
.action(ArgAction::SetTrue)
|
||||||
.overrides_with(options::TRUNCATE_SET1),
|
.overrides_with(options::TRUNCATE_SET1),
|
||||||
)
|
)
|
||||||
|
|
|
@ -1521,7 +1521,7 @@ fn test_multibyte_octal_sequence() {
|
||||||
.args(&["-d", r"\501"])
|
.args(&["-d", r"\501"])
|
||||||
.pipe_in("(1Ł)")
|
.pipe_in("(1Ł)")
|
||||||
.succeeds()
|
.succeeds()
|
||||||
.stderr_is("tr: warning: the ambiguous octal escape \\501 is being\n interpreted as the 2-byte sequence \\050, 1\n")
|
.stderr_is("tr: warning: the ambiguous octal escape \\501 is being interpreted as the 2-byte sequence \\050, 1\n")
|
||||||
.stdout_is("Ł)");
|
.stdout_is("Ł)");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue