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

[PATCH 4/4] fetch: cleanup refs with --use-mirror

From
Sam Vilain <sam@vilain.net>
Date
Nov 25, 2009, 10:06 UTC
Message-ID
<1259143617-26580-5-git-send-email-sam@vilain.net>
In-Reply-To
<1259143617-26580-4-git-send-email-sam@vilain.net>

Remove identical refs after a successful fetch. The ref under 'refs/mirrors/HOST/XXX' is compared with 'refs/XXX', and if matched, then the 'refs/mirrors/' version is removed.

Signed-off-by: Sam Vilain <sam@vilain.net>
---
  This is a simple mechanism for removing stale mirror refs; a more
  sophisticated approach would use the revision walker.
 builtin-fetch.c |   62 ++++++++++++++++++++++++++++++++++++++++++++++++++++--
 1 files changed, 59 insertions(+), 3 deletions(-)
diff --git a/builtin-fetch.c b/builtin-fetch.c
index daa287a..0c52f23 100644
--- a/builtin-fetch.c
+++ b/builtin-fetch.c
@@ -211,6 +211,57 @@ struct ref *mirror_refmap(struct transport* transport,
 	return rv;
 }
 
+int clean_up_mirror_ref(const char *refname,
+			const unsigned char *sha1,
+			int flags,
+			void *leading)
+{
+	char *orig_refname;
+	char *target_refname;
+	char *x;
+	unsigned char found_sha1[20];
+
+	orig_refname = xmalloc(strlen(refname)+strlen(leading)+1);
+	x = strchr(refname, '/');
+	if (!x)
+		return 0;
+	target_refname = xmalloc(strlen(x)+strlen("refs/remotes/")+1); 
+
+	strcpy(orig_refname, leading);
+	x = orig_refname + strlen(leading);
+	strcpy(x, refname);
+
+	warning("cleaning up mirror ref: %s (%s)",
+		orig_refname, sha1_to_hex(sha1));
+
+	strcpy(target_refname, "refs/remotes/");
+	strcpy(target_refname+5, strchr(refname, '/')+1);
+
+	warning("target ref is %s", target_refname);
+
+	if (resolve_ref(target_refname, found_sha1, 1, NULL)) {
+		if (!hashcmp(found_sha1, sha1)) {
+			warning("deleting ref %s", orig_refname);
+			delete_ref(orig_refname, sha1, REF_NODEREF);
+		}
+	}
+}
+
+void clean_up_mirror_refs(struct remote* remote)
+{
+	int rem_l = strlen(remote->name);
+	char *dst_name = xmalloc(rem_l+14);
+	char *x;
+	strcpy(dst_name, "refs/mirrors/");
+	x = dst_name + 13;
+	strcpy(x, remote->name);
+	x += rem_l;
+	*x++ = '/';
+
+	warning("cleaning up mirror refs for remote %s", remote->name);
+	for_each_ref_in(dst_name, clean_up_mirror_ref,
+			(void *)dst_name);
+}
 
 static struct ref *get_ref_map(struct transport *transport,
 			       struct refspec *refs, int ref_count, int tags,
@@ -884,9 +935,14 @@ int cmd_fetch(int argc, const char **argv, const char *prefix)
 		transport = NULL;
 		urls_remaining--;
 		if (use_mirror) {
-			if (!exit_code && urls_remaining >= 1) {
-				warning("successful fetch from mirror");
-				urls_remaining = 1;
+			if (!exit_code) {
+				if (urls_remaining >= 1) {
+					warning("successful fetch from mirror");
+					urls_remaining = 1;
+				}
+				else {
+					clean_up_mirror_refs(remote);
+				}
 			}
 			if (urls_remaining == 1) {
 				transport = real_transport;
-- 
1.6.3.3
Previous: Sam VilainNext: Shawn O. Pearce
Message 5 of 8 in “Client-side mirroring patches (v0)”
  1. Sam VilainNov 25, 2009
  2. 1/4 remote: allow mirroring to be specified, and document settingsSam Vilain, Nov 25, 2009
  3. 2/4 fetch: try mirrors if selectedSam Vilain, Nov 25, 2009
  4. 3/4 fetch --use-mirror: don't fetch with 'autotags' for actual fetchSam Vilain, Nov 25, 2009
  5. 4/4 fetch: cleanup refs with --use-mirrorSam Vilain, Nov 25, 2009
  6. Shawn O. PearceNov 26, 2009
  7. Shawn O. PearceNov 26, 2009
  8. Nanako ShiraishiJan 1, 2010

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.