feat(scripts): add SPECIFY_INIT_DIR to target a member project from the repo root#2892
Open
PascalThuet wants to merge 6 commits into
Open
feat(scripts): add SPECIFY_INIT_DIR to target a member project from the repo root#2892PascalThuet wants to merge 6 commits into
PascalThuet wants to merge 6 commits into
Conversation
…utside its directory Adds a project-root override so a non-interactive / CI caller can run a Spec Kit command against a member project (e.g. apps/web in a monorepo) from outside that directory, without cd. SPECIFY_INIT_DIR names the project root — the directory containing .specify/ — and is honored by get_repo_root in scripts/bash/common.sh, mirrored in scripts/powershell/common.ps1. Strict by design, per maintainer guidance on github#2834: when set, the path must exist and contain .specify/, otherwise the resolver hard-errors and never falls back to the current directory or the git toplevel (which would silently write to the wrong project's specs/). Relative paths normalize against the current directory (with CDPATH="" to avoid CDPATH-based misresolution); trailing slashes are tolerated; an empty string is treated as unset. Resolution stays two independent axes: SPECIFY_INIT_DIR selects the project, while SPECIFY_FEATURE_DIRECTORY / .specify/feature.json / branch detection select the feature within it (project-then-feature). The bash get_repo_root call sites that feed real resolution are split into decl/assignment so the hard error propagates instead of being masked by `local`. Env var only; the --project CLI flag is deferred. Adds tests/test_init_dir.py (positive + negative, bash and PowerShell) and documents the variable and the two-axis precedence in docs/reference/core.md. Refs: github#2834 Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Extends SPECIFY_INIT_DIR coverage to the bundled Git extension — the actual /speckit.specify before_specify entrypoint — so a monorepo/CI user setting it gets the feature branch created in, and auto-commit run against, the targeted project rather than the cwd/git toplevel. create-new-feature.sh/.ps1 and auto-commit.sh/.ps1 now resolve the project root from SPECIFY_INIT_DIR first, with the same strict contract as core (must exist + contain .specify/, hard error, no silent fallback). Adds bash tests for the git entrypoint. Also addresses the max-effort review of the diff: - common.sh: split the remaining `local x=$(get_repo_root)` / `local x=$(get_current_branch)` call sites (has_git, get_feature_paths) so a SPECIFY_INIT_DIR validation failure is never masked by `local`. - docs: note that the agent-context update selects the most recently modified plan within the resolved project (feature-axis selectors apply to the core feature scripts), and that SPECIFY_INIT_DIR is honored by core + git ext. - CHANGELOG: drop the hand-added [Unreleased] block; the release workflow generates entries from commit subjects, so manual entries would duplicate. Refs: github#2834 Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Addresses the duplication the review flagged: the strict SPECIFY_INIT_DIR validation was inlined per-script across the git extension. Extract it into a named resolver — resolve_specify_init_dir (bash) / Resolve-SpecifyInitDir (PowerShell) — defined once per independently-shippable library: - core scripts/bash/common.sh + scripts/powershell/common.ps1 (get_repo_root now delegates to it) - extensions/git git-common.sh + git-common.ps1 (create-new-feature and auto-commit call it instead of carrying their own inline copy) The three libraries still each carry one copy because the git and agent-context extensions must run without the core scripts installed — a single cross-library source would couple them — but the per-script inline duplication within the git extension is gone, and each copy is now a named, greppable function that is trivial to diff and keep in sync. Behavior and error strings are unchanged. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds
SPECIFY_INIT_DIRas an explicit project-root override for Spec Kit scripts that may be invoked from outside the target project, such as a monorepo root or CI task.Behavior
SPECIFY_INIT_DIR=/path/to/projectmakes supported scripts operate on that Spec Kit project..specify/.cwdor the git toplevel.Changes
SPECIFY_INIT_DIR.git/agent-contextextension scripts.Validation
uv run pytest tests/test_init_dir.py tests/extensions/git/test_git_extension.py tests/test_extensions.py -quvx ruff check tests/extensions/git/test_git_extension.pybash -n extensions/git/scripts/bash/create-new-feature.sh extensions/git/scripts/bash/git-common.sh scripts/bash/common.shgit diff --checkpwshis not available in my local environment, so PowerShell tests are included but skipped locally.