Skip to content

Conversation

@satococoa
Copy link
Owner

@satococoa satococoa commented Oct 17, 2025

Summary

  • add ${WTP_REPO_BASENAME} expansion when resolving worktree base directories and update the default to ../worktrees/${WTP_REPO_BASENAME}
  • adjust CLI helpers, tests, and examples to use the expanded base directory for display and path resolution
  • document the new placeholder in README and architecture notes

Testing

  • go test ./...

https://chatgpt.com/codex/tasks/task_e_68f26696ce10832785e2fc425a19846a

Summary by CodeRabbit

  • Breaking Changes

    • Worktree paths now include the repository name as an intermediate directory; upgrading without a config may change layout and require migration steps.
  • New Features

    • Added ${WTP_REPO_BASENAME} placeholder for repo-scoped worktree paths.
    • CLI emits warnings and suggested move commands when legacy worktree layouts are detected.
  • Documentation

    • Quick Start, architecture, diagrams, and examples updated to use repo‑prefixed paths and explain the placeholder.
  • Tests

    • Many tests updated and new tests added to reflect repo‑prefixed paths and warning behavior.

Copilot AI review requested due to automatic review settings October 17, 2025 16:24
@coderabbitai
Copy link

coderabbitai bot commented Oct 17, 2025

Note

Currently processing new changes in this PR. This may take a few minutes, please wait...

📥 Commits

Reviewing files that changed from the base of the PR and between 57b0351 and 0576c96.

📒 Files selected for processing (1)
  • cmd/wtp/list.go (3 hunks)
 ______________________________________
< All those GPUs aren't just for show. >
 --------------------------------------
  \
   \   \
        \ /\
        ( )
      .( o ).

Note

Other AI code review bot(s) detected

CodeRabbit has detected other AI code review bot(s) in this pull request and will avoid duplicating their findings in the review comments. This may lead to a less comprehensive review.

Walkthrough

Default worktree base_dir now supports a ${WTP_REPO_BASENAME} placeholder expanded during path resolution; commands (cd, list, remove, init) were updated to use ResolveWorktreePath and consistent writer/errWriter handling. Documentation, examples, tests, and new legacy-layout detection/warning helpers were added to surface migration guidance.

Changes

Cohort / File(s) Summary
Documentation
README.md, docs/architecture.md
Replace ../worktrees examples with ../worktrees/<repo-name> and document ${WTP_REPO_BASENAME} placeholder plus a vNEXT breaking-change/migration note.
Config: default & expansion
internal/config/config.go, internal/config/config_test.go
Change DefaultBaseDir to ../worktrees/${WTP_REPO_BASENAME}; add expandBaseDirVariables and integrate placeholder expansion into ResolveWorktreePath; update tests and add TestExpandBaseDirVariables.
Init command
cmd/wtp/init.go, cmd/wtp/init_test.go
Add writeFile var (mockable); update .wtp.yml template to include ${WTP_REPO_BASENAME}; tests updated to expect new default and to mock write failures.
Command wiring & writers
cmd/wtp/cd.go, cmd/wtp/list.go, cmd/wtp/remove.go, cmd/wtp/cd_test.go, cmd/wtp/list_test.go, cmd/wtp/remove_test.go
Change command helper signatures to accept cmd *cli.Command; derive writers/errWriter from command root; call legacy-layout warning hooks before path operations; update tests to set cmd.ErrWriter = io.Discard and adjust expected paths to include repo prefix.
Remove flow & safety
cmd/wtp/remove.go, cmd/wtp/remove_test.go
Refactor removal flow: locate target, guard against removing current worktree, encapsulate git removal in executeWorktreeRemoval, use cfg.ResolveWorktreePath for name resolution, and update tests to use .../worktrees/<repo>/....
Legacy layout warnings
cmd/wtp/legacy_warning.go, cmd/wtp/legacy_warning_test.go
New detection/warning code to detect legacy worktree layouts, enumerate suggested migrations (git worktree move examples), and emit warnings unless repository has config; tests added.
Worktree managed logic & tests
cmd/wtp/worktree_managed.go, cmd/wtp/worktree_managed_test.go
Only call filepath.Abs when needed and return errors on Abs failure; add tests for managed-path detection (absolute/relative/outside).
Executor tests: failure injection
internal/hooks/executor_test.go
Rework failure-injection strategies to use file-type substitutions (regular file, broken symlink, blocking file) to reliably trigger traversal/copy errors.
Internal test updates & e2e
test/e2e/hook_streaming_test.go, test/e2e/worktree_test.go, various *_test.go
Update expected worktree paths to include repository basename directory; resolve symlinks in assertions; use config.DefaultBaseDir in test setups.
List rendering & widths
cmd/wtp/list.go, cmd/wtp/list_test.go
Adjust column spacing logic (introduce columnSpacingSlots), change derivePathWidth/clamp calculations, and remove some defensive fallbacks; updated tests to align with new width logic.
Misc & module
go.mod, other test helpers
Manifest updates and minor test scaffolding changes (e.g., use io.Discard for ErrWriter).

Sequence Diagram(s)

