diff mbox series

[v3,1/2] t7501: add tests for --include and --only

Message ID 20240110163622.51182-4-shyamthakkar001@gmail.com (mailing list archive)
State New, archived
Headers show
Series t7501: add tests for --include, --only, | expand

Commit Message

Ghanshyam Thakkar Jan. 10, 2024, 4:35 p.m. UTC
Add tests for --include (-i) and --only (-o) of commit. This includes
testing --include with and without staged changes, testing --only with
and without staged changes and testing --only and --include together.

Some tests already exist in t7501 for testing --only, however, it is
only tested in combination with --amend, --allow-empty and to-be-born
branch, and not for testing --only separately.

Similarly there are no separate tests for --include.

These tests are an addition to other similar tests in t7501,
as described above in the case of --only, therefore, they belong
in t7501-commit-basic-functionality.

Signed-off-by: Ghanshyam Thakkar <shyamthakkar001@gmail.com>
---
 t/t7501-commit-basic-functionality.sh | 43 ++++++++++++++++++++++++++-
 1 file changed, 42 insertions(+), 1 deletion(-)

Comments

Junio C Hamano Jan. 10, 2024, 6:37 p.m. UTC | #1
Ghanshyam Thakkar <shyamthakkar001@gmail.com> writes:

> -# FIXME: Test the various index usages, -i and -o, test reflog,
> +# fixme: test the various index usages, test reflog,
>  # signoff

Why the sudden downcasing?  If this were to turn it to "TODO:"
(110+) or "NEEDSWORK:" (110+) from less often used "FIXME:" (40-),
such a change might be defensible, but there is only one instance
of downcased "fixme:", so I am curious how this happened.

> +test_expect_success '--include fails with untracked files' '
> +	echo content >baz &&
> +	test_must_fail git commit --include -m "initial" baz
> +'

OK, this is because "--allow-empty" is not passed.  This should fail
without -i/-o (which should be the same as passing -o), with -i, or
with -o.

Calling this commit "initial" is highly misleading.  There are bunch
of commits already, but path "baz" has never been used.

> +test_expect_success '--include with staged changes' '
> +	echo newcontent >baz &&
> +	echo newcontent >file &&
> +	git add file &&
> +	git commit --include -m "file baz" baz  &&

I suspect that you found a bug whose behaviour we do not want to
carve into stone with this test.  When this test begins, because the
previous step failed to create the initial commit, we are creating
the root commit, without --allow-empty, with contents in the index
for path "file".  At this point

    $ git commit -m "file baz" baz

(or with "-o", which is the same thing) does error out with

    error: pathspec 'baz' did not match any file(s) known to git

because the "only" thing is to take the changes between HEAD and the
index and limit them further to those paths that match "baz", but
there is no path that matches "baz".

This command

    $ git commit -m "file baz" -i baz

should either error out the same way, or behave more or less[*] like

    $ git add baz && git commit -m "file baz"

and record changes to both "file" and "baz".

    Side note: The "more or less" is we should do "git rm baz"
               instead, if you removed the path.

But it seems that the current code simply ignores the unmatching
pathspec "baz" that is on the command line, hence recording only the
change to the contents of "file".

> +	git diff --name-only >remaining &&
> +	test_must_be_empty remaining &&
> +	git diff --name-only --staged >remaining &&
> +	test_must_be_empty remaining

These two tests to see if the working tree is clean and if the index
is clean are not wrong per-se, but is insufficient.  Judging from
the commit message you used, I think you expected this commit to
contain both changes to 'file' and 'baz'.  That needs to be also
checked with something like "git diff --name-only HEAD^ HEAD".

Now which behaviour between "error out because there is no path in
the index that matches pathspec 'baz'" and "add baz to the index and
commit that addition, together with what is already in the index" we
would want to take is probably open for discussion.  Such a discussion
may decide that the current behaviour is fine.  Until then...

> +test_expect_success '--only fails with untracked files' '
> +	echo content >newfile &&
> +	test_must_fail git commit --only -m "newfile" newfile
> +'

And this should fail the same way without "-o".  Don't we have such
a test that we can just sneak "with -o the same thing happens" test
next to it?

> +test_expect_success '--only excludes staged changes' '
> +	echo content >file &&
> +	echo content >baz &&
> +	git add baz &&
> +	git commit --only -m "file" file &&

This should behave exactly the same way without "-o".

