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

Re: What's cooking in git.git (Mar 2009, #01; Tue, 03)

From
Christian Couder <chriscool@tuxfamily.org>
Date
Mar 5, 2009, 06:43 UTC
Message-ID
<200903050743.49858.chriscool@tuxfamily.org>
In-Reply-To
<7vprgzdlom.fsf@gitster.siamese.dyndns.org>
Le mardi 3 mars 2009, Junio C Hamano a écrit :
Show 17 quoted lines
> * cc/replace (Mon Feb 2 06:13:06 2009 +0100) 11 commits
>  - builtin-replace: use "usage_msg_opt" to give better error messages
>  - parse-options: add new function "usage_msg_opt"
>  - builtin-replace: teach "git replace" to actually replace
>  - Add new "git replace" command
>  - environment: add global variable to disable replacement
>  - mktag: call "check_sha1_signature" with the replacement sha1
>  - replace_object: add a test case
>  - object: call "check_sha1_signature" with the replacement sha1
>  - sha1_file: add a "read_sha1_file_repl" function
>  - replace_object: add mechanism to replace objects found in
>    "refs/replace/"
>  - refs: add a "for_each_replace_ref" function
>
> I think the code is much cleaner than the first round, but I am not
> convinced it is doing the right thing in the connectivity traverser.
> Independent review sorely needed.

I haven't look much at connectivity traverser lately but I think I should first describe some of the issues in other areas.

There are command to reproduce all the steps. (You have to use pu.)

# # Let's start by creating a good environment to test a few things: #

$ cd git/t
$ sed -e 's/test_done/exit 1\ntest_done/' t6050-replace.sh > tt.sh
$ ./tt.sh
*   ok 1: set up buggy branch
*   ok 2: replace the author
*   ok 3: tag replaced commit
*   ok 4: "git fsck" works
*   ok 5: repack, clone and fetch work
*   ok 6: "git replace" listing and deleting
*   ok 7: "git replace" replacing
FATAL: Unexpected exit with code 1
$ cd trash\ directory.tt

# # Now let's see what happens when we replace an object: #

$ git rev-parse HEAD ffccc9d552388844dbe94a361c07e7cb1731e12f $ git cat-file commit ffccc tree 5c37393794868bc8e708cccd7c9d9aaa7a5e53cb parent 14ac020163ea60a9d683ce68e36c946f31ecc856 author A U Thor <author@example.com> 1112912353 -0700 committer C O Mitter <committer@example.com> 1112912353 -0700

hello: again 3 more lines $ git ls-tree 5c37 100644 blob 47ea9c3df4682ae7d2c9139fa9ac6dbc9b6eb43d hello $ git cat-file blob 47ea9c3df4682ae7d2c9139fa9ac6dbc9b6eb43d | sed -e 's/line 7/changed line 7/' > new_hello $ cat new_hello | git hash-object -t blob --stdin -w 201722c515afacad101b62525a9e57899eac5182 $ git replace 47ea9c3df4682ae7d2c9139fa9ac6dbc9b6eb43d 201722c515afacad101b62525a9e57899eac5182

# # So now the tree of the current commit has a blob that is replaced. # The problem is that we don't see it, except if we "touch" the file: #

$ git diff $ touch hello $ git diff

diff --git a/hello b/hello
--- a/hello
+++ b/hello
@@ -4,7 +4,7 @@ line 3
 line 4
 line 5
 line 6
-changed line 7
+line 7
 line 8
 line 9
 line 10

#
# And now we cannot create a commit with the above diff:
#

$ git commit hello
...
nothing added to commit but untracked files present (use "git add" to track)
$ git add hello
$ git status
...
nothing added to commit but untracked files present (use "git add" to track)

#
# So I am not sure if that is a big problem, because that happens only
# if we want to commit something exactly like what we replaced. And in
# this case the best thing to do might be to simply remove the replace
# ref.
#

$ git replace -d 47ea9c3df4682ae7d2c9139fa9ac6dbc9b6eb43d
$ git diff
$ touch hello
$ git diff

#
# We got back to a normal situation.
#
# Now let's try something different
# First let's replace the current commit:
#

$ git rev-parse HEAD
ffccc9d552388844dbe94a361c07e7cb1731e12f
$ git cat-file commit ffccc | sed -e "s/A U/O/" | git hash-object -t 
commit --stdin -w
$ git cat-file commit dd1ca
tree 5c37393794868bc8e708cccd7c9d9aaa7a5e53cb
parent 14ac020163ea60a9d683ce68e36c946f31ecc856
author O Thor <author@example.com> 1112912353 -0700
committer C O Mitter <committer@example.com> 1112912353 -0700

hello: again 3 more lines
$ git replace HEAD dd1ca

#
# Let's create a commit based on the current one:
#

$ echo 'line 17' >> hello
$ git commit -m 'Add line 17' hello
[master 8f60c7e] Add line 17
 1 files changed, 1 insertions(+), 0 deletions(-)
$ git rev-parse HEAD^
ffccc9d552388844dbe94a361c07e7cb1731e12f
$ git reset --hard HEAD^
HEAD is now at dd1ca8e hello: again 3 more lines

#
# We are now on the replacement commit, though before the last
# command we were on a commit on top of the original one.
#

$ echo 'line 17' >> hello
$ git commit -m 'Add line 17' hello
[master c4a823a] Add line 17
 1 files changed, 1 insertions(+), 0 deletions(-)

#
# We build on top of the replacement commit, not the original one.
# This means that the original one may be dangling:
#

$ git fsck --full --no-reflogs
dangling commit 8f60c7ee5d6e0379ff813a26a2479289605eb935
...

#
# Of course on a published history, where "git replace" might
# be most usefull, you don't want to use "git reset --hard". So
# this might not be a big problem either.
#

Anyway, thanks in advance for advise/opinion about this.

Best regards,
Christian.
Previous: Johannes Schindelin
Message 7 of 7 in “What's cooking in git.git (Mar 2009, #01; Tue, 03)”
  1. Junio C HamanoMar 3, 2009
  2. Jeff KingMar 3, 2009
  3. Junio C HamanoMar 16, 2009
  4. Jeff KingMar 17, 2009
  5. Jakub NarebskiMar 3, 2009
  6. Johannes SchindelinMar 3, 2009
  7. Christian CouderMar 5, 2009

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.