Merge pull request #11565

This commit is contained in:
Johannes Altmanninger
2025-06-16 12:25:08 +02:00
15 changed files with 189 additions and 58 deletions

View File

@@ -2,17 +2,25 @@
set -ex
cleanup () {
if [ -n "$template_file" ] && [ -e "$template_file" ]; then
rm "$template_file"
fi
}
trap cleanup EXIT INT TERM HUP
RUSTFLAGS='-D warnings'; export RUSTFLAGS
RUSTDOCFLAGS='-D warnings'; export RUSTDOCFLAGS
repo_root="$(dirname "$0")/.."
build_dir="$repo_root/target/debug"
cargo build --workspace --all-targets
template_file=$(mktemp)
FISH_GETTEXT_EXTRACTION_FILE=$template_file cargo build --workspace --all-targets
PATH="$build_dir:$PATH" "$repo_root/build_tools/style.fish" --all --check
cargo clippy --workspace --all-targets
cargo test --no-default-features --workspace --all-targets
cargo test --doc --workspace
cargo doc --workspace
"$repo_root/tests/test_driver.py" "$build_dir"
FISH_GETTEXT_EXTRACTION_FILE=$template_file "$repo_root/tests/test_driver.py" "$build_dir"

View File

@@ -2,6 +2,10 @@
#
# Tool to generate gettext messages template file.
# Writes to stdout.
# Intended to be called from `update_translations.fish`.
argparse use-existing-template= -- $argv
or exit $status
begin
# Write header. This is required by msguniq.
@@ -15,17 +19,25 @@ begin
echo ""
end
set -l rust_extraction_file (mktemp)
set -g repo_root (status dirname)/..
# We need to build to ensure that the proc macro for extracting strings runs.
FISH_GETTEXT_EXTRACTION_FILE=$rust_extraction_file cargo check
or exit 1
set -l rust_extraction_file
if set -l --query _flag_use_existing_template
set rust_extraction_file $_flag_use_existing_template
else
set rust_extraction_file (mktemp)
# We need to build to ensure that the proc macro for extracting strings runs.
FISH_GETTEXT_EXTRACTION_FILE=$rust_extraction_file cargo check
or exit 1
end
# Get rid of duplicates and sort.
msguniq --no-wrap --strict --sort-output $rust_extraction_file
or exit 1
rm $rust_extraction_file
if not set -l --query _flag_use_existing_template
rm $rust_extraction_file
end
function extract_fish_script_messages --argument-names regex
@@ -47,13 +59,15 @@ begin
# 5. Double quotes are escaped, such that they are not interpreted as the start or end of
# a msgid.
# 6. We transform the string into the format expected in a PO file.
cat share/config.fish share/completions/*.fish share/functions/*.fish |
cat $share_dir/config.fish $share_dir/completions/*.fish $share_dir/functions/*.fish |
string replace --filter --regex $regex '$1' |
string unescape |
sort -u |
sed -E -e 's_\\\\_\\\\\\\\_g' -e 's_"_\\\\"_g' -e 's_^(.*)$_msgid "\1"\nmsgstr ""\n_'
end
set -g share_dir $repo_root/share
# This regex handles explicit requests to translate a message. These are more important to translate
# than messages which should be implicitly translated.
set -l explicit_regex '.*\( *_ (([\'"]).+?(?<!\\\\)\\2) *\).*'

View File

@@ -21,6 +21,15 @@
# - Specify `--dry-run` to see if any updates to the PO files would by applied by this script.
# If this flag is specified, the script will exit with an error if there are outstanding
# changes, and will display the diff. Do not specify other flags if `--dry-run` is specified.
#
# Specify `--use-existing-template=FILE` to prevent running cargo for extracting an up-to-date
# version of the localized strings. This flag is intended for testing setups which make it
# inconvenient to run cargo here, but run it in an earlier step to ensure up-to-date values.
# This argument is passed on to the `fish_xgettext.fish` script and has no other uses.
# `FILE` must be the path to a gettext template file generated from our compilation process.
# It can be obtained by running:
# set -l FILE (mktemp)
# FISH_GETTEXT_EXTRACTION_FILE=$FILE cargo check
# The sort utility is locale-sensitive.
# Ensure that sorting output is consistent by setting LC_ALL here.
@@ -44,7 +53,7 @@ function cleanup_exit
exit $exit_status
end
argparse --exclusive 'no-mo,only-mo,dry-run' no-mo only-mo dry-run -- $argv
argparse --exclusive 'no-mo,only-mo,dry-run' no-mo only-mo dry-run use-existing-template= -- $argv
or exit $status
# Make sure that the template file is not included in $po_files.
@@ -84,7 +93,11 @@ if set -l --query _flag_only_mo
end
if set -l --query extract
$build_tools/fish_xgettext.fish >$template_file
set -l xgettext_args
if set -l --query _flag_use_existing_template
set xgettext_args --use-existing-template=$_flag_use_existing_template
end
$build_tools/fish_xgettext.fish $xgettext_args >$template_file
or exit 1
end
@@ -126,7 +139,7 @@ rm $template_file
if set -g --query tmpdir
rm $tmpdir/template.po
diff -ur po $tmpdir
diff -ur $po_dir $tmpdir
or cleanup_exit
end

View File

@@ -700,6 +700,11 @@ msgstr ""
msgid "%ls: expected a numeric value"
msgstr "%ls: Erwartete numerischen Wert"
#
#, c-format
msgid "%ls: fish was not built with embedded files"
msgstr ""
#, c-format
msgid "%ls: function name required"
msgstr "%ls: Brauche Funktionsnamen"
@@ -1179,6 +1184,10 @@ msgstr "Illegale Instruktion"
msgid "Incomplete escape sequence '%ls'"
msgstr "Unvollständige Escapesequenz '%ls'"
#
msgid "Information request"
msgstr ""
#, c-format
msgid "Integer %lld in '%ls' followed by non-digit"
msgstr "Ganzzahl %lld in '%ls' gefolgt von nicht-Ziffer"
@@ -1709,6 +1718,10 @@ msgstr "Nicht passender Platzhalter"
msgid "Unsupported use of '='. In fish, please use 'set %ls %ls'."
msgstr ""
#
msgid "Unused signal"
msgstr ""
msgid "Urgent socket condition"
msgstr "Vorrangige Socket-Bedingung"

View File

@@ -698,6 +698,11 @@ msgstr ""
msgid "%ls: expected a numeric value"
msgstr "%ls: expected a numeric value"
#
#, c-format
msgid "%ls: fish was not built with embedded files"
msgstr ""
#, c-format
msgid "%ls: function name required"
msgstr ""
@@ -1177,6 +1182,9 @@ msgstr "Illegal instruction"
msgid "Incomplete escape sequence '%ls'"
msgstr ""
msgid "Information request"
msgstr "Information request"
#, c-format
msgid "Integer %lld in '%ls' followed by non-digit"
msgstr ""
@@ -1707,6 +1715,9 @@ msgstr ""
msgid "Unsupported use of '='. In fish, please use 'set %ls %ls'."
msgstr ""
msgid "Unused signal"
msgstr "Unused signal"
msgid "Urgent socket condition"
msgstr "Urgent socket condition"
@@ -79398,15 +79409,9 @@ msgstr ""
#~ msgid "Virtual timer expired"
#~ msgstr "Virtual timer expired"
#~ msgid "Information request"
#~ msgstr "Information request"
#~ msgid "Emulator trap"
#~ msgstr "Emulator trap"
#~ msgid "Unused signal"
#~ msgstr "Unused signal"
#~ msgid "Process file after the compiler reads in the standard specs file, in order to override the defaults that the gcc driver program uses when determining what switches to pass to cc1, cc1plus, as, ld, etc"
#~ msgstr "Process file after the compiler reads in the standard specs file, in order to override the defaults that the gcc driver program uses when determining what switches to pass to cc1, cc1plus, as, ld, etc"

View File

@@ -799,6 +799,11 @@ msgstr ""
msgid "%ls: expected a numeric value"
msgstr "%ls : valeur numérique attendue"
#
#, c-format
msgid "%ls: fish was not built with embedded files"
msgstr ""
#, c-format
msgid "%ls: function name required"
msgstr ""
@@ -1278,6 +1283,9 @@ msgstr "Instruction illégale"
msgid "Incomplete escape sequence '%ls'"
msgstr ""
msgid "Information request"
msgstr "Demande d'information"
#, c-format
msgid "Integer %lld in '%ls' followed by non-digit"
msgstr ""
@@ -1808,6 +1816,9 @@ msgstr ""
msgid "Unsupported use of '='. In fish, please use 'set %ls %ls'."
msgstr "Usage de '=' non supporté. Dans fish, veuillez utiliser 'set %ls %ls'."
msgid "Unused signal"
msgstr "Signal inutilisé"
msgid "Urgent socket condition"
msgstr "Condition urgente de socket"
@@ -80784,15 +80795,9 @@ msgstr ""
#~ msgid "Virtual timer expired"
#~ msgstr "Délai virtuel expiré"
#~ msgid "Information request"
#~ msgstr "Demande d'information"
#~ msgid "Emulator trap"
#~ msgstr "Déroutement d'émulation"
#~ msgid "Unused signal"
#~ msgstr "Signal inutilisé"
#, c-format
#~ msgid "getcwd() failed with errno %d/%s"
#~ msgstr "getcwd() a échoué avec lerreur %d/%s"

View File

@@ -694,6 +694,11 @@ msgstr ""
msgid "%ls: expected a numeric value"
msgstr "%ls: oczekiwano wartości liczbowej"
#
#, c-format
msgid "%ls: fish was not built with embedded files"
msgstr ""
#, c-format
msgid "%ls: function name required"
msgstr ""
@@ -1173,6 +1178,9 @@ msgstr "Niedozwolona instrukcja"
msgid "Incomplete escape sequence '%ls'"
msgstr ""
msgid "Information request"
msgstr "Żądanie informacji"
#, c-format
msgid "Integer %lld in '%ls' followed by non-digit"
msgstr ""
@@ -1703,6 +1711,9 @@ msgstr ""
msgid "Unsupported use of '='. In fish, please use 'set %ls %ls'."
msgstr "Nieobsługiwane użycie '='. W fish używane jest 'set %ls %ls'."
msgid "Unused signal"
msgstr "Niewykorzystywany sygnał"
msgid "Urgent socket condition"
msgstr ""
@@ -79219,12 +79230,6 @@ msgstr ""
#~ msgid "Could not return shell to foreground"
#~ msgstr "Nie można przywrócić powłoki na pierwszy plan"
#~ msgid "Information request"
#~ msgstr "Żądanie informacji"
#~ msgid "Unused signal"
#~ msgstr "Niewykorzystywany sygnał"
#, c-format
#~ msgid "Send job %d '%ls' to background\n"
#~ msgstr "Wyślij zadanie %d '%ls' w tło\n"

View File

@@ -699,6 +699,11 @@ msgstr ""
msgid "%ls: expected a numeric value"
msgstr "%ls: esperava valor numérico"
#
#, c-format
msgid "%ls: fish was not built with embedded files"
msgstr ""
#, c-format
msgid "%ls: function name required"
msgstr ""
@@ -1178,6 +1183,9 @@ msgstr "Instrução ilegal"
msgid "Incomplete escape sequence '%ls'"
msgstr ""
msgid "Information request"
msgstr "Requisição de informação"
#, c-format
msgid "Integer %lld in '%ls' followed by non-digit"
msgstr ""
@@ -1708,6 +1716,9 @@ msgstr ""
msgid "Unsupported use of '='. In fish, please use 'set %ls %ls'."
msgstr ""
msgid "Unused signal"
msgstr "Sinal não utilizado"
msgid "Urgent socket condition"
msgstr "Condição urgente de socket"
@@ -79275,15 +79286,9 @@ msgstr ""
#~ msgid "Virtual timer expired"
#~ msgstr "Temporizador virtual expirado"
#~ msgid "Information request"
#~ msgstr "Requisição de informação"
#~ msgid "Emulator trap"
#~ msgstr "Armadilha de emulador"
#~ msgid "Unused signal"
#~ msgstr "Sinal não utilizado"
#~ msgid "Use new incremental GNU format"
#~ msgstr "Use new incremental GNU format"

View File

@@ -695,6 +695,11 @@ msgstr ""
msgid "%ls: expected a numeric value"
msgstr ""
#
#, c-format
msgid "%ls: fish was not built with embedded files"
msgstr ""
#, c-format
msgid "%ls: function name required"
msgstr ""
@@ -1174,6 +1179,9 @@ msgstr "Ogiltig instruktion"
msgid "Incomplete escape sequence '%ls'"
msgstr ""
msgid "Information request"
msgstr "Informationsbegäran"
#, c-format
msgid "Integer %lld in '%ls' followed by non-digit"
msgstr ""
@@ -1704,6 +1712,9 @@ msgstr ""
msgid "Unsupported use of '='. In fish, please use 'set %ls %ls'."
msgstr ""
msgid "Unused signal"
msgstr "Oanvänd signal"
msgid "Urgent socket condition"
msgstr "Viktig socket-situation"
@@ -79266,15 +79277,9 @@ msgstr ""
#~ msgid "Virtual timer expired"
#~ msgstr "Virtuell timer utlöst"
#~ msgid "Information request"
#~ msgstr "Informationsbegäran"
#~ msgid "Emulator trap"
#~ msgstr "Emulatorfälla"
#~ msgid "Unused signal"
#~ msgstr "Oanvänd signal"
#~ msgid "Use new incremental GNU format"
#~ msgstr "Använd nytt inkrementellt GNU-format"

View File

@@ -692,6 +692,11 @@ msgstr ""
msgid "%ls: expected a numeric value"
msgstr "%ls: 预期数字类型值"
#
#, c-format
msgid "%ls: fish was not built with embedded files"
msgstr ""
#, c-format
msgid "%ls: function name required"
msgstr "%ls: 函数名称是必须的"
@@ -1171,6 +1176,10 @@ msgstr ""
msgid "Incomplete escape sequence '%ls'"
msgstr "不完整的转义序列 '%ls'"
#
msgid "Information request"
msgstr ""
#, c-format
msgid "Integer %lld in '%ls' followed by non-digit"
msgstr "整数 %lld 在 '%ls' 中,后面跟随着非数字"
@@ -1701,6 +1710,10 @@ msgstr "未匹配的通配符"
msgid "Unsupported use of '='. In fish, please use 'set %ls %ls'."
msgstr "不支持使用'='. 在fish类中,请使用'set %ls %ls'."
#
msgid "Unused signal"
msgstr ""
msgid "Urgent socket condition"
msgstr ""

View File

@@ -327,6 +327,11 @@ fn parse_cmd_opts(
struct Docs;
pub fn status(parser: &Parser, streams: &mut IoStreams, args: &mut [&wstr]) -> BuiltinResult {
localizable_consts!(
#[allow(dead_code)]
NO_EMBEDDED_FILES_MSG "%ls: fish was not built with embedded files"
);
let cmd = args[0];
let argc = args.len();
@@ -474,10 +479,9 @@ pub fn status(parser: &Parser, streams: &mut IoStreams, args: &mut [&wstr]) -> B
}
#[cfg(not(feature = "embed-data"))]
{
streams.err.appendln(wgettext_fmt!(
"%ls: fish was not built with embedded files",
cmd,
));
streams
.err
.appendln(sprintf!(NO_EMBEDDED_FILES_MSG.localize(), cmd));
return Err(STATUS_CMD_ERROR);
}
}
@@ -520,10 +524,9 @@ pub fn status(parser: &Parser, streams: &mut IoStreams, args: &mut [&wstr]) -> B
}
#[cfg(not(feature = "embed-data"))]
{
streams.err.appendln(wgettext_fmt!(
"%ls: fish was not built with embedded files",
cmd,
));
streams
.err
.appendln(sprintf!(NO_EMBEDDED_FILES_MSG.localize(), cmd));
return Err(STATUS_CMD_ERROR);
}
}

View File

@@ -362,13 +362,16 @@ const fn new(signal: i32, name: &'static wstr, desc: LocalizableString) -> Self
}
macro_rules! signal_entry {
($name:ident, $desc:expr) => {
($name:ident, $desc:literal) => {
LookupEntry::new(
libc::$name,
L!(stringify!($name)),
localizable_string!($desc),
)
};
($name:ident, $desc:expr) => {
LookupEntry::new(libc::$name, L!(stringify!($name)), $desc)
};
}
// Lookup table used to convert between signal names and signal ids, etc.
@@ -406,24 +409,41 @@ macro_rules! signal_entry {
signal_entry!(SIGIOT, "Abort (Alias for SIGABRT)"),
#[cfg(any(apple, bsd))]
signal_entry!(SIGEMT, "Unused signal"),
signal_entry!(SIGEMT, SIGEMT_DESC),
#[cfg(any(apple, bsd))]
signal_entry!(SIGINFO, "Information request"),
signal_entry!(SIGINFO, SIGINFO_DESC),
#[cfg(target_os = "linux")]
signal_entry!(SIGSTKFLT, "Stack fault"),
signal_entry!(SIGSTKFLT, SIGSTKFLT_DESC),
#[cfg(target_os = "linux")]
signal_entry!(SIGIOT, "Abort (Alias for SIGABRT)"),
signal_entry!(SIGIOT, SIGIOT_DESC),
#[cfg(target_os = "linux")]
signal_entry!(SIGPWR, "Power failure"),
signal_entry!(SIGPWR, SIGPWR_DESC),
// TODO: determine whether SIGWIND is defined on any platform.
//signal_entry!(SIGWIND, "Window size change"),
];
localizable_consts!(
#[allow(dead_code)]
SIGEMT_DESC "Unused signal"
#[allow(dead_code)]
SIGINFO_DESC "Information request"
#[allow(dead_code)]
SIGSTKFLT_DESC "Stack fault"
#[allow(dead_code)]
SIGIOT_DESC "Abort (Alias for SIGABRT)"
#[allow(dead_code)]
SIGPWR_DESC "Power failure"
);
// Return true if two strings are equal, ignoring ASCII case.
fn equals_ascii_icase(left: &wstr, right: &wstr) -> bool {
if left.len() != right.len() {

View File

@@ -194,6 +194,7 @@ macro_rules! localizable_consts {
)*
) => {
$(
$(#[$attr])*
$vis const $name: $crate::wutil::gettext::LocalizableString =
localizable_string!($string);
)*
@@ -247,8 +248,10 @@ macro_rules! wgettext_fmt {
#[serial]
fn test_unlocalized() {
let _cleanup = test_init();
let s: &'static wstr = wgettext!("abc");
let abc_str = LocalizableString::from_external_source(WString::from("abc"));
let s: &'static wstr = wgettext!(abc_str);
assert_eq!(s, "abc");
let s2: &'static wstr = wgettext!("static");
let static_str = LocalizableString::from_external_source(WString::from("static"));
let s2: &'static wstr = wgettext!(static_str);
assert_eq!(s2, "static");
}

View File

@@ -0,0 +1,19 @@
#RUN: fish=%fish %fish %s
#REQUIRES: msguniq --help
# Compiling in this test is too expensive.
# We need the gettext template extracted from the Rust sources passed in via env var,
# in order to pass it on.
#REQUIRES: test -e "$FISH_GETTEXT_EXTRACTION_FILE"
set -l dir (status dirname)
# Ensure that fish is in $PATH for the translation scripts.
set -lxp PATH (path dirname $fish)
# Using cargo in this test is expensive because $HOME is changed,
# so the entire toolchain needs to be downloaded and installed,
# followed by a clean build of the repo.
# The `--use-existing-template` argument allows using the pre-built version of the gettext template
# file.
$dir/../../build_tools/update_translations.fish --dry-run --use-existing-template=$FISH_GETTEXT_EXTRACTION_FILE
or exit 1