Re: [PATCH v3 1/1] ls-tree.c: support `--oid-only` option for "git-ls-tree"
On 2021-11-22 16:07:28+0800, Teng Long <dyroneteng@gmail.com> wrote:
Show 26 quoted lines
> Sometimes, we only want to get the objects from output of `ls-tree`
> and commands like `sed` or `cut` is usually used to intercept the
> origin output to achieve this purpose in practical.
>
> This commit supply an option names `--oid-only` to let `git ls-tree`
> only print out the OID of the object. `--oid-only` and `--name-only`
> are mutually exclusive in use.
>
> Signed-off-by: Teng Long <dyroneteng@gmail.com>
> ---
> Documentation/git-ls-tree.txt | 8 +++++--
> builtin/ls-tree.c | 27 ++++++++++++++++-------
> t/t3104-ls-tree-oid.sh | 40 +++++++++++++++++++++++++++++++++++
> 3 files changed, 65 insertions(+), 10 deletions(-)
> create mode 100755 t/t3104-ls-tree-oid.sh
>
> diff --git a/Documentation/git-ls-tree.txt b/Documentation/git-ls-tree.txt
> index db02d6d79a..bc711dc00a 100644
> --- a/Documentation/git-ls-tree.txt
> +++ b/Documentation/git-ls-tree.txt
> @@ -10,7 +10,8 @@ SYNOPSIS
> --------
> [verse]
> 'git ls-tree' [-d] [-r] [-t] [-l] [-z]
> - [--name-only] [--name-status] [--full-name] [--full-tree] [--abbrev[=<n>]]
> + [--name-only] [--name-status] [--oid-only]
Please indicate those options are incompatible (as someone else said):
[--name-only | --name-status | --oid-only]
Show 56 quoted lines
> + [--full-name] [--full-tree] [--abbrev[=<n>]]
> <tree-ish> [<path>...]
>
> DESCRIPTION
> @@ -59,7 +60,10 @@ OPTIONS
> --name-only::
> --name-status::
> List only filenames (instead of the "long" output), one per line.
> -
> + Cannot be used with `--oid-only` together.
> +--oid-only::
> + List only OIDs of the objects, one per line. Cannot be used with
> + `--name-only` or `--name-status` together.
> --abbrev[=<n>]::
> Instead of showing the full 40-byte hexadecimal object
> lines, show the shortest prefix that is at least '<n>'
> diff --git a/builtin/ls-tree.c b/builtin/ls-tree.c
> index 3a442631c7..1e4a82e669 100644
> --- a/builtin/ls-tree.c
> +++ b/builtin/ls-tree.c
> @@ -18,19 +18,26 @@ static int line_termination = '\n';
> #define LS_RECURSIVE 1
> #define LS_TREE_ONLY 2
> #define LS_SHOW_TREES 4
> -#define LS_NAME_ONLY 8
> -#define LS_SHOW_SIZE 16
> +#define LS_SHOW_SIZE 8
> static int abbrev;
> static int ls_options;
> static struct pathspec pathspec;
> static int chomp_prefix;
> static const char *ls_tree_prefix;
>
> -static const char * const ls_tree_usage[] = {
> +static const char * const ls_tree_usage[] = {
> N_("git ls-tree [<options>] <tree-ish> [<path>...]"),
> NULL
> };
>
> +enum {
> + MODE_UNSPECIFIED = 0,
> + MODE_NAME_ONLY,
> + MODE_OID_ONLY
> +};
> +
> +static int cmdmode = MODE_UNSPECIFIED;
> +
> static int show_recursive(const char *base, int baselen, const char *pathname)
> {
> int i;
> @@ -90,7 +97,12 @@ static int show_tree(const struct object_id *oid, struct strbuf *base,
> else if (ls_options & LS_TREE_ONLY)
> return 0;
>
> - if (!(ls_options & LS_NAME_ONLY)) {
> + if (cmdmode == 2) {I think it's better to use the enum name:
if (cmdmode == MODE_OID_ONLY) {Show 5 quoted lines
> + printf("%s\n", find_unique_abbrev(oid, abbrev));
> + return 0;
> + }
> +
> + if (cmdmode == 0) {Ditto:
if (cmdmode == MODE_UNSPECIFIED) {Speaking about this, where will MODE_NAME_ONLY be used?
Show 63 quoted lines
> if (ls_options & LS_SHOW_SIZE) {
> char size_text[24];
> if (!strcmp(type, blob_type)) {
> @@ -135,10 +147,9 @@ int cmd_ls_tree(int argc, const char **argv, const char *prefix)
> N_("terminate entries with NUL byte"), 0),
> OPT_BIT('l', "long", &ls_options, N_("include object size"),
> LS_SHOW_SIZE),
> - OPT_BIT(0, "name-only", &ls_options, N_("list only filenames"),
> - LS_NAME_ONLY),
> - OPT_BIT(0, "name-status", &ls_options, N_("list only filenames"),
> - LS_NAME_ONLY),
> + OPT_CMDMODE('n', "name-only", &cmdmode, N_("list only filenames"), MODE_NAME_ONLY),
> + OPT_CMDMODE('s', "name-status", &cmdmode, N_("list only filenames"), MODE_NAME_ONLY),
> + OPT_CMDMODE('o', "oid-only", &cmdmode, N_("list only oids"), MODE_OID_ONLY),
> OPT_SET_INT(0, "full-name", &chomp_prefix,
> N_("use full path names"), 0),
> OPT_BOOL(0, "full-tree", &full_tree,
> diff --git a/t/t3104-ls-tree-oid.sh b/t/t3104-ls-tree-oid.sh
> new file mode 100755
> index 0000000000..4c02cdd3c3
> --- /dev/null
> +++ b/t/t3104-ls-tree-oid.sh
> @@ -0,0 +1,40 @@
> +#!/bin/sh
> +
> +test_description='git ls-tree oids handling.'
> +
> +. ./test-lib.sh
> +
> +test_expect_success 'setup' '
> + echo 111 >1.txt &&
> + echo 222 >2.txt &&
> + mkdir -p path0/a/b/c &&
> + echo 333 >path0/a/b/c/3.txt &&
> + find *.txt path* \( -type f -o -type l \) -print |
> + xargs git update-index --add &&
> + tree=$(git write-tree) &&
> + echo $tree
> +'
> +
> +test_expect_success 'usage: --oid-only' '
> + git ls-tree --oid-only $tree >current &&
> + git ls-tree $tree | awk "{print \$3}" >expected &&
> + test_cmp current expected
> +'
> +
> +test_expect_success 'usage: --oid-only with -r' '
> + git ls-tree --oid-only -r $tree >current &&
> + git ls-tree -r $tree | awk "{print \$3}" >expected &&
> + test_cmp current expected
> +'
> +
> +test_expect_success 'usage: --oid-only with --abbrev' '
> + git ls-tree --oid-only --abbrev=6 $tree >current &&
> + git ls-tree --abbrev=6 $tree | awk "{print \$3}" > expected &&
> + test_cmp current expected
> +'
> +
> +test_expect_failure 'usage: incompatible options: --name-only with --oid-only' '
> + test_incompatible_usage git ls-tree --oid-only --name-only
> +'
> +
> +test_doneIt seems like you haven't updated the test code from v2
--
Danh