> +	git diff --name-only >actual &&
> +	test_must_be_empty actual &&
> +	git diff --name-only --staged >actual &&
> +	test_grep "baz" actual
> +'
> +
> +test_expect_success '--include and --only do not mix' '
> +	test_when_finished "git reset --hard" &&
> +	echo new >file &&
> +	echo new >baz &&
> +	test_must_fail git commit --include --only -m "bar" bar baz

OK.  If you grep for 'cannot be used together' in t/ directory,
there are many tests that make sure how an invocation like this
should fail, i.e. with an error message that mentions incompatible
options.  Don't we want to do the same?

Thanks.
Ghanshyam Thakkar Jan. 11, 2024, 1:58 a.m. UTC | #2
On Thu Jan 11, 2024 at 12:07 AM IST, Junio C Hamano wrote:
> Ghanshyam Thakkar <shyamthakkar001@gmail.com> writes:
>
> > -# FIXME: Test the various index usages, -i and -o, test reflog,
> > +# fixme: test the various index usages, test reflog,
> >  # signoff
>
> Why the sudden downcasing?  If this were to turn it to "TODO:"
> (110+) or "NEEDSWORK:" (110+) from less often used "FIXME:" (40-),
> such a change might be defensible, but there is only one instance
> of downcased "fixme:", so I am curious how this happened.

Wow, I must have done it mistakenly. I guess everything on that line
became lowercase. But, I will fix it.

> > +test_expect_success '--include fails with untracked files' '
> > +	echo content >baz &&
> > +	test_must_fail git commit --include -m "initial" baz
> > +'
>
> OK, this is because "--allow-empty" is not passed.  This should fail
> without -i/-o (which should be the same as passing -o), with -i, or
> with -o.
>
> Calling this commit "initial" is highly misleading.  There are bunch
> of commits already, but path "baz" has never been used.

I will fix this.

> > +test_expect_success '--include with staged changes' '
> > +	echo newcontent >baz &&
> > +	echo newcontent >file &&
> > +	git add file &&
> > +	git commit --include -m "file baz" baz  &&
>
> I suspect that you found a bug whose behaviour we do not want to
> carve into stone with this test.  When this test begins, because the
> previous step failed to create the initial commit, we are creating
> the root commit, without --allow-empty, with contents in the index
> for path "file".  At this point
>
>     $ git commit -m "file baz" baz
>
> (or with "-o", which is the same thing) does error out with
>
>     error: pathspec 'baz' did not match any file(s) known to git
>
> because the "only" thing is to take the changes between HEAD and the
> index and limit them further to those paths that match "baz", but
> there is no path that matches "baz".


> This command
>
>     $ git commit -m "file baz" -i baz
>
> should either error out the same way, or behave more or less[*] like
>
>     $ git add baz && git commit -m "file baz"
>
> and record changes to both "file" and "baz".
>
>     Side note: The "more or less" is we should do "git rm baz"
>                instead, if you removed the path.
>
> But it seems that the current code simply ignores the unmatching
> pathspec "baz" that is on the command line, hence recording only the
> change to the contents of "file".
>
yeah, it seems like if there is anything staged, even if we provide
--include with untracked files, it will commit the staged files
(excluding the untracked files) and will not error out like --only.

Also in v1 there was another test before this one which added the
baz file to the index. That test was removed due to duplication and
while cleaning up the v1 for v2, due to --include not giving an error,
I did not notice that 'baz' was being left out. Will fix the tests.
Apologies for such mistakes.

> > +	git diff --name-only >remaining &&
> > +	test_must_be_empty remaining &&
> > +	git diff --name-only --staged >remaining &&
> > +	test_must_be_empty remaining
>
> These two tests to see if the working tree is clean and if the index
> is clean are not wrong per-se, but is insufficient.  Judging from
> the commit message you used, I think you expected this commit to
> contain both changes to 'file' and 'baz'.  That needs to be also
> checked with something like "git diff --name-only HEAD^ HEAD".

Yeah, the "git diff --name-only HEAD^ HEAD" is more definitive.
I will add that in v4.

> Now which behaviour between "error out because there is no path in
> the index that matches pathspec 'baz'" and "add baz to the index and
> commit that addition, together with what is already in the index" we
> would want to take is probably open for discussion.  Such a discussion
> may decide that the current behaviour is fine.  Until then...
>
> > +test_expect_success '--only fails with untracked files' '
> > +	echo content >newfile &&
> > +	test_must_fail git commit --only -m "newfile" newfile
> > +'
>
> And this should fail the same way without "-o".  Don't we have such
> a test that we can just sneak "with -o the same thing happens" test
> next to it?

