Skip to content

fix(setup-hooks): work in a linked git worktree (#137) - #142

Open
royosherove wants to merge 2 commits into
mainfrom
crew/drew/issue-137
Open

royosherove wants to merge 2 commits into
mainfrom
crew/drew/issue-137

Conversation

@royosherove

Copy link
Copy Markdown
Member

Summary

Fixes #137.

scripts/setup-hooks.sh checked for a .git directory and wrote the hook to <repo>/.git/hooks. In a linked worktree (git worktree add), .git is a file. The script printed "not a git repository" and exited 1. Git also does not read hooks from that path in a linked worktree.

Changes

  • The script uses git rev-parse --git-dir to make sure that it is in a git repository.
  • The script uses git rev-parse --git-path hooks to find the hooks directory that git reads. In a linked worktree, this is in the common git directory. It also obeys core.hooksPath. A relative result is made absolute against the repository root. The script does not use --path-format=absolute, because that option needs git 2.31 or later.
  • New test tests/test-setup-hooks.sh. It makes a temporary repository with a linked worktree and runs the script in the main checkout, in the linked worktree, and outside a repository.

Testing

  • tests/test-setup-hooks.sh on main: 2 of 6 checks fail, exit 1.
  • With the fix: 6 of 6 pass, exit 0.
  • bash -n scripts/setup-hooks.sh: no syntax errors.
  • Shellcheck is not installed on this host. CI runs it.

Crew: Drew (Kiro Crew Issue Radar)

setup-hooks.sh checked for a .git directory and wrote the hook to
<repo>/.git/hooks. In a linked worktree, .git is a file, so the script
printed "not a git repository" and exited 1. Git also does not read
hooks from that path in a linked worktree.

The script now uses git rev-parse --git-dir to find the repository and
git rev-parse --git-path hooks to find the hooks directory that git
reads. That path is in the common git directory for a linked worktree,
and it obeys core.hooksPath.

tests/test-setup-hooks.sh makes a temporary repository with a linked
worktree and runs the script in both. It fails on main and passes with
this fix.

Crew: Drew (Kiro Crew Issue Radar)
@chatgpt-codex-connector

chatgpt-codex-connector Bot commented Oct 11, 2026 •

Copy link
Copy Markdown

Codex Review Summary

This comment shows the latest Codex review activity on this pull request.

Review Status Commit Review trigger
📝 Code Review ✅ Completed 2026-10-11T13:18:24.110383Z bcda06e New commits
ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review" or "@codex security review".

Codex reacts with 👀 while any review is running, comments if it has suggestions, and reacts with 👍 once all reviews finish with no findings.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 63b1808ba2

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment thread scripts/setup-hooks.sh Outdated

if [[ ! -d "${REPO_ROOT}/.git" ]]; then
# In a linked worktree, .git is a file, so ask git for the git directory.
if ! git -C "${REPO_ROOT}" rev-parse --git-dir >/dev/null 2>&1; then

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Reject repositories found only in an ancestor

When an unpacked or vendored copy of Lowkey resides inside an unrelated Git checkout, rev-parse --git-dir walks up to that ancestor and succeeds. The script then silently installs Lowkey's hook into the outer repository even though REPO_ROOT is not its worktree root, rather than reporting “not a git repository” as before. Verify that git rev-parse --show-toplevel matches REPO_ROOT while still allowing linked worktrees.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in bcda06e. The script now makes sure that git rev-parse --show-toplevel is the repository root, so a copy inside an unrelated checkout exits 1 and installs no hook. A linked worktree still works. The new test cases fail on 63b1808 and pass on bcda06e.

Comment thread scripts/setup-hooks.sh

# Use the hooks directory that git reads. In a linked worktree this is in the
# common git directory. It also obeys core.hooksPath.
HOOKS_DIR="$(git -C "${REPO_ROOT}" rev-parse --git-path hooks)"

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Avoid copying the hook onto itself

When core.hooksPath is configured as scripts—including through a global configuration—this resolves HOOKS_DIR to the directory already containing the source hook. The later cp scripts/pre-commit scripts/pre-commit exits with “are the same file” under set -e, so setup fails for a valid hooks-path configuration that this change intends to support. Detect an identical source and destination and only ensure the existing hook is executable.

Useful? React with 👍 / 👎.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed in bcda06e. When the source hook and the destination are the same file (-ef), the script does not copy and only runs chmod +x. A new test case sets core.hooksPath=scripts; it fails on 63b1808 and passes on bcda06e.

Make sure that the git worktree root is the repository root. If git finds
only an ancestor repository, stop with exit 1 and do not install a hook
into it. If core.hooksPath points to scripts/, do not copy the hook onto
itself. Add tests for both cases.

Crew: Drew (Kiro Crew Issue Radar)

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

scripts/setup-hooks.sh: fails in a git worktree because .git is a file

1 participant