Repository navigation
0.5.0 - 2026-10-06
Release Notes
Breaking changes
The CLI is consolidated around plan, apply, drift and audit. Per-category commands become hidden aliases that warn and then run the new command. They are removed in 0.6.0.
| Old invocation | New invocation | Status in 0.5.x |
|---|---|---|
ward security plan|apply|audit |
ward plan|apply|audit --category security |
Alias, warns |
ward rulesets plan|apply|audit |
ward plan|apply|audit --category rulesets |
Alias, warns |
ward protection plan|apply|audit |
ward plan|apply|audit --category branch-protection |
Alias, warns |
ward commit plan|apply |
ward plan|apply --category files |
Alias, warns |
ward teams plan|apply |
ward plan|apply --category access |
Alias, warns |
ward teams list |
ward audit --category access |
Alias, warns |
ward teams audit |
ward drift --category access |
Alias, warns |
ward settings plan|apply |
ward plan|apply --category repository |
Alias, warns |
ward settings audit |
ward drift --category repository |
Alias, warns |
ward settings ... --ruleset copilot-review |
Declare the ruleset in ward.toml (see Configuration) |
Removed, exits 2 with the snippet |
ward drift check |
ward drift |
Alias, warns |
ward init --from SOURCE |
ward import SOURCE |
Alias, warns |
--json |
--format json |
Hidden flag, warns |
--format table |
--format text |
Accepted as an alias |
ward --repo X plan (flag before the subcommand) |
ward plan --repo X |
Removed, usage error |
ward import --parallelism N, ward init --parallelism N |
ward --parallelism N import ... or ward import ... --parallelism N (the global flag) |
Same flag, now global only |
ward security apply --skip-verify |
ward apply --category security --skip-verify |
New flag on apply |
Changed or lost capabilities:
ward settings applynow has a wider scope. It runs the whole repository category, so it also covers metadata, custom properties, immutable releases, labels, and prune. The old command managed only[categories.repository.settings]and topics.- The Copilot code review ruleset is declarative.
ward settings --ruleset copilot-reviewis gone. Add theCopilot Code Reviewentry to[categories.rulesets]instead. The rulesets category must be managed and sensitive. The entry setsreview_draft_pull_requests = falsebecause GitHub echoes it back. ward teams applyincludes collaborators only when the manifest lists them. A missingteamsorcollaboratorskey now means the list is not managed. Before, a missing key was an empty list, soprune = trueremoved every collaborator (or every team) that the manifest did not name. Only an explicit list, includingcollaborators = [], withprune = trueremoves entries.ward importwrites both lists explicitly. It leaves out a list that it could not read completely (permission denied or unavailable), so the key means not managed.- The default scope is wider.
ward auditand the former per-category commands now default to all configured systems, likeward plan. Before,audit,teams,settings,rulesetsandprotectionrequired--systemor--repo. - Coverage counts only real read failures as
degradedand as warnings: permission denied or unavailable. Settings that GitHub does not expose and secret values it never returns are counted in a newunsupportedfield. The text summary reads, for example,Coverage: 5/9 read, 4 not exposed by GitHub. Before, a healthy run reported these known limits as degraded coverage and warnings. - The repository category records its successful reads in coverage. Before, it listed only failures, so it reported
0/5 collectedafter a successful read. - The audit-log records change. Apply runs through the aliases write the unified
apply.<category>actions (for exampleapply.accessandapply.repository) instead of per-command actions such asupdate_repository_settingsandcreate_copilot_review_ruleset. - The text output changes. The aliases print the standard plan and apply report instead of their own tables.
ward auditprints one section per category. Its security table gains theDep.SUandAIcolumns, andCopRvmoves to the rulesets section. The rulesets, branch protection and access audit views are sections ofward audit. - Flags must follow the subcommand.
--org,--system,--repoand--jsonare no longer global. Only--config,--parallelismand-vare global. ward applywithout--yesfails with exit code 2 when stdin is not a terminal.ward doctorno longer prints any part of the GitHub token. It reports only the token source, in text and in JSON.ward teams auditnow maps toward drift --category access. Like drift, it reports differences only for categories withdisposition = "managed". The old command listed mismatches for any disposition.ward driftexits with code 1 whenward teams auditorward settings auditfinds drift. The oldauditcommands exited with code 0.--categoryis validated at parse time and accepts comma-separated values. The old names stay as aliases (repo,general,file,ruleset,protection,teams,environment,integration).branch_protectionwith an underscore also works.
Added (CLI)
ward completionsleaves out the deprecated commands and the hidden--jsonflagward audit --category security,rulesets,branch-protection,access, with a ruleset table, branch-protection fields and team access. JSON keysrulesets,branch_protectionandaccess.teamsare additive. Copilot code review is detected by rule type.ward apply -yandward apply --skip-verify--format text|jsononplan,apply,drift,audit,repos listanddoctor
Added
- One category-based Ward manifest with source provenance, management policies, coverage evidence, stable references, and external-value placeholders
- Comprehensive repository import for General settings, security, rulesets, detailed branch protection, Actions, environments, access, integrations, labels, and configuration files
ward import --target,--include,--exclude, and--strictfor one-command baseline and target setup- Binary-safe configuration-file snapshots with Git modes, source SHAs, include/exclude globs, and atomic Git Data API commits
- Unified
ward planandward applywith category filtering, high-impact gates, dependency-aware ordering, verification, and structured audit records - Bounded GitHub retries for rate limits and transient 5xx responses
- Explicit-only systems via
match_prefix = false
Changed
- Repository import now snapshots every reusable setting available through documented public GitHub APIs and records partial/unsupported state instead of guessing
- Imported sensitive categories default to observe-only and require explicit managed+sensitive opt-in
- Secret values, credentialed webhook URLs, and deploy-key replacement material use external placeholders
- Inherited organization/enterprise resources and self-hosted runners are retained as references rather than cloned
- Configuration files are always delivered through a dedicated branch and pull request; dependent enforcement is deferred until merge
- Imported manifests target only the source repository unless existing same-owner targets are supplied explicitly
- Generic managed-file delivery settings moved from
[templates]to[file_delivery] - Focused plan/apply commands now use the same reconciliation engine and exact category scope as
ward planandward apply - Per-system category blocks replace the corresponding global category while omitted categories inherit global desired state
Removed
- Removed
ward repos inspect. It now exits with code 2 and points toward audit --repo NAME - Removed
ward config set,ward config add-systemandward config remove-system. They now exit with code 2 and point toward config editor editingward.tomldirectly. Thetoml_editdependency is gone - Removed the interactive
ward initwizard.ward initnow writes only the minimal scaffold and--non-interactiveis an accepted no-op. Useward import OWNER/REPOorward init --from OWNER/REPOfor onboarding - Removed the interactive TUI, its disk cache, and the
ratatui/crosstermdependencies - Removed built-in/custom templates, ecosystem detection, and target-project version inference
- Removed the unsafe
rollback, redundantsetup, template-management, and custom policy DSL commands - Removed dead dependencies, GitHub API wrappers, output modules, and audit-log rollback readers
- Removed the old top-level manifest sections and their separate security planning engine
Fixed
- Optional endpoint failures no longer erase unrelated imported categories
- GitHub path/ref encoding, pagination, webhook redaction, invitation cancellation, deploy-key replacement ordering, and secret idempotence
- Ruleset/branch-protection actor identity and status-check app bindings now round-trip without reusing source-local IDs
- Legacy security reads correctly handle both full repository and direct
security_and_analysispayloads
Install ward-cli 0.5.0
Install prebuilt binaries via shell script
curl --proto '=https' --tlsv1.2 -LsSf https://github.com/OriginalMHV/Ward/releases/download/v0.5.0/ward-cli-installer.sh | shInstall prebuilt binaries via powershell script
powershell -ExecutionPolicy Bypass -c "irm https://github.com/OriginalMHV/Ward/releases/download/v0.5.0/ward-cli-installer.ps1 | iex"Install prebuilt binaries via Homebrew
brew install OriginalMHV/tap/ward-cliDownload ward-cli 0.5.0
| File | Platform | Checksum |
|---|---|---|
| ward-cli-aarch64-apple-darwin.tar.xz | Apple Silicon macOS | checksum |
| ward-cli-x86_64-apple-darwin.tar.xz | Intel macOS | checksum |
| ward-cli-x86_64-pc-windows-msvc.zip | x64 Windows | checksum |
| ward-cli-aarch64-unknown-linux-gnu.tar.xz | ARM64 Linux | checksum |
| ward-cli-x86_64-unknown-linux-gnu.tar.xz | x64 Linux | checksum |