Well, I could not find any test which specifically for untracked
files. I will keep looking for it and if not found, perhaps, I can add
both "-i and -o with untracked files" tests after "nothing to commit"
tests in t7501 which are similar in nature.

> > +	git commit --only -m "file" file &&
>
> This should behave exactly the same way without "-o".

That is true, however, I could not find any tests in the t75-- series
that test without -o and which provide pathspec in the commit command
also. So, should I drop -o option in this test? or add a test without
-o?

>
> > +	git diff --name-only >actual &&
> > +	test_must_be_empty actual &&
> > +	git diff --name-only --staged >actual &&
> > +	test_grep "baz" actual
> > +'
> > +
> > +test_expect_success '--include and --only do not mix' '
> > +	test_when_finished "git reset --hard" &&
> > +	echo new >file &&
> > +	echo new >baz &&
> > +	test_must_fail git commit --include --only -m "bar" bar baz
>
> OK.  If you grep for 'cannot be used together' in t/ directory,
> there are many tests that make sure how an invocation like this
> should fail, i.e. with an error message that mentions incompatible
> options.  Don't we want to do the same?

I did it like this because in t7501, there are couple of existing 
"do not mix" tests similar to this one, which only check if the command
fails. However, the approach you mentioned is obviously better, so, I
will update it in v4.

> Thanks.

Thank you for the review!
Phillip Wood Jan. 11, 2024, 4:33 p.m. UTC | #3
On 10/01/2024 16:35, Ghanshyam Thakkar wrote:

I don't have much to add to what Junio said, I've just left one comment 
below

> +test_expect_success '--only excludes staged changes' '
> +	echo content >file &&
> +	echo content >baz &&
> +	git add baz &&
> +	git commit --only -m "file" file &&
> +
> +	git diff --name-only >actual &&
> +	test_must_be_empty actual &&
> +	git diff --name-only --staged >actual &&
> +	test_grep "baz" actual

using test_grep feels a bit weak here, I think it would be better to use 
test_cmp to ensure that there are no other staged changes.

Best Wishes

Phillip
diff mbox series

Patch

diff --git a/t/t7501-commit-basic-functionality.sh b/t/t7501-commit-basic-functionality.sh
index 3d8500a52e..e005175d0b 100755
--- a/t/t7501-commit-basic-functionality.sh
+++ b/t/t7501-commit-basic-functionality.sh
@@ -3,7 +3,7 @@ 
 # Copyright (c) 2007 Kristian Høgsberg <krh@redhat.com>
 #
 
-# FIXME: Test the various index usages, -i and -o, test reflog,
+# fixme: test the various index usages, test reflog,
 # signoff
 
 test_description='git commit'
@@ -150,6 +150,47 @@  test_expect_success 'setup: commit message from file' '
 	git commit -F msg -a
 '
 
+test_expect_success '--include fails with untracked files' '
+	echo content >baz &&
+	test_must_fail git commit --include -m "initial" baz
+'
+
+test_expect_success '--include with staged changes' '
+	echo newcontent >baz &&
+	echo newcontent >file &&
+	git add file &&
+	git commit --include -m "file baz" baz  &&
+
+	git diff --name-only >remaining &&
+	test_must_be_empty remaining &&
+	git diff --name-only --staged >remaining &&
+	test_must_be_empty remaining
+'
+
+test_expect_success '--only fails with untracked files' '
+	echo content >newfile &&
+	test_must_fail git commit --only -m "newfile" newfile
+'
+
+test_expect_success '--only excludes staged changes' '
+	echo content >file &&
+	echo content >baz &&
+	git add baz &&
+	git commit --only -m "file" file &&
+
+	git diff --name-only >actual &&
+	test_must_be_empty actual &&
+	git diff --name-only --staged >actual &&
+	test_grep "baz" actual
+'
+
+test_expect_success '--include and --only do not mix' '
+	test_when_finished "git reset --hard" &&
+	echo new >file &&
+	echo new >baz &&
+	test_must_fail git commit --include --only -m "bar" bar baz
+'
+
 test_expect_success 'amend commit' '
 	cat >editor <<-\EOF &&
 	#!/bin/sh