diff --git a/.github/scripts/update-homebrew-tap.sh b/.github/scripts/update-homebrew-tap.sh index 5d8f970e..04c43366 100644 --- a/.github/scripts/update-homebrew-tap.sh +++ b/.github/scripts/update-homebrew-tap.sh @@ -3,7 +3,7 @@ # # Expected environment: # TAG – git tag, e.g. "v0.8.31" -# MANIFEST – path to deepseek-artifacts-sha256.txt +# MANIFEST – path to codewhale-artifacts-sha256.txt # TAP_REPO – owner/repo of the Homebrew tap # TOKEN – PAT with contents:write on TAP_REPO (optional; skips if unset) @@ -43,15 +43,6 @@ readonly SHA_COD_LINUX_ARM="$(sha codewhale-linux-arm64)" readonly SHA_TUI_LINUX_ARM="$(sha codewhale-tui-linux-arm64)" readonly SHA_COD_LINUX_X64="$(sha codewhale-linux-x64)" readonly SHA_TUI_LINUX_X64="$(sha codewhale-tui-linux-x64)" -# Legacy shims (removed in v0.9.0) -readonly SHA_LEG_MACOS_ARM="$(sha deepseek-macos-arm64)" -readonly SHA_LEG_TUI_MACOS_ARM="$(sha deepseek-tui-macos-arm64)" -readonly SHA_LEG_MACOS_X64="$(sha deepseek-macos-x64)" -readonly SHA_LEG_TUI_MACOS_X64="$(sha deepseek-tui-macos-x64)" -readonly SHA_LEG_LINUX_ARM="$(sha deepseek-linux-arm64)" -readonly SHA_LEG_TUI_LINUX_ARM="$(sha deepseek-tui-linux-arm64)" -readonly SHA_LEG_LINUX_X64="$(sha deepseek-linux-x64)" -readonly SHA_LEG_TUI_LINUX_X64="$(sha deepseek-tui-linux-x64)" # --- temp dirs -------------------------------------------------------- @@ -78,14 +69,6 @@ class DeepseekTui < Formula url "${BASE_URL}/codewhale-tui-macos-arm64", using: :nounzip sha256 "${SHA_TUI_MACOS_ARM}" end - resource "legacy-shim" do - url "${BASE_URL}/deepseek-macos-arm64", using: :nounzip - sha256 "${SHA_LEG_MACOS_ARM}" - end - resource "legacy-tui-shim" do - url "${BASE_URL}/deepseek-tui-macos-arm64", using: :nounzip - sha256 "${SHA_LEG_TUI_MACOS_ARM}" - end else url "${BASE_URL}/codewhale-macos-x64", using: :nounzip sha256 "${SHA_COD_MACOS_X64}" @@ -93,14 +76,6 @@ class DeepseekTui < Formula url "${BASE_URL}/codewhale-tui-macos-x64", using: :nounzip sha256 "${SHA_TUI_MACOS_X64}" end - resource "legacy-shim" do - url "${BASE_URL}/deepseek-macos-x64", using: :nounzip - sha256 "${SHA_LEG_MACOS_X64}" - end - resource "legacy-tui-shim" do - url "${BASE_URL}/deepseek-tui-macos-x64", using: :nounzip - sha256 "${SHA_LEG_TUI_MACOS_X64}" - end end end @@ -112,14 +87,6 @@ class DeepseekTui < Formula url "${BASE_URL}/codewhale-tui-linux-arm64", using: :nounzip sha256 "${SHA_TUI_LINUX_ARM}" end - resource "legacy-shim" do - url "${BASE_URL}/deepseek-linux-arm64", using: :nounzip - sha256 "${SHA_LEG_LINUX_ARM}" - end - resource "legacy-tui-shim" do - url "${BASE_URL}/deepseek-tui-linux-arm64", using: :nounzip - sha256 "${SHA_LEG_TUI_LINUX_ARM}" - end else url "${BASE_URL}/codewhale-linux-x64", using: :nounzip sha256 "${SHA_COD_LINUX_X64}" @@ -127,22 +94,12 @@ class DeepseekTui < Formula url "${BASE_URL}/codewhale-tui-linux-x64", using: :nounzip sha256 "${SHA_TUI_LINUX_X64}" end - resource "legacy-shim" do - url "${BASE_URL}/deepseek-linux-x64", using: :nounzip - sha256 "${SHA_LEG_LINUX_X64}" - end - resource "legacy-tui-shim" do - url "${BASE_URL}/deepseek-tui-linux-x64", using: :nounzip - sha256 "${SHA_LEG_TUI_LINUX_X64}" - end end end def install bin.install Dir["*"].first => "codewhale" resource("tui").stage { bin.install Dir["*"].first => "codewhale-tui" } - resource("legacy-shim").stage { bin.install Dir["*"].first => "deepseek" } - resource("legacy-tui-shim").stage { bin.install Dir["*"].first => "deepseek-tui" } end test do diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 2e1fe653..28302a20 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -159,48 +159,6 @@ jobs: target: x86_64-pc-windows-msvc binary: codewhale-tui.exe artifact_name: codewhale-tui-windows-x64.exe - # --- deepseek (legacy dispatcher shim; compatibility-only) --- - - os: ubuntu-latest - target: x86_64-unknown-linux-gnu - binary: deepseek - artifact_name: deepseek-linux-x64 - - os: ubuntu-latest - target: aarch64-unknown-linux-gnu - binary: deepseek - artifact_name: deepseek-linux-arm64 - - os: macos-latest - target: x86_64-apple-darwin - binary: deepseek - artifact_name: deepseek-macos-x64 - - os: macos-latest - target: aarch64-apple-darwin - binary: deepseek - artifact_name: deepseek-macos-arm64 - - os: windows-latest - target: x86_64-pc-windows-msvc - binary: deepseek.exe - artifact_name: deepseek-windows-x64.exe - # --- deepseek-tui (legacy TUI shim; compatibility-only) --- - - os: ubuntu-latest - target: x86_64-unknown-linux-gnu - binary: deepseek-tui - artifact_name: deepseek-tui-linux-x64 - - os: ubuntu-latest - target: aarch64-unknown-linux-gnu - binary: deepseek-tui - artifact_name: deepseek-tui-linux-arm64 - - os: macos-latest - target: x86_64-apple-darwin - binary: deepseek-tui - artifact_name: deepseek-tui-macos-x64 - - os: macos-latest - target: aarch64-apple-darwin - binary: deepseek-tui - artifact_name: deepseek-tui-macos-arm64 - - os: windows-latest - target: x86_64-pc-windows-msvc - binary: deepseek-tui.exe - artifact_name: deepseek-tui-windows-x64.exe runs-on: ${{ matrix.os }} steps: - uses: actions/checkout@v4 @@ -504,8 +462,6 @@ jobs: - uses: actions/download-artifact@v4 with: path: artifacts - # Match both the canonical `codewhale*` artifacts and the legacy - # `deepseek*` shim artifacts that ship for the transition release. pattern: '*' - name: Generate Windows npm launcher asset shell: bash @@ -537,11 +493,6 @@ jobs: base="$(basename "${file}")" printf '%s %s\n' "${hash}" "${base}" >> "${manifest}" done < <(find artifacts -type f ! -path 'artifacts/checksums/*' -print0 | sort -z) - # Legacy alias manifest so v0.8.40 `deepseek update` clients can - # still find a manifest by their hardcoded name. Same content as the - # canonical manifest; retire it only with an explicit release-infra - # cutover that also removes the legacy shim artifacts. - cp "${manifest}" "artifacts/checksums/deepseek-artifacts-sha256.txt" cat "${manifest}" - uses: softprops/action-gh-release@v1 with: @@ -632,8 +583,6 @@ jobs: shasum -a 256 -c codewhale-artifacts-sha256.txt ``` - The legacy `deepseek-artifacts-sha256.txt` is also attached for backward compatibility and contains the same hashes as the canonical manifest. - ## Contributors Thanks to @sximelon, @cyq1017, @Artenx, @LHqweasd, @wywsoor, @@ -679,13 +628,13 @@ jobs: run: | gh release download ${{ needs.resolve.outputs.tag }} \ --repo ${{ github.repository }} \ - --pattern 'deepseek-artifacts-sha256.txt' \ + --pattern 'codewhale-artifacts-sha256.txt' \ --dir /tmp - name: Update Homebrew tap if: steps.homebrew-token.outputs.available == 'true' env: TAG: ${{ needs.resolve.outputs.tag }} - MANIFEST: /tmp/deepseek-artifacts-sha256.txt + MANIFEST: /tmp/codewhale-artifacts-sha256.txt TAP_REPO: Hmbown/homebrew-deepseek-tui TOKEN: ${{ secrets.HOMEBREW_TAP_PAT || secrets.RELEASE_TAG_PAT }} run: bash .github/scripts/update-homebrew-tap.sh diff --git a/CHANGELOG.md b/CHANGELOG.md index 88352df9..e5998cad 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.9.0] - 2026-06-07 + ### Added - Added `/restore list [N]` so users can inspect more side-git rollback @@ -233,6 +235,16 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Changed +- Removed the deprecated `deepseek` and `deepseek-tui` binary shims from the + v0.9.0 Cargo crates and GitHub release artifact matrix. The canonical + `codewhale`, `codew`, and `codewhale-tui` entry points remain, the private + deprecated `npm/deepseek-tui` notice package stays unpublished, and DeepSeek + provider/model/env/config compatibility remains first-class. +- Command-adjacent config persistence and auto model routing now live in + neutral TUI modules instead of command-owned files, reducing command-boundary + coupling while preserving current `/config`, `/model`, UI, runtime, and + sub-agent behavior (#2871). Thanks @aboimpinto for landing this first staged + command-boundary layer from the broader #2851/#2791 design direction. - `/config` now reports the canonical `~/.codewhale/settings.toml` path for TUI settings while still reading legacy DeepSeek-branded settings fallbacks and migrating them into the CodeWhale home on load. @@ -407,6 +419,8 @@ HarmonyOS/OpenHarmony port and MatePad Edge validation trail (#2634), #2867), **@reidliu41** for the hotbar action-registry foundation (#2866), and **@ljm3790865** for the multi-tab core/persistence foundation and broader collaboration direction (#2864, #2753), +**@aboimpinto** for the direct command-support boundary cleanup in #2871 and +the broader #2851/#2791 command-layer design direction, **@idling11** for the PlanArtifact direction in Plan mode (#2733), the dense tool-call transcript collapse/sidebar detail direction (#2738, #2734, #2692, #2694), and the HarnessPosture config model for provider/model posture (#2741, @@ -5836,7 +5850,8 @@ Welcome — and thank you. - Hooks system and config profiles - Example skills and launch assets -[Unreleased]: https://github.com/Hmbown/CodeWhale/compare/v0.8.53...HEAD +[Unreleased]: https://github.com/Hmbown/CodeWhale/compare/v0.9.0...HEAD +[0.9.0]: https://github.com/Hmbown/CodeWhale/compare/v0.8.53...v0.9.0 [0.8.53]: https://github.com/Hmbown/CodeWhale/compare/v0.8.52...v0.8.53 [0.8.52]: https://github.com/Hmbown/CodeWhale/compare/v0.8.51...v0.8.52 [0.8.51]: https://github.com/Hmbown/CodeWhale/compare/v0.8.50...v0.8.51 diff --git a/Cargo.lock b/Cargo.lock index f24db582..f3b55c66 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -770,7 +770,7 @@ checksum = "e9b18233253483ce2f65329a24072ec414db782531bdbb7d0bbc4bd2ce6b7e21" [[package]] name = "codewhale-agent" -version = "0.8.53" +version = "0.9.0" dependencies = [ "codewhale-config", "serde", @@ -778,7 +778,7 @@ dependencies = [ [[package]] name = "codewhale-app-server" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "axum", @@ -804,7 +804,7 @@ dependencies = [ [[package]] name = "codewhale-cli" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "chrono", @@ -832,7 +832,7 @@ dependencies = [ [[package]] name = "codewhale-config" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "codewhale-execpolicy", @@ -846,7 +846,7 @@ dependencies = [ [[package]] name = "codewhale-core" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "chrono", @@ -864,7 +864,7 @@ dependencies = [ [[package]] name = "codewhale-execpolicy" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "codewhale-protocol", @@ -873,7 +873,7 @@ dependencies = [ [[package]] name = "codewhale-hooks" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "async-trait", @@ -887,7 +887,7 @@ dependencies = [ [[package]] name = "codewhale-mcp" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "serde", @@ -896,7 +896,7 @@ dependencies = [ [[package]] name = "codewhale-protocol" -version = "0.8.53" +version = "0.9.0" dependencies = [ "serde", "serde_json", @@ -904,7 +904,7 @@ dependencies = [ [[package]] name = "codewhale-release" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "reqwest", @@ -916,7 +916,7 @@ dependencies = [ [[package]] name = "codewhale-secrets" -version = "0.8.53" +version = "0.9.0" dependencies = [ "dirs", "keyring", @@ -929,7 +929,7 @@ dependencies = [ [[package]] name = "codewhale-state" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "chrono", @@ -941,7 +941,7 @@ dependencies = [ [[package]] name = "codewhale-tools" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "async-trait", @@ -955,7 +955,7 @@ dependencies = [ [[package]] name = "codewhale-tui" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "arboard", @@ -1026,11 +1026,11 @@ dependencies = [ [[package]] name = "codewhale-tui-core" -version = "0.8.53" +version = "0.9.0" [[package]] name = "codewhale-whaleflow" -version = "0.8.53" +version = "0.9.0" dependencies = [ "anyhow", "serde", diff --git a/Cargo.toml b/Cargo.toml index 8efbeb9a..7af93959 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -21,7 +21,7 @@ default-members = ["crates/cli", "crates/app-server", "crates/tui"] resolver = "2" [workspace.package] -version = "0.8.53" +version = "0.9.0" edition = "2024" # Rust 1.88 stabilized `let_chains` in `if`/`while` conditions, which the # codebase relies on extensively. Cargo enforces this so users on older diff --git a/crates/agent/Cargo.toml b/crates/agent/Cargo.toml index 5e563534..0b4c3b93 100644 --- a/crates/agent/Cargo.toml +++ b/crates/agent/Cargo.toml @@ -7,5 +7,5 @@ repository.workspace = true description = "Model/provider registry and fallback strategy for DeepSeek workspace architecture" [dependencies] -codewhale-config = { path = "../config", version = "0.8.53" } +codewhale-config = { path = "../config", version = "0.9.0" } serde.workspace = true diff --git a/crates/app-server/Cargo.toml b/crates/app-server/Cargo.toml index 39e37022..f420c36d 100644 --- a/crates/app-server/Cargo.toml +++ b/crates/app-server/Cargo.toml @@ -10,15 +10,15 @@ description = "Codex-style app-server transport for DeepSeek workspace architect anyhow.workspace = true axum.workspace = true clap.workspace = true -codewhale-agent = { path = "../agent", version = "0.8.53" } -codewhale-config = { path = "../config", version = "0.8.53" } -codewhale-core = { path = "../core", version = "0.8.53" } -codewhale-execpolicy = { path = "../execpolicy", version = "0.8.53" } -codewhale-hooks = { path = "../hooks", version = "0.8.53" } -codewhale-mcp = { path = "../mcp", version = "0.8.53" } -codewhale-protocol = { path = "../protocol", version = "0.8.53" } -codewhale-state = { path = "../state", version = "0.8.53" } -codewhale-tools = { path = "../tools", version = "0.8.53" } +codewhale-agent = { path = "../agent", version = "0.9.0" } +codewhale-config = { path = "../config", version = "0.9.0" } +codewhale-core = { path = "../core", version = "0.9.0" } +codewhale-execpolicy = { path = "../execpolicy", version = "0.9.0" } +codewhale-hooks = { path = "../hooks", version = "0.9.0" } +codewhale-mcp = { path = "../mcp", version = "0.9.0" } +codewhale-protocol = { path = "../protocol", version = "0.9.0" } +codewhale-state = { path = "../state", version = "0.9.0" } +codewhale-tools = { path = "../tools", version = "0.9.0" } serde.workspace = true serde_json.workspace = true rustls.workspace = true diff --git a/crates/cli/Cargo.toml b/crates/cli/Cargo.toml index f567b79b..0c33cc84 100644 --- a/crates/cli/Cargo.toml +++ b/crates/cli/Cargo.toml @@ -15,24 +15,18 @@ path = "src/main.rs" name = "codew" path = "src/bin/codew_legacy_shim.rs" -# Legacy alias — forwards to `codewhale` and prints a deprecation notice. -# Will be removed in v0.9.0. -[[bin]] -name = "deepseek" -path = "src/bin/deepseek_legacy_shim.rs" - [dependencies] anyhow.workspace = true clap.workspace = true clap_complete.workspace = true -codewhale-agent = { path = "../agent", version = "0.8.53" } -codewhale-app-server = { path = "../app-server", version = "0.8.53" } -codewhale-config = { path = "../config", version = "0.8.53" } -codewhale-execpolicy = { path = "../execpolicy", version = "0.8.53" } -codewhale-mcp = { path = "../mcp", version = "0.8.53" } -codewhale-release = { path = "../release", version = "0.8.53" } -codewhale-secrets = { path = "../secrets", version = "0.8.53" } -codewhale-state = { path = "../state", version = "0.8.53" } +codewhale-agent = { path = "../agent", version = "0.9.0" } +codewhale-app-server = { path = "../app-server", version = "0.9.0" } +codewhale-config = { path = "../config", version = "0.9.0" } +codewhale-execpolicy = { path = "../execpolicy", version = "0.9.0" } +codewhale-mcp = { path = "../mcp", version = "0.9.0" } +codewhale-release = { path = "../release", version = "0.9.0" } +codewhale-secrets = { path = "../secrets", version = "0.9.0" } +codewhale-state = { path = "../state", version = "0.9.0" } chrono.workspace = true dirs.workspace = true serde.workspace = true diff --git a/crates/cli/src/bin/deepseek_legacy_shim.rs b/crates/cli/src/bin/deepseek_legacy_shim.rs deleted file mode 100644 index abd00896..00000000 --- a/crates/cli/src/bin/deepseek_legacy_shim.rs +++ /dev/null @@ -1,61 +0,0 @@ -//! Legacy `deepseek` alias. -//! -//! Forwards argv to the `codewhale` dispatcher and prints a one-line -//! deprecation notice to stderr on each invocation. This binary exists -//! for one release cycle to give existing installs a smooth path to the -//! new name; it will be removed in v0.9.0. See `docs/REBRAND.md` for the -//! full migration story. - -use std::env; -use std::process::Command; - -fn main() { - eprintln!( - "warning: `deepseek` is deprecated; run `codewhale` instead. \ - This alias will be removed in v0.9.0." - ); - let args: Vec = env::args_os() - .skip(1) - .map(|a| a.to_string_lossy().into_owned()) - .collect(); - - let status = match spawn_codewhale(&args) { - Ok(s) => s, - Err(e) => { - eprintln!( - "error: failed to spawn `codewhale`: {e}. Is it on PATH? \ - Install with `cargo install codewhale-cli` or via npm/Homebrew." - ); - std::process::exit(127); - } - }; - std::process::exit(status.code().unwrap_or(1)); -} - -fn spawn_codewhale(args: &[String]) -> std::io::Result { - // Try PATH first. - match Command::new("codewhale").args(args).status() { - Ok(s) => return Ok(s), - Err(e) if e.kind() == std::io::ErrorKind::NotFound => {} - Err(e) => return Err(e), - } - - // On Windows, after an update the sibling `codewhale.exe` may be in the - // same directory as this shim but not on PATH (#2006). - #[cfg(windows)] - { - if let Ok(exe_path) = env::current_exe() - && let Some(dir) = exe_path.parent() - { - let sibling = dir.join("codewhale.exe"); - if sibling.is_file() { - return Command::new(sibling).args(args).status(); - } - } - } - - Err(std::io::Error::new( - std::io::ErrorKind::NotFound, - "codewhale not found on PATH or in sibling directory", - )) -} diff --git a/crates/config/Cargo.toml b/crates/config/Cargo.toml index 034f988f..5e99e8b5 100644 --- a/crates/config/Cargo.toml +++ b/crates/config/Cargo.toml @@ -8,8 +8,8 @@ description = "Config schema and precedence model for DeepSeek workspace archite [dependencies] anyhow.workspace = true -codewhale-execpolicy = { path = "../execpolicy", version = "0.8.53" } -codewhale-secrets = { path = "../secrets", version = "0.8.53" } +codewhale-execpolicy = { path = "../execpolicy", version = "0.9.0" } +codewhale-secrets = { path = "../secrets", version = "0.9.0" } dirs.workspace = true serde.workspace = true serde_json.workspace = true diff --git a/crates/core/Cargo.toml b/crates/core/Cargo.toml index b8a5cb56..26c9400c 100644 --- a/crates/core/Cargo.toml +++ b/crates/core/Cargo.toml @@ -9,13 +9,13 @@ description = "Core runtime boundaries for DeepSeek workspace architecture" [dependencies] anyhow.workspace = true chrono.workspace = true -codewhale-agent = { path = "../agent", version = "0.8.53" } -codewhale-config = { path = "../config", version = "0.8.53" } -codewhale-execpolicy = { path = "../execpolicy", version = "0.8.53" } -codewhale-hooks = { path = "../hooks", version = "0.8.53" } -codewhale-mcp = { path = "../mcp", version = "0.8.53" } -codewhale-protocol = { path = "../protocol", version = "0.8.53" } -codewhale-state = { path = "../state", version = "0.8.53" } -codewhale-tools = { path = "../tools", version = "0.8.53" } +codewhale-agent = { path = "../agent", version = "0.9.0" } +codewhale-config = { path = "../config", version = "0.9.0" } +codewhale-execpolicy = { path = "../execpolicy", version = "0.9.0" } +codewhale-hooks = { path = "../hooks", version = "0.9.0" } +codewhale-mcp = { path = "../mcp", version = "0.9.0" } +codewhale-protocol = { path = "../protocol", version = "0.9.0" } +codewhale-state = { path = "../state", version = "0.9.0" } +codewhale-tools = { path = "../tools", version = "0.9.0" } serde_json.workspace = true uuid.workspace = true diff --git a/crates/execpolicy/Cargo.toml b/crates/execpolicy/Cargo.toml index dfe0d1bb..8049523a 100644 --- a/crates/execpolicy/Cargo.toml +++ b/crates/execpolicy/Cargo.toml @@ -8,5 +8,5 @@ description = "Execution policy and approval model parity for DeepSeek workspace [dependencies] anyhow.workspace = true -codewhale-protocol = { path = "../protocol", version = "0.8.53" } +codewhale-protocol = { path = "../protocol", version = "0.9.0" } serde.workspace = true diff --git a/crates/hooks/Cargo.toml b/crates/hooks/Cargo.toml index 3083a3b3..c0e47730 100644 --- a/crates/hooks/Cargo.toml +++ b/crates/hooks/Cargo.toml @@ -10,7 +10,7 @@ description = "Hook dispatch and notifications parity for DeepSeek workspace arc anyhow.workspace = true async-trait.workspace = true chrono.workspace = true -codewhale-protocol = { path = "../protocol", version = "0.8.53" } +codewhale-protocol = { path = "../protocol", version = "0.9.0" } reqwest.workspace = true serde.workspace = true serde_json.workspace = true diff --git a/crates/tools/Cargo.toml b/crates/tools/Cargo.toml index fc65af8d..02dacc73 100644 --- a/crates/tools/Cargo.toml +++ b/crates/tools/Cargo.toml @@ -9,7 +9,7 @@ description = "Tool invocation lifecycle, schema validation, and scheduler paral [dependencies] anyhow.workspace = true async-trait.workspace = true -codewhale-protocol = { path = "../protocol", version = "0.8.53" } +codewhale-protocol = { path = "../protocol", version = "0.9.0" } serde.workspace = true serde_json.workspace = true thiserror.workspace = true diff --git a/crates/tui/CHANGELOG.md b/crates/tui/CHANGELOG.md index 88352df9..e5998cad 100644 --- a/crates/tui/CHANGELOG.md +++ b/crates/tui/CHANGELOG.md @@ -7,6 +7,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ## [Unreleased] +## [0.9.0] - 2026-06-07 + ### Added - Added `/restore list [N]` so users can inspect more side-git rollback @@ -233,6 +235,16 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0 ### Changed +- Removed the deprecated `deepseek` and `deepseek-tui` binary shims from the + v0.9.0 Cargo crates and GitHub release artifact matrix. The canonical + `codewhale`, `codew`, and `codewhale-tui` entry points remain, the private + deprecated `npm/deepseek-tui` notice package stays unpublished, and DeepSeek + provider/model/env/config compatibility remains first-class. +- Command-adjacent config persistence and auto model routing now live in + neutral TUI modules instead of command-owned files, reducing command-boundary + coupling while preserving current `/config`, `/model`, UI, runtime, and + sub-agent behavior (#2871). Thanks @aboimpinto for landing this first staged + command-boundary layer from the broader #2851/#2791 design direction. - `/config` now reports the canonical `~/.codewhale/settings.toml` path for TUI settings while still reading legacy DeepSeek-branded settings fallbacks and migrating them into the CodeWhale home on load. @@ -407,6 +419,8 @@ HarmonyOS/OpenHarmony port and MatePad Edge validation trail (#2634), #2867), **@reidliu41** for the hotbar action-registry foundation (#2866), and **@ljm3790865** for the multi-tab core/persistence foundation and broader collaboration direction (#2864, #2753), +**@aboimpinto** for the direct command-support boundary cleanup in #2871 and +the broader #2851/#2791 command-layer design direction, **@idling11** for the PlanArtifact direction in Plan mode (#2733), the dense tool-call transcript collapse/sidebar detail direction (#2738, #2734, #2692, #2694), and the HarnessPosture config model for provider/model posture (#2741, @@ -5836,7 +5850,8 @@ Welcome — and thank you. - Hooks system and config profiles - Example skills and launch assets -[Unreleased]: https://github.com/Hmbown/CodeWhale/compare/v0.8.53...HEAD +[Unreleased]: https://github.com/Hmbown/CodeWhale/compare/v0.9.0...HEAD +[0.9.0]: https://github.com/Hmbown/CodeWhale/compare/v0.8.53...v0.9.0 [0.8.53]: https://github.com/Hmbown/CodeWhale/compare/v0.8.52...v0.8.53 [0.8.52]: https://github.com/Hmbown/CodeWhale/compare/v0.8.51...v0.8.52 [0.8.51]: https://github.com/Hmbown/CodeWhale/compare/v0.8.50...v0.8.51 diff --git a/crates/tui/Cargo.toml b/crates/tui/Cargo.toml index 9fca03ca..c4efe10e 100644 --- a/crates/tui/Cargo.toml +++ b/crates/tui/Cargo.toml @@ -18,19 +18,13 @@ toml = ["schemaui/toml"] name = "codewhale-tui" path = "src/main.rs" -# Legacy alias — forwards to `codewhale-tui` and prints a deprecation -# notice. Will be removed in v0.9.0. -[[bin]] -name = "deepseek-tui" -path = "src/bin/deepseek_tui_legacy_shim.rs" - [dependencies] anyhow = "1.0.100" -codewhale-config = { path = "../config", version = "0.8.53" } -codewhale-protocol = { path = "../protocol", version = "0.8.53" } -codewhale-release = { path = "../release", version = "0.8.53" } -codewhale-secrets = { path = "../secrets", version = "0.8.53" } -codewhale-tools = { path = "../tools", version = "0.8.53" } +codewhale-config = { path = "../config", version = "0.9.0" } +codewhale-protocol = { path = "../protocol", version = "0.9.0" } +codewhale-release = { path = "../release", version = "0.9.0" } +codewhale-secrets = { path = "../secrets", version = "0.9.0" } +codewhale-tools = { path = "../tools", version = "0.9.0" } schemaui = { version = "0.12.0", default-features = false, optional = true } async-stream = "0.3.6" async-trait = "0.1" diff --git a/crates/tui/build.rs b/crates/tui/build.rs index 722139a9..111bbc5c 100644 --- a/crates/tui/build.rs +++ b/crates/tui/build.rs @@ -121,11 +121,9 @@ fn configure_windows_stack() { match std::env::var("CARGO_CFG_TARGET_ENV").as_deref() { Ok("msvc") => { println!("cargo:rustc-link-arg-bin=codewhale-tui=/STACK:8388608"); - println!("cargo:rustc-link-arg-bin=deepseek-tui=/STACK:8388608"); } Ok("gnu") => { println!("cargo:rustc-link-arg-bin=codewhale-tui=-Wl,--stack,8388608"); - println!("cargo:rustc-link-arg-bin=deepseek-tui=-Wl,--stack,8388608"); } _ => {} } diff --git a/crates/tui/src/bin/deepseek_tui_legacy_shim.rs b/crates/tui/src/bin/deepseek_tui_legacy_shim.rs deleted file mode 100644 index 2e36db97..00000000 --- a/crates/tui/src/bin/deepseek_tui_legacy_shim.rs +++ /dev/null @@ -1,32 +0,0 @@ -//! Legacy `deepseek-tui` alias. -//! -//! Forwards argv to the `codewhale-tui` runtime and prints a one-line -//! deprecation notice to stderr on each invocation. This binary exists -//! for one release cycle to give existing installs a smooth path to the -//! new name; it will be removed in v0.9.0. See `docs/REBRAND.md` for the -//! full migration story. - -use std::env; -use std::process::Command; - -fn main() { - eprintln!( - "warning: `deepseek-tui` is deprecated; run `codewhale-tui` (or `codewhale`) instead. \ - This alias will be removed in v0.9.0." - ); - let args: Vec = env::args_os() - .skip(1) - .map(|a| a.to_string_lossy().into_owned()) - .collect(); - let status = match Command::new("codewhale-tui").args(&args).status() { - Ok(s) => s, - Err(e) => { - eprintln!( - "error: failed to spawn `codewhale-tui`: {e}. Is it on PATH? \ - Install with `cargo install codewhale-tui` or via npm/Homebrew." - ); - std::process::exit(127); - } - }; - std::process::exit(status.code().unwrap_or(1)); -} diff --git a/crates/tui/src/prompts.rs b/crates/tui/src/prompts.rs index 1e8136b9..07c58793 100644 --- a/crates/tui/src/prompts.rs +++ b/crates/tui/src/prompts.rs @@ -2739,7 +2739,12 @@ mod tests { // Working-set metadata is now injected into the latest user message // per turn. The legacy argument remains for call-site compatibility // but must not reintroduce volatile bytes into the system prompt. + let _env_guard = crate::test_support::lock_test_env(); let tmp = tempdir().expect("tempdir"); + let home_tmp = tempdir().expect("home tempdir"); + let _home = EnvVarGuard::set("HOME", home_tmp.path().as_os_str()); + let _userprofile = EnvVarGuard::set("USERPROFILE", home_tmp.path().as_os_str()); + let _skills_dir = EnvVarGuard::remove("DEEPSEEK_SKILLS_DIR"); let workspace = tmp.path(); let summary = "## Repo Working Set\nWorkspace: /tmp/x\n"; @@ -2770,7 +2775,12 @@ mod tests { // rendered prompt must produce identical bytes. The relay block // lands below the static boundary in // `system_prompt_for_mode_with_context_and_skills`. + let _env_guard = crate::test_support::lock_test_env(); let tmp = tempdir().expect("tempdir"); + let home_tmp = tempdir().expect("home tempdir"); + let _home = EnvVarGuard::set("HOME", home_tmp.path().as_os_str()); + let _userprofile = EnvVarGuard::set("USERPROFILE", home_tmp.path().as_os_str()); + let _skills_dir = EnvVarGuard::remove("DEEPSEEK_SKILLS_DIR"); let workspace = tmp.path(); let handoff_dir = workspace.join(".deepseek"); std::fs::create_dir_all(&handoff_dir).unwrap(); diff --git a/crates/tui/src/tui/tab/benches.rs b/crates/tui/src/tui/tab/benches.rs index 3c63650f..103ef60a 100644 --- a/crates/tui/src/tui/tab/benches.rs +++ b/crates/tui/src/tui/tab/benches.rs @@ -14,7 +14,7 @@ //! - Persistence save/load (startup + shutdown overhead) //! - Group color rendering (per-frame work in tab bar) -#![allow(unused_imports)] +#![allow(unused_imports, clippy::module_inception, clippy::print_stderr)] #[cfg(test)] mod benches { diff --git a/crates/tui/src/tui/tab/delegator.rs b/crates/tui/src/tui/tab/delegator.rs index 9b88557b..10df3b9d 100644 --- a/crates/tui/src/tui/tab/delegator.rs +++ b/crates/tui/src/tui/tab/delegator.rs @@ -406,7 +406,7 @@ mod tests { let results_to = delegator.results_for_tab(to); assert_eq!(results_to.len(), 1); - assert_eq!(results_to[0].was_successful, true); + assert!(results_to[0].was_successful); } #[test] diff --git a/crates/tui/src/tui/tab/group.rs b/crates/tui/src/tui/tab/group.rs index 14095dce..e61fb1d0 100644 --- a/crates/tui/src/tui/tab/group.rs +++ b/crates/tui/src/tui/tab/group.rs @@ -356,7 +356,7 @@ mod tests { mgr.delete_group(&g1); assert!(mgr.group_of(tab1).is_none()); - assert!(mgr.tab_to_group.get(&tab1).is_none()); + assert!(!mgr.tab_to_group.contains_key(&tab1)); } #[test] diff --git a/crates/tui/src/tui/tab/key_e2e.rs b/crates/tui/src/tui/tab/key_e2e.rs index dbd9098d..d80d4f9c 100644 --- a/crates/tui/src/tui/tab/key_e2e.rs +++ b/crates/tui/src/tui/tab/key_e2e.rs @@ -212,11 +212,11 @@ mod tests { manager.switch_to_by_id(to); // Press Ctrl+Shift+D 4 times - assert_eq!(simulate_process_delegation(&mut manager).is_some(), true); - assert_eq!(simulate_process_delegation(&mut manager).is_some(), true); - assert_eq!(simulate_process_delegation(&mut manager).is_some(), true); + assert!(simulate_process_delegation(&mut manager).is_some()); + assert!(simulate_process_delegation(&mut manager).is_some()); + assert!(simulate_process_delegation(&mut manager).is_some()); // 4th should be the last task - assert_eq!(simulate_process_delegation(&mut manager).is_some(), true); + assert!(simulate_process_delegation(&mut manager).is_some()); // 5th should be none assert_eq!(simulate_process_delegation(&mut manager), None); } diff --git a/crates/tui/src/tui/tab/mention.rs b/crates/tui/src/tui/tab/mention.rs index eadfb2d4..733305a7 100644 --- a/crates/tui/src/tui/tab/mention.rs +++ b/crates/tui/src/tui/tab/mention.rs @@ -210,7 +210,7 @@ mod tests { #[test] fn test_resolve_tab_mention() { // Tab IDs in the visual order they appear in the tab bar. - let tab_ids = vec![100, 50, 200]; + let tab_ids = [100, 50, 200]; // Tab 1 = first in visual order (100) assert_eq!(resolve_tab_mention(1, tab_ids.iter()), Some(100)); // Tab 2 = second in visual order (50) diff --git a/crates/tui/tests/support/qa_harness/harness.rs b/crates/tui/tests/support/qa_harness/harness.rs index 3ebda0fa..a32b4c7b 100644 --- a/crates/tui/tests/support/qa_harness/harness.rs +++ b/crates/tui/tests/support/qa_harness/harness.rs @@ -226,12 +226,6 @@ impl Harness { { return PathBuf::from(path); } - // Legacy fallback for callers still referencing the old bin name. - if name == "codewhale-tui" - && let Some(path) = option_env!("CARGO_BIN_EXE_deepseek-tui") - { - return PathBuf::from(path); - } panic!("env {key} not set; is the binary declared in this crate?") } diff --git a/docs/REBRAND.md b/docs/REBRAND.md index f3b25a0e..71360955 100644 --- a/docs/REBRAND.md +++ b/docs/REBRAND.md @@ -69,10 +69,10 @@ Anything that targets the DeepSeek provider API stays exactly as it was: Docker, or direct downloads. - **Docker image**: `ghcr.io/hmbown/codewhale`. -## Deprecation shims (through v0.8.x) +## Deprecation shims (removed in v0.9.0) To keep existing shell aliases, scripts, and CI working through the rename, -v0.8.41 and later v0.8.x releases ship **deprecation shims**: +v0.8.41 and later v0.8.x releases shipped **deprecation shims**: - A `deepseek` binary that prints a one-line warning to stderr and forwards argv to `codewhale`. @@ -80,7 +80,9 @@ v0.8.41 and later v0.8.x releases ship **deprecation shims**: - The legacy `deepseek-tui` npm package is deprecated and no longer receives new releases. Install the `codewhale` npm package instead. -These shims will be removed in **v0.9.0**. Please migrate before then. +These binary shims are removed in **v0.9.0**. DeepSeek provider support, model +IDs, `DEEPSEEK_*` environment variables, and legacy `~/.deepseek/` state +fallbacks remain supported. ## Migrating in practice @@ -114,15 +116,12 @@ downloads until the formula and tap repo are renamed. ### Manual / GitHub Releases -`v0.8.41` Releases attach **both** the canonical `codewhale-*` / -`codewhale-tui-*` assets and the legacy `deepseek-*` / `deepseek-tui-*` -shim assets. Existing `deepseek update` invocations on v0.8.40 keep working; -they land you on the deprecation shim, which then prompts the install of -`codewhale`. - -A second checksum manifest, `deepseek-artifacts-sha256.txt`, is attached as -an alias of `codewhale-artifacts-sha256.txt` so v0.8.40's hardcoded lookup -still verifies. +`v0.8.41` through `v0.8.x` Releases attached both the canonical +`codewhale-*` / `codewhale-tui-*` assets and compatibility-only +`deepseek-*` / `deepseek-tui-*` shim assets. Starting in v0.9.0, Releases attach +only the canonical `codewhale-*` / `codewhale-tui-*` assets and the canonical +`codewhale-artifacts-sha256.txt` checksum manifest. Install or update through +`codewhale` before moving to v0.9.0. ### Sessions, skills, and manual workspaces diff --git a/npm/codewhale/package.json b/npm/codewhale/package.json index a94e99a2..f8222ee0 100644 --- a/npm/codewhale/package.json +++ b/npm/codewhale/package.json @@ -1,7 +1,7 @@ { "name": "codewhale", - "version": "0.8.53", - "codewhaleBinaryVersion": "0.8.53", + "version": "0.9.0", + "codewhaleBinaryVersion": "0.9.0", "description": "Install and run CodeWhale, the agentic terminal for DeepSeek and other OpenAI-compatible coding models.", "author": "Hmbown", "license": "MIT", diff --git a/npm/deepseek-tui/README.md b/npm/deepseek-tui/README.md index 898ae530..8259848e 100644 --- a/npm/deepseek-tui/README.md +++ b/npm/deepseek-tui/README.md @@ -8,9 +8,9 @@ npm install -g codewhale ``` This legacy npm package is deprecated and receives no further releases. -`codewhale` ships the canonical `codewhale` and `codewhale-tui` binaries, plus -compatibility-only deprecation shims under the old `deepseek` / -`deepseek-tui` binary names for v0.8.x. +`codewhale` ships the canonical `codewhale`, `codew`, and `codewhale-tui` +binaries. Compatibility-only deprecation shims under the old `deepseek` / +`deepseek-tui` binary names were available in v0.8.x and are removed in v0.9.0. See [docs/REBRAND.md](https://github.com/Hmbown/CodeWhale/blob/main/docs/REBRAND.md) for the full migration story.