From: Chris Packham <judge.packham@gmail.com>
To: Jonathan Nieder <jrnieder@gmail.com>
Cc: GIT <git@vger.kernel.org>
Subject: Re: Question about .git/objects/info/alternates
Date: Wed, 24 Mar 2010 11:53:08 -0700 [thread overview]
Message-ID: <a038bef51003241153g33445607qb3ab750e08b0584@mail.gmail.com> (raw)
In-Reply-To: <20100323024223.GA12257@progeny.tock>
On Mon, Mar 22, 2010 at 7:42 PM, Jonathan Nieder <jrnieder@gmail.com> wrote:
> Chris Packham wrote:
>
>> I would like to have base somehow find the objects it doesn't have in
>> its object store and either download them or just copy them from the
>> object store of projecta.
> [...]
>> From reading [2] I think 'rm
>> .git/objects/info/alternates && git repack -a' might do the trick but
>> I'm not sure.
>
> Almost. Try ‘git repack -a && rm .git/objects/info/alternates’ instead. :)
>
> (Please back up the repository or try with something less important
> first, since I am not sure.)
>
> Hope that helps,
> Jonathan
>
git repack -a did the correct thing.
It occurs to me that the UI around alternates is a bit lacking i.e.
there isn't a git command to display the alternates in use or to add
them to an existing repository (or at least I couldn't find one
skimming the docs or googling). So here's my attempt to add a 'git
alternates' command which can display, add or remove an alternate. The
adding and removing could be done with standard shell commands but
I've found the recursive displaying quite useful and couldn't think of
a simple command line to achieve the same thing .
------8<------
From a5c64de20937da132376d717f19a1d52b54701d2 Mon Sep 17 00:00:00 2001
From: Chris Packham <judge.packham@gmail.com>
Date: Wed, 24 Mar 2010 11:34:11 -0700
Subject: [PATCH] Add git alternates command
Provides a friendlier UI for displaying and configuring alternates.
Signed-off-by: Chris Packham <judge.packham@gmail.com>
---
This patch assumes multiple alterates are possible. If this is not correct then
it could be simplfied as there would be no need for walk_alternates.
Makefile | 1 +
git-alternates.sh | 159 +++++++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 160 insertions(+), 0 deletions(-)
create mode 100755 git-alternates.sh
diff --git a/Makefile b/Makefile
index 3a6c6ea..1a7b084 100644
--- a/Makefile
+++ b/Makefile
@@ -334,6 +334,7 @@ TEST_PROGRAMS_NEED_X =
unexport CDPATH
SCRIPT_SH += git-am.sh
+SCRIPT_SH += git-alternates.sh
SCRIPT_SH += git-bisect.sh
SCRIPT_SH += git-difftool--helper.sh
SCRIPT_SH += git-filter-branch.sh
diff --git a/git-alternates.sh b/git-alternates.sh
new file mode 100755
index 0000000..74ec707
--- /dev/null
+++ b/git-alternates.sh
@@ -0,0 +1,159 @@
+#!/bin/sh
+#
+# This file is licensed under the GPL v2
+#
+
+USAGE='[-r|--recursive] [-a|--add <dir>] [-f|--force -d|--delete <dir>]'
+
+. git-sh-setup
+
+#
+# Runs through the alternates file calling the callback function $1
+# with the name of the alternate as the first argument to the callback
+# any additional arguments are passed to the callback function.
+#
+walk_alternates()
+{
+ local alternates=$GIT_DIR/objects/info/alternates
+ local callback=$1
+ shift
+
+ if [ -e $alternates ]; then
+ while read line
+ do
+ $callback $line $*
+ done < $alternates
+ fi
+}
+
+#
+# Walk function to display one alternate object store and, if the user
+# has specified -r, recursively call show_alternates on the git
+# repository that the object store belongs to.
+#
+show_alternates_walk()
+{
+ say "Object store $1"
+ say " referenced via $GIT_DIR"
+
+ local new_git_dir=${line%%/objects}
+ if [ "$recursive" == "true" -a "$GIT_DIR" != "$new_git_dir" ]
+ then
+ GIT_DIR=$new_git_dir show_alternates
+ fi
+}
+
+show_alternates()
+{
+ walk_alternates show_alternates_walk
+}
+
+#
+# Walk function to check that the specified alternate does not
+# already exist.
+#
+check_current_alternate_walk()
+{
+ if test "$1" = "$2"; then
+ die "fatal: Object store $2 is already used by $GIT_DIR"
+ fi
+}
+
+add_alternate()
+{
+ if test ! -d $dir; then
+ die "fatal: $dir is not a directory"
+ fi
+
+ walk_alternates check_current_alternate_walk $dir
+
+ # At this point we know that $dir is a directory that exists
+ # and that its not already being used as an alternate. We could
+ # go further and verify that $dir has valid objects.
+
+ # if we're still going we can safely add the alternate
+ touch $GIT_DIR/objects/info/alternates
+ echo "$(readlink -f $dir)" >> $GIT_DIR/objects/info/alternates
+ say "$dir added as an alternate"
+ say " use 'git repack -adl' to remove duplicate objects"
+}
+
+rewrite_alternates()
+{
+ if test "$1" != "$2"; then
+ echo $2 >> $3
+ fi
+}
+
+del_alternate()
+{
+ if test ! $force = "true"; then
+ say "Not forced, use"
+ say " 'git repack -a' to fetch missing objects, then "
+ say " '$dashless -f -d $dir' to remove the alternate"
+ die
+ fi
+
+ local alternates=$GIT_DIR/objects/info/alternates
+
+ new_alts_file=$(mktemp $alternates-XXXXXX)
+ touch $new_alts_file
+
+ walk_alternates rewrite_alternates $dir $new_alts_file
+ mv $new_alts_file $alternates
+
+ # save the git from repeatedly reading a 0 length file
+ if test $(stat -c "%s" $alternates) -eq 0; then
+ rm $alternates
+ fi
+}
+
+dir=""
+oper=""
+force="false"
+
+# Option parsing
+while test $# != 0
+do
+ case "$1" in
+ -r|--recursive)
+ recursive="true"
+ ;;
+ -a|--add)
+ if test ! -z "$oper"; then
+ usage
+ fi
+ oper="add"
+ case "$#,$1" in
+ 1,*) usage ;;
+ *) dir=$2; shift ;;
+ esac
+ ;;
+ -d|--delete)
+ if test ! -z "$oper"; then
+ usage
+ fi
+ oper="del"
+ case "$#,$1" in
+ 1,*) usage ;;
+ *) dir=$2; shift ;;
+ esac
+ ;;
+ -f|--force)
+ force="true"
+ ;;
+ -*)
+ usage
+ ;;
+ *)
+ ;;
+ esac
+ shift
+done
+
+# Now go and do it
+case $oper in
+ add) add_alternate ;;
+ del) del_alternate ;;
+ *) show_alternates ;;
+esac
--
1.7.0.3
next prev parent reply other threads:[~2010-03-24 18:53 UTC|newest]
Thread overview: 17+ messages / expand[flat|nested] mbox.gz Atom feed top
2010-03-22 17:26 Question about .git/objects/info/alternates Chris Packham
2010-03-23 2:42 ` Jonathan Nieder
2010-03-24 18:53 ` Chris Packham [this message]
2010-03-24 19:23 ` Jonathan Nieder
2010-03-24 19:58 ` Junio C Hamano
2010-03-24 20:35 ` Chris Packham
2010-03-25 6:07 ` Chris Packham
2010-03-25 6:07 ` [PATCHv2 1/2] Add git alternate command Chris Packham
2010-03-29 7:32 ` Junio C Hamano
2010-03-31 4:35 ` Chris Packham
2010-03-25 6:07 ` [PATCHv2 2/2] tests for " Chris Packham
2010-03-25 7:38 ` Johannes Sixt
2010-03-25 18:51 ` Chris Packham
2010-03-26 0:48 ` Miklos Vajna
2010-03-26 6:44 ` Johannes Sixt
2010-03-24 20:16 ` Question about .git/objects/info/alternates Stephen Boyd
2010-03-24 20:37 ` Chris Packham
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=a038bef51003241153g33445607qb3ab750e08b0584@mail.gmail.com \
--to=judge.packham@gmail.com \
--cc=git@vger.kernel.org \
--cc=jrnieder@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).