sequenceDiagram
  participant User as User (invokes wtp)
  participant CLI as wtp CLI
  participant Cmd as Command (cd/list/remove/...)
  participant Config as internal/config
  participant FS as Filesystem / Git
  Note over Config: New: expandBaseDirVariables\n(replace ${WTP_REPO_BASENAME})
  User->>CLI: run command
  CLI->>Cmd: dispatch to command handler (cmd *cli.Command)
  Cmd->>Config: LoadConfig() / ResolveWorktreePath(mainRepoPath, "")
  Config-->>Cmd: resolved baseDir/worktreePath
  Cmd->>Cmd: maybeWarnLegacyWorktreeLayout(errWriter, mainRepoPath, cfg, worktrees)
  alt legacy layout detected
    Cmd->>User: emit migration warning + example git worktree move command
  end
  Cmd->>FS: perform git/fs operations (create/remove/list)
  FS-->>Cmd: result / error
  Cmd-->>User: final output / status
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

  • Areas to focus on:
    • cmd/wtp/legacy_warning.go path normalization, skip/duplicate logic, and when warnings are suppressed.
    • internal/config.expandBaseDirVariables correctness (multiple placeholders, trailing slashes, empty repo basename).
    • CLI writer/errWriter selection and changed command helper signatures across cd/list/remove to avoid output regressions.
    • Removal guards and executeWorktreeRemoval error handling to ensure safe behavior when removing worktrees.
    • Tests that mock writeFile and filesystem interactions for proper setup/teardown.

Possibly related PRs

Poem

🐇 I hop through worktrees, one by one,
A repo-name burrow for each bright sun.
Placeholders bloom where branches stay,
I nudge old nests to move away.
Hooray — tidy burrows for every day! 🌿

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 18.67% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed The pull request title "feat: expand default worktree base dir with repo placeholders" directly and accurately describes the primary change in the changeset. The title is specific and clear: it identifies that the default worktree base directory is being expanded/updated to support repository placeholder variables (specifically ${WTP_REPO_BASENAME}). The title avoids vague terms, noise, or file lists, and is concise enough to be easily understood when scanning commit history. While the PR includes various supporting changes (test updates, documentation, legacy layout warnings), the title appropriately focuses on the main structural feature being introduced.

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull Request Overview

This PR adds support for expanding the ${WTP_REPO_BASENAME} placeholder in worktree base directories. The default base directory changes from ../worktrees to ../worktrees/${WTP_REPO_BASENAME}, allowing automatic isolation of worktrees by repository name without manual configuration.

Key Changes:

  • Introduced ${WTP_REPO_BASENAME} placeholder expansion in config path resolution
  • Updated default base directory to include repository name isolation
  • Refactored test setup to use more reliable error simulation methods

Reviewed Changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated no comments.

Show a summary per file
File Description
internal/config/config.go Added expandBaseDirVariables function and updated default base directory constant
internal/config/config_test.go Added tests for placeholder expansion and updated existing tests to use new default
cmd/wtp/init.go Updated template config file with placeholder documentation
cmd/wtp/init_test.go Added test setup for file write mocking
cmd/wtp/cd.go, remove.go, list.go Updated to use config.DefaultBaseDir constant and simplified path resolution
cmd/wtp/cd_test.go, remove_test.go, list_test.go Updated mock paths to include repository name segment
test/e2e/hook_streaming_test.go Updated worktree path assertions to include repository name
internal/hooks/executor_test.go Replaced permission-based error tests with more reliable file-blocking approaches
docs/architecture.md Updated documentation examples to show new path structure
README.md Added placeholder documentation and updated examples

Tip: Customize your code reviews with copilot-instructions.md. Create the file or learn how to get started.

@satococoa satococoa self-assigned this Oct 17, 2025
Copy link

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

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.

ℹ️ 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

