From 0757bfefafe85c6401332343991f43fcf2135c00 Mon Sep 17 00:00:00 2001 From: jawwad-ali Date: Mon, 29 Jun 2026 20:35:49 +0500 Subject: [PATCH 1/2] fix(scripts): warn when spec template is missing in create-new-feature.ps1 (parity with bash) create-new-feature.sh prints 'Warning: Spec template not found; created empty spec file' to stderr when no spec template resolves, then touches an empty spec. The PowerShell twin created the empty file silently with no warning, so on Windows a missing/broken template tree gave no signal. Emit the same warning on stderr (keeps stdout/JSON pure), matching the bash wording and stream. Co-Authored-By: Claude Opus 4.8 (1M context) --- scripts/powershell/create-new-feature.ps1 | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/scripts/powershell/create-new-feature.ps1 b/scripts/powershell/create-new-feature.ps1 index 5826815e01..91b36bebdb 100644 --- a/scripts/powershell/create-new-feature.ps1 +++ b/scripts/powershell/create-new-feature.ps1 @@ -211,6 +211,10 @@ if (-not $DryRun) { $utf8NoBom = New-Object System.Text.UTF8Encoding($false) [System.IO.File]::WriteAllText($specFile, $content, $utf8NoBom) } else { + # Match the bash twin (create-new-feature.sh): warn on stderr that no + # spec template was found before creating an empty spec file, so the + # missing-template signal is not silently swallowed on Windows. + [Console]::Error.WriteLine("Warning: Spec template not found; created empty spec file") New-Item -ItemType File -Path $specFile -Force | Out-Null } } From 383692ac9fe3421a1f56508c965000ecacd22120 Mon Sep 17 00:00:00 2001 From: jawwad-ali Date: Mon, 29 Jun 2026 20:36:40 +0500 Subject: [PATCH 2/2] test: assert create-new-feature.ps1 warns on missing spec template Regression test for the bash/PowerShell parity fix: with no resolvable spec template, the PowerShell script must emit 'Spec template not found' on stderr (matching bash) while keeping stdout parseable JSON and still creating the empty spec file. Gated on pwsh; decodes stdout/stderr as UTF-8. Co-Authored-By: Claude Opus 4.8 (1M context) --- tests/test_timestamp_branches.py | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/tests/test_timestamp_branches.py b/tests/test_timestamp_branches.py index 6fe0c14ed5..2a0a2ca696 100644 --- a/tests/test_timestamp_branches.py +++ b/tests/test_timestamp_branches.py @@ -332,6 +332,27 @@ def test_explicit_number_zero_is_honored_matching_bash(self, ps_git_repo: Path): assert data["FEATURE_NUM"] == "000" assert data["BRANCH_NAME"] == "000-zero" + @pytest.mark.skipif(not _has_pwsh(), reason="pwsh not installed") + def test_missing_spec_template_warns_matching_bash(self, ps_git_repo: Path): + """When no spec template can be resolved, create-new-feature.ps1 must warn on + stderr (and still create an empty spec file), matching the bash twin's + 'Warning: Spec template not found; created empty spec file'. Before the fix + PowerShell created the empty file silently.""" + # Remove the template the fixture installs so resolution finds nothing. + (ps_git_repo / ".specify" / "templates" / "spec-template.md").unlink() + script = ps_git_repo / "scripts" / "powershell" / "create-new-feature.ps1" + result = subprocess.run( + ["pwsh", "-NoProfile", "-File", str(script), + "-Json", "-ShortName", "no-tmpl", "No template feature"], + cwd=ps_git_repo, capture_output=True, text=True, encoding="utf-8", + ) + assert result.returncode == 0, result.stderr + assert "Spec template not found" in result.stderr + # stdout stays parseable JSON and the empty spec file is still created. + data = json.loads(result.stdout) + spec_file = Path(data["SPEC_FILE"]) + assert spec_file.is_file() + # ── check_feature_branch Tests ───────────────────────────────────────────────