Merge branch 'ab/align-parse-options-help'
When "git cmd -h" shows more than one line of usage text (e.g. the cmd subcommand may take sub-sub-command), parse-options API learned to align these lines, even across i18n/l10n. * ab/align-parse-options-help: parse-options: properly align continued usage output git rev-parse --parseopt tests: add more usagestr tests send-pack: properly use parse_options() API for usage string parse-options API users: align usage output in C-strings
This commit is contained in:
commit
d7bc852151
@ -9,10 +9,10 @@ git-send-pack - Push objects over Git protocol to another repository
|
||||
SYNOPSIS
|
||||
--------
|
||||
[verse]
|
||||
'git send-pack' [--all] [--dry-run] [--force] [--receive-pack=<git-receive-pack>]
|
||||
'git send-pack' [--dry-run] [--force] [--receive-pack=<git-receive-pack>]
|
||||
[--verbose] [--thin] [--atomic]
|
||||
[--[no-]signed|--signed=(true|false|if-asked)]
|
||||
[<host>:]<directory> [<ref>...]
|
||||
[<host>:]<directory> (--all | <ref>...)
|
||||
|
||||
DESCRIPTION
|
||||
-----------
|
||||
|
@ -7,8 +7,8 @@
|
||||
|
||||
static const char * const ls_remote_usage[] = {
|
||||
N_("git ls-remote [--heads] [--tags] [--refs] [--upload-pack=<exec>]\n"
|
||||
" [-q | --quiet] [--exit-code] [--get-url]\n"
|
||||
" [--symref] [<repository> [<refs>...]]"),
|
||||
" [-q | --quiet] [--exit-code] [--get-url]\n"
|
||||
" [--symref] [<repository> [<refs>...]]"),
|
||||
NULL
|
||||
};
|
||||
|
||||
|
@ -17,10 +17,10 @@
|
||||
#include "protocol.h"
|
||||
|
||||
static const char * const send_pack_usage[] = {
|
||||
N_("git send-pack [--all | --mirror] [--dry-run] [--force] "
|
||||
"[--receive-pack=<git-receive-pack>] [--verbose] [--thin] [--atomic] "
|
||||
"[<host>:]<directory> [<ref>...]\n"
|
||||
" --all and explicit <ref> specification are mutually exclusive."),
|
||||
N_("git send-pack [--mirror] [--dry-run] [--force]\n"
|
||||
" [--receive-pack=<git-receive-pack>]\n"
|
||||
" [--verbose] [--thin] [--atomic]\n"
|
||||
" [<host>:]<directory> (--all | <ref>...)"),
|
||||
NULL,
|
||||
};
|
||||
|
||||
|
@ -11,9 +11,9 @@
|
||||
|
||||
static const char* show_branch_usage[] = {
|
||||
N_("git show-branch [-a | --all] [-r | --remotes] [--topo-order | --date-order]\n"
|
||||
" [--current] [--color[=<when>] | --no-color] [--sparse]\n"
|
||||
" [--more=<n> | --list | --independent | --merge-base]\n"
|
||||
" [--no-name | --sha1-name] [--topics] [(<rev> | <glob>)...]"),
|
||||
" [--current] [--color[=<when>] | --no-color] [--sparse]\n"
|
||||
" [--more=<n> | --list | --independent | --merge-base]\n"
|
||||
" [--no-name | --sha1-name] [--topics] [(<rev> | <glob>)...]"),
|
||||
N_("git show-branch (-g | --reflog)[=<n>[,<base>]] [--list] [<ref>]"),
|
||||
NULL
|
||||
};
|
||||
|
@ -85,7 +85,7 @@ static const char * const git_stash_push_usage[] = {
|
||||
|
||||
static const char * const git_stash_save_usage[] = {
|
||||
N_("git stash save [-p|--patch] [-k|--[no-]keep-index] [-q|--quiet]\n"
|
||||
" [-u|--include-untracked] [-a|--all] [<message>]"),
|
||||
" [-u|--include-untracked] [-a|--all] [<message>]"),
|
||||
NULL
|
||||
};
|
||||
|
||||
|
@ -23,10 +23,10 @@
|
||||
|
||||
static const char * const git_tag_usage[] = {
|
||||
N_("git tag [-a | -s | -u <key-id>] [-f] [-m <msg> | -F <file>]\n"
|
||||
"\t\t<tagname> [<head>]"),
|
||||
" <tagname> [<head>]"),
|
||||
N_("git tag -d <tagname>..."),
|
||||
N_("git tag -l [-n[<num>]] [--contains <commit>] [--no-contains <commit>] [--points-at <object>]\n"
|
||||
"\t\t[--format=<format>] [--merged <commit>] [--no-merged <commit>] [<pattern>...]"),
|
||||
" [--format=<format>] [--merged <commit>] [--no-merged <commit>] [<pattern>...]"),
|
||||
N_("git tag -v [--format=<format>] <tagname>..."),
|
||||
NULL
|
||||
};
|
||||
|
@ -904,25 +904,77 @@ static int usage_with_options_internal(struct parse_opt_ctx_t *ctx,
|
||||
FILE *outfile = err ? stderr : stdout;
|
||||
int need_newline;
|
||||
|
||||
const char *usage_prefix = _("usage: %s");
|
||||
/*
|
||||
* The translation could be anything, but we can count on
|
||||
* msgfmt(1)'s --check option to have asserted that "%s" is in
|
||||
* the translation. So compute the length of the "usage: "
|
||||
* part. We are assuming that the translator wasn't overly
|
||||
* clever and used e.g. "%1$s" instead of "%s", there's only
|
||||
* one "%s" in "usage_prefix" above, so there's no reason to
|
||||
* do so even with a RTL language.
|
||||
*/
|
||||
size_t usage_len = strlen(usage_prefix) - strlen("%s");
|
||||
/*
|
||||
* TRANSLATORS: the colon here should align with the
|
||||
* one in "usage: %s" translation.
|
||||
*/
|
||||
const char *or_prefix = _(" or: %s");
|
||||
/*
|
||||
* TRANSLATORS: You should only need to translate this format
|
||||
* string if your language is a RTL language (e.g. Arabic,
|
||||
* Hebrew etc.), not if it's a LTR language (e.g. German,
|
||||
* Russian, Chinese etc.).
|
||||
*
|
||||
* When a translated usage string has an embedded "\n" it's
|
||||
* because options have wrapped to the next line. The line
|
||||
* after the "\n" will then be padded to align with the
|
||||
* command name, such as N_("git cmd [opt]\n<8
|
||||
* spaces>[opt2]"), where the 8 spaces are the same length as
|
||||
* "git cmd ".
|
||||
*
|
||||
* This format string prints out that already-translated
|
||||
* line. The "%*s" is whitespace padding to account for the
|
||||
* padding at the start of the line that we add in this
|
||||
* function. The "%s" is a line in the (hopefully already
|
||||
* translated) N_() usage string, which contained embedded
|
||||
* newlines before we split it up.
|
||||
*/
|
||||
const char *usage_continued = _("%*s%s");
|
||||
const char *prefix = usage_prefix;
|
||||
int saw_empty_line = 0;
|
||||
|
||||
if (!usagestr)
|
||||
return PARSE_OPT_HELP;
|
||||
|
||||
if (!err && ctx && ctx->flags & PARSE_OPT_SHELL_EVAL)
|
||||
fprintf(outfile, "cat <<\\EOF\n");
|
||||
|
||||
fprintf_ln(outfile, _("usage: %s"), _(*usagestr++));
|
||||
while (*usagestr && **usagestr)
|
||||
/*
|
||||
* TRANSLATORS: the colon here should align with the
|
||||
* one in "usage: %s" translation.
|
||||
*/
|
||||
fprintf_ln(outfile, _(" or: %s"), _(*usagestr++));
|
||||
while (*usagestr) {
|
||||
if (**usagestr)
|
||||
fprintf_ln(outfile, _(" %s"), _(*usagestr));
|
||||
else
|
||||
fputc('\n', outfile);
|
||||
usagestr++;
|
||||
const char *str = _(*usagestr++);
|
||||
struct string_list list = STRING_LIST_INIT_DUP;
|
||||
unsigned int j;
|
||||
|
||||
if (!saw_empty_line && !*str)
|
||||
saw_empty_line = 1;
|
||||
|
||||
string_list_split(&list, str, '\n', -1);
|
||||
for (j = 0; j < list.nr; j++) {
|
||||
const char *line = list.items[j].string;
|
||||
|
||||
if (saw_empty_line && *line)
|
||||
fprintf_ln(outfile, _(" %s"), line);
|
||||
else if (saw_empty_line)
|
||||
fputc('\n', outfile);
|
||||
else if (!j)
|
||||
fprintf_ln(outfile, prefix, line);
|
||||
else
|
||||
fprintf_ln(outfile, usage_continued,
|
||||
(int)usage_len, "", line);
|
||||
}
|
||||
string_list_clear(&list, 0);
|
||||
|
||||
prefix = or_prefix;
|
||||
}
|
||||
|
||||
need_newline = 1;
|
||||
|
@ -282,4 +282,58 @@ test_expect_success 'test --parseopt --stuck-long and short option with unset op
|
||||
test_cmp expect output
|
||||
'
|
||||
|
||||
test_expect_success 'test --parseopt help output: "wrapped" options normal "or:" lines' '
|
||||
sed -e "s/^|//" >spec <<-\EOF &&
|
||||
|cmd [--some-option]
|
||||
| [--another-option]
|
||||
|cmd [--yet-another-option]
|
||||
|--
|
||||
|h,help show the help
|
||||
EOF
|
||||
|
||||
sed -e "s/^|//" >expect <<-\END_EXPECT &&
|
||||
|cat <<\EOF
|
||||
|usage: cmd [--some-option]
|
||||
| or: [--another-option]
|
||||
| or: cmd [--yet-another-option]
|
||||
|
|
||||
| -h, --help show the help
|
||||
|
|
||||
|EOF
|
||||
END_EXPECT
|
||||
|
||||
test_must_fail git rev-parse --parseopt -- -h >out <spec >actual &&
|
||||
test_cmp expect actual
|
||||
'
|
||||
|
||||
test_expect_success 'test --parseopt help output: multi-line blurb after empty line' '
|
||||
sed -e "s/^|//" >spec <<-\EOF &&
|
||||
|cmd [--some-option]
|
||||
| [--another-option]
|
||||
|
|
||||
|multi
|
||||
|line
|
||||
|blurb
|
||||
|--
|
||||
|h,help show the help
|
||||
EOF
|
||||
|
||||
sed -e "s/^|//" >expect <<-\END_EXPECT &&
|
||||
|cat <<\EOF
|
||||
|usage: cmd [--some-option]
|
||||
| or: [--another-option]
|
||||
|
|
||||
| multi
|
||||
| line
|
||||
| blurb
|
||||
|
|
||||
| -h, --help show the help
|
||||
|
|
||||
|EOF
|
||||
END_EXPECT
|
||||
|
||||
test_must_fail git rev-parse --parseopt -- -h >out <spec >actual &&
|
||||
test_cmp expect actual
|
||||
'
|
||||
|
||||
test_done
|
||||
|
Loading…
Reference in New Issue
Block a user