From b70d42ae5acf4b7fcc806935d97215b679ed843b Mon Sep 17 00:00:00 2001 From: Martin Quinson Date: Fri, 1 Mar 2024 01:10:23 +0100 Subject: [PATCH] Fix the --translate-only option I added a lot of verbose messages to understand what's going on, rewrote a bit of code I didn't understant but was not recently modified, and the bug introduced last month was gone. At the end, I'm not sure of what happened, but this fixes https://github.com/mquinson/po4a/issues/482 Thanks Alexander for the diagnostic and the reproducer! --- NEWS | 3 + po4a | 78 +++++++++++++++++------- t/Testhelper.pm | 2 +- t/add/modifiers/_output | 1 + t/cfg-multi.t | 22 ++++++- t/cfg/args-alias-redef/_output | 1 + t/cfg/args-alias/_output | 1 + t/cfg/args-alias/_output-keep100 | 1 + t/cfg/args-global/_output | 1 + t/cfg/args-global/_output-keep100 | 1 + t/cfg/args-master/_output | 1 + t/cfg/args-master/_output-keep100 | 1 + t/cfg/multiple-fuzzied-noup/_output | 1 + t/cfg/multiple-nopo/_output-noupdate | 1 + t/cfg/multiple-uptodate/_output-only-one | 4 ++ t/cfg/multiple-uptodate/_output-only-two | 5 ++ t/cfg/single-fuzzied-noup/_output | 1 + t/cfg/single-nopo/_output-noupdate | 1 + 18 files changed, 101 insertions(+), 25 deletions(-) create mode 100644 t/cfg/multiple-uptodate/_output-only-one create mode 100644 t/cfg/multiple-uptodate/_output-only-two diff --git a/NEWS b/NEWS index 0b62ad29a..c9187ca7b 100644 --- a/NEWS +++ b/NEWS @@ -9,6 +9,9 @@ __ __/ _ \|___ |___ \ \ V /| |_| | / / / __/ \_/ \___(_)_/ |_____| (unreleased) +po4a main script: + * Fix the behavior of --translate-only (GitHub's #482) [Mt & Golubev Alexander]. + Documentation: * Fix typos (GitHub's #478) [Marco Ciampa & Helge Kreutzmann] diff --git a/po4a b/po4a index 14222062f..72736013e 100755 --- a/po4a +++ b/po4a @@ -1319,11 +1319,12 @@ while () { } if ( scalar @{ $po4a_opts{"partial"} } ) { foreach my $file ( @{ $po4a_opts{"partial"} } ) { - if ( grep ( m/(\S+):\Q$file\E\b/, @split_args ) ) { - $partial{'lang'}{$1} = 1; - $partial{'master'}{$main} = 1; - $partial{'files'}{$file} = 1; - last; + foreach my $arg (@split_args) { + if ( $arg =~ m/(\S+):\Q$file\E\b/ ) { + $partial{'lang'}{$1} = 1; + $partial{'master'}{$main} = 1; + $partial{'files'}{$file} = 1; + } } } } @@ -1344,7 +1345,7 @@ while () { $document{$main}{'format'} = $aliases{$1}{"module"}; if ( defined $aliases{$1}{"options"} ) { - # print STDERR "Override the global options with the alias ones\n"; + # print STDERR "Override the global options with the alias ones\n"; %options = %{ $aliases{$1}{"options"} }; # XXX not a merge, but overwrite } } @@ -1440,16 +1441,18 @@ while () { } } } elsif ( $cmd =~ m/po4a_alias: *(.*)/ ) { - my $name = $1; + my $name = $1; shift @split_args; - if ( defined $aliases{$name} ) { # If that alias was previously defined - die "Alias $name redefined from ".$aliases{$name}{"module"}." to $main\n" - if ( $aliases{$name}{"module"} ne $main ); # Sanity checks - # Concat the new content to the existing alias - @split_args = map { parse_config_options( "$config_file:$nb", $_, \%{ $aliases{$name}{"options"} } ); } @split_args; - } else { - # Otherwise, define a new option set accordingly + if ( defined $aliases{$name} ) { # If that alias was previously defined + die "Alias $name redefined from " . $aliases{$name}{"module"} . " to $main\n" + if ( $aliases{$name}{"module"} ne $main ); + + # Concat the new content to the existing alias after a sanity check + @split_args = + map { parse_config_options( "$config_file:$nb", $_, \%{ $aliases{$name}{"options"} } ); } @split_args; + + } else { # Otherwise, define a new option set accordingly my %alias = (); $alias{"module"} = $main; @@ -1530,13 +1533,33 @@ if ( $pot_filename =~ m/\$master/ ) { # Skip documents not specified, strings are read directly from POT file foreach my $master ( keys %document ) { - next unless length $master; - delete $document{$master} unless exists $partial{'master'}{$master}; + next unless length $master; + if ( exists $partial{'master'}{$master} ) { + print wrap_msg( gettext("Document %s kept for update (--translate-only)."), $master ) + if ( $po4a_opts{"verbose"} ); + } else { + print wrap_msg( gettext("Skip the update of %s as requested (--translate-only)."), $master ) + if ( $po4a_opts{"verbose"} ); + delete $document{$master}; + } } # Do not read PO files if no file is processed for this language - foreach my $lang ( keys %po_filename ) { - delete $po_filename{$lang} unless exists $partial{'lang'}{$lang}; + my $skipped_langs = ""; + my $kept_langs = ""; + foreach my $lang ( sort keys %po_filename ) { + if ( exists $partial{'lang'}{$lang} ) { + $kept_langs .= " $lang"; + } else { + $skipped_langs .= " $lang"; + delete $po_filename{$lang}; + } + } + if ( $po4a_opts{"verbose"} ) { + $skipped_langs =~ s/^ //; + $kept_langs =~ s/^ //; + print wrap_msg( gettext("Languages skipped because of --translate-only: %s; kept languages: %s."), + $skipped_langs, $kept_langs ); } } @@ -1654,8 +1677,16 @@ if ($update_pot_file) { print wrap_msg( gettext(" (%d entries)"), $potfile->count_entries() ) unless ( $po4a_opts{"quiet"} ); } else { - print wrap_msg( gettext("POT file %s already up to date."), $pot_filename ) - if ( $po4a_opts{"verbose"} and not $po4a_opts{"no-update"} ); + if ( $po4a_opts{"no-update"} ) { + print wrap_msg( gettext("NOT updating the POT file %s as requested (--no-update)."), $pot_filename ) + if ( $po4a_opts{"verbose"} ); + } elsif ( scalar @{ $po4a_opts{"partial"} } ) { + print wrap_msg( gettext("NOT updating the POT file %s because of --translate-only."), $pot_filename ) + if ( $po4a_opts{"verbose"} ); + } else { + print wrap_msg( gettext("POT file %s already up to date."), $pot_filename ) + if ( $po4a_opts{"verbose"} and not $po4a_opts{"no-update"} ); + } } my %split_po; # po_files: '$lang','$master' => '$path' @@ -1930,7 +1961,12 @@ if ( not $po4a_opts{"no-translations"} ) { next if ( $master eq '' ); next unless defined $document{$master}{$lang}; if ( scalar @{ $po4a_opts{"partial"} } ) { - next unless defined $partial{'files'}{ $document{$master}{$lang} }; + unless ( defined $partial{'files'}{ $document{$master}{$lang} } ) { + print wrap_msg( gettext("Skip master file %s in language %s because of --translate-only."), + $master, $lang ) + if ( $po4a_opts{"verbose"} ); + next; + } } unless ( $po4a_opts{"force"} ) { diff --git a/t/Testhelper.pm b/t/Testhelper.pm index 889128a4a..187a3f4fb 100644 --- a/t/Testhelper.pm +++ b/t/Testhelper.pm @@ -270,7 +270,7 @@ sub run_one_po4aconf { pass("Change directory back to $cwd"); my $expected_outfile = $t->{'expected_outfile'} // "$path/_output"; - unless ( $t->{'diff_outfile'} ) { + unless ( -e $expected_outfile ) { $expected_outfile = "$path/$expected_outfile" if ( not -e $expected_outfile ) && ( -e "$path/$expected_outfile" ); unless ( -e $expected_outfile ) { diff --git a/t/add/modifiers/_output b/t/add/modifiers/_output index 7a93e0caf..a6fcb4050 100644 --- a/t/add/modifiers/_output +++ b/t/add/modifiers/_output @@ -1,4 +1,5 @@ NOT creating modifiers.pot as requested (--no-update). +NOT updating the POT file modifiers.pot as requested (--no-update). with-1 is 100% translated (2 strings). without-2 is 100% translated (2 strings). without-3 is 100% translated (2 strings). diff --git a/t/cfg-multi.t b/t/cfg-multi.t index aec9dde00..80fbb56bc 100644 --- a/t/cfg-multi.t +++ b/t/cfg-multi.t @@ -11,9 +11,9 @@ use Testhelper; my @tests; push @tests, { - 'doc' => 'Multiple languages, no pot no po', - 'po4a.conf' => 'cfg/multiple-nopotpo/po4a.conf', - 'closed_path' => 'cfg/*/', # Do not use or modify the other tests + 'doc' => 'Multiple languages, no pot no po', + 'po4a.conf' => 'cfg/multiple-nopotpo/po4a.conf', + 'closed_path' => 'cfg/*/', # Do not use or modify the other tests 'expected_files' => 'multiple.de.po multiple.es.po multiple.fr.po multiple.it.po multiple.pot', }, { @@ -48,6 +48,22 @@ push @tests, { . 'multiple.man.de.1 multiple.man.es.1 multiple.man.fr.1 multiple.man.it.1 multiple.pot', }, + { + 'doc' => 'Multiple languages, translation uptodate, translate only one language', + 'po4a.conf' => 'cfg/multiple-uptodate/po4a.conf', + 'options' => ' --translate-only multiple.man.de.1', + 'closed_path' => 'cfg/*/', + 'expected_outfile' => 'cfg/multiple-uptodate/_output-only-one', + 'expected_files' => 'multiple.man.de.1', + }, + { + 'doc' => 'Multiple languages, translation uptodate, translate only two languages', + 'po4a.conf' => 'cfg/multiple-uptodate/po4a.conf', + 'options' => ' --translate-only multiple.man.de.1 --translate-only multiple.man.es.1', + 'closed_path' => 'cfg/*/', + 'expected_outfile' => 'cfg/multiple-uptodate/_output-only-two', + 'expected_files' => 'multiple.man.de.1 multiple.man.es.1', + }, { 'doc' => 'Multiple languages, translation already fuzzy', 'po4a.conf' => 'cfg/multiple-fuzzy/po4a.conf', diff --git a/t/cfg/args-alias-redef/_output b/t/cfg/args-alias-redef/_output index d0467854e..b6bfe9945 100644 --- a/t/cfg/args-alias-redef/_output +++ b/t/cfg/args-alias-redef/_output @@ -1,4 +1,5 @@ NOT creating args.pot as requested (--no-update). +NOT updating the POT file args.pot as requested (--no-update). man.de.1 is 20% translated (1 of 5 strings). Discard man.es.1 (3 of 5 strings; only 60% translated; need 70%). man.fr.1 is 80% translated (4 of 5 strings). diff --git a/t/cfg/args-alias/_output b/t/cfg/args-alias/_output index 0a88fc814..da4af66dc 100644 --- a/t/cfg/args-alias/_output +++ b/t/cfg/args-alias/_output @@ -1,4 +1,5 @@ NOT creating args.pot as requested (--no-update). +NOT updating the POT file args.pot as requested (--no-update). man.de.1 is 20% translated (1 of 5 strings). Discard man.de.2 (1 of 5 strings; only 20% translated; need 80%). Discard man.es.1 (3 of 5 strings; only 60% translated; need 70%). diff --git a/t/cfg/args-alias/_output-keep100 b/t/cfg/args-alias/_output-keep100 index ec49800ce..cacbc50f3 100644 --- a/t/cfg/args-alias/_output-keep100 +++ b/t/cfg/args-alias/_output-keep100 @@ -1,4 +1,5 @@ NOT creating args.pot as requested (--no-update). +NOT updating the POT file args.pot as requested (--no-update). Discard man.de.1 (1 of 5 strings; only 20% translated; need 100%). Discard man.de.2 (1 of 5 strings; only 20% translated; need 100%). Discard man.es.1 (3 of 5 strings; only 60% translated; need 100%). diff --git a/t/cfg/args-global/_output b/t/cfg/args-global/_output index 32a9b921c..b649c4434 100644 --- a/t/cfg/args-global/_output +++ b/t/cfg/args-global/_output @@ -1,4 +1,5 @@ NOT creating args.pot as requested (--no-update). +NOT updating the POT file args.pot as requested (--no-update). man.de.1 is 20% translated (1 of 5 strings). man.es.1 is 60% translated (3 of 5 strings). man.fr.1 is 80% translated (4 of 5 strings). diff --git a/t/cfg/args-global/_output-keep100 b/t/cfg/args-global/_output-keep100 index c0b91f56c..2b9d1e4a1 100644 --- a/t/cfg/args-global/_output-keep100 +++ b/t/cfg/args-global/_output-keep100 @@ -1,4 +1,5 @@ NOT creating args.pot as requested (--no-update). +NOT updating the POT file args.pot as requested (--no-update). Discard man.de.1 (1 of 5 strings; only 20% translated; need 100%). Discard man.es.1 (3 of 5 strings; only 60% translated; need 100%). Discard man.fr.1 (4 of 5 strings; only 80% translated; need 100%). diff --git a/t/cfg/args-master/_output b/t/cfg/args-master/_output index 208d3a1c7..db00cb6a9 100644 --- a/t/cfg/args-master/_output +++ b/t/cfg/args-master/_output @@ -1,4 +1,5 @@ NOT creating args.pot as requested (--no-update). +NOT updating the POT file args.pot as requested (--no-update). Discard man.de.1 (1 of 5 strings; only 20% translated; need 22%). Discard man.es.1 (3 of 5 strings; only 60% translated; need 66%). man.fr.1 is 80% translated (4 of 5 strings). diff --git a/t/cfg/args-master/_output-keep100 b/t/cfg/args-master/_output-keep100 index c0b91f56c..2b9d1e4a1 100644 --- a/t/cfg/args-master/_output-keep100 +++ b/t/cfg/args-master/_output-keep100 @@ -1,4 +1,5 @@ NOT creating args.pot as requested (--no-update). +NOT updating the POT file args.pot as requested (--no-update). Discard man.de.1 (1 of 5 strings; only 20% translated; need 100%). Discard man.es.1 (3 of 5 strings; only 60% translated; need 100%). Discard man.fr.1 (4 of 5 strings; only 80% translated; need 100%). diff --git a/t/cfg/multiple-fuzzied-noup/_output b/t/cfg/multiple-fuzzied-noup/_output index 9f3763842..a33da7709 100644 --- a/t/cfg/multiple-fuzzied-noup/_output +++ b/t/cfg/multiple-fuzzied-noup/_output @@ -1,4 +1,5 @@ NOT updating multiple.pot as requested (--no-update). +NOT updating the POT file multiple.pot as requested (--no-update). Discard multiple.man.de.1 (3 of 4 strings; only 75% translated; need 80%). Discard multiple.man.es.1 (3 of 4 strings; only 75% translated; need 80%). Discard multiple.man.fr.1 (3 of 4 strings; only 75% translated; need 80%). diff --git a/t/cfg/multiple-nopo/_output-noupdate b/t/cfg/multiple-nopo/_output-noupdate index bd913a32e..d3cc84a76 100644 --- a/t/cfg/multiple-nopo/_output-noupdate +++ b/t/cfg/multiple-nopo/_output-noupdate @@ -1,4 +1,5 @@ NOT updating multiple.pot as requested (--no-update). +NOT updating the POT file multiple.pot as requested (--no-update). PO file multiple.de.po for language de is missing -- skipping. PO file multiple.es.po for language es is missing -- skipping. PO file multiple.fr.po for language fr is missing -- skipping. diff --git a/t/cfg/multiple-uptodate/_output-only-one b/t/cfg/multiple-uptodate/_output-only-one new file mode 100644 index 000000000..50b13626d --- /dev/null +++ b/t/cfg/multiple-uptodate/_output-only-one @@ -0,0 +1,4 @@ +Document multiple.man.1 kept for update (--translate-only). +Languages skipped because of --translate-only: es fr it; kept languages: de. +NOT updating the POT file multiple.pot because of --translate-only. +multiple.man.de.1 is 100% translated (4 strings). diff --git a/t/cfg/multiple-uptodate/_output-only-two b/t/cfg/multiple-uptodate/_output-only-two new file mode 100644 index 000000000..1c2f2fbdf --- /dev/null +++ b/t/cfg/multiple-uptodate/_output-only-two @@ -0,0 +1,5 @@ +Document multiple.man.1 kept for update (--translate-only). +Languages skipped because of --translate-only: fr it; kept languages: de es. +NOT updating the POT file multiple.pot because of --translate-only. +multiple.man.de.1 is 100% translated (4 strings). +multiple.man.es.1 is 100% translated (4 strings). diff --git a/t/cfg/single-fuzzied-noup/_output b/t/cfg/single-fuzzied-noup/_output index fde8e19f8..9fb696e0b 100644 --- a/t/cfg/single-fuzzied-noup/_output +++ b/t/cfg/single-fuzzied-noup/_output @@ -1,2 +1,3 @@ NOT updating single-fuzzied-noup.pot as requested (--no-update). +NOT updating the POT file single-fuzzied-noup.pot as requested (--no-update). Discard single-fuzzied-noup.man.fr.1 (3 of 4 strings; only 75% translated; need 80%). diff --git a/t/cfg/single-nopo/_output-noupdate b/t/cfg/single-nopo/_output-noupdate index c8d15b4c8..223727166 100644 --- a/t/cfg/single-nopo/_output-noupdate +++ b/t/cfg/single-nopo/_output-noupdate @@ -1,2 +1,3 @@ NOT updating single.pot as requested (--no-update). +NOT updating the POT file single.pot as requested (--no-update). PO file single.fr.po for language fr is missing -- skipping.