From 1841b1fabd554e32d6373305d71a487f37b34636 Mon Sep 17 00:00:00 2001 From: Paul O'Fallon Date: Fri, 31 Jul 2026 11:57:42 -0400 Subject: [PATCH 1/2] chore(ai-clis): order after uv-providing features MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit specifyCli installs via uv, and install.sh self-provisions uv when it is absent. Nothing ordered that against features that also install uv, so ai-clis could run first, run the Astral installer, and then have its uv overwritten by python-tools moments later — wasted work and a nondeterministic build. installsAfter is the right knob rather than dependsOn: dependsOn is a hard, auto-installing dependency and cannot be conditioned on option values, so it would force uv into every container using this feature, including the ones that omit specifyCli. installsAfter only reorders features the user already selected and is inert otherwise. Co-Authored-By: Claude Opus 5 --- src/ai-clis/README.md | 2 ++ src/ai-clis/devcontainer-feature.json | 6 +++++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/src/ai-clis/README.md b/src/ai-clis/README.md index da6d29b..de053ca 100644 --- a/src/ai-clis/README.md +++ b/src/ai-clis/README.md @@ -69,3 +69,5 @@ Use `install` to list exactly the CLIs you need — new CLIs added in future rel ``` **Requires:** Node.js (installs after `ghcr.io/devcontainers/features/node`) + +**uv:** `specifyCli` installs via [uv](https://docs.astral.sh/uv/). This feature installs uv itself if it isn't already present, so no extra feature is required. If you do include a uv-providing feature — this repo's `python-tools`, or one of the community `uv` features — it is ordered first via `installsAfter` and reused, avoiding a duplicate install. diff --git a/src/ai-clis/devcontainer-feature.json b/src/ai-clis/devcontainer-feature.json index ee8a7d5..97727f4 100644 --- a/src/ai-clis/devcontainer-feature.json +++ b/src/ai-clis/devcontainer-feature.json @@ -17,6 +17,10 @@ } }, "installsAfter": [ - "ghcr.io/devcontainers/features/node" + "ghcr.io/devcontainers/features/node", + "ghcr.io/get2knowio/devcontainer-features/python-tools", + "ghcr.io/va-h/devcontainers-features/uv", + "ghcr.io/jsburckhardt/devcontainer-features/uv", + "ghcr.io/gvatsal60/dev-container-features/uv" ] } From a4640d22988bed14857bd10559d8b5a4b0bb7d89 Mon Sep 17 00:00:00 2001 From: Paul O'Fallon Date: Fri, 31 Jul 2026 12:02:15 -0400 Subject: [PATCH 2/2] ci: give validate the features path so it stops crashing devcontainers/action@v1 defaults base-path-to-features to '', so validate-only scandirs an empty path and dies with ENOENT before reading any metadata. release.yaml already passes ./src; validate.yml never did. This workflow only triggers on src/**/devcontainer-feature.json, and no PR had touched one since early June, so the breakage went unnoticed. Co-Authored-By: Claude Opus 5 --- .github/workflows/validate.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/validate.yml b/.github/workflows/validate.yml index 474619d..b3c2dbb 100644 --- a/.github/workflows/validate.yml +++ b/.github/workflows/validate.yml @@ -16,3 +16,6 @@ jobs: uses: devcontainers/action@v1 with: validate-only: "true" + # Without this the action scandirs '' and crashes with ENOENT before + # reading any metadata. release.yaml passes the same path to publish. + base-path-to-features: "./src"