git/list[1] front-page[2] threads[3] people[4] search[5] about
 

[PATCH] t6300: values containing ')' are broken in ref formats

From
Kousik Sanagavarapu <five231003@gmail.com>
Date
Nov 5, 2024, 18:41 UTC
Message-ID
<20241105190235.13502-1-five231003@gmail.com>

Document that values containing ')' in formats are not parsed correctly in ref-filter.

The problem here is that ref-filter, while parsing the format string, looks for the first occurence of ')' and marks it to be the end of _that_ particular atom - which is obviously wrong in cases where the format is of type

	atom:key=value
where "value" has ')' somewhere in it.

However formats having a '(' instead in "value" will parse correctly because in a general format string we also mark start of the format by making note of '%(' instead of just '('.

For example, in
	%(if:equals=somere)f)%(refname:short)...

the string that ref-filter should compare against is "somere)f", although since the parsing behavior in these cases is broken, we instead compare against "somere".

While in
	%(if:equals=somere(f)%(refname:short)...
ref-filter rightly compares against "somere(f" as expected.

As a side note it should be mentioned that values containing ')' are legit in %(refname) (and other atoms like %(upstream)). Meaning the parser wouldn't err out such values as they are legal, which is also confirmed by - say the refname coming from

	$ git branch '1)branch'
or a remote name coming from
	$ git remote add 'up)stream' 'some.url'
	$ git push --set-upstream 'up)stream' '1)branch'
since none of these fail.
Signed-off-by: Kousik Sanagavarapu <five231003@gmail.com>
---

This raises the question of what can be done to parse ')' in values of the format correctly. It seems to me like a clean solution would involve a huge refactoring involving a large portion of ref-filter but I maybe wrong.

So this patch also hopes to open up discussion on not only solving this bug but also how in general ref-filter currently parses and formats atoms and if it is the way in which we would like to do things in the future, which would in turn also be helpful in the long term goal of merging both pretty and ref-filter.

Here is also a simple script to demonstrate the difference between '(' and ')' in values in formats - as described in the commit msg -

#!/bin/sh
rm -rf /tmp/atom-test-dir &&

# create env git init /tmp/atom-test-dir 1>/tmp/init-dump 2>>/tmp/init-dump && cd /tmp/atom-test-dir && echo "smtg" >file && git add file && git commit -s -m "initial revision" >/tmp/commit-dump &&

# using "(" in refname works good
echo "test with refname as \"bran(ch\"" &&
git branch "bran(ch" &&
printf "bran(ch\n\n" >expect &&
git for-each-ref --format="%(if:equals=bran(ch)%(refname:short)%(then)%(refname:short)%(end)" refs/heads/ >actual &&
if ! diff -u expect actual; then
	echo "		actual is different from expect"
else
	echo "		actual is the same as expect"
fi
echo "" &&
# using ")" in refname will parse wrong in ref-filter code
echo "test with refname as \"bran()ch\"" &&
git branch "bran()ch" &&
printf "bran()ch\n\n\n" >expect &&
git for-each-ref --format="%(if:equals=bran()ch)%(refname:short)%(then)%(refname:short)%(end)" refs/heads/ >actual &&
if ! diff -u expect actual; then
	echo "		actual is different from expect"
else
	echo "		actual is the same as expect"
fi
 t/t6300-for-each-ref.sh | 15 +++++++++++++++
 1 file changed, 15 insertions(+)
diff --git a/t/t6300-for-each-ref.sh b/t/t6300-for-each-ref.sh
index c39d4e7e9c..ce5c607193 100755
--- a/t/t6300-for-each-ref.sh
+++ b/t/t6300-for-each-ref.sh
@@ -2141,4 +2141,19 @@ test_expect_success GPG 'show lack of signature with custom format' '
 	test_cmp expect actual
 '
 
+test_expect_failure 'format having values containing ) parse correctly' '
+	git branch "1)feat" &&
+	cat >expect <<-\EOF &&
+	refs/heads/1)feat
+	not equals
+	not equals
+	not equals
+	not equals
+	not equals
+	EOF
+	git for-each-ref --format="%(if:equals=1)feat)%(refname:short)%(then)%(refname)%(else)not equals%(end)" \
+		refs/heads/ >actual &&
+	test_cmp expect actual
+'
+
 test_done
-- 
2.47.0.230.g0cf584699a
Next: Junio C Hamano
Message 1 of 14 in “t6300: values containing ')' are broken in ref formats”
  1. t6300: values containing ')' are broken in ref formatsKousik Sanagavarapu, Nov 5, 2024
  2. Junio C HamanoNov 6, 2024
  3. Jeff KingNov 6, 2024
  4. Junio C HamanoNov 6, 2024
  5. Kousik SanagavarapuNov 6, 2024
  6. Jeff KingNov 6, 2024
  7. Kousik SanagavarapuNov 7, 2024
  8. Jeff KingNov 6, 2024
  9. Kousik SanagavarapuNov 7, 2024
  10. Junio C HamanoNov 7, 2024
  11. Kousik SanagavarapuNov 8, 2024
  12. Jeff KingNov 8, 2024
  13. Kousik SanagavarapuNov 8, 2024
  14. Kousik SanagavarapuNov 6, 2024

Read the whole thread, see it on lore, or plain text.

$ cat FOOTERMessages come from the public archive at lore.kernel.org/git, fetched every hour. The front page is chosen and written each morning by an AI editor and can be wrong; the threads themselves are the record. About and API. For agents: an MCP server at https://gitlist.dev/mcp, and any thread, story or person page as Markdown by adding .md to its URL (or sending Accept: text/markdown). Details in /llms.txt.