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

[PATCH 3/7] Add a --push option to "git-remote add"

From
Paolo Bonzini <bonzini@gnu.org>
Date
Apr 28, 2008, 15:32 UTC
Message-ID
<65b938da49b447129297d4dbf20191be52d16670.1209391614.git.bonzini@gnu.org>
In-Reply-To
<ff298458e7efc14721fdc0420432bf33efd76784.1209391614.git.bonzini@gnu.org>

This patch adds a --push option to "git-remote add" which sets up a push refspec. This will be useful after the following patch to "git-push", which will make heavier use of push refspecs. Even now, however, the option combination "--mirror --push" can be used to set up a mirror *of this repository*, with a normal fetch refspec (refs/heads/*:refs/remotes/mirror/*) but with the remote.<nick>.mirror option set.

Signed-off-by: Paolo Bonzini <bonzini@gnu.org>
---
 Documentation/git-remote.txt |   25 +++++++++++++++++++------
 builtin-remote.c             |   32 ++++++++++++++++++++++++--------
 t/t5505-remote.sh            |   26 +++++++++++++++++++++++++-
 t/t5517-push-mirror.sh       |    2 +-
 4 files changed, 69 insertions(+), 16 deletions(-)
	My earlier preference for "--mirror" as an option for
	mirrored-from-here remotes is due to my earlier experience
	with arch (from which I migrated to git).  However, I'm very
	fine with "--mirror --push" since it's consistent with the
	meaning of the new option --push.
	This patch does not depend on patch 4, on the contrary the
	dependency is the other way round.  However, it does not make
	much sense as an independent change.  That's why the documentation
	for --push leaves something to be desired.  It will be fixed in
	patch 4, as the doc will refer to the behavior implemented there.
diff --git a/Documentation/git-remote.txt b/Documentation/git-remote.txt
index b20e851..e779905 100644
--- a/Documentation/git-remote.txt
+++ b/Documentation/git-remote.txt
@@ -10,7 +10,7 @@ SYNOPSIS
 --------
 [verse]
 'git-remote'
-'git-remote' add [-t <branch>] [-m <master>] [-f] [--mirror] <name> <url>
+'git-remote' add [-t <branch>] [-m <master>] [-f] [--mirror] [--push] <name> <url>
 'git-remote' rm <name>
 'git-remote' show <name>
 'git-remote' prune <name>
@@ -47,11 +47,24 @@ With `-m <master>` option, `$GIT_DIR/remotes/<name>/HEAD` is set
 up to point at remote's `<master>` branch instead of whatever
 branch the `HEAD` at the remote repository actually points at.
 +
-In mirror mode, enabled with `\--mirror`, the refs will not be stored
-in the 'refs/remotes/' namespace, but in 'refs/heads/'.  This option
-only makes sense in bare repositories.  If a remote uses mirror
-mode, furthermore, `git push` will always behave as if `\--mirror`
-was passed.
+`\--push` mode adds a `push` configuration line for the remote.
+It also affects the operation of mirror mode.
++
+Mirror mode, enabled with `\--mirror`, specifies that one of the
+repositories (either the current one or the remote one) is giving
+up control on its refs namespace to the other repository.  If a
+remote uses mirror mode, furthermore, `git push` will always
+behave as if `\--mirror` was passed.
+
+If `\--mirror` is given without `\--push`, this repository will
+act as a mirror of the remote, and hence the remote's refs will not
+be stored in the 'refs/remotes/' namespace, but in 'refs/heads/';
+this only makes sense in bare repositories.  If the two options
+are given in combination, instead, the other repository will
+act as a mirror of this one; in this case, the effect of mirror
+mode is that `git-push` will always add any newly created local
+refs to the remote, will force updates of locally updated refs,
+and will remove any deleted refs from the remote too.
 
 'rm'::
 
diff --git a/builtin-remote.c b/builtin-remote.c
index 8b63619..759dddb 100644
--- a/builtin-remote.c
+++ b/builtin-remote.c
@@ -56,7 +56,7 @@ static int fetch_remote(const char *name)
 
 static int add(int argc, const char **argv)
 {
-	int fetch = 0, mirror = 0;
+	int fetch = 0, mirror = 0, push = 0;
 	struct path_list track = { NULL, 0, 0 };
 	const char *master = NULL;
 	struct remote *remote;
@@ -71,6 +71,7 @@ static int add(int argc, const char **argv)
 			"branch(es) to track", opt_parse_track),
 		OPT_STRING('m', "master", &master, "branch", "master branch"),
 		OPT_BOOLEAN(0, "mirror", &mirror, "no separate remotes"),
+		OPT_BOOLEAN(0, "push", &push, "make \"git push\" work on this remote"),
 		OPT_END()
 	};
 
@@ -101,23 +102,38 @@ static int add(int argc, const char **argv)
 	strbuf_reset(&buf);
 	strbuf_addf(&buf, "remote.%s.fetch", name);
 
-	if (track.nr == 0)
-		path_list_append("*", &track);
-	for (i = 0; i < track.nr; i++) {
-		struct path_list_item *item = track.items + i;
+	for (i = 0; i < (track.nr ? track.nr : 1); i++) {
+		const char *path = track.nr ? track.items[i].path : "*";
 
 		strbuf_reset(&buf2);
 		strbuf_addch(&buf2, '+');
-		if (mirror)
+		if (mirror && !push)
 			strbuf_addf(&buf2, "refs/%s:refs/%s",
-					item->path, item->path);
+					path, path);
 		else
 			strbuf_addf(&buf2, "refs/heads/%s:refs/remotes/%s/%s",
-					item->path, name, item->path);
+					path, name, path);
 		if (git_config_set_multivar(buf.buf, buf2.buf, "^$", 0))
 			return 1;
 	}
 
+	if (push) {
+		strbuf_reset(&buf);
+		strbuf_addf(&buf, "remote.%s.push", name);
+
+		for (i = 0; i < (track.nr ? track.nr : 1); i++) {
+			strbuf_reset(&buf2);
+			if (track.nr) {
+				const char *path = track.items[i].path;
+				strbuf_addf(&buf2, "refs/heads/%s:refs/heads/%s",
+						path, path);
+			} else
+				strbuf_addstr(&buf2, ":");
+			if (git_config_set_multivar(buf.buf, buf2.buf, "^$", 0))
+				return 1;
+		}
+	}
+
 	if (mirror) {
 		strbuf_reset(&buf);
 		strbuf_addf(&buf, "remote.%s.mirror", name);
diff --git a/t/t5505-remote.sh b/t/t5505-remote.sh
index 48ff2d4..56e5e06 100755
--- a/t/t5505-remote.sh
+++ b/t/t5505-remote.sh
@@ -28,7 +28,7 @@ tokens_match () {
 }
 
 check_remote_track () {
-	actual=$(git remote show "$1" | sed -n -e '$p') &&
+	actual=$(git remote show "$1" | sed -n -e '/Tracked/!d;n;p') &&
 	shift &&
 	tokens_match "$*" "$actual"
 }
@@ -269,4 +269,28 @@ test_expect_success 'reject adding remote with an invalid name' '
 
 '
 
+test_expect_success 'fetching from push mirror leaves refs/head intact' '
+
+	(cd four && git init
+	 >file34 &&
+	 git add file34 &&
+	 test_tick &&
+	 git commit -m "Initial alternative")
+	cd one && 
+	git remote add --mirror --push four ../four &&
+	git fetch four &&
+	git rev-parse -s --verify refs/remotes/four/master
+	! test -f file34
+'
+
+test_expect_success 'fetching from mirror overwrites refs/head' '
+
+	cd four &&
+	test -f file34 &&
+	git remote add --mirror one ../one &&
+	git fetch one &&
+	! git rev-parse -s --verify refs/remotes/one/master
+	! test -f file34
+'
+
 test_done
diff --git a/t/t5517-push-mirror.sh b/t/t5517-push-mirror.sh
index ea49ded..cacc08c 100755
--- a/t/t5517-push-mirror.sh
+++ b/t/t5517-push-mirror.sh
@@ -25,7 +25,7 @@ mk_repo_pair () {
 	(
 		cd master &&
 		git init &&
-		git remote add $1 up ../mirror
+		git remote add --push $1 up ../mirror
 	)
 }
 
-- 
1.5.5
Previous: Paolo BonziniNext: Paolo Bonzini
Message 27 of 74 in “make "git push" update origin and mirrors, "git push --mirror" update mirrors”
  1. make "git push" update origin and mirrors, "git push --mirror" update mirrorsPaolo Bonzini, Apr 26, 2008
  2. Shawn O. PearceApr 26, 2008
  3. Junio C HamanoApr 26, 2008
  4. Shawn O. PearceApr 27, 2008
  5. Shawn O. PearceApr 27, 2008
  6. Junio C HamanoApr 27, 2008
  7. Shawn O. PearceApr 27, 2008
  8. Junio C HamanoApr 27, 2008
  9. Paolo BonziniApr 27, 2008
  10. Jeff KingApr 28, 2008
  11. Paolo BonziniApr 28, 2008
  12. Jeff KingApr 28, 2008
  13. Jeff KingApr 28, 2008
  14. Paolo BonziniApr 28, 2008
  15. Johannes SchindelinApr 28, 2008
  16. Paolo BonziniApr 28, 2008
  17. Johannes SchindelinApr 28, 2008
  18. Shawn O. PearceApr 28, 2008
  19. Paolo BonziniApr 28, 2008
  20. Stephen R. van den BergApr 28, 2008
  21. Jeff KingApr 28, 2008
  22. Paolo BonziniApr 27, 2008
  23. Paolo BonziniApr 27, 2008
  24. 0/7 limit the usage of the default remote "origin" to the minimumPaolo Bonzini, Apr 28, 2008
  25. 1/7 add special "matching refs" refspecPaolo Bonzini, Apr 28, 2008
  26. 2/7 add push line in git-clonePaolo Bonzini, Apr 28, 2008
  27. 3/7 Add a --push option to "git-remote add"Paolo Bonzini, Apr 28, 2008
  28. 4/7 make "git push" update all push repositories.Paolo Bonzini, Apr 28, 2008
  29. 5/7 don't rely on zero-argument "git fetch" from within git pullPaolo Bonzini, Apr 28, 2008
  30. 6/7 warn on "git pull" without a given branch.<name>.remote valuePaolo Bonzini, Apr 28, 2008
  31. 7/7 make "git fetch" update all fetch repositoriesPaolo Bonzini, Apr 28, 2008
  32. Alex RiesenApr 28, 2008
  33. Paolo BonziniApr 28, 2008
  34. Alex RiesenApr 28, 2008
  35. Paolo BonziniApr 29, 2008
  36. Alex RiesenApr 29, 2008
  37. Andreas EricssonApr 29, 2008
  38. Paolo BonziniApr 29, 2008
  39. Johannes SchindelinApr 29, 2008
  40. Paolo BonziniApr 29, 2008
  41. Alex RiesenApr 29, 2008
  42. Paolo BonziniApr 29, 2008
  43. Andreas EricssonApr 29, 2008
  44. Paolo BonziniApr 29, 2008
  45. Andreas EricssonApr 29, 2008
  46. Paolo BonziniApr 29, 2008
  47. しらいしななこApr 29, 2008
  48. Alex RiesenApr 29, 2008
  49. Paolo BonziniApr 29, 2008
  50. Alex RiesenApr 29, 2008
  51. Paolo BonziniApr 29, 2008
  52. Alex RiesenApr 29, 2008
  53. Johannes SchindelinApr 29, 2008
  54. Jeff KingApr 29, 2008
  55. Junio C HamanoApr 29, 2008
  56. Paolo BonziniApr 30, 2008
  57. Johannes SchindelinApr 29, 2008
  58. Alex RiesenApr 29, 2008
  59. Junio C HamanoMay 1, 2008
  60. Paolo BonziniMay 6, 2008
  61. Paolo BonziniMay 14, 2008
  62. Junio C HamanoMay 14, 2008
  63. Paolo BonziniMay 14, 2008
  64. Junio C HamanoMay 14, 2008
  65. Paolo BonziniMay 14, 2008
  66. Junio C HamanoApr 30, 2008
  67. Paolo BonziniApr 30, 2008
  68. Jeff KingApr 29, 2008
  69. Alex RiesenApr 29, 2008
  70. Junio C HamanoApr 29, 2008
  71. Jeff KingApr 29, 2008
  72. Paolo BonziniApr 30, 2008
  73. Paolo BonziniApr 29, 2008
  74. Johannes SchindelinApr 29, 2008

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.