Comment on lines 54 to 58
return &Config{
Version: CurrentVersion,
Defaults: Defaults{
BaseDir: "../worktrees",
BaseDir: DefaultBaseDir,
},

Choose a reason for hiding this comment

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

P1 Badge Preserve compatibility with pre-existing default worktrees

Changing DefaultBaseDir to ../worktrees/${WTP_REPO_BASENAME} means that repositories without an explicit .wtp.yml now assume worktrees live under ../worktrees/<repo>/…. Existing users who previously relied on the old default (../worktrees/<branch>) and never generated a config file will still have their worktrees directly under ../worktrees, so isWorktreeManaged/ResolveWorktreePath will treat those directories as unmanaged and commands like wtp list, wtp cd, or wtp remove will no longer find them after upgrading. Consider detecting the legacy layout or retaining the old default when no config file exists so current worktrees remain usable.

Useful? React with 👍 / 👎.

Copy link
Owner Author

Choose a reason for hiding this comment

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

@codex
We don’t need automatic detection.
Update the README.md to mention this breaking change for users who don’t use .wtp.yml.

Choose a reason for hiding this comment

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

Summary

  • Documented the breaking change for users relying on the legacy ../worktrees default and outlined how to preserve that layout when upgrading. README.mdL217-L226

Testing

  • ⚠️ Not run (not requested)

View task →

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (1)
internal/config/config_test.go (1)

26-72: Excellent test coverage for placeholder expansion.

The new test comprehensively validates expandBaseDirVariables behavior across multiple scenarios: single placeholder, multiple placeholders, no placeholder, and trailing slash handling.

However, there's a minor cleanup opportunity:

 	for _, tt := range tests {
-		tt := tt
 		t.Run(tt.name, func(t *testing.T) {

The tt := tt copy is no longer needed in Go 1.22+, as loop variables are now properly scoped per iteration by default.

Based on learnings

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 780af9d and e2e95b4.

📒 Files selected for processing (14)
  • README.md (6 hunks)
  • cmd/wtp/cd.go (2 hunks)
  • cmd/wtp/cd_test.go (2 hunks)
  • cmd/wtp/init.go (3 hunks)
  • cmd/wtp/init_test.go (2 hunks)
  • cmd/wtp/list.go (1 hunks)
  • cmd/wtp/list_test.go (11 hunks)
  • cmd/wtp/remove.go (2 hunks)
  • cmd/wtp/remove_test.go (13 hunks)
  • docs/architecture.md (3 hunks)
  • internal/config/config.go (4 hunks)
  • internal/config/config_test.go (5 hunks)
  • internal/hooks/executor_test.go (3 hunks)
  • test/e2e/hook_streaming_test.go (1 hunks)
🧰 Additional context used
📓 Path-based instructions (7)
**/*.go

📄 CodeRabbit inference engine (AGENTS.md)

**/*.go: Run gofmt and goimports; keep imports grouped and organized; local import prefix follows module path github.com/satococoa/wtp
Adhere to golangci-lint rules configured for the project (vet, staticcheck, gosec, mnd, lll=120, etc.)
Errors should be wrapped with context and must not be ignored
Use snake_case for Go filenames; document exported identifiers when non-trivial

Files:

  • cmd/wtp/cd_test.go
  • cmd/wtp/list.go
  • cmd/wtp/remove_test.go
  • cmd/wtp/init_test.go
  • cmd/wtp/list_test.go
  • cmd/wtp/cd.go
  • internal/hooks/executor_test.go
  • cmd/wtp/init.go
  • cmd/wtp/remove.go
  • test/e2e/hook_streaming_test.go
  • internal/config/config.go
  • internal/config/config_test.go
cmd/wtp/**

📄 CodeRabbit inference engine (AGENTS.md)

cmd/wtp/**: CLI entrypoint and commands are implemented under cmd/wtp
Update CLI help text to reflect user-facing changes
Command behavior: wtp cd prints only the absolute worktree path with no side effects
Command behavior: wtp completion generates pure completion scripts via urfave/cli
Command behavior: wtp hook emits shell functions that intercept wtp cd; wtp shell-init combines completion and hook output

Files:

  • cmd/wtp/cd_test.go
  • cmd/wtp/list.go
  • cmd/wtp/remove_test.go
  • cmd/wtp/init_test.go
  • cmd/wtp/list_test.go
  • cmd/wtp/cd.go
  • cmd/wtp/init.go
  • cmd/wtp/remove.go
**/*_test.go

📄 CodeRabbit inference engine (AGENTS.md)

**/*_test.go: Unit tests live alongside packages and use *_test.go naming
Prefer table-driven tests and mock git operations in unit tests

Files:

  • cmd/wtp/cd_test.go
  • cmd/wtp/remove_test.go
  • cmd/wtp/init_test.go
  • cmd/wtp/list_test.go
  • internal/hooks/executor_test.go
  • test/e2e/hook_streaming_test.go
  • internal/config/config_test.go
docs/**

📄 CodeRabbit inference engine (AGENTS.md)

Maintain docs such as docs/architecture.md and docs/testing-guidelines.md alongside changes

Files:

  • docs/architecture.md
internal/{git,config,hooks,command,errors,io}/**

📄 CodeRabbit inference engine (AGENTS.md)

Place internal packages within internal/{git,config,hooks,command,errors,io}

Files:

  • internal/hooks/executor_test.go
  • internal/config/config.go
  • internal/config/config_test.go
README.md

📄 CodeRabbit inference engine (AGENTS.md)

Update README when user-facing behavior changes

Files:

  • README.md
test/e2e/**

📄 CodeRabbit inference engine (AGENTS.md)

test/e2e/**: End-to-end tests reside under test/e2e
Document new workflows with realistic scenarios in test/e2e
Rely on real git workflows in E2E tests

Files:

  • test/e2e/hook_streaming_test.go
🧠 Learnings (5)
📚 Learning: 2025-10-07T15:56:11.510Z
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to cmd/wtp/completion.go : Use getWorktreeNameFromPath() to resolve worktree display names consistently across completion, errors, and parsing

Applied to files:

  • cmd/wtp/list.go
  • cmd/wtp/remove_test.go
  • cmd/wtp/cd.go
  • cmd/wtp/remove.go
  • internal/config/config.go
📚 Learning: 2025-10-07T15:56:11.510Z
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to .wtp.yml : Project hooks are declared in .wtp.yml; keep commands deterministic and safe, avoiding destructive defaults

Applied to files:

  • docs/architecture.md
  • README.md
📚 Learning: 2025-10-07T15:56:11.510Z
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to cmd/wtp/** : Command behavior: wtp cd prints only the absolute worktree path with no side effects

Applied to files:

  • docs/architecture.md
  • cmd/wtp/cd.go
📚 Learning: 2025-10-07T15:56:11.510Z
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to cmd/wtp/** : Command behavior: wtp hook <shell> emits shell functions that intercept wtp cd; wtp shell-init <shell> combines completion and hook output

Applied to files:

  • docs/architecture.md
📚 Learning: 2025-10-07T15:56:11.510Z
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to cmd/wtp/** : CLI entrypoint and commands are implemented under cmd/wtp

Applied to files:

  • docs/architecture.md
🧬 Code graph analysis (6)
cmd/wtp/list.go (1)
internal/config/config.go (1)
  • DefaultBaseDir (42-42)
cmd/wtp/remove_test.go (1)
internal/command/types.go (1)
  • Command (4-8)
cmd/wtp/list_test.go (1)
internal/config/config.go (2)
  • Defaults (20-22)
  • DefaultBaseDir (42-42)
cmd/wtp/cd.go (1)
internal/config/config.go (1)
  • DefaultBaseDir (42-42)
cmd/wtp/remove.go (1)
internal/config/config.go (1)
  • DefaultBaseDir (42-42)
internal/config/config_test.go (1)
internal/config/config.go (3)
  • Defaults (20-22)
  • DefaultBaseDir (42-42)
  • Config (13-17)
🪛 GitHub Check: Lint
cmd/wtp/cd_test.go

[failure] 44-44:
File is not properly formatted (gofmt)

internal/config/config_test.go

[failure] 62-62:
The copy of the 'for' variable "tt" can be deleted (Go 1.22+) (copyloopvar)

⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: E2E Tests (macos-latest)
🔇 Additional comments (23)
docs/architecture.md (1)

105-105: LGTM! Documentation accurately reflects the new placeholder-based path resolution.

The documentation updates consistently show the new ${WTP_REPO_BASENAME} placeholder in configuration examples and use the <repo> notation in path examples. This clearly communicates the dynamic, repository-scoped path handling to users.

Also applies to: 171-171, 174-174, 215-215

cmd/wtp/list.go (1)

175-175: LGTM! Centralized default base directory reference.

This change correctly replaces the hardcoded "../worktrees" with config.DefaultBaseDir, ensuring consistency with the centralized configuration management introduced in this PR.

cmd/wtp/init_test.go (2)

141-141: LGTM! Test expectation updated correctly.

The test now correctly expects the ${WTP_REPO_BASENAME} placeholder in the generated configuration file, matching the changes in cmd/wtp/init.go.


201-205: LGTM! Proper mocking enables error path testing.

The addition of writeFile mocking with proper save/restore pattern enables testing of the file write error path without relying on filesystem permissions.

cmd/wtp/list_test.go (1)

112-112: LGTM! Consistent use of centralized default base directory.

All test cases now correctly use config.DefaultBaseDir instead of hardcoded path strings. The special case at line 696 appropriately preserves the .worktrees override for subdirectory context testing while using the constant elsewhere.

Also applies to: 181-181, 226-226, 248-248, 309-309, 377-377, 427-427, 458-458, 561-561, 696-696, 787-787

cmd/wtp/init.go (3)

19-19: LGTM! Mockable function enables comprehensive testing.

The writeFile variable allows mocking in tests, enabling validation of error handling paths as demonstrated in cmd/wtp/init_test.go.


58-59: LGTM! Configuration template updated with placeholder.

The generated configuration now includes the ${WTP_REPO_BASENAME} placeholder with clear documentation, aligning with the PR's core feature.


92-92: LGTM! Uses mockable writeFile function.

Correctly uses the mockable writeFile function instead of directly calling os.WriteFile, enabling comprehensive test coverage.

test/e2e/hook_streaming_test.go (1)

49-50: LGTM! E2E test updated for dynamic repository-based paths.

The test now correctly constructs the worktree path using filepath.Base(repo.Path()) to dynamically extract the repository name, matching the behavior of the ${WTP_REPO_BASENAME} placeholder expansion.

cmd/wtp/remove.go (2)

36-36: LGTM! Centralized default base directory reference.

This change correctly replaces the hardcoded "../worktrees" with config.DefaultBaseDir, consistent with changes across other command files.


291-291: LGTM! Simplified path resolution using centralized resolver.

The change delegates base directory resolution to cfg.ResolveWorktreePath(), centralizing path resolution logic and ensuring consistent handling of the ${WTP_REPO_BASENAME} placeholder.

cmd/wtp/cd_test.go (1)

23-23: Fix formatting issue on line 44.

The test data updates correctly reflect the new repository-scoped path structure with the main prefix. However, line 44 has a formatting issue that needs to be corrected.

Please run gofmt to fix the indentation:

#!/bin/bash
# Fix formatting issues in the file
gofmt -w cmd/wtp/cd_test.go

Based on static analysis hints.

Also applies to: 44-44, 50-50

⛔ Skipped due to learnings
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to **/*.go : Run gofmt and goimports; keep imports grouped and organized; local import prefix follows module path github.com/satococoa/wtp
cmd/wtp/cd.go (2)

29-39: LGTM! Centralized path resolution is well-integrated.

The changes correctly delegate base directory resolution to cfg.ResolveWorktreePath(mainRepoPath, ""), which handles the new ${WTP_REPO_BASENAME} placeholder expansion. This ensures consistent path resolution across the codebase.


281-281: LGTM! Consistent path resolution.

Using cfg.ResolveWorktreePath(mainRepoPath, "") here maintains consistency with the centralized path resolution approach used throughout the file.

internal/config/config_test.go (1)

375-427: LGTM! Test cases properly reflect placeholder expansion.

The updated test cases correctly validate that:

  • Default base_dir expands ${WTP_REPO_BASENAME} to the repository basename
  • Relative paths without placeholders work as before
  • Absolute paths are handled correctly
  • Empty worktree names return just the base directory
README.md (2)

189-220: LGTM! Clear documentation of placeholder expansion.

The documentation effectively explains:

  • How to use ${WTP_REPO_BASENAME} in configuration
  • That it expands to the repository directory name
  • The benefit of zero-config isolation between repositories

This will help users understand and leverage the new feature.


332-354: LGTM! Directory structure clearly illustrates placeholder expansion.

The updated diagram with <repo-name>/ effectively visualizes how the placeholder creates repository-specific worktree directories, maintaining the same hierarchical structure within each repository's namespace.

cmd/wtp/remove_test.go (1)

43-83: LGTM! Test data properly updated for new path structure.

All test cases correctly reflect the new worktree path structure where worktrees are organized under worktrees/main/... (with main being the repository basename in test fixtures). The expectations are consistent across different test scenarios.

internal/config/config.go (2)

160-169: LGTM! Clean and correct placeholder expansion implementation.

The expandBaseDirVariables function:

  • Correctly extracts the repository basename using filepath.Base
  • Handles empty baseDir gracefully by returning early
  • Uses strings.ReplaceAll for straightforward substitution
  • Properly handles trailing slashes (filepath.Base strips them automatically)

This implementation is solid and maintainable.


152-158: LGTM! Proper integration of placeholder expansion.

Calling expandBaseDirVariables before converting to an absolute path ensures that placeholders are resolved using the repository root context. This correctly sequences the operations: expand variables → resolve relative paths → join with worktree name.

internal/hooks/executor_test.go (3)

817-837: LGTM! More reliable error injection approach.

Creating a blocking file at the destination path and attempting to create a nested path under it is a more reliable way to trigger destination creation errors compared to permission-based approaches. This should work consistently across different filesystems and platforms.


839-863: LGTM! Platform-independent error injection.

Replacing the directory with a regular file to force ReadDir failures is more robust than permission-based testing. This approach should work reliably across different platforms and doesn't require special permission handling.


904-934: LGTM! Effective use of broken symlink for error testing.

Using a broken symlink (pointing to a non-existent target) to simulate a file that cannot be copied is a clever and portable way to test error propagation from nested copyFile calls. This avoids platform-specific permission manipulation.

@satococoa
Copy link
Owner Author

@codex fix lint

@chatgpt-codex-connector
Copy link

Summary

Testing

  • go test ./...

View task →

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (2)
README.md (2)

15-15: Clarify placeholder notation in feature overview.

Line 15 uses <repo-name> as a visual placeholder, but the actual configuration template uses ${WTP_REPO_BASENAME}. For consistency with the Configuration section (line 192), consider either:

  1. Using the full syntax: ../worktrees/${WTP_REPO_BASENAME}/feature/auth
  2. Or add a note clarifying that <repo-name> expands via the ${WTP_REPO_BASENAME} placeholder
-`feature/auth` branch goes to `../worktrees/<repo-name>/feature/auth` - no redundant typing,
+`feature/auth` branch goes to `../worktrees/${WTP_REPO_BASENAME}/feature/auth` - no redundant typing,

130-144: Add clarification that <repo-name> is a placeholder in Quick Start examples.

The examples show ../worktrees/<repo-name>/... paths, but it's not immediately clear whether this is a literal directory name or a placeholder. Add a brief note to help users understand that <repo-name> will expand to their repository's basename (e.g., myproject).

 # Create worktree from existing branch (local or remote)
+# → Creates worktree at ../worktrees/<repo-name>/feature/auth (where <repo-name> is your repository's basename)
 # Automatically tracks remote branch if not found locally
 wtp add feature/auth
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between e2e95b4 and c265161.

📒 Files selected for processing (1)
  • README.md (6 hunks)
🧰 Additional context used
📓 Path-based instructions (1)
README.md

📄 CodeRabbit inference engine (AGENTS.md)

Update README when user-facing behavior changes

Files:

  • README.md
🧠 Learnings (2)
📓 Common learnings
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to cmd/wtp/completion.go : Use getWorktreeNameFromPath() to resolve worktree display names consistently across completion, errors, and parsing
📚 Learning: 2025-10-07T15:56:11.510Z
Learnt from: CR
PR: satococoa/wtp#0
File: AGENTS.md:0-0
Timestamp: 2025-10-07T15:56:11.510Z
Learning: Applies to .wtp.yml : Project hooks are declared in .wtp.yml; keep commands deterministic and safe, avoiding destructive defaults

Applied to files:

  • README.md
🔇 Additional comments (2)
README.md (2)

191-226: Documentation of placeholder expansion and breaking changes is comprehensive.

The configuration section clearly explains the ${WTP_REPO_BASENAME} placeholder, its expansion behavior, and includes an explicit breaking change notice for users upgrading from the previous default. The migration path is well-documented. The breaking change notice is appropriately placed and formatted.


341-356: Worktree structure diagram correctly reflects the new repository-scoped layout.

The updated diagram accurately shows the new default structure with <repo-name> as a top-level directory under ../worktrees/, replacing the previous flat layout. The diagram is clear and the comments linking to wtp add commands help users understand the mapping.

@satococoa
Copy link
Owner Author

@codex

fix these lint errors.

Run golangci/golangci-lint-action@v4
prepare environment
run golangci-lint
  Running [/home/runner/golangci-lint-1.64.8-linux-amd64/golangci-lint run --out-format=github-actions --timeout=5m] in [] ...
  Error: The copy of the 'for' variable "tt" can be deleted (Go 1.22+) (copyloopvar)
  Error: File is not properly formatted (gofmt)
  
  level=warning msg="[config_reader] The output format `github-actions` is deprecated, please use `colored-line-number`"
  
  Error: issues found
  Ran golangci-lint in 20420ms

@chatgpt-codex-connector
Copy link

Summary

  • Reformatted TestCdCommand_AlwaysOutputsAbsolutePath in cmd/wtp/cd_test.go with gofmt to restore standard indentation and satisfy linting expectations. cmd/wtp/cd_test.goL29-L77
  • Removed the redundant loop-variable copy in TestExpandBaseDirVariables, leveraging Go 1.22’s per-iteration scoping to clear the copyloopvar warning. internal/config/config_test.goL61-L70

Testing

  • go test ./...

View task →

@satococoa satococoa force-pushed the codex/update-defaultbasedir-for-worktrees branch from 13781a6 to a950867 Compare October 31, 2025 16:35
Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (2)
cmd/wtp/worktree_managed.go (1)

29-46: Consider logging when path resolution fails.

The function now returns false when filepath.Abs fails, treating the error as "worktree not managed." While this is a reasonable fallback given the boolean return type, silently swallowing path resolution errors could make debugging difficult if users have malformed paths or permission issues.

Consider adding a debug log or comment explaining that path resolution failures are treated as "not managed":

 	absWorktreePath := worktreePath
 	if !filepath.IsAbs(worktreePath) {
 		var err error
 		absWorktreePath, err = filepath.Abs(worktreePath)
 		if err != nil {
+			// Treat path resolution failure as "not managed"
 			return false
 		}
 	}
internal/config/config.go (1)

160-169: Consider handling empty repoRoot edge case.

If repoRoot is empty, filepath.Base("") returns ".", which would expand ${WTP_REPO_BASENAME} to ".". While this is unlikely in normal usage (called from repository context), it could produce unexpected paths like ../worktrees/./<branch>.

Consider adding a guard or comment:

 func expandBaseDirVariables(baseDir, repoRoot string) string {
 	if baseDir == "" {
 		return baseDir
 	}
+	if repoRoot == "" {
+		repoRoot = "." // or return baseDir unchanged
+	}
 
 	repoBaseName := filepath.Base(repoRoot)
 	expanded := strings.ReplaceAll(baseDir, "${WTP_REPO_BASENAME}", repoBaseName)
 
 	return expanded
 }
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 13781a6 and a950867.

📒 Files selected for processing (14)
  • README.md (6 hunks)
  • cmd/wtp/cd.go (1 hunks)
  • cmd/wtp/cd_test.go (2 hunks)
  • cmd/wtp/init.go (3 hunks)
  • cmd/wtp/init_test.go (2 hunks)
  • cmd/wtp/list_test.go (11 hunks)
  • cmd/wtp/remove.go (1 hunks)
  • cmd/wtp/remove_test.go (15 hunks)
  • cmd/wtp/worktree_managed.go (1 hunks)
  • docs/architecture.md (3 hunks)
  • internal/config/config.go (4 hunks)
  • internal/config/config_test.go (5 hunks)
  • internal/hooks/executor_test.go (3 hunks)
  • test/e2e/hook_streaming_test.go (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (6)
  • cmd/wtp/init.go
  • internal/config/config_test.go
  • cmd/wtp/init_test.go
  • cmd/wtp/cd.go
  • docs/architecture.md
  • cmd/wtp/list_test.go
🧰 Additional context used
🧬 Code graph analysis (1)
cmd/wtp/remove_test.go (1)
internal/command/types.go (1)
  • Command (4-8)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Build
🔇 Additional comments (10)
test/e2e/hook_streaming_test.go (1)

49-50: LGTM! Test correctly updated for per-repository worktree isolation.

The updated path construction properly implements the new directory structure by inserting the repository basename between "worktrees" and the branch name. The comment accurately documents the new default location pattern.

README.md (2)

15-15: LGTM! Examples consistently updated.

The documentation examples clearly show the new repository-scoped worktree paths with <repo-name> placeholder, helping users understand the new default behavior.

Also applies to: 130-130, 135-135, 139-139, 143-143


217-226: Clear migration guidance for breaking change.

The breaking change note properly warns users about the impact and provides a clear migration path (adding .wtp.yml with base_dir: "../worktrees" to preserve legacy layout).

cmd/wtp/cd_test.go (1)

23-23: Test fixtures correctly updated for new path structure.

The test data properly reflects the new default base directory structure with repository name isolation (/worktrees/main/feature/auth).

Also applies to: 44-44, 50-50

cmd/wtp/remove.go (1)

285-285: Correct use of centralized path resolution.

Using cfg.ResolveWorktreePath(mainRepoPath, "") ensures placeholder expansion is applied consistently. The empty string argument effectively retrieves the resolved base directory.

cmd/wtp/remove_test.go (1)

57-58: Test data systematically updated for new structure.

All test fixtures consistently reflect the new repository-scoped path structure (/worktrees/main/...), ensuring tests verify the correct behavior.

Also applies to: 65-65, 145-146, 153-153, 162-163, 170-170, 179-180, 187-187

internal/config/config.go (1)

42-42: Core placeholder expansion properly integrated.

The changes correctly introduce repository-based path isolation by:

  • Defining the templated default
  • Using it consistently in default config
  • Applying expansion before path resolution

Also applies to: 57-57, 153-153

internal/hooks/executor_test.go (3)

860-870: Improved test reliability with explicit blocking file.

Creating a regular file to block directory creation is more reliable than depending on non-existent parent directories, making the test behavior more predictable across different systems.


881-895: Better failure injection approach.

Replacing the directory with a regular file to force ReadDir to fail is clearer and more portable than relying on permission-based failures.


951-960: Broken symlink appropriately simulates copy failure.

Using a broken symlink to trigger nested file copy errors is a clean approach that doesn't rely on file system permissions.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (3)
cmd/wtp/worktree_managed_test.go (2)

71-73: Simplify redundant path operations.

filepath.Clean already normalizes paths and removes trailing separators, making the explicit TrimSuffix redundant.

Apply this diff:

-	baseDir := cfg.ResolveWorktreePath(canonicalMainRepoPath, "")
-	baseDir = strings.TrimSuffix(baseDir, string(filepath.Separator))
-	baseDir = filepath.Clean(baseDir)
+	baseDir := filepath.Clean(cfg.ResolveWorktreePath(canonicalMainRepoPath, ""))

78-82: Consider adding explanatory comments.

These assertions validate test setup preconditions (ensuring the relative path resolves inside the base directory). While the logic is sound, a brief comment would clarify the intent for future maintainers.

Example:

// Verify test setup: relPath should be inside baseDir (not escape with "..")
relPath, err := filepath.Rel(baseDir, absWorktreePath)
require.NoError(t, err)
require.NotEqual(t, "..", relPath)
require.False(t, strings.HasPrefix(relPath, ".."+string(filepath.Separator)))
test/e2e/worktree_test.go (1)

33-45: Consider resolving symlinks for worktree paths to ensure consistent comparison.

The comparison resolves symlinks for expectedPath but only cleans the worktree paths from the list. If repo.ListWorktrees() returns paths containing symlinks, the comparison filepath.Clean(wt) == resolvedExpectedPath could fail even when pointing to the same location.

Apply this diff to resolve symlinks for both paths:

 	found := false
 	for _, wt := range worktrees {
-		if filepath.Clean(wt) == resolvedExpectedPath {
+		resolvedWt, err := filepath.EvalSymlinks(filepath.Clean(wt))
+		if err == nil && resolvedWt == resolvedExpectedPath {
 			found = true
 			break
 		}
 	}

Alternatively, verify that repo.ListWorktrees() already returns fully resolved paths, making this change unnecessary:

#!/bin/bash
# Verify whether ListWorktrees returns resolved or unresolved symlink paths

# Find the implementation of ListWorktrees
ast-grep --pattern 'func ($$$) ListWorktrees() $$$  {
  $$$
}'

# Search for any symlink handling in the test framework
rg -n -A5 -B5 'ListWorktrees' test/e2e/framework/
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between a950867 and 3d81425.

📒 Files selected for processing (2)
  • cmd/wtp/worktree_managed_test.go (1 hunks)
  • test/e2e/worktree_test.go (2 hunks)
🧰 Additional context used
🧬 Code graph analysis (2)
cmd/wtp/worktree_managed_test.go (1)
internal/config/config.go (3)
  • Config (13-17)
  • Defaults (20-22)
  • DefaultBaseDir (42-42)
test/e2e/worktree_test.go (1)
test/e2e/framework/assertions.go (2)
  • AssertNoError (68-71)
  • AssertTrue (144-147)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: Build
🔇 Additional comments (5)
cmd/wtp/worktree_managed_test.go (3)

1-13: LGTM!

Package declaration and imports are properly organized and all appear necessary for the test implementations.


31-45: LGTM!

The negative test case correctly validates that paths outside the configured base directory return false.


15-29: Based on my analysis of the code, the original review comment is incorrect.

The Go filepath.Abs() function returns an absolute representation of a path by joining it with the current working directory if it's not already absolute. Crucially, it does not require the paths to exist on the filesystem. The function calls Clean on the result, but this is purely string-based manipulation.

Examining the isWorktreeManagedCommon implementation shows:

  1. It calls filepath.Abs() on paths only when they are not already absolute
  2. Since worktreePath is constructed as filepath.Join(tempDir, "worktrees", "repo", "feature", "foo"), it is an absolute path and filepath.Abs() will not be invoked on it
  3. The function uses only filepath.Rel() to compute relative paths—another purely lexical operation that doesn't access the filesystem
  4. No existence checks (like os.Stat()) or file operations are performed

The test is valid: creating only mainRepoPath on disk while leaving worktreePath uncreated does not cause any issues since the function operates entirely on path strings.


Likely an incorrect or invalid review comment.

test/e2e/worktree_test.go (2)

5-5: LGTM: Import added for path manipulation.

The path/filepath import is correctly added to support the new worktree path construction and symlink resolution logic.


28-32: No changes required—code is correct.

The symlink resolution is appropriate defensive programming. EvalSymlinks returns the path name after the evaluation of any symbolic links. On non-symlinked paths (like those created by the test), it simply returns the canonical path without error. Since the test framework does not use symlinks and the worktree path is freshly created, this code will succeed reliably.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 2

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 3d81425 and df8cc63.

📒 Files selected for processing (7)
  • cmd/wtp/cd.go (4 hunks)
  • cmd/wtp/legacy_warning.go (1 hunks)
  • cmd/wtp/legacy_warning_test.go (1 hunks)
  • cmd/wtp/list.go (3 hunks)
  • cmd/wtp/list_test.go (22 hunks)
  • cmd/wtp/remove.go (5 hunks)
  • cmd/wtp/remove_test.go (17 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • cmd/wtp/remove_test.go
🧰 Additional context used
🧬 Code graph analysis (6)
cmd/wtp/legacy_warning.go (2)
internal/config/config.go (2)
  • Config (13-17)
  • ConfigFileName (40-40)
internal/git/worktree.go (1)
  • Worktree (14-19)
cmd/wtp/list.go (1)
internal/config/config.go (1)
  • Config (13-17)
cmd/wtp/remove.go (4)
internal/git/worktree.go (1)
  • Worktree (14-19)
internal/config/config.go (4)
  • LoadConfig (49-79)
  • Config (13-17)
  • Defaults (20-22)
  • DefaultBaseDir (42-42)
internal/errors/errors.go (2)
  • WorktreeNotFound (86-100)
  • WorktreeRemovalFailed (133-166)
internal/command/builders.go (1)
  • GitWorktreeRemove (66-79)
cmd/wtp/list_test.go (1)
internal/config/config.go (3)
  • Config (13-17)
  • Defaults (20-22)
  • DefaultBaseDir (42-42)
cmd/wtp/legacy_warning_test.go (2)
internal/config/config.go (4)
  • Config (13-17)
  • Defaults (20-22)
  • DefaultBaseDir (42-42)
  • ConfigFileName (40-40)
internal/git/worktree.go (1)
  • Worktree (14-19)
cmd/wtp/cd.go (1)
internal/config/config.go (4)
  • LoadConfig (49-79)
  • Config (13-17)
  • Defaults (20-22)
  • DefaultBaseDir (42-42)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (1)
  • GitHub Check: E2E Tests (macos-latest)
🔇 Additional comments (6)
cmd/wtp/remove.go (6)

62-65: LGTM: Standardized writer access pattern.

The refactoring to access the writer through rootCmd.Writer follows a consistent pattern and includes appropriate nil fallback.


117-139: LGTM: Well-structured refactoring into helper functions.

The extraction of locateTargetWorktree, guardAgainstRemovingCurrentWorktree, and executeWorktreeRemoval into separate helpers improves readability and maintainability. The error handling flow is clear and correct.


165-191: LGTM: Helper functions are well-implemented.

Both locateTargetWorktree and guardAgainstRemovingCurrentWorktree properly handle error cases, use appropriate error messages, and implement the correct logic for their responsibilities.


193-208: LGTM: Robust error handling for worktree removal.

The function properly handles both command execution errors and Git-specific errors, and includes Git output in error messages for better debugging.


336-336: LGTM: Correct implementation of placeholder-based base_dir resolution.

The change to use cfg.ResolveWorktreePath(mainRepoPath, "") properly leverages the new centralized path resolution logic that handles ${WTP_REPO_BASENAME} placeholder expansion, aligning with the PR's core objective.


141-163: ****

The notifyLegacyLayout function is not duplicating centralized utilities—it's already calling them. The wrapper is defined and used only in remove.go (called at line 115), and it delegates the actual warning logic to the centralized maybeWarnLegacyWorktreeLayout from legacy_warning.go. The pattern does not appear duplicated across other command files.

Likely an incorrect or invalid review comment.

Comment on lines +72 to +77
moveCommand := strings.Join([]string{
"git worktree move",
filepath.Join("..", "worktrees", "feature", "foo"),
filepath.Join("..", "worktrees", filepath.Base(mainRepoPath), "feature", "foo"),
}, " ")
assert.Contains(t, output, moveCommand)
Copy link

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Update test expectation for quoted move command.

Once the warning prints the migration command with safe quoting, this assertion should expect the %q output (e.g. "git worktree move \"../worktrees/...\" \"../worktrees/...\""). Please update the test string accordingly so it matches the corrected warning format.

🤖 Prompt for AI Agents
In cmd/wtp/legacy_warning_test.go around lines 72 to 77, the test currently
builds an unquoted moveCommand and asserts it appears in output, but the warning
now emits the migration command with shell-safe quoting (%q); update the
expectation to match that by constructing the expected string with quoted paths
(e.g. use fmt.Sprintf("%q", path) for each path or fmt.Sprintf("git worktree
move %q %q", src, dst)) and then assert.Contains(t, output,
expectedQuotedMoveCommand).

Comment on lines +55 to +56
fmt.Fprintf(w, " git worktree move %s %s\n", migration.currentRel, migration.suggestedRel)
}
Copy link

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Quote the suggested git worktree move command.

If the repo name or worktree path contains spaces (totally valid on macOS/Windows), this suggestion becomes git worktree move ../worktrees/My Repo/foo ..., which breaks the one-liner the warning asks the user to run. Please emit shell-safe quoting so the guidance works everywhere.

-		fmt.Fprintf(w, "      git worktree move %s %s\n", migration.currentRel, migration.suggestedRel)
+		fmt.Fprintf(w, "      git worktree move %q %q\n", migration.currentRel, migration.suggestedRel)

This uses Go’s %q formatter to escape spaces and special characters consistently.

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
fmt.Fprintf(w, " git worktree move %s %s\n", migration.currentRel, migration.suggestedRel)
}
fmt.Fprintf(w, " git worktree move %q %q\n", migration.currentRel, migration.suggestedRel)
}
🤖 Prompt for AI Agents
In cmd/wtp/legacy_warning.go around lines 55-56, the formatted suggestion for
the git worktree move command doesn't quote paths, so names with spaces or
special characters will break the one-line suggestion; change the fmt.Fprintf
call to use Go's %q formatter for the path arguments (e.g., replace %s with %q
for migration.currentRel and migration.suggestedRel) so the output is shell-safe
and properly escaped.

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 0

🧹 Nitpick comments (2)
cmd/wtp/list.go (2)

107-110: Consider reusing the rootCmd alias for consistency.

The rootCmd alias is introduced here but cmd.Root() is called again at line 158. For consistency and to fully benefit from the alias, consider reusing rootCmd in the errWriter logic as well.


156-164: Simplify the errWriter selection logic for better readability.

The current nested conditionals work correctly but are harder to follow. Consider this clearer structure:

-	errWriter := io.Discard
-	if cmd != nil {
-		if root := cmd.Root(); root != nil && root.ErrWriter != nil {
-			errWriter = root.ErrWriter
-		} else if root != nil && root.ErrWriter == nil {
-			errWriter = os.Stderr
-		}
-	}
+	errWriter := io.Discard
+	if cmd != nil {
+		root := cmd.Root()
+		if root != nil {
+			if root.ErrWriter != nil {
+				errWriter = root.ErrWriter
+			} else {
+				errWriter = os.Stderr
+			}
+		}
+	}
📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between df8cc63 and 57b0351.

📒 Files selected for processing (1)
  • cmd/wtp/list.go (5 hunks)
🧰 Additional context used
🧬 Code graph analysis (1)
cmd/wtp/list.go (1)
internal/config/config.go (1)
  • Config (13-17)
🔇 Additional comments (3)
cmd/wtp/list.go (3)

35-35: LGTM! Good addition of the spacing slots constant.

The new columnSpacingSlots constant improves maintainability and is correctly used in line 408 for spacing calculations.


130-130: LGTM! Correct parameter name change.

The parameter name change from _ to cmd is appropriate since the function now uses this parameter for errWriter selection and legacy layout warnings.


408-409: LGTM! Good refactor of spacing calculation.

Using the columnSpacingSlots constant makes the spacing calculation clearer and more maintainable.

@satococoa satococoa force-pushed the codex/update-defaultbasedir-for-worktrees branch from 0576c96 to df8cc63 Compare November 1, 2025 14:30
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants