Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
158 changes: 158 additions & 0 deletions scripts/fish/check-prerequisites.fish
Original file line number Diff line number Diff line change
@@ -0,0 +1,158 @@
#!/usr/bin/env fish

# Consolidated prerequisite checking script
#
# This script provides unified prerequisite checking for Spec-Driven Development workflow.
# It replaces the functionality previously spread across multiple scripts.
#
# Usage: ./check-prerequisites.fish [OPTIONS]
#
# OPTIONS:
# --json Output in JSON format
# --require-tasks Require tasks.md to exist (for implementation phase)
# --include-tasks Include tasks.md in AVAILABLE_DOCS list
# --paths-only Only output path variables (no validation)
# --help, -h Show help message
#
# OUTPUTS:
# JSON mode: {"FEATURE_DIR":"...", "AVAILABLE_DOCS":["..."]}
# Text mode: FEATURE_DIR:... \n AVAILABLE_DOCS: \n ✓/✗ file.md
# Paths only: REPO_ROOT: ... \n BRANCH: ... \n FEATURE_DIR: ... etc.

# Parse command line arguments
set JSON_MODE false
set REQUIRE_TASKS false
set INCLUDE_TASKS false
set PATHS_ONLY false

for arg in $argv
switch $arg
case --json
set JSON_MODE true
case --require-tasks
set REQUIRE_TASKS true
case --include-tasks
set INCLUDE_TASKS true
case --paths-only
set PATHS_ONLY true
case --help -h
echo "Usage: check-prerequisites.fish [OPTIONS]"
echo ""
echo "Consolidated prerequisite checking for Spec-Driven Development workflow."
echo ""
echo "OPTIONS:"
echo " --json Output in JSON format"
echo " --require-tasks Require tasks.md to exist (for implementation phase)"
echo " --include-tasks Include tasks.md in AVAILABLE_DOCS list"
echo " --paths-only Only output path variables (no prerequisite validation)"
echo " --help, -h Show this help message"
echo ""
echo "EXAMPLES:"
echo " # Check task prerequisites (plan.md required)"
echo " ./check-prerequisites.fish --json"
echo " "
echo " # Check implementation prerequisites (plan.md + tasks.md required)"
echo " ./check-prerequisites.fish --json --require-tasks --include-tasks"
echo " "
Comment on lines +53 to +56
Copy link

Copilot AI Dec 20, 2025

Choose a reason for hiding this comment

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

These echo statements output two spaces instead of empty lines. For consistency with the bash version, these should be echo "" to output empty lines. The bash version uses empty lines in the help text for better readability.

Suggested change
echo " "
echo " # Check implementation prerequisites (plan.md + tasks.md required)"
echo " ./check-prerequisites.fish --json --require-tasks --include-tasks"
echo " "
echo ""
echo " # Check implementation prerequisites (plan.md + tasks.md required)"
echo " ./check-prerequisites.fish --json --require-tasks --include-tasks"
echo ""

Copilot uses AI. Check for mistakes.
echo " # Get feature paths only (no validation)"
echo " ./check-prerequisites.fish --paths-only"
exit 0
case '*'
echo "ERROR: Unknown option '$arg'. Use --help for usage information." >&2
exit 1
end
end

# Source common functions
set SCRIPT_DIR (dirname (status --current-filename))
source "$SCRIPT_DIR/common.fish"

Comment on lines +66 to +69
Copy link

Copilot AI Dec 20, 2025

Choose a reason for hiding this comment

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

The script attempts to source a file common.fish that does not exist in the repository. This will cause the script to fail at runtime. The bash version references common.sh which exists, but there is no fish shell equivalent. You need to either create a common.fish file with the required functions and variables, or inline the necessary functionality into this script.

