As explained in the document. This option has an advantage over the command sequence "git worktree add && git worktree lock": there will be no gap that somebody can accidentally "prune" the new worktree (or soon, explicitly "worktree remove" it). "worktree add" does keep a lock on while it's preparing the worktree. If --lock is specified, this lock remains after the worktree is created. Suggested-by: David Taylor <David.Taylor@xxxxxxxx> Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@xxxxxxxxx> --- A patch that adds --lock may look like this. Documentation/git-worktree.txt | 7 ++++++- builtin/worktree.c | 12 +++++++++++- t/t2025-worktree-add.sh | 6 ++++++ 3 files changed, 23 insertions(+), 2 deletions(-) diff --git a/Documentation/git-worktree.txt b/Documentation/git-worktree.txt index 553cf8413f..b472acc356 100644 --- a/Documentation/git-worktree.txt +++ b/Documentation/git-worktree.txt @@ -9,7 +9,7 @@ git-worktree - Manage multiple working trees SYNOPSIS -------- [verse] -'git worktree add' [-f] [--detach] [--checkout] [-b <new-branch>] <path> [<branch>] +'git worktree add' [-f] [--detach] [--checkout] [--lock] [-b <new-branch>] <path> [<branch>] 'git worktree list' [--porcelain] 'git worktree lock' [--reason <string>] <worktree> 'git worktree prune' [-n] [-v] [--expire <expire>] @@ -107,6 +107,11 @@ OPTIONS such as configuring sparse-checkout. See "Sparse checkout" in linkgit:git-read-tree[1]. +--lock:: + Keep the working tree locked after creation. This is the + equivalent of `git worktree lock` after `git worktree add`, + but without race condition. + -n:: --dry-run:: With `prune`, do not remove anything; just report what it would diff --git a/builtin/worktree.c b/builtin/worktree.c index 9993ded41a..3dab07c829 100644 --- a/builtin/worktree.c +++ b/builtin/worktree.c @@ -24,6 +24,7 @@ struct add_opts { int force; int detach; int checkout; + int keep_locked; const char *new_branch; int force_new_branch; }; @@ -305,7 +306,15 @@ static int add_worktree(const char *path, const char *refname, done: strbuf_reset(&sb); strbuf_addf(&sb, "%s/locked", sb_repo.buf); - unlink_or_warn(sb.buf); + if (!ret && opts->keep_locked) { + /* + * Don't keep the confusing "initializing" message + * after it's already over. + */ + truncate(sb.buf, 0); + } else { + unlink_or_warn(sb.buf); + } argv_array_clear(&child_env); strbuf_release(&sb); strbuf_release(&symref); @@ -328,6 +337,7 @@ static int add(int ac, const char **av, const char *prefix) N_("create or reset a branch")), OPT_BOOL(0, "detach", &opts.detach, N_("detach HEAD at named commit")), OPT_BOOL(0, "checkout", &opts.checkout, N_("populate the new working tree")), + OPT_BOOL(0, "lock", &opts.keep_locked, N_("keep the new working tree locked")), OPT_END() }; diff --git a/t/t2025-worktree-add.sh b/t/t2025-worktree-add.sh index b618d6be21..6dce920c03 100755 --- a/t/t2025-worktree-add.sh +++ b/t/t2025-worktree-add.sh @@ -63,6 +63,12 @@ test_expect_success '"add" worktree' ' ) ' +test_expect_success '"add" worktree with lock' ' + git rev-parse HEAD >expect && + git worktree add --detach --lock here-with-lock master && + test_must_be_empty .git/worktrees/here-with-lock/locked +' + test_expect_success '"add" worktree from a subdir' ' ( mkdir sub && -- 2.11.0.157.gd943d85