{"thread":{"id":"57588","subject":"[PATCH 0/7] More i18n fixes","startedAt":"2022-03-20T21:54:58Z","lastAt":"2022-04-03T22:29:26Z","messageCount":28,"participants":["Jean-Noël Avila via GitGitGadget","Bagas Sanjaya via GitGitGadget","Bagas Sanjaya","Johannes Sixt","Ævar Arnfjörð Bjarmason","Junio C Hamano","Jean-Noël AVILA"],"isPatch":true,"patchVersion":1,"patchTotal":7},"messages":[{"id":"451688","messageId":"pull.1181.git.1647813291.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":null,"subject":"[PATCH 0/7] More i18n fixes","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:44Z","receivedAt":"2022-03-20T21:54:58Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"This is another i18n PR (and hopefully the last for a while).\n\nAs usual, the intent is kept the same: curbing the number of strings to\ntranslate, remove constant, error prone parts out of the way, trying in some\nsense to \"put a precedent\" so that the template strings can be reused later.\n\nThis series has also a RFC status: can \"bad argument\" messages be merged\nwith unrecognized argument?\n\nBagas Sanjaya (1):\n  sequencer: factor GIT_AUTHOR_* from message strings\n\nJean-Noël Avila (6):\n  i18n: factorize generic failure messages\n  i18n: factorize \"bad argument\" messages\n  i18n: factorize \"Server does not support foo\" messages\n  i18n: factorize \"foo does not take arguments\" messages\n  i18n: factorize read-cache error messages\n  i18n: factorize unrecognized options arguments messages\n\n add-patch.c                     |  4 ++--\n builtin/am.c                    |  2 +-\n builtin/bisect--helper.c        |  2 +-\n builtin/commit-graph.c          |  2 +-\n builtin/config.c                |  2 +-\n builtin/env--helper.c           |  2 +-\n builtin/gc.c                    |  8 ++++----\n builtin/merge.c                 |  6 +++---\n builtin/revert.c                |  4 ++--\n contrib/scalar/scalar.c         |  2 +-\n diff.c                          |  4 ++--\n fetch-pack.c                    |  8 ++++----\n read-cache.c                    |  8 ++++----\n ref-filter.c                    |  8 ++++----\n remote-curl.c                   |  2 +-\n sequencer.c                     | 12 ++++++------\n setup.c                         |  4 ++--\n submodule.c                     |  2 +-\n t/t3510-cherry-pick-sequence.sh |  8 ++++----\n t/t6436-merge-overwrite.sh      |  2 +-\n 20 files changed, 46 insertions(+), 46 deletions(-)\n\n\nbase-commit: 74cc1aa55f30ed76424a0e7226ab519aa6265061\nPublished-As: https://github.com/gitgitgadget/git/releases/tag/pr-1181%2Fjnavila%2Fmore_i18n_fixes-v1\nFetch-It-Via: git fetch https://github.com/gitgitgadget/git pr-1181/jnavila/more_i18n_fixes-v1\nPull-Request: https://github.com/gitgitgadget/git/pull/1181\n-- \ngitgitgadget\n"},{"id":"451689","messageId":"73a3a8d7d97e00c94d891e30b96729e65ee4aede.1647813291.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH 1/7] i18n: factorize generic failure messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:45Z","receivedAt":"2022-03-20T21:55:03Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nIn these message the command that failed should not be translated. So\nit is simpler to just remove these parts from the message.\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n add-patch.c                     | 4 ++--\n builtin/am.c                    | 2 +-\n builtin/gc.c                    | 4 ++--\n builtin/merge.c                 | 6 +++---\n builtin/revert.c                | 4 ++--\n fetch-pack.c                    | 2 +-\n remote-curl.c                   | 2 +-\n setup.c                         | 4 ++--\n t/t3510-cherry-pick-sequence.sh | 8 ++++----\n t/t6436-merge-overwrite.sh      | 2 +-\n 10 files changed, 19 insertions(+), 19 deletions(-)\n\ndiff --git a/add-patch.c b/add-patch.c\nindex 55d719f7845..d545dea2ff2 100644\n--- a/add-patch.c\n+++ b/add-patch.c\n@@ -1181,7 +1181,7 @@ static int run_apply_check(struct add_p_state *s,\n \t\t\t    \"apply\", \"--check\", NULL);\n \tstrvec_pushv(&cp.args, s->mode->apply_check_args);\n \tif (pipe_command(&cp, s->buf.buf, s->buf.len, NULL, 0, NULL, 0))\n-\t\treturn error(_(\"'git apply --cached' failed\"));\n+\t\treturn error(_(\"'%s' failed\"), \"git apply --cached\");\n \n \treturn 0;\n }\n@@ -1683,7 +1683,7 @@ soft_increment:\n \t\t\tstrvec_pushv(&cp.args, s->mode->apply_args);\n \t\t\tif (pipe_command(&cp, s->buf.buf, s->buf.len,\n \t\t\t\t\t NULL, 0, NULL, 0))\n-\t\t\t\terror(_(\"'git apply' failed\"));\n+\t\t\t\terror(_(\"'%s' failed\"), \"git apply\");\n \t\t}\n \t\tif (repo_read_index(s->s.r) >= 0)\n \t\t\trepo_refresh_and_write_index(s->s.r, REFRESH_QUIET, 0,\ndiff --git a/builtin/am.c b/builtin/am.c\nindex 0f4111bafa0..b26a55318e7 100644\n--- a/builtin/am.c\n+++ b/builtin/am.c\n@@ -586,7 +586,7 @@ static int is_mail(FILE *fp)\n \tint ret = 1;\n \n \tif (fseek(fp, 0L, SEEK_SET))\n-\t\tdie_errno(_(\"fseek failed\"));\n+\t\tdie_errno(_(\"'%s' failed\"), \"fseek\");\n \n \tif (regcomp(&regex, header_regex, REG_NOSUB | REG_EXTENDED))\n \t\tdie(\"invalid pattern: %s\", header_regex);\ndiff --git a/builtin/gc.c b/builtin/gc.c\nindex ffaf0daf5d9..d512c127b99 100644\n--- a/builtin/gc.c\n+++ b/builtin/gc.c\n@@ -1104,7 +1104,7 @@ static int multi_pack_index_expire(struct maintenance_run_opts *opts)\n \t\tstrvec_push(&child.args, \"--no-progress\");\n \n \tif (run_command(&child))\n-\t\treturn error(_(\"'git multi-pack-index expire' failed\"));\n+\t\treturn error(_(\"'%s' failed\"), \"git multi-pack-index expire\");\n \n \treturn 0;\n }\n@@ -1163,7 +1163,7 @@ static int multi_pack_index_repack(struct maintenance_run_opts *opts)\n \t\t\t\t  (uintmax_t)get_auto_pack_size());\n \n \tif (run_command(&child))\n-\t\treturn error(_(\"'git multi-pack-index repack' failed\"));\n+\t\treturn error(_(\"'%s' failed\"), \"git multi-pack-index repack\");\n \n \treturn 0;\n }\ndiff --git a/builtin/merge.c b/builtin/merge.c\nindex f178f5a3ee1..3155f116610 100644\n--- a/builtin/merge.c\n+++ b/builtin/merge.c\n@@ -325,7 +325,7 @@ static int save_state(struct object_id *stash)\n \tclose(cp.out);\n \n \tif (finish_command(&cp) || len < 0)\n-\t\tdie(_(\"stash failed\"));\n+\t\tdie(_(\"'%s' failed\"), \"stash\");\n \telse if (!len)\t\t/* no changes */\n \t\tgoto out;\n \tstrbuf_setlen(&buffer, buffer.len-1);\n@@ -352,7 +352,7 @@ static void read_empty(const struct object_id *oid, int verbose)\n \targs[i] = NULL;\n \n \tif (run_command_v_opt(args, RUN_GIT_CMD))\n-\t\tdie(_(\"read-tree failed\"));\n+\t\tdie(_(\"'%s' failed\"), \"read-tree\");\n }\n \n static void reset_hard(const struct object_id *oid, int verbose)\n@@ -369,7 +369,7 @@ static void reset_hard(const struct object_id *oid, int verbose)\n \targs[i] = NULL;\n \n \tif (run_command_v_opt(args, RUN_GIT_CMD))\n-\t\tdie(_(\"read-tree failed\"));\n+\t\tdie(_(\"'%s' failed\"), \"read-tree\");\n }\n \n static void restore_state(const struct object_id *head,\ndiff --git a/builtin/revert.c b/builtin/revert.c\nindex 51776abea63..ed032eaf0f8 100644\n--- a/builtin/revert.c\n+++ b/builtin/revert.c\n@@ -238,7 +238,7 @@ int cmd_revert(int argc, const char **argv, const char *prefix)\n \tsequencer_init_config(&opts);\n \tres = run_sequencer(argc, argv, &opts);\n \tif (res < 0)\n-\t\tdie(_(\"revert failed\"));\n+\t\tdie(_(\"'%s' failed\"), \"revert\");\n \treturn res;\n }\n \n@@ -251,6 +251,6 @@ int cmd_cherry_pick(int argc, const char **argv, const char *prefix)\n \tsequencer_init_config(&opts);\n \tres = run_sequencer(argc, argv, &opts);\n \tif (res < 0)\n-\t\tdie(_(\"cherry-pick failed\"));\n+\t\tdie(_(\"'%s' failed\"), \"cherry-pick\");\n \treturn res;\n }\ndiff --git a/fetch-pack.c b/fetch-pack.c\nindex 87657907e78..09b1cf6173a 100644\n--- a/fetch-pack.c\n+++ b/fetch-pack.c\n@@ -989,7 +989,7 @@ static int get_pack(struct fetch_pack_args *args,\n \t\t\targs->check_self_contained_and_connected &&\n \t\t\tret == 0;\n \telse\n-\t\tdie(_(\"%s failed\"), cmd_name);\n+\t\tdie(_(\"'%s' failed\"), cmd_name);\n \tif (use_sideband && finish_async(&demux))\n \t\tdie(_(\"error in sideband demultiplexer\"));\n \ndiff --git a/remote-curl.c b/remote-curl.c\nindex ff44f41011e..28619583ec5 100644\n--- a/remote-curl.c\n+++ b/remote-curl.c\n@@ -1287,7 +1287,7 @@ static int push_dav(int nr_spec, const char **specs)\n \t\tstrvec_push(&child.args, specs[i]);\n \n \tif (run_command(&child))\n-\t\tdie(_(\"git-http-push failed\"));\n+\t\tdie(_(\"'%s' failed\"), \"git-http-push\");\n \treturn 0;\n }\n \ndiff --git a/setup.c b/setup.c\nindex 04ce33cdcd4..3d123cc11fd 100644\n--- a/setup.c\n+++ b/setup.c\n@@ -1506,12 +1506,12 @@ int daemonize(void)\n \t\tcase 0:\n \t\t\tbreak;\n \t\tcase -1:\n-\t\t\tdie_errno(_(\"fork failed\"));\n+\t\t\tdie_errno(_(\"'%s' failed\"), \"fork\");\n \t\tdefault:\n \t\t\texit(0);\n \t}\n \tif (setsid() == -1)\n-\t\tdie_errno(_(\"setsid failed\"));\n+\t\tdie_errno(_(\"'%s' failed\"), \"setsid\");\n \tclose(0);\n \tclose(1);\n \tclose(2);\ndiff --git a/t/t3510-cherry-pick-sequence.sh b/t/t3510-cherry-pick-sequence.sh\nindex 3b0fa66c33d..75a3fbd469b 100755\n--- a/t/t3510-cherry-pick-sequence.sh\n+++ b/t/t3510-cherry-pick-sequence.sh\n@@ -193,7 +193,7 @@ test_expect_success 'check advice when we move HEAD by committing' '\n \terror: there is nothing to skip\n \thint: have you committed already?\n \thint: try \"git cherry-pick --continue\"\n-\tfatal: cherry-pick failed\n+\tfatal: '\\''cherry-pick'\\'' failed\n \tEOF\n \ttest_must_fail git cherry-pick base..yetanotherpick &&\n \techo c >foo &&\n@@ -208,7 +208,7 @@ test_expect_success 'selectively advise --skip while launching another sequence'\n \tcat >expect <<-EOF &&\n \terror: cherry-pick is already in progress\n \thint: try \"git cherry-pick (--continue | --skip | --abort | --quit)\"\n-\tfatal: cherry-pick failed\n+\tfatal: '\\''cherry-pick'\\'' failed\n \tEOF\n \ttest_must_fail git cherry-pick picked..yetanotherpick &&\n \ttest_must_fail git cherry-pick picked..yetanotherpick 2>advice &&\n@@ -216,7 +216,7 @@ test_expect_success 'selectively advise --skip while launching another sequence'\n \tcat >expect <<-EOF &&\n \terror: cherry-pick is already in progress\n \thint: try \"git cherry-pick (--continue | --abort | --quit)\"\n-\tfatal: cherry-pick failed\n+\tfatal: '\\''cherry-pick'\\'' failed\n \tEOF\n \tgit reset --merge &&\n \ttest_must_fail git cherry-pick picked..yetanotherpick 2>advice &&\n@@ -227,7 +227,7 @@ test_expect_success 'allow skipping commit but not abort for a new history' '\n \tpristine_detach initial &&\n \tcat >expect <<-EOF &&\n \terror: cannot abort from a branch yet to be born\n-\tfatal: cherry-pick failed\n+\tfatal: '\\''cherry-pick'\\'' failed\n \tEOF\n \tgit checkout --orphan new_disconnected &&\n \tgit reset --hard &&\ndiff --git a/t/t6436-merge-overwrite.sh b/t/t6436-merge-overwrite.sh\nindex c0b7bd7c3fe..e8abcd10f5c 100755\n--- a/t/t6436-merge-overwrite.sh\n+++ b/t/t6436-merge-overwrite.sh\n@@ -166,7 +166,7 @@ test_expect_success 'will not be confused by symlink in leading path' '\n \n cat >expect <<\\EOF\n error: Untracked working tree file 'c0.c' would be overwritten by merge.\n-fatal: read-tree failed\n+fatal: 'read-tree' failed\n EOF\n \n test_expect_success 'will not overwrite untracked file on unborn branch' '\n-- \ngitgitgadget\n\n"},{"id":"451690","messageId":"8bdbb32f54421f99be55493257b31b203a11f202.1647813292.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH 2/7] sequencer: factor GIT_AUTHOR_* from message strings","fromName":"Bagas Sanjaya via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:46Z","receivedAt":"2022-03-20T21:55:08Z","isPatch":true,"sender":{"key":"bagasdotme@gmail.com","avatar":"https://avatars.githubusercontent.com/u/40219486?v=4"},"body":"From: Bagas Sanjaya <bagasdotme@gmail.com>\n\nFactor messages containing GIT_AUTHOR_* variable.\n\nSigned-off-by: Bagas Sanjaya <bagasdotme@gmail.com>\n---\n sequencer.c | 12 ++++++------\n 1 file changed, 6 insertions(+), 6 deletions(-)\n\ndiff --git a/sequencer.c b/sequencer.c\nindex 84eed9e96bc..647f5efa656 100644\n--- a/sequencer.c\n+++ b/sequencer.c\n@@ -848,17 +848,17 @@ int read_author_script(const char *path, char **name, char **email, char **date,\n \tfor (i = 0; i < kv.nr; i++) {\n \t\tif (!strcmp(kv.items[i].string, \"GIT_AUTHOR_NAME\")) {\n \t\t\tif (name_i != -2)\n-\t\t\t\tname_i = error(_(\"'GIT_AUTHOR_NAME' already given\"));\n+\t\t\t\tname_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_NAME\");\n \t\t\telse\n \t\t\t\tname_i = i;\n \t\t} else if (!strcmp(kv.items[i].string, \"GIT_AUTHOR_EMAIL\")) {\n \t\t\tif (email_i != -2)\n-\t\t\t\temail_i = error(_(\"'GIT_AUTHOR_EMAIL' already given\"));\n+\t\t\t\temail_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_EMAIL\");\n \t\t\telse\n \t\t\t\temail_i = i;\n \t\t} else if (!strcmp(kv.items[i].string, \"GIT_AUTHOR_DATE\")) {\n \t\t\tif (date_i != -2)\n-\t\t\t\tdate_i = error(_(\"'GIT_AUTHOR_DATE' already given\"));\n+\t\t\t\tdate_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_DATE\");\n \t\t\telse\n \t\t\t\tdate_i = i;\n \t\t} else {\n@@ -867,11 +867,11 @@ int read_author_script(const char *path, char **name, char **email, char **date,\n \t\t}\n \t}\n \tif (name_i == -2)\n-\t\terror(_(\"missing 'GIT_AUTHOR_NAME'\"));\n+\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_NAME\");\n \tif (email_i == -2)\n-\t\terror(_(\"missing 'GIT_AUTHOR_EMAIL'\"));\n+\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_EMAIL\");\n \tif (date_i == -2)\n-\t\terror(_(\"missing 'GIT_AUTHOR_DATE'\"));\n+\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_DATE\");\n \tif (date_i < 0 || email_i < 0 || date_i < 0 || err)\n \t\tgoto finish;\n \t*name = kv.items[name_i].util;\n-- \ngitgitgadget\n\n"},{"id":"451691","messageId":"c94d5c932f4bd0311c7d85e6fdb36f8801a81a83.1647813292.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH 3/7] i18n: factorize \"bad argument\" messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:47Z","receivedAt":"2022-03-20T21:55:11Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n builtin/bisect--helper.c | 2 +-\n diff.c                   | 4 ++--\n submodule.c              | 2 +-\n 3 files changed, 4 insertions(+), 4 deletions(-)\n\ndiff --git a/builtin/bisect--helper.c b/builtin/bisect--helper.c\nindex 8b2b259ff0d..289a7d2bc9e 100644\n--- a/builtin/bisect--helper.c\n+++ b/builtin/bisect--helper.c\n@@ -268,7 +268,7 @@ static int bisect_write(const char *state, const char *rev,\n \t} else if (one_of(state, terms->term_good, \"skip\", NULL)) {\n \t\tstrbuf_addf(&tag, \"refs/bisect/%s-%s\", state, rev);\n \t} else {\n-\t\tres = error(_(\"Bad bisect_write argument: %s\"), state);\n+\t\tres = error(_(\"bad %s argument: %s\"), \"bisect_write\", state);\n \t\tgoto finish;\n \t}\n \ndiff --git a/diff.c b/diff.c\nindex 6b22946cd0e..5e045b4ba87 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5010,7 +5010,7 @@ static int diff_opt_color_moved(const struct option *opt,\n \t} else {\n \t\tint cm = parse_color_moved(arg);\n \t\tif (cm < 0)\n-\t\t\treturn error(_(\"bad --color-moved argument: %s\"), arg);\n+\t\t\treturn error(_(\"bad %s argument: %s\"), \"--color-moved\", arg);\n \t\toptions->color_moved = cm;\n \t}\n \treturn 0;\n@@ -5334,7 +5334,7 @@ static int diff_opt_word_diff(const struct option *opt,\n \t\telse if (!strcmp(arg, \"none\"))\n \t\t\toptions->word_diff = DIFF_WORDS_NONE;\n \t\telse\n-\t\t\treturn error(_(\"bad --word-diff argument: %s\"), arg);\n+\t\t\treturn error(_(\"bad %s argument: %s\"), \"--word-diff\", arg);\n \t} else {\n \t\tif (options->word_diff == DIFF_WORDS_NONE)\n \t\t\toptions->word_diff = DIFF_WORDS_PLAIN;\ndiff --git a/submodule.c b/submodule.c\nindex 5ace18a7d94..010f8252c5e 100644\n--- a/submodule.c\n+++ b/submodule.c\n@@ -470,7 +470,7 @@ void handle_ignore_submodules_arg(struct diff_options *diffopt,\n \telse if (!strcmp(arg, \"dirty\"))\n \t\tdiffopt->flags.ignore_dirty_submodules = 1;\n \telse if (strcmp(arg, \"none\"))\n-\t\tdie(_(\"bad --ignore-submodules argument: %s\"), arg);\n+\t\tdie(_(\"bad %s argument: %s\"), \"--ignore-submodules\", arg);\n \t/*\n \t * Please update _git_status() in git-completion.bash when you\n \t * add new options\n-- \ngitgitgadget\n\n"},{"id":"451692","messageId":"bf23e1ebe6543d8831e1bdb6a465fa292cae3955.1647813292.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH 4/7] i18n: factorize \"Server does not support foo\" messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:48Z","receivedAt":"2022-03-20T21:55:11Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n fetch-pack.c | 6 +++---\n 1 file changed, 3 insertions(+), 3 deletions(-)\n\ndiff --git a/fetch-pack.c b/fetch-pack.c\nindex 09b1cf6173a..fcbc5cc5944 100644\n--- a/fetch-pack.c\n+++ b/fetch-pack.c\n@@ -1106,16 +1106,16 @@ static struct ref *do_fetch_pack(struct fetch_pack_args *args,\n \t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-since\");\n \t\tdeepen_since_ok = 1;\n \t} else if (args->deepen_since)\n-\t\tdie(_(\"Server does not support --shallow-since\"));\n+\t\tdie(_(\"Server does not support %s\"), \"--shallow-since\");\n \tif (server_supports(\"deepen-not\")) {\n \t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-not\");\n \t\tdeepen_not_ok = 1;\n \t} else if (args->deepen_not)\n-\t\tdie(_(\"Server does not support --shallow-exclude\"));\n+\t\tdie(_(\"Server does not support %s\"), \"--shallow-exclude\");\n \tif (server_supports(\"deepen-relative\"))\n \t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-relative\");\n \telse if (args->deepen_relative)\n-\t\tdie(_(\"Server does not support --deepen\"));\n+\t\tdie(_(\"Server does not support %s\"), \"--deepen\");\n \tif (!server_supports_hash(the_hash_algo->name, NULL))\n \t\tdie(_(\"Server does not support this repository's object format\"));\n \n-- \ngitgitgadget\n\n"},{"id":"451693","messageId":"2e1bd504673e8e2ec77ac8e99edb9aac0fb82db2.1647813292.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH 5/7] i18n: factorize \"foo does not take arguments\" messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:49Z","receivedAt":"2022-03-20T21:55:13Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n contrib/scalar/scalar.c | 2 +-\n ref-filter.c            | 8 ++++----\n 2 files changed, 5 insertions(+), 5 deletions(-)\n\ndiff --git a/contrib/scalar/scalar.c b/contrib/scalar/scalar.c\nindex 7db2a97416e..1aeecea1daa 100644\n--- a/contrib/scalar/scalar.c\n+++ b/contrib/scalar/scalar.c\n@@ -502,7 +502,7 @@ cleanup:\n static int cmd_list(int argc, const char **argv)\n {\n \tif (argc != 1)\n-\t\tdie(_(\"`scalar list` does not take arguments\"));\n+\t\tdie(_(\"%s does not take arguments\"), \"`scalar list`\");\n \n \tif (run_git(\"config\", \"--global\", \"--get-all\", \"scalar.repo\", NULL) < 0)\n \t\treturn -1;\ndiff --git a/ref-filter.c b/ref-filter.c\nindex 7838bd22b8d..74f84cc0ed7 100644\n--- a/ref-filter.c\n+++ b/ref-filter.c\n@@ -317,7 +317,7 @@ static int objecttype_atom_parser(struct ref_format *format, struct used_atom *a\n \t\t\t\t  const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(objecttype) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(objecttype)\");\n \tif (*atom->name == '*')\n \t\toi_deref.info.typep = &oi_deref.type;\n \telse\n@@ -349,7 +349,7 @@ static int deltabase_atom_parser(struct ref_format *format, struct used_atom *at\n \t\t\t\t const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(deltabase) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(deltabase)\");\n \tif (*atom->name == '*')\n \t\toi_deref.info.delta_base_oid = &oi_deref.delta_base_oid;\n \telse\n@@ -361,7 +361,7 @@ static int body_atom_parser(struct ref_format *format, struct used_atom *atom,\n \t\t\t    const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(body) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(body)\");\n \tatom->u.contents.option = C_BODY_DEP;\n \treturn 0;\n }\n@@ -565,7 +565,7 @@ static int rest_atom_parser(struct ref_format *format, struct used_atom *atom,\n \t\t\t    const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(rest) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(rest)\");\n \tformat->use_rest = 1;\n \treturn 0;\n }\n-- \ngitgitgadget\n\n"},{"id":"451694","messageId":"ca52567b201578ef8cfc7dccf2b99cad54dd374c.1647813292.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH 7/7] i18n: factorize unrecognized options arguments messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:51Z","receivedAt":"2022-03-20T21:55:15Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n builtin/commit-graph.c | 2 +-\n builtin/config.c       | 2 +-\n builtin/env--helper.c  | 2 +-\n builtin/gc.c           | 4 ++--\n 4 files changed, 5 insertions(+), 5 deletions(-)\n\ndiff --git a/builtin/commit-graph.c b/builtin/commit-graph.c\nindex 51c4040ea6c..1a4c798f908 100644\n--- a/builtin/commit-graph.c\n+++ b/builtin/commit-graph.c\n@@ -134,7 +134,7 @@ static int write_option_parse_split(const struct option *opt, const char *arg,\n \telse if (!strcmp(arg, \"replace\"))\n \t\t*flags = COMMIT_GRAPH_SPLIT_REPLACE;\n \telse\n-\t\tdie(_(\"unrecognized --split argument, %s\"), arg);\n+\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--split\", arg);\n \n \treturn 0;\n }\ndiff --git a/builtin/config.c b/builtin/config.c\nindex e7b88a9c08d..aaf87761e58 100644\n--- a/builtin/config.c\n+++ b/builtin/config.c\n@@ -106,7 +106,7 @@ static int option_parse_type(const struct option *opt, const char *arg,\n \t\telse if (!strcmp(arg, \"color\"))\n \t\t\tnew_type = TYPE_COLOR;\n \t\telse\n-\t\t\tdie(_(\"unrecognized --type argument, %s\"), arg);\n+\t\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--type\", arg);\n \t}\n \n \tto_type = opt->value;\ndiff --git a/builtin/env--helper.c b/builtin/env--helper.c\nindex 27349098b07..e58e0de9a7b 100644\n--- a/builtin/env--helper.c\n+++ b/builtin/env--helper.c\n@@ -24,7 +24,7 @@ static int option_parse_type(const struct option *opt, const char *arg,\n \telse if (!strcmp(arg, \"ulong\"))\n \t\t*cmdmode = ENV_HELPER_TYPE_ULONG;\n \telse\n-\t\tdie(_(\"unrecognized --type argument, %s\"), arg);\n+\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--type\", arg);\n \n \treturn 0;\n }\ndiff --git a/builtin/gc.c b/builtin/gc.c\nindex d512c127b99..1a9ee85a4d3 100644\n--- a/builtin/gc.c\n+++ b/builtin/gc.c\n@@ -750,7 +750,7 @@ static int maintenance_opt_schedule(const struct option *opt, const char *arg,\n \t*priority = parse_schedule(arg);\n \n \tif (!*priority)\n-\t\tdie(_(\"unrecognized --schedule argument '%s'\"), arg);\n+\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--schedule\", arg);\n \n \treturn 0;\n }\n@@ -2393,7 +2393,7 @@ static int maintenance_opt_scheduler(const struct option *opt, const char *arg,\n \n \t*scheduler = parse_scheduler(arg);\n \tif (*scheduler == SCHEDULER_INVALID)\n-\t\treturn error(_(\"unrecognized --scheduler argument '%s'\"), arg);\n+\t\treturn error(_(\"unrecognized %s argument '%s'\"), \"--scheduler\", arg);\n \treturn 0;\n }\n \n-- \ngitgitgadget\n"},{"id":"451695","messageId":"b8f97e6fde819caa5aeefdf4d2f28d69c7222e4b.1647813292.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH 6/7] i18n: factorize read-cache error messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-03-20T21:54:50Z","receivedAt":"2022-03-20T21:55:16Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n read-cache.c | 8 ++++----\n 1 file changed, 4 insertions(+), 4 deletions(-)\n\ndiff --git a/read-cache.c b/read-cache.c\nindex 1ad56d02e1d..39a633ea4b8 100644\n--- a/read-cache.c\n+++ b/read-cache.c\n@@ -1735,8 +1735,8 @@ static unsigned int get_index_format_default(struct repository *r)\n \t\tif (r->settings.index_version >= 0)\n \t\t\tversion = r->settings.index_version;\n \t\tif (version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n-\t\t\twarning(_(\"index.version set, but the value is invalid.\\n\"\n-\t\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n+\t\t\twarning(_(\"%s set, but the value is invalid.\\n\"\n+\t\t\t\t  \"Using version %i\"), \"index.version\", INDEX_FORMAT_DEFAULT);\n \t\t\treturn INDEX_FORMAT_DEFAULT;\n \t\t}\n \t\treturn version;\n@@ -1745,8 +1745,8 @@ static unsigned int get_index_format_default(struct repository *r)\n \tversion = strtoul(envversion, &endp, 10);\n \tif (*endp ||\n \t    version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n-\t\twarning(_(\"GIT_INDEX_VERSION set, but the value is invalid.\\n\"\n-\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n+\t\twarning(_(\"%s set, but the value is invalid.\\n\"\n+\t\t\t  \"Using version %i\"), \"GIT_INDEX_VERSION\", INDEX_FORMAT_DEFAULT);\n \t\tversion = INDEX_FORMAT_DEFAULT;\n \t}\n \treturn version;\n-- \ngitgitgadget\n\n"},{"id":"451696","messageId":"19947a0f-fdc2-eb80-741b-0ba5ed6335d8@gmail.com","threadId":"57588","inReplyTo":"8bdbb32f54421f99be55493257b31b203a11f202.1647813292.git.gitgitgadget@gmail.com","subject":"Re: [PATCH 2/7] sequencer: factor GIT_AUTHOR_* from message strings","fromName":"Bagas Sanjaya","fromEmail":"bagasdotme@gmail.com","sentAt":"2022-03-21T05:22:10Z","receivedAt":"2022-03-21T05:22:19Z","isPatch":true,"sender":{"key":"bagasdotme@gmail.com","avatar":"https://avatars.githubusercontent.com/u/40219486?v=4"},"body":"On 21/03/22 04.54, Bagas Sanjaya via GitGitGadget wrote:\n> From: Bagas Sanjaya <bagasdotme@gmail.com>\n> \n> Factor messages containing GIT_AUTHOR_* variable.\n> \n> Signed-off-by: Bagas Sanjaya <bagasdotme@gmail.com>\n> ---\n>   sequencer.c | 12 ++++++------\n>   1 file changed, 6 insertions(+), 6 deletions(-)\n> \n> diff --git a/sequencer.c b/sequencer.c\n> index 84eed9e96bc..647f5efa656 100644\n> --- a/sequencer.c\n> +++ b/sequencer.c\n> @@ -848,17 +848,17 @@ int read_author_script(const char *path, char **name, char **email, char **date,\n>   \tfor (i = 0; i < kv.nr; i++) {\n>   \t\tif (!strcmp(kv.items[i].string, \"GIT_AUTHOR_NAME\")) {\n>   \t\t\tif (name_i != -2)\n> -\t\t\t\tname_i = error(_(\"'GIT_AUTHOR_NAME' already given\"));\n> +\t\t\t\tname_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_NAME\");\n>   \t\t\telse\n>   \t\t\t\tname_i = i;\n>   \t\t} else if (!strcmp(kv.items[i].string, \"GIT_AUTHOR_EMAIL\")) {\n>   \t\t\tif (email_i != -2)\n> -\t\t\t\temail_i = error(_(\"'GIT_AUTHOR_EMAIL' already given\"));\n> +\t\t\t\temail_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_EMAIL\");\n>   \t\t\telse\n>   \t\t\t\temail_i = i;\n>   \t\t} else if (!strcmp(kv.items[i].string, \"GIT_AUTHOR_DATE\")) {\n>   \t\t\tif (date_i != -2)\n> -\t\t\t\tdate_i = error(_(\"'GIT_AUTHOR_DATE' already given\"));\n> +\t\t\t\tdate_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_DATE\");\n>   \t\t\telse\n>   \t\t\t\tdate_i = i;\n>   \t\t} else {\n> @@ -867,11 +867,11 @@ int read_author_script(const char *path, char **name, char **email, char **date,\n>   \t\t}\n>   \t}\n>   \tif (name_i == -2)\n> -\t\terror(_(\"missing 'GIT_AUTHOR_NAME'\"));\n> +\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_NAME\");\n>   \tif (email_i == -2)\n> -\t\terror(_(\"missing 'GIT_AUTHOR_EMAIL'\"));\n> +\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_EMAIL\");\n>   \tif (date_i == -2)\n> -\t\terror(_(\"missing 'GIT_AUTHOR_DATE'\"));\n> +\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_DATE\");\n>   \tif (date_i < 0 || email_i < 0 || date_i < 0 || err)\n>   \t\tgoto finish;\n>   \t*name = kv.items[name_i].util;\n\nLooks OK. Thanks for picking this up.\n\nAcked-by: Bagas Sanjaya <bagasdotme@gmail.com>\n\n-- \nAn old man doll... just what I always wanted! - Clara\n"},{"id":"451698","messageId":"e44b6ccf-21a2-72c6-4d40-dc0004895255@kdbg.org","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"Re: [PATCH 0/7] More i18n fixes","fromName":"Johannes Sixt","fromEmail":"j6t@kdbg.org","sentAt":"2022-03-21T06:48:42Z","receivedAt":"2022-03-21T06:48:49Z","isPatch":true,"sender":{"key":"j6t@kdbg.org","avatar":"https://avatars.githubusercontent.com/u/14810926?v=4"},"body":"Am 20.03.22 um 22:54 schrieb Jean-Noël Avila via GitGitGadget:\n> This is another i18n PR (and hopefully the last for a while).\n> \n> As usual, the intent is kept the same: curbing the number of strings to\n> translate, remove constant, error prone parts out of the way, trying in some\n> sense to \"put a precedent\" so that the template strings can be reused later.\n\nI feel that many of the example conversions look like sentence lego\nbecause there remains only one English word, e.g., \"'%s' failed\". The\nconverted code does not leave a hint for the translators what the %s\nwill be. Is it a command, a function name, somehting else? Even if the\nhint was provided, different translations may be required depending on\nthe substituted entity. Did you investigate the existing translations\nwhether all of them can be converted to the new scheme?\n\n> This series has also a RFC status: can \"bad argument\" messages be merged\n> with unrecognized argument?\n\nThe cases that patch 7/7 transforms look like they need not keep\n\"unrecognized argument\", but can be converted to \"bad argument\".\n\nDisclaimer: neither am I a translator nor a user of a translated Git.\n\n-- Hannes\n"},{"id":"451726","messageId":"220321.86ils79z0c.gmgdl@evledraar.gmail.com","threadId":"57588","inReplyTo":"e44b6ccf-21a2-72c6-4d40-dc0004895255@kdbg.org","subject":"Re: [PATCH 0/7] More i18n fixes","fromName":"Ævar Arnfjörð Bjarmason","fromEmail":"avarab@gmail.com","sentAt":"2022-03-21T13:59:24Z","receivedAt":"2022-03-21T14:13:45Z","isPatch":true,"sender":{"key":"avarab@gmail.com","avatar":"https://avatars.githubusercontent.com/u/45301?v=4"},"body":"\nOn Mon, Mar 21 2022, Johannes Sixt wrote:\n\n> Am 20.03.22 um 22:54 schrieb Jean-Noël Avila via GitGitGadget:\n>> This is another i18n PR (and hopefully the last for a while).\n>> \n>> As usual, the intent is kept the same: curbing the number of strings to\n>> translate, remove constant, error prone parts out of the way, trying in some\n>> sense to \"put a precedent\" so that the template strings can be reused later.\n>\n> I feel that many of the example conversions look like sentence lego\n> because there remains only one English word, e.g., \"'%s' failed\". The\n> converted code does not leave a hint for the translators what the %s\n> will be. Is it a command, a function name, somehting else? Even if the\n> hint was provided, different translations may be required depending on\n> the substituted entity. Did you investigate the existing translations\n> whether all of them can be converted to the new scheme?\n>\n>> This series has also a RFC status: can \"bad argument\" messages be merged\n>> with unrecognized argument?\n>\n> The cases that patch 7/7 transforms look like they need not keep\n> \"unrecognized argument\", but can be converted to \"bad argument\".\n>\n> Disclaimer: neither am I a translator nor a user of a translated Git.\n\nJust to add to this:\n\n - Careful use of sentence lego is OK, but e.g. in my native language a\n   command-line option would use a male noun article, whereas commands\n   would be feminine.\n\n   (I still haven't submitted an Icelandic translation, but this applies\n   in general).\n\n   As a result string like \"'%s' failed\" can be *workable*, i.e. you can\n   translate it assuming you'll get any arbitrary string, but the\n   translation will often be rather tortured.\n\n   So it's much preferred (and this also goes to Johannes's comment) to\n   instead do e.g.:\n\n       \"failed to run the '%s' command\"\n       \"failed to use the '%s' argument\"\n\n   Or whatever, and e.g. for:\n\t\n\t-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(objecttype) does not take arguments\"));\n\t+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(objecttype)\");\n\n   Instead say \"the '%s' format does not...\", i.e. disambiguate with\n   \"format\".\n\n - While perfect shouldn't be the enemy of the good, it would be most\n   welcome to improve some of the warts revealed by these messages,\n   notably that e.g. the \"failed to run X command\" don't report\n   errno. E.g. this in git.c is a good template (except for the \"\\n\" we\n   should ideally get rid of):\n\n       _(\"failed to run command '%s': %s\\n\")\n\n - On that topic, it would be really useful to see if we can unify some\n   of these with *existing* po/git.pot messaging, I don't know if that's\n   part of your workflow, but in some cases I've seen we can either\n   tweak wording slightly to match an existing message, or could further\n   unify some existing similar messages.\n\n - Even if we say \"failed to run git-apply\" or whatever now we should\n   really be adding quotes to these as we convert them. In some cases\n   the changes that (good):\n\t\n\t-\t\tdie(_(\"git-http-push failed\"));\n\t+\t\tdie(_(\"'%s' failed\"), \"git-http-push\");\n\n   But not in others (bad):\n\t\n\t-\t\tres = error(_(\"Bad bisect_write argument: %s\"), state);\n\t+\t\tres = error(_(\"bad %s argument: %s\"), \"bisect_write\", state);\n\n   I.e. that should be 'bad '%s' argument. And also on the \"unify\" point\n   above, e.g. grep.c has this:\n\n       grep.c: die(\"bad %s argument: %s\", opt, arg);\n\n   So we could covert that one to \"bad '%s' argument: '%s\"\" while we're\n   at it...\n\n- In some cases there's ucase to lcase conversions, like Bad->bad above\n  (good), but others are missed, e.g. (also missing quotes as noted\n  above):\n\n\t-\t\tdie(_(\"Server does not support --shallow-since\"));\n\t+\t\tdie(_(\"Server does not support %s\"), \"--shallow-since\");\n\n - On quotes, let's consistently use '' quotes, and not e.g.g:\n\t\n\t-\t\tdie(_(\"`scalar list` does not take arguments\"));\n\t+\t\tdie(_(\"%s does not take arguments\"), \"`scalar list`\");\n\n"},{"id":"451748","messageId":"xmqqlex3xh4d.fsf@gitster.g","threadId":"57588","inReplyTo":"220321.86ils79z0c.gmgdl@evledraar.gmail.com","subject":"Re: [PATCH 0/7] More i18n fixes","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2022-03-21T19:03:46Z","receivedAt":"2022-03-21T19:03:53Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Ævar Arnfjörð Bjarmason <avarab@gmail.com> writes:\n\n>> Disclaimer: neither am I a translator nor a user of a translated Git.\n>\n> Just to add to this:\n>\n>  - Careful use of sentence lego is OK, but e.g. in my native language a\n>    command-line option would use a male noun article, whereas commands\n>    would be feminine.\n\nHmph, if we gather wisdom from folks with different native languages\nand varying rules, I am unsure that we still can say that \"careful\"\nuse of sentence lego is OK.\n"},{"id":"451755","messageId":"2096494.irdbgypaU6@cayenne","threadId":"57588","inReplyTo":"xmqqlex3xh4d.fsf@gitster.g","subject":"Re: [PATCH 0/7] More i18n fixes","fromName":"Jean-Noël AVILA","fromEmail":"jn.avila@free.fr","sentAt":"2022-03-21T20:13:01Z","receivedAt":"2022-03-21T20:13:33Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"On Monday, 21 March 2022 20:03:46 CET Junio C Hamano wrote:\n> Ævar Arnfjörð Bjarmason <avarab@gmail.com> writes:\n> \n> >> Disclaimer: neither am I a translator nor a user of a translated Git.\n> >\n> > Just to add to this:\n> >\n> >  - Careful use of sentence lego is OK, but e.g. in my native language a\n> >    command-line option would use a male noun article, whereas commands\n> >    would be feminine.\n> \n> Hmph, if we gather wisdom from folks with different native languages\n> and varying rules, I am unsure that we still can say that \"careful\"\n> use of sentence lego is OK.\n> \n\nTo me, this is not sentence lego because:\n * the placeholders are replacing constant strings that won't have declensions \nor grammatical agreements\n * the placeholders are linked to content where the variables have the same \ntype, which makes them have the same genre for each language. This is the case \nfor commands, options, env variables,...\n\nGiven these prerequisites, there's nothing that needs careful lego, because \nthere is no risk at all. The only needed refinement, which I haven't addressed \nin this series,  is making it clear for the translator what the placeholder is \nreferring to in order to get the wording correct.\n\n\n\n"},{"id":"451766","messageId":"3656471.kQq0lBPeGt@cayenne","threadId":"57588","inReplyTo":"220321.86ils79z0c.gmgdl@evledraar.gmail.com","subject":"Re: [PATCH 0/7] More i18n fixes","fromName":"Jean-Noël AVILA","fromEmail":"jn.avila@free.fr","sentAt":"2022-03-21T20:35:49Z","receivedAt":"2022-03-21T20:36:15Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"On Monday, 21 March 2022 14:59:24 CET Ævar Arnfjörð Bjarmason wrote:\n> \n> On Mon, Mar 21 2022, Johannes Sixt wrote:\n> \n> > Am 20.03.22 um 22:54 schrieb Jean-Noël Avila via GitGitGadget:\n> >> This is another i18n PR (and hopefully the last for a while).\n> >> \n> >> As usual, the intent is kept the same: curbing the number of strings to\n> >> translate, remove constant, error prone parts out of the way, trying in some\n> >> sense to \"put a precedent\" so that the template strings can be reused later.\n> >\n> > I feel that many of the example conversions look like sentence lego\n> > because there remains only one English word, e.g., \"'%s' failed\". The\n> > converted code does not leave a hint for the translators what the %s\n> > will be. Is it a command, a function name, somehting else? Even if the\n> > hint was provided, different translations may be required depending on\n> > the substituted entity. Did you investigate the existing translations\n> > whether all of them can be converted to the new scheme?\n> >\n> >> This series has also a RFC status: can \"bad argument\" messages be merged\n> >> with unrecognized argument?\n> >\n> > The cases that patch 7/7 transforms look like they need not keep\n> > \"unrecognized argument\", but can be converted to \"bad argument\".\n> >\n> > Disclaimer: neither am I a translator nor a user of a translated Git.\n> \n> Just to add to this:\n> \n>  - Careful use of sentence lego is OK, but e.g. in my native language a\n>    command-line option would use a male noun article, whereas commands\n>    would be feminine.\n> \n>    (I still haven't submitted an Icelandic translation, but this applies\n>    in general).\n> \n>    As a result string like \"'%s' failed\" can be *workable*, i.e. you can\n>    translate it assuming you'll get any arbitrary string, but the\n>    translation will often be rather tortured.\n> \n>    So it's much preferred (and this also goes to Johannes's comment) to\n>    instead do e.g.:\n> \n>        \"failed to run the '%s' command\"\n>        \"failed to use the '%s' argument\"\n> \n>    Or whatever, and e.g. for:\n> \t\n> \t-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(objecttype) does not take arguments\"));\n> \t+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(objecttype)\");\n> \n>    Instead say \"the '%s' format does not...\", i.e. disambiguate with\n>    \"format\".\n> \n>  - While perfect shouldn't be the enemy of the good, it would be most\n>    welcome to improve some of the warts revealed by these messages,\n>    notably that e.g. the \"failed to run X command\" don't report\n>    errno. E.g. this in git.c is a good template (except for the \"\\n\" we\n>    should ideally get rid of):\n> \n>        _(\"failed to run command '%s': %s\\n\")\n\nOK. \n\n> \n>  - On that topic, it would be really useful to see if we can unify some\n>    of these with *existing* po/git.pot messaging, I don't know if that's\n>    part of your workflow, but in some cases I've seen we can either\n>    tweak wording slightly to match an existing message, or could further\n>    unify some existing similar messages.\n> \n\nThat's part of the workflow, although not hand-made, but greped. There are two types of factorizations:\n* strings where introducing a placeholder creates duplicates\n* strings that basically mean the same, but expressed differently (require human parsing)\n\n>  - Even if we say \"failed to run git-apply\" or whatever now we should\n>    really be adding quotes to these as we convert them. In some cases\n>    the changes that (good):\n> \t\n> \t-\t\tdie(_(\"git-http-push failed\"));\n> \t+\t\tdie(_(\"'%s' failed\"), \"git-http-push\");\n> \n>    But not in others (bad):\n> \t\n> \t-\t\tres = error(_(\"Bad bisect_write argument: %s\"), state);\n> \t+\t\tres = error(_(\"bad %s argument: %s\"), \"bisect_write\", state);\n> \n>    I.e. that should be 'bad '%s' argument. And also on the \"unify\" point\n>    above, e.g. grep.c has this:\n> \n>        grep.c: die(\"bad %s argument: %s\", opt, arg);\n> \n>    So we could covert that one to \"bad '%s' argument: '%s\"\" while we're\n>    at it...\n> \n> - In some cases there's ucase to lcase conversions, like Bad->bad above\n>   (good), but others are missed, e.g. (also missing quotes as noted\n>   above):\n> \n> \t-\t\tdie(_(\"Server does not support --shallow-since\"));\n> \t+\t\tdie(_(\"Server does not support %s\"), \"--shallow-since\");\n> \n>  - On quotes, let's consistently use '' quotes, and not e.g.g:\n> \t\n> \t-\t\tdie(_(\"`scalar list` does not take arguments\"));\n> \t+\t\tdie(_(\"%s does not take arguments\"), \"`scalar list`\");\n> \n> \n\nOK for disambiguation, lowercasing and quoting all placeholders.\nBTW, disambiguation may have the side effect of revealing where the type of placeholders may not be matching the types of replaced variables.\n\n\nWill reroll.\n\nThanks.\n\n\n\n"},{"id":"452958","messageId":"pull.1181.v2.git.1648915853.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.git.1647813291.gitgitgadget@gmail.com","subject":"[PATCH v2 0/6] More i18n fixes","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-04-02T16:10:47Z","receivedAt":"2022-04-02T16:11:47Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"This is another i18n PR (and hopefully the last for a while).\n\nAs usual, the intent is kept the same: curbing the number of strings to\ntranslate, remove constant, error prone parts out of the way, trying in some\nsense to \"put a precedent\" so that the template strings can be reused later.\n\nChanges in v2:\n\n * Make the messages clearer as to what the placeholders are.\n * Generalize the quoting of placeholders\n * Merge the messages with bad arguments to one\n\nBagas Sanjaya (1):\n  sequencer: factor GIT_AUTHOR_* from message strings\n\nJean-Noël Avila (5):\n  i18n: factorize generic failure messages\n  i18n: factorize server support messages in fetch-pack\n  i18n: factorize \"foo does not take arguments\" messages\n  i18n: factorize read-cache error messages\n  i18n: factorize \"bad argument\" messages\n\n add-patch.c                     |  4 ++--\n builtin/am.c                    |  2 +-\n builtin/bisect--helper.c        |  2 +-\n builtin/commit-graph.c          |  2 +-\n builtin/config.c                |  2 +-\n builtin/env--helper.c           |  2 +-\n builtin/gc.c                    |  8 +++----\n builtin/merge.c                 |  6 ++---\n builtin/revert.c                |  4 ++--\n contrib/scalar/scalar.c         |  2 +-\n diff.c                          |  4 ++--\n fetch-pack.c                    | 40 ++++++++++++++++-----------------\n grep.c                          |  2 +-\n read-cache.c                    |  8 +++----\n ref-filter.c                    |  8 +++----\n remote-curl.c                   |  2 +-\n send-pack.c                     |  2 +-\n sequencer.c                     | 12 +++++-----\n setup.c                         |  4 ++--\n submodule-config.c              |  8 +++----\n submodule.c                     |  2 +-\n t/t1300-config.sh               |  2 +-\n t/t1600-index.sh                |  6 ++---\n t/t3510-cherry-pick-sequence.sh |  8 +++----\n t/t6436-merge-overwrite.sh      |  2 +-\n t/t7900-maintenance.sh          |  4 ++--\n 26 files changed, 74 insertions(+), 74 deletions(-)\n\n\nbase-commit: 74cc1aa55f30ed76424a0e7226ab519aa6265061\nPublished-As: https://github.com/gitgitgadget/git/releases/tag/pr-1181%2Fjnavila%2Fmore_i18n_fixes-v2\nFetch-It-Via: git fetch https://github.com/gitgitgadget/git pr-1181/jnavila/more_i18n_fixes-v2\nPull-Request: https://github.com/gitgitgadget/git/pull/1181\n\nRange-diff vs v1:\n\n 1:  73a3a8d7d97 ! 1:  4bba3e1f6cb i18n: factorize generic failure messages\n     @@ Metadata\n       ## Commit message ##\n          i18n: factorize generic failure messages\n      \n     -    In these message the command that failed should not be translated. So\n     -    it is simpler to just remove these parts from the message.\n     +    In these message the command or the function that failed should not be\n     +    translated. So it is simpler to just remove these parts from the\n     +    message.\n      \n          Signed-off-by: Jean-Noël Avila <jn.avila@free.fr>\n      \n     @@ add-patch.c: static int run_apply_check(struct add_p_state *s,\n       \tstrvec_pushv(&cp.args, s->mode->apply_check_args);\n       \tif (pipe_command(&cp, s->buf.buf, s->buf.len, NULL, 0, NULL, 0))\n      -\t\treturn error(_(\"'git apply --cached' failed\"));\n     -+\t\treturn error(_(\"'%s' failed\"), \"git apply --cached\");\n     ++\t\treturn error(_(\"the command '%s' failed\"), \"git apply --cached\");\n       \n       \treturn 0;\n       }\n     @@ add-patch.c: soft_increment:\n       \t\t\tif (pipe_command(&cp, s->buf.buf, s->buf.len,\n       \t\t\t\t\t NULL, 0, NULL, 0))\n      -\t\t\t\terror(_(\"'git apply' failed\"));\n     -+\t\t\t\terror(_(\"'%s' failed\"), \"git apply\");\n     ++\t\t\t\terror(_(\"the command '%s' failed\"), \"git apply\");\n       \t\t}\n       \t\tif (repo_read_index(s->s.r) >= 0)\n       \t\t\trepo_refresh_and_write_index(s->s.r, REFRESH_QUIET, 0,\n     @@ builtin/am.c: static int is_mail(FILE *fp)\n       \n       \tif (fseek(fp, 0L, SEEK_SET))\n      -\t\tdie_errno(_(\"fseek failed\"));\n     -+\t\tdie_errno(_(\"'%s' failed\"), \"fseek\");\n     ++\t\tdie_errno(_(\"the function '%s' failed\"), \"fseek\");\n       \n       \tif (regcomp(&regex, header_regex, REG_NOSUB | REG_EXTENDED))\n       \t\tdie(\"invalid pattern: %s\", header_regex);\n     @@ builtin/gc.c: static int multi_pack_index_expire(struct maintenance_run_opts *op\n       \n       \tif (run_command(&child))\n      -\t\treturn error(_(\"'git multi-pack-index expire' failed\"));\n     -+\t\treturn error(_(\"'%s' failed\"), \"git multi-pack-index expire\");\n     ++\t\treturn error(_(\"the command '%s' failed\"), \"git multi-pack-index expire\");\n       \n       \treturn 0;\n       }\n     @@ builtin/gc.c: static int multi_pack_index_repack(struct maintenance_run_opts *op\n       \n       \tif (run_command(&child))\n      -\t\treturn error(_(\"'git multi-pack-index repack' failed\"));\n     -+\t\treturn error(_(\"'%s' failed\"), \"git multi-pack-index repack\");\n     ++\t\treturn error(_(\"the command '%s' failed\"), \"git multi-pack-index repack\");\n       \n       \treturn 0;\n       }\n     @@ builtin/merge.c: static int save_state(struct object_id *stash)\n       \n       \tif (finish_command(&cp) || len < 0)\n      -\t\tdie(_(\"stash failed\"));\n     -+\t\tdie(_(\"'%s' failed\"), \"stash\");\n     ++\t\tdie(_(\"the command '%s' failed\"), \"stash\");\n       \telse if (!len)\t\t/* no changes */\n       \t\tgoto out;\n       \tstrbuf_setlen(&buffer, buffer.len-1);\n     @@ builtin/merge.c: static void read_empty(const struct object_id *oid, int verbose\n       \n       \tif (run_command_v_opt(args, RUN_GIT_CMD))\n      -\t\tdie(_(\"read-tree failed\"));\n     -+\t\tdie(_(\"'%s' failed\"), \"read-tree\");\n     ++\t\tdie(_(\"the command '%s' failed\"), \"read-tree\");\n       }\n       \n       static void reset_hard(const struct object_id *oid, int verbose)\n     @@ builtin/merge.c: static void reset_hard(const struct object_id *oid, int verbose\n       \n       \tif (run_command_v_opt(args, RUN_GIT_CMD))\n      -\t\tdie(_(\"read-tree failed\"));\n     -+\t\tdie(_(\"'%s' failed\"), \"read-tree\");\n     ++\t\tdie(_(\"the command '%s' failed\"), \"read-tree\");\n       }\n       \n       static void restore_state(const struct object_id *head,\n     @@ builtin/revert.c: int cmd_revert(int argc, const char **argv, const char *prefix\n       \tres = run_sequencer(argc, argv, &opts);\n       \tif (res < 0)\n      -\t\tdie(_(\"revert failed\"));\n     -+\t\tdie(_(\"'%s' failed\"), \"revert\");\n     ++\t\tdie(_(\"the command '%s' failed\"), \"revert\");\n       \treturn res;\n       }\n       \n     @@ builtin/revert.c: int cmd_cherry_pick(int argc, const char **argv, const char *p\n       \tres = run_sequencer(argc, argv, &opts);\n       \tif (res < 0)\n      -\t\tdie(_(\"cherry-pick failed\"));\n     -+\t\tdie(_(\"'%s' failed\"), \"cherry-pick\");\n     ++\t\tdie(_(\"the command '%s' failed\"), \"cherry-pick\");\n       \treturn res;\n       }\n      \n     @@ fetch-pack.c: static int get_pack(struct fetch_pack_args *args,\n       \t\t\tret == 0;\n       \telse\n      -\t\tdie(_(\"%s failed\"), cmd_name);\n     -+\t\tdie(_(\"'%s' failed\"), cmd_name);\n     ++\t\tdie(_(\"the command '%s' failed\"), cmd_name);\n       \tif (use_sideband && finish_async(&demux))\n       \t\tdie(_(\"error in sideband demultiplexer\"));\n       \n     @@ remote-curl.c: static int push_dav(int nr_spec, const char **specs)\n       \n       \tif (run_command(&child))\n      -\t\tdie(_(\"git-http-push failed\"));\n     -+\t\tdie(_(\"'%s' failed\"), \"git-http-push\");\n     ++\t\tdie(_(\"the command '%s' failed\"), \"git-http-push\");\n       \treturn 0;\n       }\n       \n     @@ setup.c: int daemonize(void)\n       \t\t\tbreak;\n       \t\tcase -1:\n      -\t\t\tdie_errno(_(\"fork failed\"));\n     -+\t\t\tdie_errno(_(\"'%s' failed\"), \"fork\");\n     ++\t\t\tdie_errno(_(\"the function '%s' failed\"), \"fork\");\n       \t\tdefault:\n       \t\t\texit(0);\n       \t}\n       \tif (setsid() == -1)\n      -\t\tdie_errno(_(\"setsid failed\"));\n     -+\t\tdie_errno(_(\"'%s' failed\"), \"setsid\");\n     ++\t\tdie_errno(_(\"the function '%s' failed\"), \"setsid\");\n       \tclose(0);\n       \tclose(1);\n       \tclose(2);\n     @@ t/t3510-cherry-pick-sequence.sh: test_expect_success 'check advice when we move\n       \thint: have you committed already?\n       \thint: try \"git cherry-pick --continue\"\n      -\tfatal: cherry-pick failed\n     -+\tfatal: '\\''cherry-pick'\\'' failed\n     ++\tfatal: the command '\\''cherry-pick'\\'' failed\n       \tEOF\n       \ttest_must_fail git cherry-pick base..yetanotherpick &&\n       \techo c >foo &&\n     @@ t/t3510-cherry-pick-sequence.sh: test_expect_success 'selectively advise --skip\n       \terror: cherry-pick is already in progress\n       \thint: try \"git cherry-pick (--continue | --skip | --abort | --quit)\"\n      -\tfatal: cherry-pick failed\n     -+\tfatal: '\\''cherry-pick'\\'' failed\n     ++\tfatal: the command '\\''cherry-pick'\\'' failed\n       \tEOF\n       \ttest_must_fail git cherry-pick picked..yetanotherpick &&\n       \ttest_must_fail git cherry-pick picked..yetanotherpick 2>advice &&\n     @@ t/t3510-cherry-pick-sequence.sh: test_expect_success 'selectively advise --skip\n       \terror: cherry-pick is already in progress\n       \thint: try \"git cherry-pick (--continue | --abort | --quit)\"\n      -\tfatal: cherry-pick failed\n     -+\tfatal: '\\''cherry-pick'\\'' failed\n     ++\tfatal: the command '\\''cherry-pick'\\'' failed\n       \tEOF\n       \tgit reset --merge &&\n       \ttest_must_fail git cherry-pick picked..yetanotherpick 2>advice &&\n     @@ t/t3510-cherry-pick-sequence.sh: test_expect_success 'allow skipping commit but\n       \tcat >expect <<-EOF &&\n       \terror: cannot abort from a branch yet to be born\n      -\tfatal: cherry-pick failed\n     -+\tfatal: '\\''cherry-pick'\\'' failed\n     ++\tfatal: the command '\\''cherry-pick'\\'' failed\n       \tEOF\n       \tgit checkout --orphan new_disconnected &&\n       \tgit reset --hard &&\n     @@ t/t6436-merge-overwrite.sh: test_expect_success 'will not be confused by symlink\n       cat >expect <<\\EOF\n       error: Untracked working tree file 'c0.c' would be overwritten by merge.\n      -fatal: read-tree failed\n     -+fatal: 'read-tree' failed\n     ++fatal: the command 'read-tree' failed\n       EOF\n       \n       test_expect_success 'will not overwrite untracked file on unborn branch' '\n 2:  8bdbb32f544 = 2:  03022a2fcd1 sequencer: factor GIT_AUTHOR_* from message strings\n 3:  c94d5c932f4 < -:  ----------- i18n: factorize \"bad argument\" messages\n 4:  bf23e1ebe65 ! 3:  b06b7670516 i18n: factorize \"Server does not support foo\" messages\n     @@ Metadata\n      Author: Jean-Noël Avila <jn.avila@free.fr>\n      \n       ## Commit message ##\n     -    i18n: factorize \"Server does not support foo\" messages\n     +    i18n: factorize server support messages in fetch-pack\n     +\n     +    The messages \"Server supports foo\" and \"Server does not support bar\"\n     +    are uniformized and options are quoted.\n      \n          Signed-off-by: Jean-Noël Avila <jn.avila@free.fr>\n      \n       ## fetch-pack.c ##\n      @@ fetch-pack.c: static struct ref *do_fetch_pack(struct fetch_pack_args *args,\n     - \t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-since\");\n     + \t\tadvertise_sid = 0;\n     + \n     + \tif (server_supports(\"shallow\"))\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"shallow\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"shallow\");\n     + \telse if (args->depth > 0 || is_repository_shallow(r))\n     + \t\tdie(_(\"Server does not support shallow clients\"));\n     + \tif (args->depth > 0 || args->deepen_since || args->deepen_not)\n     + \t\targs->deepen = 1;\n     + \tif (server_supports(\"multi_ack_detailed\")) {\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"multi_ack_detailed\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"multi_ack_detailed\");\n     + \t\tmulti_ack = 2;\n     + \t\tif (server_supports(\"no-done\")) {\n     +-\t\t\tprint_verbose(args, _(\"Server supports %s\"), \"no-done\");\n     ++\t\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"no-done\");\n     + \t\t\tif (args->stateless_rpc)\n     + \t\t\t\tno_done = 1;\n     + \t\t}\n     + \t}\n     + \telse if (server_supports(\"multi_ack\")) {\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"multi_ack\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"multi_ack\");\n     + \t\tmulti_ack = 1;\n     + \t}\n     + \tif (server_supports(\"side-band-64k\")) {\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"side-band-64k\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"side-band-64k\");\n     + \t\tuse_sideband = 2;\n     + \t}\n     + \telse if (server_supports(\"side-band\")) {\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"side-band\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"side-band\");\n     + \t\tuse_sideband = 1;\n     + \t}\n     + \tif (server_supports(\"allow-tip-sha1-in-want\")) {\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"allow-tip-sha1-in-want\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"allow-tip-sha1-in-want\");\n     + \t\tallow_unadvertised_object_request |= ALLOW_TIP_SHA1;\n     + \t}\n     + \tif (server_supports(\"allow-reachable-sha1-in-want\")) {\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"allow-reachable-sha1-in-want\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"allow-reachable-sha1-in-want\");\n     + \t\tallow_unadvertised_object_request |= ALLOW_REACHABLE_SHA1;\n     + \t}\n     + \tif (server_supports(\"thin-pack\"))\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"thin-pack\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"thin-pack\");\n     + \telse\n     + \t\targs->use_thin_pack = 0;\n     + \tif (server_supports(\"no-progress\"))\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"no-progress\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"no-progress\");\n     + \telse\n     + \t\targs->no_progress = 0;\n     + \tif (server_supports(\"include-tag\"))\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"include-tag\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"include-tag\");\n     + \telse\n     + \t\targs->include_tag = 0;\n     + \tif (server_supports(\"ofs-delta\"))\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"ofs-delta\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"ofs-delta\");\n     + \telse\n     + \t\tprefer_ofs_delta = 0;\n     + \n     + \tif (server_supports(\"filter\")) {\n     + \t\tserver_supports_filtering = 1;\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"filter\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"filter\");\n     + \t} else if (args->filter_options.choice) {\n     + \t\twarning(\"filtering not recognized by server, ignoring\");\n     + \t}\n     + \n     + \tif (server_supports(\"deepen-since\")) {\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-since\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"deepen-since\");\n       \t\tdeepen_since_ok = 1;\n       \t} else if (args->deepen_since)\n      -\t\tdie(_(\"Server does not support --shallow-since\"));\n     -+\t\tdie(_(\"Server does not support %s\"), \"--shallow-since\");\n     ++\t\tdie(_(\"Server does not support '%s'\"), \"--shallow-since\");\n       \tif (server_supports(\"deepen-not\")) {\n     - \t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-not\");\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-not\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"deepen-not\");\n       \t\tdeepen_not_ok = 1;\n       \t} else if (args->deepen_not)\n      -\t\tdie(_(\"Server does not support --shallow-exclude\"));\n     -+\t\tdie(_(\"Server does not support %s\"), \"--shallow-exclude\");\n     ++\t\tdie(_(\"Server does not support '%s'\"), \"--shallow-exclude\");\n       \tif (server_supports(\"deepen-relative\"))\n     - \t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-relative\");\n     +-\t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-relative\");\n     ++\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"deepen-relative\");\n       \telse if (args->deepen_relative)\n      -\t\tdie(_(\"Server does not support --deepen\"));\n     -+\t\tdie(_(\"Server does not support %s\"), \"--deepen\");\n     ++\t\tdie(_(\"Server does not support '%s'\"), \"--deepen\");\n       \tif (!server_supports_hash(the_hash_algo->name, NULL))\n       \t\tdie(_(\"Server does not support this repository's object format\"));\n       \n 5:  2e1bd504673 ! 4:  6221c37145c i18n: factorize \"foo does not take arguments\" messages\n     @@ Metadata\n       ## Commit message ##\n          i18n: factorize \"foo does not take arguments\" messages\n      \n     +    The messages are split into the ones for ref-filter which deal with\n     +    atoms and scalar which has an option.\n     +\n          Signed-off-by: Jean-Noël Avila <jn.avila@free.fr>\n      \n       ## contrib/scalar/scalar.c ##\n     @@ contrib/scalar/scalar.c: cleanup:\n       {\n       \tif (argc != 1)\n      -\t\tdie(_(\"`scalar list` does not take arguments\"));\n     -+\t\tdie(_(\"%s does not take arguments\"), \"`scalar list`\");\n     ++\t\tdie(_(\"the '%s' command does not take arguments\"), \"scalar list\");\n       \n       \tif (run_git(\"config\", \"--global\", \"--get-all\", \"scalar.repo\", NULL) < 0)\n       \t\treturn -1;\n     @@ ref-filter.c: static int objecttype_atom_parser(struct ref_format *format, struc\n       {\n       \tif (arg)\n      -\t\treturn strbuf_addf_ret(err, -1, _(\"%%(objecttype) does not take arguments\"));\n     -+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(objecttype)\");\n     ++\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(objecttype)\");\n       \tif (*atom->name == '*')\n       \t\toi_deref.info.typep = &oi_deref.type;\n       \telse\n     @@ ref-filter.c: static int deltabase_atom_parser(struct ref_format *format, struct\n       {\n       \tif (arg)\n      -\t\treturn strbuf_addf_ret(err, -1, _(\"%%(deltabase) does not take arguments\"));\n     -+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(deltabase)\");\n     ++\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(deltabase)\");\n       \tif (*atom->name == '*')\n       \t\toi_deref.info.delta_base_oid = &oi_deref.delta_base_oid;\n       \telse\n     @@ ref-filter.c: static int body_atom_parser(struct ref_format *format, struct used\n       {\n       \tif (arg)\n      -\t\treturn strbuf_addf_ret(err, -1, _(\"%%(body) does not take arguments\"));\n     -+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(body)\");\n     ++\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(body)\");\n       \tatom->u.contents.option = C_BODY_DEP;\n       \treturn 0;\n       }\n     @@ ref-filter.c: static int rest_atom_parser(struct ref_format *format, struct used\n       {\n       \tif (arg)\n      -\t\treturn strbuf_addf_ret(err, -1, _(\"%%(rest) does not take arguments\"));\n     -+\t\treturn strbuf_addf_ret(err, -1, _(\"%s does not take arguments\"), \"%(rest)\");\n     ++\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(rest)\");\n       \tformat->use_rest = 1;\n       \treturn 0;\n       }\n 6:  b8f97e6fde8 ! 5:  1888778902a i18n: factorize read-cache error messages\n     @@ read-cache.c: static unsigned int get_index_format_default(struct repository *r)\n       \t\tif (version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n      -\t\t\twarning(_(\"index.version set, but the value is invalid.\\n\"\n      -\t\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n     -+\t\t\twarning(_(\"%s set, but the value is invalid.\\n\"\n     ++\t\t\twarning(_(\"'%s' set, but the value is invalid.\\n\"\n      +\t\t\t\t  \"Using version %i\"), \"index.version\", INDEX_FORMAT_DEFAULT);\n       \t\t\treturn INDEX_FORMAT_DEFAULT;\n       \t\t}\n     @@ read-cache.c: static unsigned int get_index_format_default(struct repository *r)\n       \t    version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n      -\t\twarning(_(\"GIT_INDEX_VERSION set, but the value is invalid.\\n\"\n      -\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n     -+\t\twarning(_(\"%s set, but the value is invalid.\\n\"\n     ++\t\twarning(_(\"'%s' set, but the value is invalid.\\n\"\n      +\t\t\t  \"Using version %i\"), \"GIT_INDEX_VERSION\", INDEX_FORMAT_DEFAULT);\n       \t\tversion = INDEX_FORMAT_DEFAULT;\n       \t}\n       \treturn version;\n     +\n     + ## t/t1600-index.sh ##\n     +@@ t/t1600-index.sh: test_expect_success 'bogus GIT_INDEX_VERSION issues warning' '\n     + \t\tgit add a 2>err &&\n     + \t\tsed \"s/[0-9]//\" err >actual.err &&\n     + \t\tsed -e \"s/ Z$/ /\" <<-\\EOF >expect.err &&\n     +-\t\t\twarning: GIT_INDEX_VERSION set, but the value is invalid.\n     ++\t\t\twarning: '\\''GIT_INDEX_VERSION'\\'' set, but the value is invalid.\n     + \t\t\tUsing version Z\n     + \t\tEOF\n     + \t\ttest_cmp expect.err actual.err\n     +@@ t/t1600-index.sh: test_expect_success 'out of bounds GIT_INDEX_VERSION issues warning' '\n     + \t\tgit add a 2>err &&\n     + \t\tsed \"s/[0-9]//\" err >actual.err &&\n     + \t\tsed -e \"s/ Z$/ /\" <<-\\EOF >expect.err &&\n     +-\t\t\twarning: GIT_INDEX_VERSION set, but the value is invalid.\n     ++\t\t\twarning: '\\''GIT_INDEX_VERSION'\\'' set, but the value is invalid.\n     + \t\t\tUsing version Z\n     + \t\tEOF\n     + \t\ttest_cmp expect.err actual.err\n     +@@ t/t1600-index.sh: test_expect_success 'out of bounds index.version issues warning' '\n     + \t\tgit add a 2>err &&\n     + \t\tsed \"s/[0-9]//\" err >actual.err &&\n     + \t\tsed -e \"s/ Z$/ /\" <<-\\EOF >expect.err &&\n     +-\t\t\twarning: index.version set, but the value is invalid.\n     ++\t\t\twarning: '\\''index.version'\\'' set, but the value is invalid.\n     + \t\t\tUsing version Z\n     + \t\tEOF\n     + \t\ttest_cmp expect.err actual.err\n 7:  ca52567b201 ! 6:  febe64a8a06 i18n: factorize unrecognized options arguments messages\n     @@ Metadata\n      Author: Jean-Noël Avila <jn.avila@free.fr>\n      \n       ## Commit message ##\n     -    i18n: factorize unrecognized options arguments messages\n     +    i18n: factorize \"bad argument\" messages\n     +\n     +    We also quote the placeholders as they replace constant strings.\n      \n          Signed-off-by: Jean-Noël Avila <jn.avila@free.fr>\n      \n     + ## builtin/bisect--helper.c ##\n     +@@ builtin/bisect--helper.c: static int bisect_write(const char *state, const char *rev,\n     + \t} else if (one_of(state, terms->term_good, \"skip\", NULL)) {\n     + \t\tstrbuf_addf(&tag, \"refs/bisect/%s-%s\", state, rev);\n     + \t} else {\n     +-\t\tres = error(_(\"Bad bisect_write argument: %s\"), state);\n     ++\t\tres = error(_(\"bad '%s' argument: '%s'\"), \"bisect_write\", state);\n     + \t\tgoto finish;\n     + \t}\n     + \n     +\n       ## builtin/commit-graph.c ##\n      @@ builtin/commit-graph.c: static int write_option_parse_split(const struct option *opt, const char *arg,\n       \telse if (!strcmp(arg, \"replace\"))\n       \t\t*flags = COMMIT_GRAPH_SPLIT_REPLACE;\n       \telse\n      -\t\tdie(_(\"unrecognized --split argument, %s\"), arg);\n     -+\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--split\", arg);\n     ++\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--split\", arg);\n       \n       \treturn 0;\n       }\n     @@ builtin/config.c: static int option_parse_type(const struct option *opt, const c\n       \t\t\tnew_type = TYPE_COLOR;\n       \t\telse\n      -\t\t\tdie(_(\"unrecognized --type argument, %s\"), arg);\n     -+\t\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--type\", arg);\n     ++\t\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--type\", arg);\n       \t}\n       \n       \tto_type = opt->value;\n     @@ builtin/env--helper.c: static int option_parse_type(const struct option *opt, co\n       \t\t*cmdmode = ENV_HELPER_TYPE_ULONG;\n       \telse\n      -\t\tdie(_(\"unrecognized --type argument, %s\"), arg);\n     -+\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--type\", arg);\n     ++\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--type\", arg);\n       \n       \treturn 0;\n       }\n     @@ builtin/gc.c: static int maintenance_opt_schedule(const struct option *opt, cons\n       \n       \tif (!*priority)\n      -\t\tdie(_(\"unrecognized --schedule argument '%s'\"), arg);\n     -+\t\tdie(_(\"unrecognized %s argument '%s'\"), \"--schedule\", arg);\n     ++\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--schedule\", arg);\n       \n       \treturn 0;\n       }\n     @@ builtin/gc.c: static int maintenance_opt_scheduler(const struct option *opt, con\n       \t*scheduler = parse_scheduler(arg);\n       \tif (*scheduler == SCHEDULER_INVALID)\n      -\t\treturn error(_(\"unrecognized --scheduler argument '%s'\"), arg);\n     -+\t\treturn error(_(\"unrecognized %s argument '%s'\"), \"--scheduler\", arg);\n     ++\t\treturn error(_(\"bad '%s' argument: '%s'\"), \"--scheduler\", arg);\n     + \treturn 0;\n     + }\n     + \n     +\n     + ## diff.c ##\n     +@@ diff.c: static int diff_opt_color_moved(const struct option *opt,\n     + \t} else {\n     + \t\tint cm = parse_color_moved(arg);\n     + \t\tif (cm < 0)\n     +-\t\t\treturn error(_(\"bad --color-moved argument: %s\"), arg);\n     ++\t\t\treturn error(_(\"bad '%s' argument: '%s'\"), \"--color-moved\", arg);\n     + \t\toptions->color_moved = cm;\n     + \t}\n       \treturn 0;\n     +@@ diff.c: static int diff_opt_word_diff(const struct option *opt,\n     + \t\telse if (!strcmp(arg, \"none\"))\n     + \t\t\toptions->word_diff = DIFF_WORDS_NONE;\n     + \t\telse\n     +-\t\t\treturn error(_(\"bad --word-diff argument: %s\"), arg);\n     ++\t\t\treturn error(_(\"bad '%s' argument: '%s'\"), \"--word-diff\", arg);\n     + \t} else {\n     + \t\tif (options->word_diff == DIFF_WORDS_NONE)\n     + \t\t\toptions->word_diff = DIFF_WORDS_PLAIN;\n     +\n     + ## grep.c ##\n     +@@ grep.c: static int parse_pattern_type_arg(const char *opt, const char *arg)\n     + \t\treturn GREP_PATTERN_TYPE_FIXED;\n     + \telse if (!strcmp(arg, \"perl\"))\n     + \t\treturn GREP_PATTERN_TYPE_PCRE;\n     +-\tdie(\"bad %s argument: %s\", opt, arg);\n     ++\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n     + }\n     + \n     + define_list_config_array_extra(color_grep_slots, {\"match\"});\n     +\n     + ## send-pack.c ##\n     +@@ send-pack.c: int option_parse_push_signed(const struct option *opt,\n     + \t\t*(int *)(opt->value) = SEND_PACK_PUSH_CERT_IF_ASKED;\n     + \t\treturn 0;\n     + \t}\n     +-\tdie(\"bad %s argument: %s\", opt->long_name, arg);\n     ++\tdie(\"bad '%s' argument: '%s'\", opt->long_name, arg);\n     + }\n     + \n     + static void feed_object(const struct object_id *oid, FILE *fh, int negative)\n     +\n     + ## submodule-config.c ##\n     +@@ submodule-config.c: static int parse_fetch_recurse(const char *opt, const char *arg,\n     + \t\t * git-completion.bash when you add new options.\n     + \t\t */\n     + \t\tif (die_on_error)\n     +-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n     ++\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n     + \t\telse\n     + \t\t\treturn RECURSE_SUBMODULES_ERROR;\n     + \t}\n     +@@ submodule-config.c: static int parse_update_recurse(const char *opt, const char *arg,\n     + \t\treturn RECURSE_SUBMODULES_OFF;\n     + \tdefault:\n     + \t\tif (die_on_error)\n     +-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n     ++\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n     + \t\treturn RECURSE_SUBMODULES_ERROR;\n     + \t}\n       }\n     +@@ submodule-config.c: static int parse_push_recurse(const char *opt, const char *arg,\n     + \tcase 1:\n     + \t\t/* There's no simple \"on\" value when pushing */\n     + \t\tif (die_on_error)\n     +-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n     ++\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n     + \t\telse\n     + \t\t\treturn RECURSE_SUBMODULES_ERROR;\n     + \tcase 0:\n     +@@ submodule-config.c: static int parse_push_recurse(const char *opt, const char *arg,\n     + \t\t * git-completion.bash when you add new modes.\n     + \t\t */\n     + \t\telse if (die_on_error)\n     +-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n     ++\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n     + \t\telse\n     + \t\t\treturn RECURSE_SUBMODULES_ERROR;\n     + \t}\n     +\n     + ## submodule.c ##\n     +@@ submodule.c: void handle_ignore_submodules_arg(struct diff_options *diffopt,\n     + \telse if (!strcmp(arg, \"dirty\"))\n     + \t\tdiffopt->flags.ignore_dirty_submodules = 1;\n     + \telse if (strcmp(arg, \"none\"))\n     +-\t\tdie(_(\"bad --ignore-submodules argument: %s\"), arg);\n     ++\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--ignore-submodules\", arg);\n     + \t/*\n     + \t * Please update _git_status() in git-completion.bash when you\n     + \t * add new options\n     +\n     + ## t/t1300-config.sh ##\n     +@@ t/t1300-config.sh: test_expect_success 'unset type specifiers may be reset to conflicting ones' '\n     + \n     + test_expect_success '--type rejects unknown specifiers' '\n     + \ttest_must_fail git config --type=nonsense section.foo 2>error &&\n     +-\ttest_i18ngrep \"unrecognized --type argument\" error\n     ++\ttest_i18ngrep \"bad '\\''--type'\\'' argument\" error\n     + '\n     + \n     + test_expect_success '--replace-all does not invent newlines' '\n     +\n     + ## t/t7900-maintenance.sh ##\n     +@@ t/t7900-maintenance.sh: test_expect_success '--auto and --schedule incompatible' '\n     + \n     + test_expect_success 'invalid --schedule value' '\n     + \ttest_must_fail git maintenance run --schedule=annually 2>err &&\n     +-\ttest_i18ngrep \"unrecognized --schedule\" err\n     ++\ttest_i18ngrep \"bad '\\''--schedule'\\''\" err\n     + '\n     + \n     + test_expect_success '--schedule inheritance weekly -> daily -> hourly' '\n     +@@ t/t7900-maintenance.sh: test_expect_success !MINGW 'register and unregister with regex metacharacters' '\n     + \n     + test_expect_success 'start --scheduler=<scheduler>' '\n     + \ttest_expect_code 129 git maintenance start --scheduler=foo 2>err &&\n     +-\ttest_i18ngrep \"unrecognized --scheduler argument\" err &&\n     ++\ttest_i18ngrep \"bad '\\''--scheduler'\\'' argument\" err &&\n       \n     + \ttest_expect_code 129 git maintenance start --no-scheduler 2>err &&\n     + \ttest_i18ngrep \"unknown option\" err &&\n\n-- \ngitgitgadget\n"},{"id":"452959","messageId":"4bba3e1f6cb9cdc35b0dc8da440e38de256b4d2b.1648915853.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.v2.git.1648915853.gitgitgadget@gmail.com","subject":"[PATCH v2 1/6] i18n: factorize generic failure messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-04-02T16:10:48Z","receivedAt":"2022-04-02T16:11:49Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nIn these message the command or the function that failed should not be\ntranslated. So it is simpler to just remove these parts from the\nmessage.\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n add-patch.c                     | 4 ++--\n builtin/am.c                    | 2 +-\n builtin/gc.c                    | 4 ++--\n builtin/merge.c                 | 6 +++---\n builtin/revert.c                | 4 ++--\n fetch-pack.c                    | 2 +-\n remote-curl.c                   | 2 +-\n setup.c                         | 4 ++--\n t/t3510-cherry-pick-sequence.sh | 8 ++++----\n t/t6436-merge-overwrite.sh      | 2 +-\n 10 files changed, 19 insertions(+), 19 deletions(-)\n\ndiff --git a/add-patch.c b/add-patch.c\nindex 55d719f7845..8c9e81ec78e 100644\n--- a/add-patch.c\n+++ b/add-patch.c\n@@ -1181,7 +1181,7 @@ static int run_apply_check(struct add_p_state *s,\n \t\t\t    \"apply\", \"--check\", NULL);\n \tstrvec_pushv(&cp.args, s->mode->apply_check_args);\n \tif (pipe_command(&cp, s->buf.buf, s->buf.len, NULL, 0, NULL, 0))\n-\t\treturn error(_(\"'git apply --cached' failed\"));\n+\t\treturn error(_(\"the command '%s' failed\"), \"git apply --cached\");\n \n \treturn 0;\n }\n@@ -1683,7 +1683,7 @@ soft_increment:\n \t\t\tstrvec_pushv(&cp.args, s->mode->apply_args);\n \t\t\tif (pipe_command(&cp, s->buf.buf, s->buf.len,\n \t\t\t\t\t NULL, 0, NULL, 0))\n-\t\t\t\terror(_(\"'git apply' failed\"));\n+\t\t\t\terror(_(\"the command '%s' failed\"), \"git apply\");\n \t\t}\n \t\tif (repo_read_index(s->s.r) >= 0)\n \t\t\trepo_refresh_and_write_index(s->s.r, REFRESH_QUIET, 0,\ndiff --git a/builtin/am.c b/builtin/am.c\nindex 0f4111bafa0..a0a57049510 100644\n--- a/builtin/am.c\n+++ b/builtin/am.c\n@@ -586,7 +586,7 @@ static int is_mail(FILE *fp)\n \tint ret = 1;\n \n \tif (fseek(fp, 0L, SEEK_SET))\n-\t\tdie_errno(_(\"fseek failed\"));\n+\t\tdie_errno(_(\"the function '%s' failed\"), \"fseek\");\n \n \tif (regcomp(&regex, header_regex, REG_NOSUB | REG_EXTENDED))\n \t\tdie(\"invalid pattern: %s\", header_regex);\ndiff --git a/builtin/gc.c b/builtin/gc.c\nindex ffaf0daf5d9..c062d7bceeb 100644\n--- a/builtin/gc.c\n+++ b/builtin/gc.c\n@@ -1104,7 +1104,7 @@ static int multi_pack_index_expire(struct maintenance_run_opts *opts)\n \t\tstrvec_push(&child.args, \"--no-progress\");\n \n \tif (run_command(&child))\n-\t\treturn error(_(\"'git multi-pack-index expire' failed\"));\n+\t\treturn error(_(\"the command '%s' failed\"), \"git multi-pack-index expire\");\n \n \treturn 0;\n }\n@@ -1163,7 +1163,7 @@ static int multi_pack_index_repack(struct maintenance_run_opts *opts)\n \t\t\t\t  (uintmax_t)get_auto_pack_size());\n \n \tif (run_command(&child))\n-\t\treturn error(_(\"'git multi-pack-index repack' failed\"));\n+\t\treturn error(_(\"the command '%s' failed\"), \"git multi-pack-index repack\");\n \n \treturn 0;\n }\ndiff --git a/builtin/merge.c b/builtin/merge.c\nindex f178f5a3ee1..78468ff43a4 100644\n--- a/builtin/merge.c\n+++ b/builtin/merge.c\n@@ -325,7 +325,7 @@ static int save_state(struct object_id *stash)\n \tclose(cp.out);\n \n \tif (finish_command(&cp) || len < 0)\n-\t\tdie(_(\"stash failed\"));\n+\t\tdie(_(\"the command '%s' failed\"), \"stash\");\n \telse if (!len)\t\t/* no changes */\n \t\tgoto out;\n \tstrbuf_setlen(&buffer, buffer.len-1);\n@@ -352,7 +352,7 @@ static void read_empty(const struct object_id *oid, int verbose)\n \targs[i] = NULL;\n \n \tif (run_command_v_opt(args, RUN_GIT_CMD))\n-\t\tdie(_(\"read-tree failed\"));\n+\t\tdie(_(\"the command '%s' failed\"), \"read-tree\");\n }\n \n static void reset_hard(const struct object_id *oid, int verbose)\n@@ -369,7 +369,7 @@ static void reset_hard(const struct object_id *oid, int verbose)\n \targs[i] = NULL;\n \n \tif (run_command_v_opt(args, RUN_GIT_CMD))\n-\t\tdie(_(\"read-tree failed\"));\n+\t\tdie(_(\"the command '%s' failed\"), \"read-tree\");\n }\n \n static void restore_state(const struct object_id *head,\ndiff --git a/builtin/revert.c b/builtin/revert.c\nindex 51776abea63..d293036e790 100644\n--- a/builtin/revert.c\n+++ b/builtin/revert.c\n@@ -238,7 +238,7 @@ int cmd_revert(int argc, const char **argv, const char *prefix)\n \tsequencer_init_config(&opts);\n \tres = run_sequencer(argc, argv, &opts);\n \tif (res < 0)\n-\t\tdie(_(\"revert failed\"));\n+\t\tdie(_(\"the command '%s' failed\"), \"revert\");\n \treturn res;\n }\n \n@@ -251,6 +251,6 @@ int cmd_cherry_pick(int argc, const char **argv, const char *prefix)\n \tsequencer_init_config(&opts);\n \tres = run_sequencer(argc, argv, &opts);\n \tif (res < 0)\n-\t\tdie(_(\"cherry-pick failed\"));\n+\t\tdie(_(\"the command '%s' failed\"), \"cherry-pick\");\n \treturn res;\n }\ndiff --git a/fetch-pack.c b/fetch-pack.c\nindex 87657907e78..2e6795cd439 100644\n--- a/fetch-pack.c\n+++ b/fetch-pack.c\n@@ -989,7 +989,7 @@ static int get_pack(struct fetch_pack_args *args,\n \t\t\targs->check_self_contained_and_connected &&\n \t\t\tret == 0;\n \telse\n-\t\tdie(_(\"%s failed\"), cmd_name);\n+\t\tdie(_(\"the command '%s' failed\"), cmd_name);\n \tif (use_sideband && finish_async(&demux))\n \t\tdie(_(\"error in sideband demultiplexer\"));\n \ndiff --git a/remote-curl.c b/remote-curl.c\nindex ff44f41011e..8393f56652b 100644\n--- a/remote-curl.c\n+++ b/remote-curl.c\n@@ -1287,7 +1287,7 @@ static int push_dav(int nr_spec, const char **specs)\n \t\tstrvec_push(&child.args, specs[i]);\n \n \tif (run_command(&child))\n-\t\tdie(_(\"git-http-push failed\"));\n+\t\tdie(_(\"the command '%s' failed\"), \"git-http-push\");\n \treturn 0;\n }\n \ndiff --git a/setup.c b/setup.c\nindex 04ce33cdcd4..30a4b81257d 100644\n--- a/setup.c\n+++ b/setup.c\n@@ -1506,12 +1506,12 @@ int daemonize(void)\n \t\tcase 0:\n \t\t\tbreak;\n \t\tcase -1:\n-\t\t\tdie_errno(_(\"fork failed\"));\n+\t\t\tdie_errno(_(\"the function '%s' failed\"), \"fork\");\n \t\tdefault:\n \t\t\texit(0);\n \t}\n \tif (setsid() == -1)\n-\t\tdie_errno(_(\"setsid failed\"));\n+\t\tdie_errno(_(\"the function '%s' failed\"), \"setsid\");\n \tclose(0);\n \tclose(1);\n \tclose(2);\ndiff --git a/t/t3510-cherry-pick-sequence.sh b/t/t3510-cherry-pick-sequence.sh\nindex 3b0fa66c33d..141d217dc3f 100755\n--- a/t/t3510-cherry-pick-sequence.sh\n+++ b/t/t3510-cherry-pick-sequence.sh\n@@ -193,7 +193,7 @@ test_expect_success 'check advice when we move HEAD by committing' '\n \terror: there is nothing to skip\n \thint: have you committed already?\n \thint: try \"git cherry-pick --continue\"\n-\tfatal: cherry-pick failed\n+\tfatal: the command '\\''cherry-pick'\\'' failed\n \tEOF\n \ttest_must_fail git cherry-pick base..yetanotherpick &&\n \techo c >foo &&\n@@ -208,7 +208,7 @@ test_expect_success 'selectively advise --skip while launching another sequence'\n \tcat >expect <<-EOF &&\n \terror: cherry-pick is already in progress\n \thint: try \"git cherry-pick (--continue | --skip | --abort | --quit)\"\n-\tfatal: cherry-pick failed\n+\tfatal: the command '\\''cherry-pick'\\'' failed\n \tEOF\n \ttest_must_fail git cherry-pick picked..yetanotherpick &&\n \ttest_must_fail git cherry-pick picked..yetanotherpick 2>advice &&\n@@ -216,7 +216,7 @@ test_expect_success 'selectively advise --skip while launching another sequence'\n \tcat >expect <<-EOF &&\n \terror: cherry-pick is already in progress\n \thint: try \"git cherry-pick (--continue | --abort | --quit)\"\n-\tfatal: cherry-pick failed\n+\tfatal: the command '\\''cherry-pick'\\'' failed\n \tEOF\n \tgit reset --merge &&\n \ttest_must_fail git cherry-pick picked..yetanotherpick 2>advice &&\n@@ -227,7 +227,7 @@ test_expect_success 'allow skipping commit but not abort for a new history' '\n \tpristine_detach initial &&\n \tcat >expect <<-EOF &&\n \terror: cannot abort from a branch yet to be born\n-\tfatal: cherry-pick failed\n+\tfatal: the command '\\''cherry-pick'\\'' failed\n \tEOF\n \tgit checkout --orphan new_disconnected &&\n \tgit reset --hard &&\ndiff --git a/t/t6436-merge-overwrite.sh b/t/t6436-merge-overwrite.sh\nindex c0b7bd7c3fe..c714ac2cbc5 100755\n--- a/t/t6436-merge-overwrite.sh\n+++ b/t/t6436-merge-overwrite.sh\n@@ -166,7 +166,7 @@ test_expect_success 'will not be confused by symlink in leading path' '\n \n cat >expect <<\\EOF\n error: Untracked working tree file 'c0.c' would be overwritten by merge.\n-fatal: read-tree failed\n+fatal: the command 'read-tree' failed\n EOF\n \n test_expect_success 'will not overwrite untracked file on unborn branch' '\n-- \ngitgitgadget\n\n"},{"id":"452960","messageId":"b06b76705163e49fe69680ceb3bf925fcfe8dc58.1648915853.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.v2.git.1648915853.gitgitgadget@gmail.com","subject":"[PATCH v2 3/6] i18n: factorize server support messages in fetch-pack","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-04-02T16:10:50Z","receivedAt":"2022-04-02T16:11:53Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nThe messages \"Server supports foo\" and \"Server does not support bar\"\nare uniformized and options are quoted.\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n fetch-pack.c | 38 +++++++++++++++++++-------------------\n 1 file changed, 19 insertions(+), 19 deletions(-)\n\ndiff --git a/fetch-pack.c b/fetch-pack.c\nindex 2e6795cd439..da3075f61f2 100644\n--- a/fetch-pack.c\n+++ b/fetch-pack.c\n@@ -1044,78 +1044,78 @@ static struct ref *do_fetch_pack(struct fetch_pack_args *args,\n \t\tadvertise_sid = 0;\n \n \tif (server_supports(\"shallow\"))\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"shallow\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"shallow\");\n \telse if (args->depth > 0 || is_repository_shallow(r))\n \t\tdie(_(\"Server does not support shallow clients\"));\n \tif (args->depth > 0 || args->deepen_since || args->deepen_not)\n \t\targs->deepen = 1;\n \tif (server_supports(\"multi_ack_detailed\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"multi_ack_detailed\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"multi_ack_detailed\");\n \t\tmulti_ack = 2;\n \t\tif (server_supports(\"no-done\")) {\n-\t\t\tprint_verbose(args, _(\"Server supports %s\"), \"no-done\");\n+\t\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"no-done\");\n \t\t\tif (args->stateless_rpc)\n \t\t\t\tno_done = 1;\n \t\t}\n \t}\n \telse if (server_supports(\"multi_ack\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"multi_ack\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"multi_ack\");\n \t\tmulti_ack = 1;\n \t}\n \tif (server_supports(\"side-band-64k\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"side-band-64k\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"side-band-64k\");\n \t\tuse_sideband = 2;\n \t}\n \telse if (server_supports(\"side-band\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"side-band\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"side-band\");\n \t\tuse_sideband = 1;\n \t}\n \tif (server_supports(\"allow-tip-sha1-in-want\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"allow-tip-sha1-in-want\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"allow-tip-sha1-in-want\");\n \t\tallow_unadvertised_object_request |= ALLOW_TIP_SHA1;\n \t}\n \tif (server_supports(\"allow-reachable-sha1-in-want\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"allow-reachable-sha1-in-want\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"allow-reachable-sha1-in-want\");\n \t\tallow_unadvertised_object_request |= ALLOW_REACHABLE_SHA1;\n \t}\n \tif (server_supports(\"thin-pack\"))\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"thin-pack\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"thin-pack\");\n \telse\n \t\targs->use_thin_pack = 0;\n \tif (server_supports(\"no-progress\"))\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"no-progress\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"no-progress\");\n \telse\n \t\targs->no_progress = 0;\n \tif (server_supports(\"include-tag\"))\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"include-tag\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"include-tag\");\n \telse\n \t\targs->include_tag = 0;\n \tif (server_supports(\"ofs-delta\"))\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"ofs-delta\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"ofs-delta\");\n \telse\n \t\tprefer_ofs_delta = 0;\n \n \tif (server_supports(\"filter\")) {\n \t\tserver_supports_filtering = 1;\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"filter\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"filter\");\n \t} else if (args->filter_options.choice) {\n \t\twarning(\"filtering not recognized by server, ignoring\");\n \t}\n \n \tif (server_supports(\"deepen-since\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-since\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"deepen-since\");\n \t\tdeepen_since_ok = 1;\n \t} else if (args->deepen_since)\n-\t\tdie(_(\"Server does not support --shallow-since\"));\n+\t\tdie(_(\"Server does not support '%s'\"), \"--shallow-since\");\n \tif (server_supports(\"deepen-not\")) {\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-not\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"deepen-not\");\n \t\tdeepen_not_ok = 1;\n \t} else if (args->deepen_not)\n-\t\tdie(_(\"Server does not support --shallow-exclude\"));\n+\t\tdie(_(\"Server does not support '%s'\"), \"--shallow-exclude\");\n \tif (server_supports(\"deepen-relative\"))\n-\t\tprint_verbose(args, _(\"Server supports %s\"), \"deepen-relative\");\n+\t\tprint_verbose(args, _(\"Server supports '%s'\"), \"deepen-relative\");\n \telse if (args->deepen_relative)\n-\t\tdie(_(\"Server does not support --deepen\"));\n+\t\tdie(_(\"Server does not support '%s'\"), \"--deepen\");\n \tif (!server_supports_hash(the_hash_algo->name, NULL))\n \t\tdie(_(\"Server does not support this repository's object format\"));\n \n-- \ngitgitgadget\n\n"},{"id":"452961","messageId":"03022a2fcd14bad453925c616d86bc2f69926456.1648915853.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.v2.git.1648915853.gitgitgadget@gmail.com","subject":"[PATCH v2 2/6] sequencer: factor GIT_AUTHOR_* from message strings","fromName":"Bagas Sanjaya via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-04-02T16:10:49Z","receivedAt":"2022-04-02T16:11:57Z","isPatch":true,"sender":{"key":"bagasdotme@gmail.com","avatar":"https://avatars.githubusercontent.com/u/40219486?v=4"},"body":"From: Bagas Sanjaya <bagasdotme@gmail.com>\n\nFactor messages containing GIT_AUTHOR_* variable.\n\nSigned-off-by: Bagas Sanjaya <bagasdotme@gmail.com>\n---\n sequencer.c | 12 ++++++------\n 1 file changed, 6 insertions(+), 6 deletions(-)\n\ndiff --git a/sequencer.c b/sequencer.c\nindex 84eed9e96bc..647f5efa656 100644\n--- a/sequencer.c\n+++ b/sequencer.c\n@@ -848,17 +848,17 @@ int read_author_script(const char *path, char **name, char **email, char **date,\n \tfor (i = 0; i < kv.nr; i++) {\n \t\tif (!strcmp(kv.items[i].string, \"GIT_AUTHOR_NAME\")) {\n \t\t\tif (name_i != -2)\n-\t\t\t\tname_i = error(_(\"'GIT_AUTHOR_NAME' already given\"));\n+\t\t\t\tname_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_NAME\");\n \t\t\telse\n \t\t\t\tname_i = i;\n \t\t} else if (!strcmp(kv.items[i].string, \"GIT_AUTHOR_EMAIL\")) {\n \t\t\tif (email_i != -2)\n-\t\t\t\temail_i = error(_(\"'GIT_AUTHOR_EMAIL' already given\"));\n+\t\t\t\temail_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_EMAIL\");\n \t\t\telse\n \t\t\t\temail_i = i;\n \t\t} else if (!strcmp(kv.items[i].string, \"GIT_AUTHOR_DATE\")) {\n \t\t\tif (date_i != -2)\n-\t\t\t\tdate_i = error(_(\"'GIT_AUTHOR_DATE' already given\"));\n+\t\t\t\tdate_i = error(_(\"'%s' already given\"), \"GIT_AUTHOR_DATE\");\n \t\t\telse\n \t\t\t\tdate_i = i;\n \t\t} else {\n@@ -867,11 +867,11 @@ int read_author_script(const char *path, char **name, char **email, char **date,\n \t\t}\n \t}\n \tif (name_i == -2)\n-\t\terror(_(\"missing 'GIT_AUTHOR_NAME'\"));\n+\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_NAME\");\n \tif (email_i == -2)\n-\t\terror(_(\"missing 'GIT_AUTHOR_EMAIL'\"));\n+\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_EMAIL\");\n \tif (date_i == -2)\n-\t\terror(_(\"missing 'GIT_AUTHOR_DATE'\"));\n+\t\terror(_(\"missing '%s'\"), \"GIT_AUTHOR_DATE\");\n \tif (date_i < 0 || email_i < 0 || date_i < 0 || err)\n \t\tgoto finish;\n \t*name = kv.items[name_i].util;\n-- \ngitgitgadget\n\n"},{"id":"452962","messageId":"1888778902aa1d0d2cf118cfb7fe4b2e407953c6.1648915853.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.v2.git.1648915853.gitgitgadget@gmail.com","subject":"[PATCH v2 5/6] i18n: factorize read-cache error messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-04-02T16:10:52Z","receivedAt":"2022-04-02T16:12:01Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n read-cache.c     | 8 ++++----\n t/t1600-index.sh | 6 +++---\n 2 files changed, 7 insertions(+), 7 deletions(-)\n\ndiff --git a/read-cache.c b/read-cache.c\nindex 1ad56d02e1d..639765e8ff1 100644\n--- a/read-cache.c\n+++ b/read-cache.c\n@@ -1735,8 +1735,8 @@ static unsigned int get_index_format_default(struct repository *r)\n \t\tif (r->settings.index_version >= 0)\n \t\t\tversion = r->settings.index_version;\n \t\tif (version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n-\t\t\twarning(_(\"index.version set, but the value is invalid.\\n\"\n-\t\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n+\t\t\twarning(_(\"'%s' set, but the value is invalid.\\n\"\n+\t\t\t\t  \"Using version %i\"), \"index.version\", INDEX_FORMAT_DEFAULT);\n \t\t\treturn INDEX_FORMAT_DEFAULT;\n \t\t}\n \t\treturn version;\n@@ -1745,8 +1745,8 @@ static unsigned int get_index_format_default(struct repository *r)\n \tversion = strtoul(envversion, &endp, 10);\n \tif (*endp ||\n \t    version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n-\t\twarning(_(\"GIT_INDEX_VERSION set, but the value is invalid.\\n\"\n-\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n+\t\twarning(_(\"'%s' set, but the value is invalid.\\n\"\n+\t\t\t  \"Using version %i\"), \"GIT_INDEX_VERSION\", INDEX_FORMAT_DEFAULT);\n \t\tversion = INDEX_FORMAT_DEFAULT;\n \t}\n \treturn version;\ndiff --git a/t/t1600-index.sh b/t/t1600-index.sh\nindex 010989f90e6..60339db529f 100755\n--- a/t/t1600-index.sh\n+++ b/t/t1600-index.sh\n@@ -19,7 +19,7 @@ test_expect_success 'bogus GIT_INDEX_VERSION issues warning' '\n \t\tgit add a 2>err &&\n \t\tsed \"s/[0-9]//\" err >actual.err &&\n \t\tsed -e \"s/ Z$/ /\" <<-\\EOF >expect.err &&\n-\t\t\twarning: GIT_INDEX_VERSION set, but the value is invalid.\n+\t\t\twarning: '\\''GIT_INDEX_VERSION'\\'' set, but the value is invalid.\n \t\t\tUsing version Z\n \t\tEOF\n \t\ttest_cmp expect.err actual.err\n@@ -34,7 +34,7 @@ test_expect_success 'out of bounds GIT_INDEX_VERSION issues warning' '\n \t\tgit add a 2>err &&\n \t\tsed \"s/[0-9]//\" err >actual.err &&\n \t\tsed -e \"s/ Z$/ /\" <<-\\EOF >expect.err &&\n-\t\t\twarning: GIT_INDEX_VERSION set, but the value is invalid.\n+\t\t\twarning: '\\''GIT_INDEX_VERSION'\\'' set, but the value is invalid.\n \t\t\tUsing version Z\n \t\tEOF\n \t\ttest_cmp expect.err actual.err\n@@ -58,7 +58,7 @@ test_expect_success 'out of bounds index.version issues warning' '\n \t\tgit add a 2>err &&\n \t\tsed \"s/[0-9]//\" err >actual.err &&\n \t\tsed -e \"s/ Z$/ /\" <<-\\EOF >expect.err &&\n-\t\t\twarning: index.version set, but the value is invalid.\n+\t\t\twarning: '\\''index.version'\\'' set, but the value is invalid.\n \t\t\tUsing version Z\n \t\tEOF\n \t\ttest_cmp expect.err actual.err\n-- \ngitgitgadget\n\n"},{"id":"452963","messageId":"6221c37145c22a79bc1598be1e82be50d61636cc.1648915853.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.v2.git.1648915853.gitgitgadget@gmail.com","subject":"[PATCH v2 4/6] i18n: factorize \"foo does not take arguments\" messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-04-02T16:10:51Z","receivedAt":"2022-04-02T16:12:01Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nThe messages are split into the ones for ref-filter which deal with\natoms and scalar which has an option.\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n contrib/scalar/scalar.c | 2 +-\n ref-filter.c            | 8 ++++----\n 2 files changed, 5 insertions(+), 5 deletions(-)\n\ndiff --git a/contrib/scalar/scalar.c b/contrib/scalar/scalar.c\nindex 7db2a97416e..7ef1f141366 100644\n--- a/contrib/scalar/scalar.c\n+++ b/contrib/scalar/scalar.c\n@@ -502,7 +502,7 @@ cleanup:\n static int cmd_list(int argc, const char **argv)\n {\n \tif (argc != 1)\n-\t\tdie(_(\"`scalar list` does not take arguments\"));\n+\t\tdie(_(\"the '%s' command does not take arguments\"), \"scalar list\");\n \n \tif (run_git(\"config\", \"--global\", \"--get-all\", \"scalar.repo\", NULL) < 0)\n \t\treturn -1;\ndiff --git a/ref-filter.c b/ref-filter.c\nindex 7838bd22b8d..8497f9e25d8 100644\n--- a/ref-filter.c\n+++ b/ref-filter.c\n@@ -317,7 +317,7 @@ static int objecttype_atom_parser(struct ref_format *format, struct used_atom *a\n \t\t\t\t  const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(objecttype) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(objecttype)\");\n \tif (*atom->name == '*')\n \t\toi_deref.info.typep = &oi_deref.type;\n \telse\n@@ -349,7 +349,7 @@ static int deltabase_atom_parser(struct ref_format *format, struct used_atom *at\n \t\t\t\t const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(deltabase) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(deltabase)\");\n \tif (*atom->name == '*')\n \t\toi_deref.info.delta_base_oid = &oi_deref.delta_base_oid;\n \telse\n@@ -361,7 +361,7 @@ static int body_atom_parser(struct ref_format *format, struct used_atom *atom,\n \t\t\t    const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(body) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(body)\");\n \tatom->u.contents.option = C_BODY_DEP;\n \treturn 0;\n }\n@@ -565,7 +565,7 @@ static int rest_atom_parser(struct ref_format *format, struct used_atom *atom,\n \t\t\t    const char *arg, struct strbuf *err)\n {\n \tif (arg)\n-\t\treturn strbuf_addf_ret(err, -1, _(\"%%(rest) does not take arguments\"));\n+\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(rest)\");\n \tformat->use_rest = 1;\n \treturn 0;\n }\n-- \ngitgitgadget\n\n"},{"id":"452964","messageId":"febe64a8a069dd81523c33a93cfea9553e40c283.1648915853.git.gitgitgadget@gmail.com","threadId":"57588","inReplyTo":"pull.1181.v2.git.1648915853.gitgitgadget@gmail.com","subject":"[PATCH v2 6/6] i18n: factorize \"bad argument\" messages","fromName":"Jean-Noël Avila via GitGitGadget","fromEmail":"gitgitgadget@gmail.com","sentAt":"2022-04-02T16:10:53Z","receivedAt":"2022-04-02T16:12:03Z","isPatch":true,"sender":{"key":"jn.avila@free.fr","avatar":"https://avatars.githubusercontent.com/u/156172?v=4"},"body":"From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n\nWe also quote the placeholders as they replace constant strings.\n\nSigned-off-by: Jean-Noël Avila <jn.avila@free.fr>\n---\n builtin/bisect--helper.c | 2 +-\n builtin/commit-graph.c   | 2 +-\n builtin/config.c         | 2 +-\n builtin/env--helper.c    | 2 +-\n builtin/gc.c             | 4 ++--\n diff.c                   | 4 ++--\n grep.c                   | 2 +-\n send-pack.c              | 2 +-\n submodule-config.c       | 8 ++++----\n submodule.c              | 2 +-\n t/t1300-config.sh        | 2 +-\n t/t7900-maintenance.sh   | 4 ++--\n 12 files changed, 18 insertions(+), 18 deletions(-)\n\ndiff --git a/builtin/bisect--helper.c b/builtin/bisect--helper.c\nindex 8b2b259ff0d..3ed8a5f40b6 100644\n--- a/builtin/bisect--helper.c\n+++ b/builtin/bisect--helper.c\n@@ -268,7 +268,7 @@ static int bisect_write(const char *state, const char *rev,\n \t} else if (one_of(state, terms->term_good, \"skip\", NULL)) {\n \t\tstrbuf_addf(&tag, \"refs/bisect/%s-%s\", state, rev);\n \t} else {\n-\t\tres = error(_(\"Bad bisect_write argument: %s\"), state);\n+\t\tres = error(_(\"bad '%s' argument: '%s'\"), \"bisect_write\", state);\n \t\tgoto finish;\n \t}\n \ndiff --git a/builtin/commit-graph.c b/builtin/commit-graph.c\nindex 51c4040ea6c..913478bb029 100644\n--- a/builtin/commit-graph.c\n+++ b/builtin/commit-graph.c\n@@ -134,7 +134,7 @@ static int write_option_parse_split(const struct option *opt, const char *arg,\n \telse if (!strcmp(arg, \"replace\"))\n \t\t*flags = COMMIT_GRAPH_SPLIT_REPLACE;\n \telse\n-\t\tdie(_(\"unrecognized --split argument, %s\"), arg);\n+\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--split\", arg);\n \n \treturn 0;\n }\ndiff --git a/builtin/config.c b/builtin/config.c\nindex e7b88a9c08d..2ac36e4f641 100644\n--- a/builtin/config.c\n+++ b/builtin/config.c\n@@ -106,7 +106,7 @@ static int option_parse_type(const struct option *opt, const char *arg,\n \t\telse if (!strcmp(arg, \"color\"))\n \t\t\tnew_type = TYPE_COLOR;\n \t\telse\n-\t\t\tdie(_(\"unrecognized --type argument, %s\"), arg);\n+\t\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--type\", arg);\n \t}\n \n \tto_type = opt->value;\ndiff --git a/builtin/env--helper.c b/builtin/env--helper.c\nindex 27349098b07..49790dfa2fb 100644\n--- a/builtin/env--helper.c\n+++ b/builtin/env--helper.c\n@@ -24,7 +24,7 @@ static int option_parse_type(const struct option *opt, const char *arg,\n \telse if (!strcmp(arg, \"ulong\"))\n \t\t*cmdmode = ENV_HELPER_TYPE_ULONG;\n \telse\n-\t\tdie(_(\"unrecognized --type argument, %s\"), arg);\n+\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--type\", arg);\n \n \treturn 0;\n }\ndiff --git a/builtin/gc.c b/builtin/gc.c\nindex c062d7bceeb..cca6987fcbd 100644\n--- a/builtin/gc.c\n+++ b/builtin/gc.c\n@@ -750,7 +750,7 @@ static int maintenance_opt_schedule(const struct option *opt, const char *arg,\n \t*priority = parse_schedule(arg);\n \n \tif (!*priority)\n-\t\tdie(_(\"unrecognized --schedule argument '%s'\"), arg);\n+\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--schedule\", arg);\n \n \treturn 0;\n }\n@@ -2393,7 +2393,7 @@ static int maintenance_opt_scheduler(const struct option *opt, const char *arg,\n \n \t*scheduler = parse_scheduler(arg);\n \tif (*scheduler == SCHEDULER_INVALID)\n-\t\treturn error(_(\"unrecognized --scheduler argument '%s'\"), arg);\n+\t\treturn error(_(\"bad '%s' argument: '%s'\"), \"--scheduler\", arg);\n \treturn 0;\n }\n \ndiff --git a/diff.c b/diff.c\nindex 6b22946cd0e..c74f6e7b920 100644\n--- a/diff.c\n+++ b/diff.c\n@@ -5010,7 +5010,7 @@ static int diff_opt_color_moved(const struct option *opt,\n \t} else {\n \t\tint cm = parse_color_moved(arg);\n \t\tif (cm < 0)\n-\t\t\treturn error(_(\"bad --color-moved argument: %s\"), arg);\n+\t\t\treturn error(_(\"bad '%s' argument: '%s'\"), \"--color-moved\", arg);\n \t\toptions->color_moved = cm;\n \t}\n \treturn 0;\n@@ -5334,7 +5334,7 @@ static int diff_opt_word_diff(const struct option *opt,\n \t\telse if (!strcmp(arg, \"none\"))\n \t\t\toptions->word_diff = DIFF_WORDS_NONE;\n \t\telse\n-\t\t\treturn error(_(\"bad --word-diff argument: %s\"), arg);\n+\t\t\treturn error(_(\"bad '%s' argument: '%s'\"), \"--word-diff\", arg);\n \t} else {\n \t\tif (options->word_diff == DIFF_WORDS_NONE)\n \t\t\toptions->word_diff = DIFF_WORDS_PLAIN;\ndiff --git a/grep.c b/grep.c\nindex 82eb7da1022..6aabfc58bb3 100644\n--- a/grep.c\n+++ b/grep.c\n@@ -43,7 +43,7 @@ static int parse_pattern_type_arg(const char *opt, const char *arg)\n \t\treturn GREP_PATTERN_TYPE_FIXED;\n \telse if (!strcmp(arg, \"perl\"))\n \t\treturn GREP_PATTERN_TYPE_PCRE;\n-\tdie(\"bad %s argument: %s\", opt, arg);\n+\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n }\n \n define_list_config_array_extra(color_grep_slots, {\"match\"});\ndiff --git a/send-pack.c b/send-pack.c\nindex bc0fcdbb000..68205e8a913 100644\n--- a/send-pack.c\n+++ b/send-pack.c\n@@ -36,7 +36,7 @@ int option_parse_push_signed(const struct option *opt,\n \t\t*(int *)(opt->value) = SEND_PACK_PUSH_CERT_IF_ASKED;\n \t\treturn 0;\n \t}\n-\tdie(\"bad %s argument: %s\", opt->long_name, arg);\n+\tdie(\"bad '%s' argument: '%s'\", opt->long_name, arg);\n }\n \n static void feed_object(const struct object_id *oid, FILE *fh, int negative)\ndiff --git a/submodule-config.c b/submodule-config.c\nindex 29668b0620d..76264c6e6b6 100644\n--- a/submodule-config.c\n+++ b/submodule-config.c\n@@ -292,7 +292,7 @@ static int parse_fetch_recurse(const char *opt, const char *arg,\n \t\t * git-completion.bash when you add new options.\n \t\t */\n \t\tif (die_on_error)\n-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n+\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n \t\telse\n \t\t\treturn RECURSE_SUBMODULES_ERROR;\n \t}\n@@ -342,7 +342,7 @@ static int parse_update_recurse(const char *opt, const char *arg,\n \t\treturn RECURSE_SUBMODULES_OFF;\n \tdefault:\n \t\tif (die_on_error)\n-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n+\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n \t\treturn RECURSE_SUBMODULES_ERROR;\n \t}\n }\n@@ -359,7 +359,7 @@ static int parse_push_recurse(const char *opt, const char *arg,\n \tcase 1:\n \t\t/* There's no simple \"on\" value when pushing */\n \t\tif (die_on_error)\n-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n+\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n \t\telse\n \t\t\treturn RECURSE_SUBMODULES_ERROR;\n \tcase 0:\n@@ -376,7 +376,7 @@ static int parse_push_recurse(const char *opt, const char *arg,\n \t\t * git-completion.bash when you add new modes.\n \t\t */\n \t\telse if (die_on_error)\n-\t\t\tdie(\"bad %s argument: %s\", opt, arg);\n+\t\t\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n \t\telse\n \t\t\treturn RECURSE_SUBMODULES_ERROR;\n \t}\ndiff --git a/submodule.c b/submodule.c\nindex 5ace18a7d94..c08477762d9 100644\n--- a/submodule.c\n+++ b/submodule.c\n@@ -470,7 +470,7 @@ void handle_ignore_submodules_arg(struct diff_options *diffopt,\n \telse if (!strcmp(arg, \"dirty\"))\n \t\tdiffopt->flags.ignore_dirty_submodules = 1;\n \telse if (strcmp(arg, \"none\"))\n-\t\tdie(_(\"bad --ignore-submodules argument: %s\"), arg);\n+\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--ignore-submodules\", arg);\n \t/*\n \t * Please update _git_status() in git-completion.bash when you\n \t * add new options\ndiff --git a/t/t1300-config.sh b/t/t1300-config.sh\nindex 7dd9b325d90..69cb3af0885 100755\n--- a/t/t1300-config.sh\n+++ b/t/t1300-config.sh\n@@ -2215,7 +2215,7 @@ test_expect_success 'unset type specifiers may be reset to conflicting ones' '\n \n test_expect_success '--type rejects unknown specifiers' '\n \ttest_must_fail git config --type=nonsense section.foo 2>error &&\n-\ttest_i18ngrep \"unrecognized --type argument\" error\n+\ttest_i18ngrep \"bad '\\''--type'\\'' argument\" error\n '\n \n test_expect_success '--replace-all does not invent newlines' '\ndiff --git a/t/t7900-maintenance.sh b/t/t7900-maintenance.sh\nindex 74aa6384755..c5e62e95533 100755\n--- a/t/t7900-maintenance.sh\n+++ b/t/t7900-maintenance.sh\n@@ -401,7 +401,7 @@ test_expect_success '--auto and --schedule incompatible' '\n \n test_expect_success 'invalid --schedule value' '\n \ttest_must_fail git maintenance run --schedule=annually 2>err &&\n-\ttest_i18ngrep \"unrecognized --schedule\" err\n+\ttest_i18ngrep \"bad '\\''--schedule'\\''\" err\n '\n \n test_expect_success '--schedule inheritance weekly -> daily -> hourly' '\n@@ -529,7 +529,7 @@ test_expect_success !MINGW 'register and unregister with regex metacharacters' '\n \n test_expect_success 'start --scheduler=<scheduler>' '\n \ttest_expect_code 129 git maintenance start --scheduler=foo 2>err &&\n-\ttest_i18ngrep \"unrecognized --scheduler argument\" err &&\n+\ttest_i18ngrep \"bad '\\''--scheduler'\\'' argument\" err &&\n \n \ttest_expect_code 129 git maintenance start --no-scheduler 2>err &&\n \ttest_i18ngrep \"unknown option\" err &&\n-- \ngitgitgadget\n"},{"id":"452971","messageId":"4b46ba19-3a39-7317-42fb-4fd4bba09b36@gmail.com","threadId":"57588","inReplyTo":"4bba3e1f6cb9cdc35b0dc8da440e38de256b4d2b.1648915853.git.gitgitgadget@gmail.com","subject":"Re: [PATCH v2 1/6] i18n: factorize generic failure messages","fromName":"Bagas Sanjaya","fromEmail":"bagasdotme@gmail.com","sentAt":"2022-04-03T05:56:55Z","receivedAt":"2022-04-03T05:57:04Z","isPatch":true,"sender":{"key":"bagasdotme@gmail.com","avatar":"https://avatars.githubusercontent.com/u/40219486?v=4"},"body":"On 02/04/22 23.10, Jean-Noël Avila via GitGitGadget wrote:\n> From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n> \n> In these message the command or the function that failed should not be\n> translated. So it is simpler to just remove these parts from the\n> message.\n> \n> Signed-off-by: Jean-Noël Avila <jn.avila@free.fr>\n> ---\n>   add-patch.c                     | 4 ++--\n>   builtin/am.c                    | 2 +-\n>   builtin/gc.c                    | 4 ++--\n>   builtin/merge.c                 | 6 +++---\n>   builtin/revert.c                | 4 ++--\n>   fetch-pack.c                    | 2 +-\n>   remote-curl.c                   | 2 +-\n>   setup.c                         | 4 ++--\n>   t/t3510-cherry-pick-sequence.sh | 8 ++++----\n>   t/t6436-merge-overwrite.sh      | 2 +-\n>   10 files changed, 19 insertions(+), 19 deletions(-)\n> \n> diff --git a/add-patch.c b/add-patch.c\n> index 55d719f7845..8c9e81ec78e 100644\n> --- a/add-patch.c\n> +++ b/add-patch.c\n> @@ -1181,7 +1181,7 @@ static int run_apply_check(struct add_p_state *s,\n>   \t\t\t    \"apply\", \"--check\", NULL);\n>   \tstrvec_pushv(&cp.args, s->mode->apply_check_args);\n>   \tif (pipe_command(&cp, s->buf.buf, s->buf.len, NULL, 0, NULL, 0))\n> -\t\treturn error(_(\"'git apply --cached' failed\"));\n> +\t\treturn error(_(\"the command '%s' failed\"), \"git apply --cached\");\n>   \n>   \treturn 0;\n>   }\n> @@ -1683,7 +1683,7 @@ soft_increment:\n>   \t\t\tstrvec_pushv(&cp.args, s->mode->apply_args);\n>   \t\t\tif (pipe_command(&cp, s->buf.buf, s->buf.len,\n>   \t\t\t\t\t NULL, 0, NULL, 0))\n> -\t\t\t\terror(_(\"'git apply' failed\"));\n> +\t\t\t\terror(_(\"the command '%s' failed\"), \"git apply\");\n>   \t\t}\n>   \t\tif (repo_read_index(s->s.r) >= 0)\n>   \t\t\trepo_refresh_and_write_index(s->s.r, REFRESH_QUIET, 0,\n> diff --git a/builtin/am.c b/builtin/am.c\n> index 0f4111bafa0..a0a57049510 100644\n> --- a/builtin/am.c\n> +++ b/builtin/am.c\n> @@ -586,7 +586,7 @@ static int is_mail(FILE *fp)\n>   \tint ret = 1;\n>   \n>   \tif (fseek(fp, 0L, SEEK_SET))\n> -\t\tdie_errno(_(\"fseek failed\"));\n> +\t\tdie_errno(_(\"the function '%s' failed\"), \"fseek\");\n>   \n>   \tif (regcomp(&regex, header_regex, REG_NOSUB | REG_EXTENDED))\n>   \t\tdie(\"invalid pattern: %s\", header_regex);\n> diff --git a/builtin/gc.c b/builtin/gc.c\n> index ffaf0daf5d9..c062d7bceeb 100644\n> --- a/builtin/gc.c\n> +++ b/builtin/gc.c\n> @@ -1104,7 +1104,7 @@ static int multi_pack_index_expire(struct maintenance_run_opts *opts)\n>   \t\tstrvec_push(&child.args, \"--no-progress\");\n>   \n>   \tif (run_command(&child))\n> -\t\treturn error(_(\"'git multi-pack-index expire' failed\"));\n> +\t\treturn error(_(\"the command '%s' failed\"), \"git multi-pack-index expire\");\n>   \n>   \treturn 0;\n>   }\n> @@ -1163,7 +1163,7 @@ static int multi_pack_index_repack(struct maintenance_run_opts *opts)\n>   \t\t\t\t  (uintmax_t)get_auto_pack_size());\n>   \n>   \tif (run_command(&child))\n> -\t\treturn error(_(\"'git multi-pack-index repack' failed\"));\n> +\t\treturn error(_(\"the command '%s' failed\"), \"git multi-pack-index repack\");\n>   \n>   \treturn 0;\n>   }\n> diff --git a/builtin/merge.c b/builtin/merge.c\n> index f178f5a3ee1..78468ff43a4 100644\n> --- a/builtin/merge.c\n> +++ b/builtin/merge.c\n> @@ -325,7 +325,7 @@ static int save_state(struct object_id *stash)\n>   \tclose(cp.out);\n>   \n>   \tif (finish_command(&cp) || len < 0)\n> -\t\tdie(_(\"stash failed\"));\n> +\t\tdie(_(\"the command '%s' failed\"), \"stash\");\n>   \telse if (!len)\t\t/* no changes */\n>   \t\tgoto out;\n>   \tstrbuf_setlen(&buffer, buffer.len-1);\n> @@ -352,7 +352,7 @@ static void read_empty(const struct object_id *oid, int verbose)\n>   \targs[i] = NULL;\n>   \n>   \tif (run_command_v_opt(args, RUN_GIT_CMD))\n> -\t\tdie(_(\"read-tree failed\"));\n> +\t\tdie(_(\"the command '%s' failed\"), \"read-tree\");\n>   }\n>   \n>   static void reset_hard(const struct object_id *oid, int verbose)\n> @@ -369,7 +369,7 @@ static void reset_hard(const struct object_id *oid, int verbose)\n>   \targs[i] = NULL;\n>   \n>   \tif (run_command_v_opt(args, RUN_GIT_CMD))\n> -\t\tdie(_(\"read-tree failed\"));\n> +\t\tdie(_(\"the command '%s' failed\"), \"read-tree\");\n>   }\n>   \n>   static void restore_state(const struct object_id *head,\n> diff --git a/builtin/revert.c b/builtin/revert.c\n> index 51776abea63..d293036e790 100644\n> --- a/builtin/revert.c\n> +++ b/builtin/revert.c\n> @@ -238,7 +238,7 @@ int cmd_revert(int argc, const char **argv, const char *prefix)\n>   \tsequencer_init_config(&opts);\n>   \tres = run_sequencer(argc, argv, &opts);\n>   \tif (res < 0)\n> -\t\tdie(_(\"revert failed\"));\n> +\t\tdie(_(\"the command '%s' failed\"), \"revert\");\n>   \treturn res;\n>   }\n>   \n> @@ -251,6 +251,6 @@ int cmd_cherry_pick(int argc, const char **argv, const char *prefix)\n>   \tsequencer_init_config(&opts);\n>   \tres = run_sequencer(argc, argv, &opts);\n>   \tif (res < 0)\n> -\t\tdie(_(\"cherry-pick failed\"));\n> +\t\tdie(_(\"the command '%s' failed\"), \"cherry-pick\");\n>   \treturn res;\n>   }\n> diff --git a/fetch-pack.c b/fetch-pack.c\n> index 87657907e78..2e6795cd439 100644\n> --- a/fetch-pack.c\n> +++ b/fetch-pack.c\n> @@ -989,7 +989,7 @@ static int get_pack(struct fetch_pack_args *args,\n>   \t\t\targs->check_self_contained_and_connected &&\n>   \t\t\tret == 0;\n>   \telse\n> -\t\tdie(_(\"%s failed\"), cmd_name);\n> +\t\tdie(_(\"the command '%s' failed\"), cmd_name);\n>   \tif (use_sideband && finish_async(&demux))\n>   \t\tdie(_(\"error in sideband demultiplexer\"));\n>   \n> diff --git a/remote-curl.c b/remote-curl.c\n> index ff44f41011e..8393f56652b 100644\n> --- a/remote-curl.c\n> +++ b/remote-curl.c\n> @@ -1287,7 +1287,7 @@ static int push_dav(int nr_spec, const char **specs)\n>   \t\tstrvec_push(&child.args, specs[i]);\n>   \n>   \tif (run_command(&child))\n> -\t\tdie(_(\"git-http-push failed\"));\n> +\t\tdie(_(\"the command '%s' failed\"), \"git-http-push\");\n>   \treturn 0;\n>   }\n>   \n> diff --git a/setup.c b/setup.c\n> index 04ce33cdcd4..30a4b81257d 100644\n> --- a/setup.c\n> +++ b/setup.c\n> @@ -1506,12 +1506,12 @@ int daemonize(void)\n>   \t\tcase 0:\n>   \t\t\tbreak;\n>   \t\tcase -1:\n> -\t\t\tdie_errno(_(\"fork failed\"));\n> +\t\t\tdie_errno(_(\"the function '%s' failed\"), \"fork\");\n>   \t\tdefault:\n>   \t\t\texit(0);\n>   \t}\n>   \tif (setsid() == -1)\n> -\t\tdie_errno(_(\"setsid failed\"));\n> +\t\tdie_errno(_(\"the function '%s' failed\"), \"setsid\");\n>   \tclose(0);\n>   \tclose(1);\n>   \tclose(2);\n\nWhy not simply \"'%s' failed\"?\n\n-- \nAn old man doll... just what I always wanted! - Clara\n"},{"id":"452989","messageId":"220403.86wng6kzby.gmgdl@evledraar.gmail.com","threadId":"57588","inReplyTo":"4b46ba19-3a39-7317-42fb-4fd4bba09b36@gmail.com","subject":"Re: [PATCH v2 1/6] i18n: factorize generic failure messages","fromName":"Ævar Arnfjörð Bjarmason","fromEmail":"avarab@gmail.com","sentAt":"2022-04-03T14:34:31Z","receivedAt":"2022-04-03T14:37:30Z","isPatch":true,"sender":{"key":"avarab@gmail.com","avatar":"https://avatars.githubusercontent.com/u/45301?v=4"},"body":"\nOn Sun, Apr 03 2022, Bagas Sanjaya wrote:\n\n> On 02/04/22 23.10, Jean-Noël Avila via GitGitGadget wrote:\n> [...]\n>> index 04ce33cdcd4..30a4b81257d 100644\n>> --- a/setup.c\n>> +++ b/setup.c\n>> @@ -1506,12 +1506,12 @@ int daemonize(void)\n>>   \t\tcase 0:\n>>   \t\t\tbreak;\n>>   \t\tcase -1:\n>> -\t\t\tdie_errno(_(\"fork failed\"));\n>> +\t\t\tdie_errno(_(\"the function '%s' failed\"), \"fork\");\n>>   \t\tdefault:\n>>   \t\t\texit(0);\n>>   \t}\n>>   \tif (setsid() == -1)\n>> -\t\tdie_errno(_(\"setsid failed\"));\n>> +\t\tdie_errno(_(\"the function '%s' failed\"), \"setsid\");\n>>   \tclose(0);\n>>   \tclose(1);\n>>   \tclose(2);\n>\n> Why not simply \"'%s' failed\"?\n\nI think saying what failed is helpful in any case, a user who knows\nnothing about *nix APIs might be quite perplexed at their source control\ntelling them their fork failed, why not the spoon? :)\n\nSo including more context helps.\n\nBut also because there's languages where adjectives like \"failed\" are\ndifferent depending on the grammatical gender of the subject.\n\nSo even if the original and translation would be needlessly terse in any\ncase, the message would also become imppossible to translate in a\ngramatically correct way.\n"},{"id":"452991","messageId":"220403.86sfqukz67.gmgdl@evledraar.gmail.com","threadId":"57588","inReplyTo":"6221c37145c22a79bc1598be1e82be50d61636cc.1648915853.git.gitgitgadget@gmail.com","subject":"Re: [PATCH v2 4/6] i18n: factorize \"foo does not take arguments\" messages","fromName":"Ævar Arnfjörð Bjarmason","fromEmail":"avarab@gmail.com","sentAt":"2022-04-03T14:39:43Z","receivedAt":"2022-04-03T14:40:54Z","isPatch":true,"sender":{"key":"avarab@gmail.com","avatar":"https://avatars.githubusercontent.com/u/45301?v=4"},"body":"\nOn Sat, Apr 02 2022, Jean-Noël Avila via GitGitGadget wrote:\n\n> From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n>\n> The messages are split into the ones for ref-filter which deal with\n> atoms and scalar which has an option.\n\nI see the git-for-each-ref manpage doesn't really refer to these\nconsistently, but I tihnk s/atom/format/g or s/atom/name/g would be lot\nmore obvious, especially in the context of how these are already\ndiscussed in the manpage.\n\n> @@ -317,7 +317,7 @@ static int objecttype_atom_parser(struct ref_format *format, struct used_atom *a\n>  \t\t\t\t  const char *arg, struct strbuf *err)\n>  {\n>  \tif (arg)\n> -\t\treturn strbuf_addf_ret(err, -1, _(\"%%(objecttype) does not take arguments\"));\n> +\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(objecttype)\");\n>  \tif (*atom->name == '*')\n>  \t\toi_deref.info.typep = &oi_deref.type;\n>  \telse\n\n"},{"id":"452992","messageId":"220403.86o81ikywa.gmgdl@evledraar.gmail.com","threadId":"57588","inReplyTo":"febe64a8a069dd81523c33a93cfea9553e40c283.1648915853.git.gitgitgadget@gmail.com","subject":"Re: [PATCH v2 6/6] i18n: factorize \"bad argument\" messages","fromName":"Ævar Arnfjörð Bjarmason","fromEmail":"avarab@gmail.com","sentAt":"2022-04-03T14:41:39Z","receivedAt":"2022-04-03T14:46:51Z","isPatch":true,"sender":{"key":"avarab@gmail.com","avatar":"https://avatars.githubusercontent.com/u/45301?v=4"},"body":"\nOn Sat, Apr 02 2022, Jean-Noël Avila via GitGitGadget wrote:\n\n> From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n>\n> We also quote the placeholders as they replace constant strings.\n\nI don't think this change is good in that it takes two different cases\nwe cared about distinguishing before, and squashes them into one. I.e.:\n\n> +++ b/builtin/bisect--helper.c\n> @@ -268,7 +268,7 @@ static int bisect_write(const char *state, const char *rev,\n>  \t} else if (one_of(state, terms->term_good, \"skip\", NULL)) {\n>  \t\tstrbuf_addf(&tag, \"refs/bisect/%s-%s\", state, rev);\n>  \t} else {\n> -\t\tres = error(_(\"Bad bisect_write argument: %s\"), state);\n> +\t\tres = error(_(\"bad '%s' argument: '%s'\"), \"bisect_write\", state);\n>  \t\tgoto finish;\n>  \t}\n\nI think these should all say \"bad value provided for '%s' argument:\n'%s'\", or similar, or maybe the terse version is better. Just a\nsuggestion.\n\n> diff --git a/builtin/config.c b/builtin/config.c\n> index e7b88a9c08d..2ac36e4f641 100644\n> --- a/builtin/config.c\n> +++ b/builtin/config.c\n> @@ -106,7 +106,7 @@ static int option_parse_type(const struct option *opt, const char *arg,\n>  \t\telse if (!strcmp(arg, \"color\"))\n>  \t\t\tnew_type = TYPE_COLOR;\n>  \t\telse\n> -\t\t\tdie(_(\"unrecognized --type argument, %s\"), arg);\n> +\t\t\tdie(_(\"bad '%s' argument: '%s'\"), \"--type\", arg);\n>  \t}\n\nI thought some of these were introducing logic errors, because we were\nconflating unrecognized arguments with bad values, but these all seem to\nactually mean \"bad value\", not \"unknown flag\".\n\n> diff --git a/grep.c b/grep.c\n> index 82eb7da1022..6aabfc58bb3 100644\n> --- a/grep.c\n> +++ b/grep.c\n> @@ -43,7 +43,7 @@ static int parse_pattern_type_arg(const char *opt, const char *arg)\n>  \t\treturn GREP_PATTERN_TYPE_FIXED;\n>  \telse if (!strcmp(arg, \"perl\"))\n>  \t\treturn GREP_PATTERN_TYPE_PCRE;\n> -\tdie(\"bad %s argument: %s\", opt, arg);\n> +\tdie(\"bad '%s' argument: '%s'\", opt, arg);\n>  }\n\nThis and many other changes that follow have nothing to do with i18n.\n\nI think it's a worthwhile cleanup to mark some of these for _(), but\nshouldn't that come first, or at least after?\n"},{"id":"452993","messageId":"220403.86k0c6kyi5.gmgdl@evledraar.gmail.com","threadId":"57588","inReplyTo":"4bba3e1f6cb9cdc35b0dc8da440e38de256b4d2b.1648915853.git.gitgitgadget@gmail.com","subject":"Re: [PATCH v2 1/6] i18n: factorize generic failure messages","fromName":"Ævar Arnfjörð Bjarmason","fromEmail":"avarab@gmail.com","sentAt":"2022-04-03T14:47:16Z","receivedAt":"2022-04-03T14:55:21Z","isPatch":true,"sender":{"key":"avarab@gmail.com","avatar":"https://avatars.githubusercontent.com/u/45301?v=4"},"body":"\nOn Sat, Apr 02 2022, Jean-Noël Avila via GitGitGadget wrote:\n\n> From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n> [...]\n> diff --git a/add-patch.c b/add-patch.c\n> index 55d719f7845..8c9e81ec78e 100644\n> --- a/add-patch.c\n> +++ b/add-patch.c\n> @@ -1181,7 +1181,7 @@ static int run_apply_check(struct add_p_state *s,\n>  \t\t\t    \"apply\", \"--check\", NULL);\n>  \tstrvec_pushv(&cp.args, s->mode->apply_check_args);\n>  \tif (pipe_command(&cp, s->buf.buf, s->buf.len, NULL, 0, NULL, 0))\n> -\t\treturn error(_(\"'git apply --cached' failed\"));\n> +\t\treturn error(_(\"the command '%s' failed\"), \"git apply --cached\");\n>  \n>  \treturn 0;\n>  }\n> @@ -1683,7 +1683,7 @@ soft_increment:\n>  \t\t\tstrvec_pushv(&cp.args, s->mode->apply_args);\n>  \t\t\tif (pipe_command(&cp, s->buf.buf, s->buf.len,\n>  \t\t\t\t\t NULL, 0, NULL, 0))\n> -\t\t\t\terror(_(\"'git apply' failed\"));\n> +\t\t\t\terror(_(\"the command '%s' failed\"), \"git apply\");\n>  \t\t}\n>  \t\tif (repo_read_index(s->s.r) >= 0)\n>  \t\t\trepo_refresh_and_write_index(s->s.r, REFRESH_QUIET, 0,\n> diff --git a/builtin/am.c b/builtin/am.c\n> index 0f4111bafa0..a0a57049510 100644\n> --- a/builtin/am.c\n> +++ b/builtin/am.c\n> @@ -586,7 +586,7 @@ static int is_mail(FILE *fp)\n>  \tint ret = 1;\n>  \n>  \tif (fseek(fp, 0L, SEEK_SET))\n> -\t\tdie_errno(_(\"fseek failed\"));\n> +\t\tdie_errno(_(\"the function '%s' failed\"), \"fseek\");\n>  \n>  \tif (regcomp(&regex, header_regex, REG_NOSUB | REG_EXTENDED))\n>  \t\tdie(\"invalid pattern: %s\", header_regex);\n\n\nI don't think this needs to happen now, but I wonder if it would be\nworth it as a follow-up to e.g. create a gettext-common.h or something,\nwith macros like:\n\n\t#define I18N_COMMAND_FAILED N_(\"the command '%s' failed\")\n\t#define I18N_FUNCTION_FAILED_ERRNO N_(\"the library function '%s' failed\")\n\nThen:\n\n\terror(_(I18N_FUNCTION_FAILED_ERRNO), \"git apply\");\n\tdie_errno(_(I18N_FUNCTION_FAILED_ERRNO), \"fseek\");\n\nBut OTOH all the gettext tooling already takes care of that, so maybe\nit's not worth it. I.e. \"jump to definition\" would jump to the wrapper\nheader, as opposed to the actual code involved.\n\nSo having written that, probably not. Maybe the only worthwhile thing\nwould be some Levenshtein distance check in CI or something to see if\nwe're adding strings that are too similar to existing ones...\n"},{"id":"453009","messageId":"xmqqr16du7tw.fsf@gitster.g","threadId":"57588","inReplyTo":"220403.86sfqukz67.gmgdl@evledraar.gmail.com","subject":"Re: [PATCH v2 4/6] i18n: factorize \"foo does not take arguments\" messages","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2022-04-03T22:21:15Z","receivedAt":"2022-04-03T22:21:21Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Ævar Arnfjörð Bjarmason <avarab@gmail.com> writes:\n\n> On Sat, Apr 02 2022, Jean-Noël Avila via GitGitGadget wrote:\n>\n>> From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n>>\n>> The messages are split into the ones for ref-filter which deal with\n>> atoms and scalar which has an option.\n>\n> I see the git-for-each-ref manpage doesn't really refer to these\n> consistently, but I tihnk s/atom/format/g or s/atom/name/g would be lot\n> more obvious, especially in the context of how these are already\n> discussed in the manpage.\n\nI do not necessarily think so, even though \"atom\" is a word that\ndirectly faces those who wrote the code in for-each-ref.c that have\nbeen moved to ref-filter.c and not the end users.\n\nThese are only parts of a string that is given to --format=..., so\n\"format\" makes it more confusing than even the original.\n\nI can buy\n\n    '%(objectype)' in format does not take arguments\n\nthough.  If you did not find a specific word to refer to these\n\"field names\" that the documentation consistently uses, it is a way\nto clarify which '%(objecttype)' we are referring to, without having\nto commit to a single word.\n\nOr we can call them \"field names\" like the documentation calls them,\nwhich would make it into\n\n    field name '%(objecttype)' does not take arguments\n\nwhich is not too bad, but I somehow find the former (i.e. \"X in\nformat string does not take arguments\") probably the easiest to\nfollow, if you want to change the original.\n\nJust my 2 yen.\n\n>> @@ -317,7 +317,7 @@ static int objecttype_atom_parser(struct ref_format *format, struct used_atom *a\n>>  \t\t\t\t  const char *arg, struct strbuf *err)\n>>  {\n>>  \tif (arg)\n>> -\t\treturn strbuf_addf_ret(err, -1, _(\"%%(objecttype) does not take arguments\"));\n>> +\t\treturn strbuf_addf_ret(err, -1, _(\"the atom '%s' does not take arguments\"), \"%(objecttype)\");\n>>  \tif (*atom->name == '*')\n>>  \t\toi_deref.info.typep = &oi_deref.type;\n>>  \telse\n"},{"id":"453010","messageId":"xmqqlewlu7gh.fsf@gitster.g","threadId":"57588","inReplyTo":"1888778902aa1d0d2cf118cfb7fe4b2e407953c6.1648915853.git.gitgitgadget@gmail.com","subject":"Re: [PATCH v2 5/6] i18n: factorize read-cache error messages","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2022-04-03T22:29:18Z","receivedAt":"2022-04-03T22:29:26Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"\"Jean-Noël Avila via GitGitGadget\"  <gitgitgadget@gmail.com> writes:\n\n> From: =?UTF-8?q?Jean-No=C3=ABl=20Avila?= <jn.avila@free.fr>\n>\n> Signed-off-by: Jean-Noël Avila <jn.avila@free.fr>\n> ---\n>  read-cache.c     | 8 ++++----\n>  t/t1600-index.sh | 6 +++---\n>  2 files changed, 7 insertions(+), 7 deletions(-)\n>\n> diff --git a/read-cache.c b/read-cache.c\n> index 1ad56d02e1d..639765e8ff1 100644\n> --- a/read-cache.c\n> +++ b/read-cache.c\n> @@ -1735,8 +1735,8 @@ static unsigned int get_index_format_default(struct repository *r)\n>  \t\tif (r->settings.index_version >= 0)\n>  \t\t\tversion = r->settings.index_version;\n>  \t\tif (version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n> -\t\t\twarning(_(\"index.version set, but the value is invalid.\\n\"\n> -\t\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n> +\t\t\twarning(_(\"'%s' set, but the value is invalid.\\n\"\n> +\t\t\t\t  \"Using version %i\"), \"index.version\", INDEX_FORMAT_DEFAULT);\n>  \t\t\treturn INDEX_FORMAT_DEFAULT;\n\nNot the focus of this patch, which (I am guessing without the log\nmessage) is to prevent translators from touching the constant\n'index.version' by mistake, but I wonder if the message is helpful\nto users.  When I see such a warning, how would I figure out what\nto fix so that I do not have to see the same warning again?\n\nWe should somehow at least hint that we are talking about an entry\nin .git/config file (or it may be coming ~/.gitconfig by mistake, in\nwhich case telling where we see a funny version string does help the\nuser even more).\n\nAt least, telling that index.version is a configuration variable may\nnudge the user in the right direction, or is it too obvious and\neverybody who touches Git instinctively know when told that their\nqfwfq.zfzfz is set to an incorrect value, we are referring to their\nconfiguration variable?  I dunno.\n\n> @@ -1745,8 +1745,8 @@ static unsigned int get_index_format_default(struct repository *r)\n>  \tversion = strtoul(envversion, &endp, 10);\n>  \tif (*endp ||\n>  \t    version < INDEX_FORMAT_LB || INDEX_FORMAT_UB < version) {\n> -\t\twarning(_(\"GIT_INDEX_VERSION set, but the value is invalid.\\n\"\n> -\t\t\t  \"Using version %i\"), INDEX_FORMAT_DEFAULT);\n> +\t\twarning(_(\"'%s' set, but the value is invalid.\\n\"\n> +\t\t\t  \"Using version %i\"), \"GIT_INDEX_VERSION\", INDEX_FORMAT_DEFAULT);\n\nLikewise, but this is for an envirionment variable.\n\n\tThe environment variable '%s' set, but the value is invalid.\n\nmay be overkill and more importantly makes it impossible to reuse\nthe previous message, but the latter may be an improvement.\nconfiguration and environment variables may have different\ngramatical gender or something, perhaps.\n\n\n\n"}]}