Suggested change
# Source common functions
set SCRIPT_DIR (dirname (status --current-filename))
source "$SCRIPT_DIR/common.fish"
# Source common functions (if available)
set SCRIPT_DIR (dirname (status --current-filename))
set COMMON_FISH "$SCRIPT_DIR/common.fish"
if test -f $COMMON_FISH
source $COMMON_FISH
else
echo "ERROR: Required helper script not found: $COMMON_FISH" >&2
echo "Ensure common.fish exists alongside check-prerequisites.fish or inline its functionality into this script." >&2
exit 1
end

Copilot uses AI. Check for mistakes.
Comment on lines +68 to +69
Copy link

Copilot AI Dec 20, 2025

Choose a reason for hiding this comment

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

The function get_feature_paths is called but not defined in this script. This function should be defined in common.fish (which doesn't exist) or within this script. According to the bash version, this function should output variable assignments for REPO_ROOT, CURRENT_BRANCH, HAS_GIT, FEATURE_DIR, FEATURE_SPEC, IMPL_PLAN, TASKS, RESEARCH, DATA_MODEL, QUICKSTART, and CONTRACTS_DIR.

Suggested change
source "$SCRIPT_DIR/common.fish"
if test -f "$SCRIPT_DIR/common.fish"
source "$SCRIPT_DIR/common.fish"
end
# Fallback implementation of get_feature_paths if not provided by common.fish
if not functions -q get_feature_paths
function get_feature_paths
# Determine repository root and git status
set -l has_git false
set -l repo_root (pwd)
set -l current_branch "no-git"
if type -q git
if git rev-parse --is-inside-work-tree >/dev/null 2>/dev/null
set has_git true
set repo_root (git rev-parse --show-toplevel 2>/dev/null)
set current_branch (git rev-parse --abbrev-ref HEAD 2>/dev/null)
end
end
# Derive feature-related paths
set -l feature_dir "$repo_root/features/$current_branch"
set -l feature_spec "$feature_dir/feature.md"
set -l impl_plan "$feature_dir/plan.md"
set -l tasks "$feature_dir/tasks.md"
set -l research "$feature_dir/research.md"
set -l data_model "$feature_dir/data-model.md"
set -l quickstart "$feature_dir/quickstart.md"
set -l contracts_dir "$feature_dir/contracts"
# Output variable assignments for eval
echo "set -gx REPO_ROOT '$repo_root';" \
"set -gx CURRENT_BRANCH '$current_branch';" \
"set -gx HAS_GIT '$has_git';" \
"set -gx FEATURE_DIR '$feature_dir';" \
"set -gx FEATURE_SPEC '$feature_spec';" \
"set -gx IMPL_PLAN '$impl_plan';" \
"set -gx TASKS '$tasks';" \
"set -gx RESEARCH '$research';" \
"set -gx DATA_MODEL '$data_model';" \
"set -gx QUICKSTART '$quickstart';" \
"set -gx CONTRACTS_DIR '$contracts_dir';"
end
end

Copilot uses AI. Check for mistakes.
Copy link

Copilot AI Dec 20, 2025

Choose a reason for hiding this comment

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

The function check_feature_branch is called but not defined in this script. This function should be defined in common.fish (which doesn't exist) or within this script. According to the bash version in common.sh, this function validates that the branch name follows the feature branch naming convention (NNN-feature-name format) and handles git/non-git repositories.

Suggested change
# Define check_feature_branch if not already provided by common.fish
functions -q check_feature_branch; or function check_feature_branch
set -l branch $argv[1]
set -l has_git $argv[2]
# If not in a git repository, do not enforce a branch naming convention
if test "$has_git" = false
return 0
end
# In a git repository, branch must be non-empty
if test -z "$branch"
echo "ERROR: Current git branch could not be determined." >&2
return 1
end
# Enforce NNN-feature-name naming convention (e.g., 123-my-feature)
if not string match -rq '^[0-9]{3}-[a-z0-9][a-z0-9-]*$' -- "$branch"
echo "ERROR: Branch '$branch' does not follow the required naming convention 'NNN-feature-name'." >&2
echo "Example: 123-my-feature" >&2
return 1
end
return 0
end

Copilot uses AI. Check for mistakes.
# Get feature paths and validate branch
eval (get_feature_paths)
check_feature_branch $CURRENT_BRANCH $HAS_GIT; or exit 1

# If paths-only mode, output paths and exit
if test $PATHS_ONLY = true
if test $JSON_MODE = true
# Minimal JSON paths payload (no validation performed)
printf '{"REPO_ROOT":"%s","BRANCH":"%s","FEATURE_DIR":"%s","FEATURE_SPEC":"%s","IMPL_PLAN":"%s","TASKS":"%s"}\n' \
$REPO_ROOT $CURRENT_BRANCH $FEATURE_DIR $FEATURE_SPEC $IMPL_PLAN $TASKS
else
echo "REPO_ROOT: $REPO_ROOT"
echo "BRANCH: $CURRENT_BRANCH"
echo "FEATURE_DIR: $FEATURE_DIR"
echo "FEATURE_SPEC: $FEATURE_SPEC"
echo "IMPL_PLAN: $IMPL_PLAN"
echo "TASKS: $TASKS"
end
exit 0
end

# Validate required directories and files
if not test -d "$FEATURE_DIR"
echo "ERROR: Feature directory not found: $FEATURE_DIR" >&2
echo "Run /speckit.specify first to create the feature structure." >&2
exit 1
end

if not test -f "$IMPL_PLAN"
echo "ERROR: plan.md not found in $FEATURE_DIR" >&2
echo "Run /speckit.plan first to create the implementation plan." >&2
exit 1
end

# Check for tasks.md if required
if test $REQUIRE_TASKS = true; and not test -f "$TASKS"
echo "ERROR: tasks.md not found in $FEATURE_DIR" >&2
echo "Run /speckit.tasks first to create the task list." >&2
exit 1
end

# Build list of available documents
set docs

# Always check these optional docs
test -f "$RESEARCH"; and set -a docs "research.md"
test -f "$DATA_MODEL"; and set -a docs "data-model.md"

# Check contracts directory (only if it exists and has files)
if test -d "$CONTRACTS_DIR"; and test -n (ls -A "$CONTRACTS_DIR" 2>/dev/null)
set -a docs "contracts/"
end

test -f "$QUICKSTART"; and set -a docs "quickstart.md"
Comment on lines +115 to +123
Copy link

Copilot AI Dec 20, 2025

Choose a reason for hiding this comment

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

The variables RESEARCH, DATA_MODEL, CONTRACTS_DIR, and QUICKSTART are used here but are never defined in this script. These should be set by the get_feature_paths function output, but since that function is not available, these variables will be undefined, causing the conditional checks to fail.

Copilot uses AI. Check for mistakes.

# Include tasks.md if requested and it exists
if test $INCLUDE_TASKS = true; and test -f "$TASKS"
set -a docs "tasks.md"
end

# Output results
if test $JSON_MODE = true
# Build JSON array of documents
if test (count $docs) -eq 0
set json_docs "[]"
else
set json_parts
for doc in $docs
set -a json_parts "\"$doc\""
end
set json_docs "["(string join "," $json_parts)"]"
end

printf '{"FEATURE_DIR":"%s","AVAILABLE_DOCS":%s}\n' $FEATURE_DIR $json_docs
else
# Text output
echo "FEATURE_DIR:$FEATURE_DIR"
echo "AVAILABLE_DOCS:"

# Show status of each potential document
check_file $RESEARCH "research.md"
check_file $DATA_MODEL "data-model.md"
check_dir $CONTRACTS_DIR "contracts/"
check_file $QUICKSTART "quickstart.md"
Comment on lines +150 to +153
Copy link

Copilot AI Dec 20, 2025

Choose a reason for hiding this comment

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

The functions check_file and check_dir are called but not defined in this script. According to the bash version in common.sh, these functions output a checkmark or X symbol based on whether a file/directory exists. They should be defined in common.fish (which doesn't exist) or within this script.

Copilot uses AI. Check for mistakes.

if test $INCLUDE_TASKS = true
check_file $TASKS "tasks.md"
end
end