[PATCH 12/16] worktree: detect branch symref/detach and error conditions locally

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



The eventual goal is for git-worktree to populate the new worktree via
"git reset --hard" rather than "git checkout". As a consequence,
git-worktree will no longer be able to rely upon git-branch to determine
the state of the worktree (detached or branch symref), or to check for
error conditions, such as the requested branch already checked out
elsewhere, or an invalid reference. Therefore, imbue git-worktree with
the intelligence to determine a branch symref or detached state locally,
and to perform error checking on its own.

Signed-off-by: Eric Sunshine <sunshine@xxxxxxxxxxxxxx>
---

This patch is somewhat RFC since I spent a lot of time browsing the
branch- and ref-related APIs figuring out how to determine if the
provided refname was a branch name or some other (detached) reference.
I'm not at all sure that my use of strbuf_check_branch_ref(),
ref_exists(), and lookup_commit_reference_by_name() is the best
approach, or even appropriate, although it seems to work as desired.

 builtin/worktree.c | 15 +++++++++++++++
 1 file changed, 15 insertions(+)

diff --git a/builtin/worktree.c b/builtin/worktree.c
index e04a6d1..babdef1 100644
--- a/builtin/worktree.c
+++ b/builtin/worktree.c
@@ -3,6 +3,8 @@
 #include "dir.h"
 #include "parse-options.h"
 #include "argv-array.h"
+#include "branch.h"
+#include "refs.h"
 #include "run-command.h"
 #include "sigchain.h"
 
@@ -187,11 +189,23 @@ static int add_worktree(const char *path, const char *refname,
 	struct stat st;
 	struct child_process cp;
 	int counter = 0, len, ret;
+	struct strbuf symref = STRBUF_INIT;
+	struct commit *commit = NULL;
 	unsigned char rev[20];
 
 	if (file_exists(path) && !is_empty_dir(path))
 		die(_("'%s' already exists"), path);
 
+	if (!opts->detach && !strbuf_check_branch_ref(&symref, refname) &&
+	    ref_exists(symref.buf)) {
+		if (!opts->force)
+			die_if_checked_out(symref.buf);
+	} else {
+		commit = lookup_commit_reference_by_name(refname);
+		if (!commit)
+			die(_("invalid reference: %s"), refname);
+	}
+
 	name = worktree_basename(path, &len);
 	strbuf_addstr(&sb_repo,
 		      git_path("worktrees/%.*s", (int)(path + len - name), name));
@@ -278,6 +292,7 @@ static int add_worktree(const char *path, const char *refname,
 	strbuf_addf(&sb, "%s/locked", sb_repo.buf);
 	unlink_or_warn(sb.buf);
 	strbuf_release(&sb);
+	strbuf_release(&symref);
 	strbuf_release(&sb_repo);
 	strbuf_release(&sb_git);
 	return ret;
-- 
2.5.0.rc1.201.ga12d9f8

--
To unsubscribe from this list: send the line "unsubscribe git" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html



[Index of Archives]     [Linux Kernel Development]     [Gcc Help]     [IETF Annouce]     [DCCP]     [Netdev]     [Networking]     [Security]     [V4L]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Linux SCSI]     [Fedora Users]