| Version |
1.0.0 (not 2.0.0) |
| Tracking |
This issue + v1.0.0 milestone + GitHub Project board |
| AIM deployment |
Phase 0 (first PR) |
| Branching |
PRs to main + 1.0.0-previewN prereleases |
| Breaking changes |
Hard cut + migration guide |
| Migration guide |
docs/migration-v0.8-to-v1.0.md; per-PR entries; AI-assisted prompt at top |
| Auto-migration tool |
None |
| Deprecation cycle |
None (skip 0.9.0) |
| psake 5.x |
In scope for 1.0.0 |
| Minimum PS version |
Windows PowerShell 5.1; PowerShell 7.4+ for PS 7 (decided 2026-07-21; PlatyPS 1.x validated on 5.1, Pester 6 floor drives the 7.4+) |
| Consumer Pester minimum |
Keep ≥ 5.x (decided 2026-07-22; RequiredModules stays at 5.6.1 — Test-PSBuildPester supports Pester 5 and 6, verified by the #137 integration matrix) |
| Preview numbering |
Decoupled from phase numbers (decided 2026-07-22). No preview is cut after Phase 1 — it shipped only two small changes (Test-PSBuildPester fixes #102 + the manifest floor #141), nothing risky to soak. The first preview is preview1, cut after Phase 2, and it carries the Phase 1 shipped changes along with it. |
| Migration guide scope |
Breaking changes plus behavioral changes that can require action on upgrade (decided 2026-07-25). The guide previously said "breaking changes only", which excluded fixes like #143 that can turn a passing consumer build red. Preamble widened to match. |
| Destination |
1.0.0 published to PSGallery (decided 2026-08-19). The route is done when the release ships, not when the planning does. |
| Route tracking |
This issue is the map (decided 2026-08-19). Route steps are sub-issues wired with native dependency edges rather than checkboxes, so the frontier is visible in the tracker and claimable by parallel sessions. |
| psake 5.x |
In scope, clean re-spike (decided 2026-08-19) — #155. The extras that sank #117 (task caching, LLM Pester output, external PesterConfiguration file, Format-PSBuildResult) are 1.1.0 features, not part of a dependency bump. |
| psake 5.x outcome |
MIGRATE (#155, resolved 2026-08-19). Consumer-facing psakeFile.ps1 needs zero changes under 5.0.4 — no task renames, no $PSBPreference change — so the abort criterion did not fire. All four breaking changes in psake's own v4→v5 guide were checked and none apply. Full suite 428/0 under 5.0.4, matching the 4.9.1 baseline. psake 5.x does differ behaviorally — Invoke-psake returns a PsakeBuildResult where v4 returned nothing, and Set-BuildEnvironment in a Pester BeforeAll fails the container — but neither is triggered by upgrading PowerShellBuild, so neither is documented here. Migration filed as #161. |
| BuildHelpers break escape |
Found by the #155 spike, undocumented upstream (2026-08-19). Set-BuildEnvironment in a Pester BeforeAll leaks an escaping break from Get-BuildVariable's switch blocks; psake 4.9.x absorbs it, psake 5.x does not, and Pester fails the whole container. Guarding the call on $env:BHProjectName fixes it. Affects any consumer whose Pester tests call Set-BuildEnvironment. |
| psake abort criterion |
Fixed in advance, before the spike runs (decided 2026-08-19). Migrate if the consumer-facing PowerShellBuild/psakeFile.ps1 needs only mechanical changes; cut psake 5.x to 1.1.0 and ship 1.0.0 on 4.9.0 if task names or the $PSBPreference contract must change. Set ahead of the findings so the call is made on evidence rather than sunk cost. |
| Phase 2 ordering |
PlatyPS and psake chains run in parallel (decided 2026-08-19), gated by a single preview1 cut. They touch disjoint files, so serializing them buys nothing and halves the frontier. |
FailBuildOnSeverityLevel |
#144 option 3, extended to cover #147 (decided 2026-08-19): fold ParseError into the Error threshold and add 'Any' wired to the catch-all branch. The ParseError half is a behavior change and needs a migration-guide entry. Corrected 2026-08-20: this row originally also said the gate should fail on analyzer-level errors "so a crashed rule no longer reads as 'no findings'". That premise was wrong — #147 measured that a crashed rule does not cost findings (100 cold runs, never fewer than the known-good count). #163 therefore implements #147's preferred fix, a retry on RULE_ERROR that leaves failure semantics untouched, rather than a hard failure that would have cost some consumers a red build to help others. Implemented in #163. |
| #83 design |
Grilling ticket first (#156, decided 2026-08-19). Precedence between a supplied PesterConfiguration and $PSBPreference.Test.* is public API and must settle before implementation. The former pointer to "joshooaj's design in #80" was stale — #80 is a different, closed request. |
| Phase 4 milestone discrepancy |
Resolved 2026-08-19 — milestone stripped, then partly reversed 2026-08-28. #94 and #95 stay out (both closed). #98 and #103 are back in v1.0.0 and block #160: they are the only two public functions with no coverage of their own, and the compile-mode test that appeared to cover Build-PSBuildModule asserts on file text only — it passes over a module that exports nothing (#201). Verifying code that already ships is a different question from adding features; see the note under Phase 4. |
| Changelog and guide scope |
Internal changes get neither (decided 2026-08-20, applied to #162). CHANGELOG.md records user-facing changes only, and the migration guide covers changes triggered by upgrading PowerShellBuild. A build-toolchain pin in requirements.psd1 is neither, even when the upgraded dependency behaves differently — that belongs in the dependency's own migration guide. Sharpens the existing "Migration guide scope" row: the test is who is affected by this upgrade, not how interesting the change is. |
| Scope additions |
#124 and #138 pulled in (decided 2026-08-19). Both touch the public surface freezing at 1.0.0: #124 adds a PlatyPS setting to functions Phase 2 already rewrites, #138 is a correctness bug in a public function's output. |
| PlatyPS 1.x updatable help |
Survives, and now ships (resolved 2026-08-24, delivered 2026-08-26 in #176). New-HelpCabinetFile maps onto the old call one-for-one — CabinetFilesFolder / MarkdownModuleFile / OutputFolder against CabFilesFolder / LandingPagePath / OutputFolder. The port was small; the three defects in #169 were the work, because the function had never succeeded in 0.8.x either. One contract change fell out of it: a cabinet now requires HelpInfoUri in the consumer's manifest, because without one New-HelpCabinetFile writes the cabinet and skips the HelpInfo.xml that Update-Help resolves it through — output that looks complete and cannot be used. The function refuses rather than half-producing. |
| PlatyPS module coexistence |
Never both, at any point (corrected twice, settled 2026-08-24). Command names do not collide, but each module ships its own YamlDotNet.dll with a different assembly identity (0.0.0.0 unsigned vs 15.0.0.0 signed) loaded via NestedModules, so importing the second fails in either order on PowerShell 7; only a separate process escapes it. Verified by adding both to a requirements.psd1 and running the bootstrap, which fails. The first correction concluded "install both, never import both" and had #149 add the module to an install-only requirements file. That was still wrong: with an atomic migration (next row) there is no window in which both are needed, so the dependency swap belongs in the migration commit and nothing installs 1.x ahead of it. #149 keeps only its test half; #153 folded into the migration and is closed. |
| PlatyPS chain shape |
Two pull requests to main, split at the Markdown/MAML seam (decided 2026-08-24). 2b/2c/2d cannot land as three independent merges: a build after #150 alone would need New-MarkdownCommandHelp and New-ExternalHelp in one psake session, which the loader forbids, and #150 also changes the on-disk markdown schema that an unmigrated Build-PSBuildMAMLHelp would be handed. Rejected: one combined pull request (800+ lines, past the size where review stays careful) and a stacked integration branch (intermediate sub-pull-requests would carry red CI, discarding the gating that made stacking attractive). main requires linear history, so every option squashes to one commit anyway — the choice was review ergonomics only. PR 1 migrates Build-PSBuildMarkdown and Build-PSBuildMAMLHelp together, the coupled pair, and carries the dependency swap. PR 2 migrates Build-PSBuildUpdatableHelp and fixes #169. Both green; main stays shippable throughout. |
| PlatyPS PR 1 intermediate |
Build-PSBuildUpdatableHelp is knowingly left dangling between the two pull requests (decided 2026-08-24). After PR 1 it still calls New-ExternalHelpCab, from a module no longer installed. This costs nothing observable: the function has never worked (#169) and its tests are already skipped. Its psake PreCondition is deliberately left checking Get-Module platyPS, which is then false, so GenerateUpdatableHelp skips with a warning instead of crashing — better than today, where it throws on parameter binding. PR 1 must state this rather than leave it to be discovered. |
| Docs task coverage |
Partly wrong as originally recorded — corrected 2026-08-26. This row claimed no test source exercised the three help functions. That was false. tests/build.tests.ps1 builds tests/TestModule through -FromModule PowerShellBuild, whose Build task depends on BuildHelp, so GenerateMarkdown and GenerateMAML had been running end to end all along, and Has MAML help XML was pinning the output layout in two contexts. That existing coverage is what settled the layout contract the migration preserves — had it been noticed earlier, the flatten-versus-nest question would have answered itself. What was true: the functions had no coverage of their own, with specific options, and GenerateUpdatableHelp was genuinely unobserved because it is not in the default Build chain. #149 added the unit coverage; #152 added the task-level coverage. |
[Tracking] PowerShellBuild v1.0.0 roadmap
Goal: ship PowerShellBuild 1.0.0 — the first version with a stable public-API contract per SemVer. Treats the 0.x line as initial development per SemVer §4; 1.0.0 defines the public API per SemVer §5.
Status: planning → execution
Current version: 0.8.2
Target version: 1.0.0
Prerelease cadence: one prerelease,
1.0.0-rc1, cut in #160 and soaked ≥ 7 days before1.0.0(revised 2026-08-27 when Phase 3 was deferred; the earlierpreviewNcadence is below under Locked-in decisions). It is load-bearing rather than ceremony: several breaks this cycle are install-time —RequiredModulesnow demands psake5.0.4and Pester6.0.0, and PlatyPS was removed from it entirely — and none of them can be observed from a branch or from this repository's CI, which builds this module rather than a consumer's. Only a real gallery install exercises them.Branching: PRs land directly on
main(allowed under 0.x); 1.0.0 cuts when scope is completeDestination
PowerShellBuild
1.0.0published to PSGallery. This issue is the wayfinder map forthat route: it indexes every decision already made and points at the tickets holding the
detail. The map is complete when 1.0.0 ships — not when planning ends.
Working this map
Route steps are sub-issues of this issue (and of #105 for the PlatyPS chain), wired
with GitHub's native dependency edges, so the tracker itself shows what is takeable.
takeable right now, in any order, by anyone.
skip it. An open, unassigned route ticket is unclaimed.
to this map's decision index if it settled something.
folded issues — Tests: Build-PSBuildMarkdown #99, Tests: Build-PSBuildMAMLHelp #100, Tests: Build-PSBuildUpdatableHelp #101 close as part of their parent PR, and Test-PSBuildScriptAnalysis does not fail on the PSScriptAnalyzer rule crash from #136 #147 rides along
with Settle the FailBuildOnSeverityLevel contract: 'Any' is documented but rejected, and ParseError escapes every threshold #144. Only children of this issue and of Update PlatyPS dependency from platyPS v0.14.x to Microsoft.PowerShell.PlatyPS v1.x #105 are route tickets.
Read the frontier without a script by opening this issue: blocked children render with a
blocked marker, and the rest are the frontier.
Locked-in decisions
v1.0.0milestone + GitHub Project boardmain+1.0.0-previewNprereleasesdocs/migration-v0.8-to-v1.0.md; per-PR entries; AI-assisted prompt at topRequiredModulesstays at 5.6.1 —Test-PSBuildPestersupports Pester 5 and 6, verified by the #137 integration matrix)Test-PSBuildPesterfixes #102 + the manifest floor #141), nothing risky to soak. The first preview ispreview1, cut after Phase 2, and it carries the Phase 1 shipped changes along with it.PesterConfigurationfile,Format-PSBuildResult) are 1.1.0 features, not part of a dependency bump.psakeFile.ps1needs zero changes under 5.0.4 — no task renames, no$PSBPreferencechange — so the abort criterion did not fire. All four breaking changes in psake's own v4→v5 guide were checked and none apply. Full suite 428/0 under 5.0.4, matching the 4.9.1 baseline. psake 5.x does differ behaviorally —Invoke-psakereturns aPsakeBuildResultwhere v4 returned nothing, andSet-BuildEnvironmentin a PesterBeforeAllfails the container — but neither is triggered by upgrading PowerShellBuild, so neither is documented here. Migration filed as #161.Set-BuildEnvironmentin a PesterBeforeAllleaks an escapingbreakfromGet-BuildVariable's switch blocks; psake 4.9.x absorbs it, psake 5.x does not, and Pester fails the whole container. Guarding the call on$env:BHProjectNamefixes it. Affects any consumer whose Pester tests callSet-BuildEnvironment.PowerShellBuild/psakeFile.ps1needs only mechanical changes; cut psake 5.x to 1.1.0 and ship 1.0.0 on 4.9.0 if task names or the$PSBPreferencecontract must change. Set ahead of the findings so the call is made on evidence rather than sunk cost.preview1cut. They touch disjoint files, so serializing them buys nothing and halves the frontier.FailBuildOnSeverityLevelParseErrorinto theErrorthreshold and add'Any'wired to the catch-all branch. TheParseErrorhalf is a behavior change and needs a migration-guide entry. Corrected 2026-08-20: this row originally also said the gate should fail on analyzer-level errors "so a crashed rule no longer reads as 'no findings'". That premise was wrong — #147 measured that a crashed rule does not cost findings (100 cold runs, never fewer than the known-good count). #163 therefore implements #147's preferred fix, a retry onRULE_ERRORthat leaves failure semantics untouched, rather than a hard failure that would have cost some consumers a red build to help others. Implemented in #163.PesterConfigurationand$PSBPreference.Test.*is public API and must settle before implementation. The former pointer to "joshooaj's design in #80" was stale — #80 is a different, closed request.v1.0.0and block #160: they are the only two public functions with no coverage of their own, and the compile-mode test that appeared to coverBuild-PSBuildModuleasserts on file text only — it passes over a module that exports nothing (#201). Verifying code that already ships is a different question from adding features; see the note under Phase 4.CHANGELOG.mdrecords user-facing changes only, and the migration guide covers changes triggered by upgrading PowerShellBuild. A build-toolchain pin inrequirements.psd1is neither, even when the upgraded dependency behaves differently — that belongs in the dependency's own migration guide. Sharpens the existing "Migration guide scope" row: the test is who is affected by this upgrade, not how interesting the change is.New-HelpCabinetFilemaps onto the old call one-for-one —CabinetFilesFolder/MarkdownModuleFile/OutputFolderagainstCabFilesFolder/LandingPagePath/OutputFolder. The port was small; the three defects in #169 were the work, because the function had never succeeded in 0.8.x either. One contract change fell out of it: a cabinet now requiresHelpInfoUriin the consumer's manifest, because without oneNew-HelpCabinetFilewrites the cabinet and skips theHelpInfo.xmlthatUpdate-Helpresolves it through — output that looks complete and cannot be used. The function refuses rather than half-producing.YamlDotNet.dllwith a different assembly identity (0.0.0.0unsigned vs15.0.0.0signed) loaded viaNestedModules, so importing the second fails in either order on PowerShell 7; only a separate process escapes it. Verified by adding both to arequirements.psd1and running the bootstrap, which fails. The first correction concluded "install both, never import both" and had #149 add the module to an install-only requirements file. That was still wrong: with an atomic migration (next row) there is no window in which both are needed, so the dependency swap belongs in the migration commit and nothing installs 1.x ahead of it. #149 keeps only its test half; #153 folded into the migration and is closed.main, split at the Markdown/MAML seam (decided 2026-08-24). 2b/2c/2d cannot land as three independent merges: a build after #150 alone would needNew-MarkdownCommandHelpandNew-ExternalHelpin one psake session, which the loader forbids, and #150 also changes the on-disk markdown schema that an unmigratedBuild-PSBuildMAMLHelpwould be handed. Rejected: one combined pull request (800+ lines, past the size where review stays careful) and a stacked integration branch (intermediate sub-pull-requests would carry red CI, discarding the gating that made stacking attractive).mainrequires linear history, so every option squashes to one commit anyway — the choice was review ergonomics only. PR 1 migratesBuild-PSBuildMarkdownandBuild-PSBuildMAMLHelptogether, the coupled pair, and carries the dependency swap. PR 2 migratesBuild-PSBuildUpdatableHelpand fixes #169. Both green;mainstays shippable throughout.Build-PSBuildUpdatableHelpis knowingly left dangling between the two pull requests (decided 2026-08-24). After PR 1 it still callsNew-ExternalHelpCab, from a module no longer installed. This costs nothing observable: the function has never worked (#169) and its tests are already skipped. Its psake PreCondition is deliberately left checkingGet-Module platyPS, which is then false, soGenerateUpdatableHelpskips with a warning instead of crashing — better than today, where it throws on parameter binding. PR 1 must state this rather than leave it to be discovered.tests/build.tests.ps1buildstests/TestModulethrough-FromModule PowerShellBuild, whoseBuildtask depends onBuildHelp, soGenerateMarkdownandGenerateMAMLhad been running end to end all along, andHas MAML help XMLwas pinning the output layout in two contexts. That existing coverage is what settled the layout contract the migration preserves — had it been noticed earlier, the flatten-versus-nest question would have answered itself. What was true: the functions had no coverage of their own, with specific options, andGenerateUpdatableHelpwas genuinely unobserved because it is not in the defaultBuildchain. #149 added the unit coverage; #152 added the task-level coverage.Migration guide
Lives at
docs/migration-v0.8-to-v1.0.md. Every breaking-change PR must add an entryusing the standard structure (What changed / Why / Detection / Migration / Notes). Enforced
through
instructions/git-workflow.instructions.md(AIM) plus reviewer catch — not a PRtemplate checkbox, which Phase 1 explicitly skipped. The top-of-file section includes a
canonical AI prompt users can paste into their agent to migrate their
build.ps1automatically; #159 tests that prompt before release.
Phase 0 — Foundation
AGENTS.md,aim.config.json,instructions/CLAUDE.mdcontent →instructions/repository-specific.instructions.mdagent-workflow,shorthand,git-workflow,testing,powershell,markdown,releases,github-cli,readme,contributing,update,repository-specificCLAUDE.mdsays 0.7.3; actual is 0.8.0)Phase 1 — Conventions & guardrails ✅ complete (2026-07-22)
psake/.githubrepo, which is sufficient for general PR structure. The migration-guide entry rule for breaking-change PRs is enforced throughinstructions/git-workflow.instructions.md(AIM) + reviewer catch, not a checkbox. Repo-level override would only add value if drive-by external contributors became likely during the cycle.docs/migration-v0.8-to-v1.0.mdskeleton (docs: initialize v0.8 to v1.0 migration guide skeleton #123, merged 2026-07-03)v1.0.0milestone, link this issuePowerShellVersioninPowerShellBuild.psd1and CI matrix — done via chore: Raise minimum PowerShell version to 5.1 in module manifest #141 (merged 2026-07-22):PowerShellVersion = '5.1'(was'3.0'); no CI change needed — the orgModuleCI.ymlalready runs Windows PowerShell 5.1 plus current pwsh on Linux/Windows/macOS. Migration-guide entry and changelog entry included in chore: Raise minimum PowerShell version to 5.1 in module manifest #141.PSScriptAnalyzer1.24.0 → 1.25.0 inrequirements.psd1(chore: Pin Pester 5.8.0 and update PSScriptAnalyzer to 1.25.0 #129, merged 2026-07-03)Pesterbuild dependency to 5.8.0 inrequirements.psd1— was floating viaMinimumVersion = '5.6.1', so CI installed whatever was newest at bootstrap (chore: Pin Pester 5.8.0 and update PSScriptAnalyzer to 1.25.0 #129) — superseded: repo suite now pins Pester 6.0.0 (chore: Pin Pester 6.0.0 for the repository test suite #132), with 5.9.0 installed side-by-side viarequirements.pester-matrix.psd1for theTest-PSBuildPestercompatibility matrix (test: Add Test-PSBuildPester integration tests and fix latent bugs #137)Pesterconsumer-facing minimum inPowerShellBuild.psd1RequiredModules— decided 2026-07-22: keep ≥ 5.x; stays at 5.6.1, no manifest change.Test-PSBuildPestersupports Pester 5 and 6, and the test: Add Test-PSBuildPester integration tests and fix latent bugs #137 integration matrix verifies both majors; requiring 6.0 would force an upgrade on consumers for no functional gain.InvokeBuild5.8.1 → 5.14.23 (chore: Update InvokeBuild to 5.14.23 and actions/checkout to v4 #142, merged 2026-07-22)actions/checkoutinpublish.yamlv2 → v4 (chore: Update InvokeBuild to 5.14.23 and actions/checkout to v4 #142, merged 2026-07-22)CompatiblePSEditions = @('Desktop','Core')toPowerShellBuild.psd1(chore: Raise minimum PowerShell version to 5.1 in module manifest #141, merged 2026-07-22)main— done 2026-07-22 via the repo-level "Default" ruleset: require a pull request before merging (1 approval; merge/squash/rebase allowed); require status checks —CI / Run Pwsh Tests (ubuntu-latest / windows-latest / macOS-latest),CI / Run Tests (Windows PowerShell 5.1),CI / Run Linters— with branches up to date before merging; require linear history; require signed commits; restrict deletions; block force pushes. Bypass: Organization admin = always allow; Repository admin = pull requests only (admins cannot push directly tomain; they may merge a PR without waiting for an approval — maintainers and outside contributors need 1 approval + green CI).Phase 2 — Breaking dependency upgrades
Both chains below are open in parallel — they touch disjoint files — and both gate the
same preview cut.
PlatyPS migration (#105)
Three pull requests total, not six. 2a lands first and alone; 2b and 2c land together; 2d
lands with #169. See the PlatyPS chain shape decision above. The tickets stay separate because
they are separate units of work, not separate merges.
Build-PSBuild*Helpfunctions against currentplatyPS0.14.2 behavior, so the migration has a red-before-green target. Test-only; carries no
dependency change. Open as test: Baseline the help building functions #170, all CI legs green.
Build-PSBuildMarkdownandBuild-PSBuildMAMLHelptogether (closes Tests: Build-PSBuildMarkdown #99 and Tests: Build-PSBuildMAMLHelp #100); they are coupled by the markdownschema and cannot be split. Carries the dependency swap —
requirements.psd1, theRequiredModulesmanifest entry, the Markdown and MAML PreConditions, and themigration-guide entry for the breaking
RequiredModuleschange.Build-PSBuildUpdatableHelp(closes Tests: Build-PSBuildUpdatableHelp #101) andfix Build-PSBuildUpdatableHelp cannot succeed: missing landing page, undefined $moduleOutDir, unbound Module #169, unskipping its tests and updating its PreCondition. The riskiest link:
Windows-only,
makecab.exe-dependent, and non-functional today — a port plus threefixes, not a port.
convert committed→ document thedocs/markdown to the 1.x schemaconversion for consumers. Re-scoped 2026-08-24:
git ls-files docsreturns onlydocs/migration-v0.8-to-v1.0.md, so there is nothing here to convert. Now blocks Release: finalize the migration guide, test the AI prompt, write the 1.0.0 changelog #159rather than the chain.
PlatyPS 2f: remove the old platyPS 0.14.2 dependency #153 — 2f remove the old— closed 2026-08-24, foldedplatyPS0.14.2 dependencyinto 2b. Removing the old dependency is not a step after the migration; it is the
migration's dependency swap.
psake 5.x bump
The consumer-facing
PowerShellBuild/psakeFile.ps1needs zero changes, so the abortcriterion did not fire.
Set-BuildEnvironmenttestguard. A single small PR, not a chain — and an internal one: no changelog or migration-guide
entry, since the manifest floor stays at psake 4.9.0. Open as chore: Move the build toolchain to psake 5.0.4 #162, all CI legs green —
including Windows PowerShell 5.1, which settles the last open question about psake 5.x on
the v1.0.0 support floor. Awaiting review.
Gate
Release gate: cut 1.0.0-preview1 after Phase 2 #157 — cut— closed as superseded 2026-08-27. With Phase 31.0.0-preview1deferred, the break surface was complete, so
preview1andrc1would have soaked anidentical surface. The cycle cuts one prerelease: the
rc1in Release: bump to 1.0.0, cut rc1, soak, and publish 1.0.0 #160. The Phase 1 changes(Tests: Test-PSBuildPester #102, chore: Raise minimum PowerShell version to 5.1 in module manifest #141) ride along in it.
Phase 3 — API improvements — deferred to 1.1.0 (2026-08-27)
Design: precedence contract for a consumer-supplied PesterConfiguration (#83) #156 — design: precedence contract for a consumer-suppliedPesterConfiguration— deferred to 1.1.0, still the right five questions
Add support for passing a PesterConfiguration object to PowerShellBuild #83 —— deferred to 1.1.0,PesterConfigurationobject support, built to that contractfirst in the queue after 1.0.0
FailBuildOnSeverityLevelcontract, with Test-PSBuildScriptAnalysis does not fail on the PSScriptAnalyzer rule crash from #136 #147 (analyzer rule crashesescaping the gate) folded in
against the 1.x API
Test-PSBuildPesterRelease gate: cut 1.0.0-preview2 after Phase 3 #158 — cut— closed as superseded 2026-08-27. Phase 3 is1.0.0-preview2empty, so there is nothing for a second prerelease to soak.
Phase 4 — Test infrastructure
In v1.0.0:
Tests: Create shared fixture module #97 — shared fixture module at
tests/fixtures/PSBuildTestFixture/(closed via test: Add PSBuildTestFixture shared fixture module #135, 2026-07-09)Tests: Test-PSBuildPester #102 —
Test-PSBuildPesterintegration tests (closed via test: Add Test-PSBuildPester integration tests and fix latent bugs #137, 2026-07-09)Tests: Build-PSBuildMarkdown #99, Tests: Build-PSBuildMAMLHelp #100, Tests: Build-PSBuildUpdatableHelp #101 — folded into PR 2b, 2c, and 2d respectively, and reparented
under them. They are written against the new PlatyPS API so the tests are not written
twice, and they close with their parent PR rather than independently.
Tests: Build-PSBuildModule #98, Tests: Publish-PSBuildModule #103 — restored to scope 2026-08-28, and they block Release: bump to 1.0.0, cut rc1, soak, and publish 1.0.0 #160. These are the
only two of twelve public functions with no coverage of their own.
Publish-PSBuildModulehas no test references at all and is the function that pushes toa package repository.
Build-PSBuildModuleappears covered —build.tests.ps1has acompile-mode context with eight assertions — but every one of them asserts on file text,
none imports the built module, and the fixture's source
.psm1is a one-line commentthat structurally cannot carry a dot-sourcing loader. So the test passes over the
failure in $PSBPreference.Build.CompileModule can silently produce a module that exports nothing #201, where compiling produces a module exporting nothing.
Related test-infra work that landed during the cycle: #128/#133 (fail the build on Pester
block/container failures, not just failed tests), #140 (code-coverage tracking in the
Pester task), #143 (severity gate actually fails the build; also closed #125).
Tracked but not blocking 1.0.0 — see "Out of scope" below.
Phase 5 — Release
docs/migration-v0.8-to-v1.0.md, test the AI migration prompt against a real sampleconsumer
build.ps1(it has never been exercised), write theCHANGELOG.md1.0.0 entry.Its gate was
preview2; that is satisfied by scope rather than by a release, since Phase 3'sdeferral means nothing further breaks anything. The guide is 747 lines across 12 sections —
a coherence pass, as anticipated.
ModuleVersionto1.0.0, cut1.0.0-rc1, soak ≥ 7 days, publish1.0.0Not yet specified
In scope, but not yet sharp enough to ticket. Graduates as the frontier advances.
$PSBPreference.Docs.*setting or the 1.x API makes it inferable is unknown until 2b–2d reveal the new surface.
docs/schema conversion. This repo commits no commandmarkdown, so 2e cannot learn the answer by doing it here (see PlatyPS 2e: document the docs/ schema conversion for consumers #154 above). What a
consumer with a committed
docs/tree must do on upgrade still needs an answer, and itis a migration-guide entry rather than a code change. PlatyPS 2e: document the docs/ schema conversion for consumers #154 is the natural home for it.
psake 5.0.4 while the manifest still claims
psake>= 4.9.0. Both majors were verifiedlocally (428/0 each), but CI now exercises only 5.0.4, so the claim is asserted rather than
tested. Options are a side-by-side matrix like
requirements.pester-matrix.psd1, raising themanifest floor to 5.x, or accepting the gap. Not sharp enough to ticket until chore: Move the build toolchain to psake 5.0.4 #162 lands.
Out of scope
Ruled beyond this destination. These do not graduate; they return only if the destination
is redrawn.
Analyzetask. Upstream defect(PSScriptAnalyzer#1538/#1351, both deferred to 2.0), transient, and re-running succeeds.
CI hygiene, not consumer-facing.
psake org's shared workflow. No SemVer impact.
release.
Tests: Clear-PSBuildOutputFolder #94,Tests: Initialize-PSBuild #95— test backfill forClear-PSBuildOutputFolderandInitialize-PSBuild. Both closed; Tests: Initialize-PSBuild #95 closed 2026-08-24 via test: Cover Initialize-PSBuild behavior #164, a first outsidecontribution from @pttydou.
Tests: Build-PSBuildModule #98, Tests: Publish-PSBuildModule #103— moved back INTO scope 2026-08-28, see Phase 4.Inputs/Outputs, LLM-mode Pester output,external
PesterConfigurationfile support, and a publicFormat-PSBuildResult. Theseare 1.1.0 features that were bundled into a dependency bump; keeping them out is why the
psake spike is being re-run clean.
Definition of done
stripped from Tests: Clear-PSBuildOutputFolder #94/Tests: Initialize-PSBuild #95/Tests: Build-PSBuildModule #98/Tests: Publish-PSBuildModule #103; Tests: Build-PSBuildModule #98 and Tests: Publish-PSBuildModule #103 restored 2026-08-28 on evidence that
the existing coverage cannot fail
import the built module rather than reading its text
consumer
build.ps11.0.0-rc1has soaked ≥ 7 days with no blocker reports1.0.0is published to PSGalleryAI-assisted-development notes
instructions/files are the canonical guide for any agent working in this repo — agents must readagent-workflow.instructions.mdfirstfeat:,fix:,docs:,chore:,BREAKING CHANGE:) to keep history machine-parseable