From 589b9e05737ea45c8f0c827cf8a3486489be4b05 Mon Sep 17 00:00:00 2001 From: Gustavo Lira Date: Tue, 7 Jul 2026 10:34:12 -0300 Subject: [PATCH 1/3] feat: add test-placement skill for the plugin testing strategy (v0.7.0) Centralizes the test-placement skill here instead of duplicating it across rhdh, rhdh-plugins, and rhdh-plugin-export-overlays (supersedes overlays#2726, rhdh#5045, plugins#3670). Given a change, bug, or feature in the RHDH dynamic-plugin ecosystem, the skill proposes the right repo, the right test layer (L1 unit to L4b cluster e2e), the location, and how to scaffold the test. Encodes the RHIDP-13501 per-repo responsibility split and researched dead-ends. Co-Authored-By: Claude Fable 5 --- .claude-plugin/marketplace.json | 4 +- .claude-plugin/plugin.json | 2 +- README.md | 6 ++ pyproject.toml | 2 +- skills/rhdh/SKILL.md | 8 +++ skills/test-placement/SKILL.md | 119 ++++++++++++++++++++++++++++++++ 6 files changed, 137 insertions(+), 4 deletions(-) create mode 100644 skills/test-placement/SKILL.md diff --git a/.claude-plugin/marketplace.json b/.claude-plugin/marketplace.json index 14efd96..f5016f9 100644 --- a/.claude-plugin/marketplace.json +++ b/.claude-plugin/marketplace.json @@ -5,14 +5,14 @@ }, "metadata": { "description": "Orchestrator skill for RHDH plugin development - onboard, update, and maintain plugins in the Extensions Catalog", - "version": "0.6.1" + "version": "0.7.0" }, "plugins": [ { "name": "rhdh", "source": "./", "description": "Skills for RHDH plugin lifecycle management", - "version": "0.6.1", + "version": "0.7.0", "strict": true } ] diff --git a/.claude-plugin/plugin.json b/.claude-plugin/plugin.json index ec8a1cd..f4ba7f1 100644 --- a/.claude-plugin/plugin.json +++ b/.claude-plugin/plugin.json @@ -1,7 +1,7 @@ { "name": "rhdh", "description": "All-in-one toolkit for Red Hat Developer Hub (RHDH). Covers plugin development, overlay management, environment setup, version compatibility, CI/CD, and RHDH ecosystem navigation.", - "version": "0.6.1", + "version": "0.7.0", "author": { "name": "RHDH Store Manager" }, diff --git a/README.md b/README.md index 13766c3..4c54944 100644 --- a/README.md +++ b/README.md @@ -102,6 +102,12 @@ Track work across the four RHDH Jira projects. - **[rhdh-test-plan-review](./skills/rhdh-test-plan-review/SKILL.md)** — Reviews an RHDH test plan Jira ticket and suggests platform/integration version updates based on support lifecycle pages and RHDH release milestones +### Test Placement + +Decide where a test belongs across the RHDH ecosystem — which repo, which layer, and how to scaffold it. + +- **[test-placement](./skills/test-placement/SKILL.md)** — Given a change, bug, or feature, proposes the right repo (`rhdh-plugins` / `rhdh-plugin-export-overlays` / `rhdh`), the right test layer (L1 unit → L4b cluster e2e), the location, and scaffolding steps. Guiding rule: the cheapest environment that catches the bug wins. Encodes the RHIDP-13501 responsibility split and researched dead-ends so devs don't burn time on them. + ### Orchestration - **[rhdh](./skills/rhdh/SKILL.md)** — Entry point and router. Detects your environment, runs `doctor` checks, maintains a cross-session worklog, and routes to the right skill. Start here if you're not sure what you need. diff --git a/pyproject.toml b/pyproject.toml index f76fce1..e50f84b 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -1,6 +1,6 @@ [project] name = "rhdh-skill" -version = "0.6.1" +version = "0.7.0" description = "Claude Code skill for RHDH plugin development" readme = "README.md" license = "Apache-2.0" diff --git a/skills/rhdh/SKILL.md b/skills/rhdh/SKILL.md index 72fd0e3..6425438 100644 --- a/skills/rhdh/SKILL.md +++ b/skills/rhdh/SKILL.md @@ -202,6 +202,14 @@ What would you like to do? **To route:** Read `../backstage-upgrade/SKILL.md` and follow its intake process. +### Test Placement Routes + +| Response | Skill | +|----------|-------| +| "where should I test", "test placement", "does this need a cluster", "which repo does this test belong in", "should this be an e2e test", "test layer" | Route to `test-placement` skill | + +**To route:** Read `../test-placement/SKILL.md` and follow its instructions. + ### General Routes | Response | Action | diff --git a/skills/test-placement/SKILL.md b/skills/test-placement/SKILL.md new file mode 100644 index 0000000..768328c --- /dev/null +++ b/skills/test-placement/SKILL.md @@ -0,0 +1,119 @@ +--- +name: test-placement +description: >- + Propose where to test a change in the RHDH dynamic-plugin ecosystem: which + repo (rhdh-plugins, rhdh-plugin-export-overlays, rhdh), which test layer + (unit, integration, component, cluster-free E2E, cluster E2E), where the + test lives, and how to create it. Use when a developer asks where to test + something, whether a test needs a cluster, or which repo a test belongs in +--- + +# Test Placement Advisor + +Given the context of a change, bug, or new feature in the RHDH dynamic-plugin ecosystem, propose **where** it should be tested: which repository, which test layer, where the test lives, and how to create it. The guiding rule: **pick the cheapest environment that can actually catch the bug — most plugin validation does not need a cluster, and an increasing part doesn't need Docker either.** + +Conventions in this skill: paths are prefixed with the repo they live in — `rhdh:`, `overlays:` (= rhdh-plugin-export-overlays), `plugins:` (= rhdh-plugins). Some harnesses referenced here are **still in review** (see References for PR status). Before recommending a harness or script, verify its path exists on the target repo's `main`; if it doesn't, tell the developer it is pending in the corresponding PR instead of asserting it exists. + +## When to Use + +- A developer asks "where should I test this?", "should this be an e2e test?", "does this need a cluster?", or "which repo does this test belong in?" +- A new plugin, plugin version bump, or plugin config change needs test coverage. +- A bug escaped to a cluster e2e run and the team wants a cheaper regression test. +- Reviewing a PR that adds a test at the wrong layer (e.g. a cluster e2e for pure UI logic). + +## Step 1 — Gather context (ask if missing) + +Before recommending, establish: + +1. **What is being validated?** Plugin logic/UI component · packaging/published artifact · plugin loading/rendering inside RHDH · platform behavior (Helm/Operator/ingress/auth). +2. **Where did the change happen?** Plugin source (`rhdh-plugins` or another source repo) · packaging metadata (`rhdh-plugin-export-overlays`) · the RHDH app itself (`rhdh`). +3. **Does verifying it require a rendered UI?** (clicks, headings, navigation) +4. **Does it require real external services?** (GitHub, Keycloak, LDAP, managed DBs) +5. **Does it require cluster infrastructure?** (ConfigMap reload, routes, operator, pod logs, port-forward) + +## Step 2 — Decision table + +| The dev wants to verify… | Repo | Test type / harness | Cluster? | Docker? | +| --- | --- | --- | --- | --- | +| Plugin logic / components / API | `rhdh-plugins` (or the plugin's source repo) | unit + component tests, dev app (`yarn start`) | no | no | +| The plugin still builds as a dynamic plugin | `rhdh-plugins` | `npx @red-hat-developer-hub/cli plugin export` | no | no | +| The **published OCI artifact** installs and the **backend plugin boots** | `rhdh-plugin-export-overlays` | native smoke harness (`overlays: smoke-tests-native/`) | no | **no** | +| All plugins of a **workspace** boot together | `rhdh-plugin-export-overlays` | native smoke with a `dynamic-plugins.yaml` listing the workspace's `oci://` refs | no | **no** | +| A frontend artifact ships its bundle (`dist-scalprum/`, `plugin-manifest.json`) | `rhdh-plugin-export-overlays` | native smoke presence check | no | **no** | +| The plugin **loads inside the real RHDH app** and the **UI renders** | `rhdh` | cluster-free E2E harness (`rhdh: e2e-tests/playwright.legacy-local.config.ts`, script `e2e:legacy-local`) | no | no | +| Every plugin in the **catalog index** is sane | `rhdh` | catalog-index plugin sanity check (nightly) | no | no | +| RHDH **container** behavior (image entrypoint, install script inside the image) | `rhdh-plugin-export-overlays` (artifacts) / any (manual) | Docker smoke (`overlays: smoke-tests/` + workflow `run-workspace-smoke-tests.yaml`) · manual: [rhdh-local](https://github.com/redhat-developer/rhdh-local) | no | yes | +| Helm chart / Operator / ingress / real Keycloak / RBAC on OCP | `rhdh` e2e or `overlays: workspaces/*/e2e-tests` | cluster e2e | **yes** | n/a (cluster) | + +Rule of thumb: **source bugs → rhdh-plugins · artifact bugs → overlays · integration/render bugs → rhdh · platform bugs → cluster e2e.** If a bug is catchable in more than one place, test it in the cheapest one and don't duplicate downstream. + +## Step 3 — Layer ladder (cheapest that catches the bug wins) + +| Layer | Scope | Tooling | Cluster | Typical time | +| --- | --- | --- | --- | --- | +| **L1** Unit | Pure functions / logic | Jest/Vitest | no | ms–s | +| **L2** Integration | Backend module + plugin API, mocked external deps | `startTestBackend` + supertest | no | s | +| **L3** Component | React component/page with a test harness | RTL + dev server | no | s–min | +| **L4a** E2E cluster-free | Full app, no managed infra | Playwright + local harness | no | min | +| **L4b** E2E full | Real OCP/K8s, managed DBs, real IdPs | Playwright + cluster | **yes** | min–h | + +The full per-spec classification of the RHDH e2e suite lives in `rhdh: docs/e2e-tests/layer-migration-matrix.md` (see References) — consult it before adding or migrating an e2e spec. + +## Step 4 — How to create the test (per placement) + +### `rhdh-plugins` (or other source repo) — plugin correctness + +- **Where:** `plugins: workspaces//plugins//src/**` next to the code, following that workspace's existing test setup (Jest/RTL; MSW for API mocks). +- **How:** copy the pattern of a neighboring `*.test.ts(x)`; run with the workspace's `yarn test`. Manual verification via the workspace dev app (`yarn start`). +- Also validate packaging when the plugin's build config changed: `npx @red-hat-developer-hub/cli plugin export` must produce `dist-dynamic/` (+ `dist-scalprum/` for frontend). +- **Cannot do here:** validate the *published* OCI artifact, or integration with RHDH's app shell/shared deps. + +### `rhdh-plugin-export-overlays` — the published artifact + +- **Where:** the native smoke harness, `overlays: smoke-tests-native/`. It installs plugins from OCI with the real `install-dynamic-plugins` CLI and boots backend plugins via `startTestBackend`. +- **How:** write a `dynamic-plugins.yaml` listing the `oci://` artifact refs to validate (a workspace's refs are the `spec.dynamicArtifact` values in `overlays: workspaces//metadata/*.yaml`), then run `yarn smoke --dynamic-plugins [--out results.json]`. Exit code 0 = pass; non-zero writes `results.json` detailing `fail-load` / `fail-start`. CI: `overlays: .github/workflows/native-smoke.yaml`. +- **Known gaps (don't fight them):** catalog-extending backend modules don't boot in a minimal `startTestBackend` (upstream `catalog-backend` registration issue — stay on the Docker smoke until fixed); plugins whose `dynamicArtifact` is a local `./dynamic-plugins/dist/...` path ship inside the RHDH image and have no OCI artifact to validate here. +- **Never add UI-render tests here** — this repo has no app to render into. Delegate rendering to the `rhdh` cluster-free harness. +- The Docker smoke it replaces (backend scope) lives at `overlays: smoke-tests/` + workflow `run-workspace-smoke-tests.yaml`. +- `overlays: workspaces/*/e2e-tests` (cluster, Playwright + `e2e-test-utils`) exists for plugins whose value *is* cluster integration (topology, tekton, argocd…). Don't add one for UI-only behavior. + +### `rhdh` — the real app + +**L4a cluster-free harness** (config `rhdh: e2e-tests/playwright.legacy-local.config.ts`, docs `rhdh: docs/e2e-tests/local-e2e-harness.md`) — the only cheap place a frontend dynamic plugin can be *rendered*. To enable a spec/test: + +1. Plugin not yet installed by the harness? Add its OCI entry to `rhdh: e2e-tests/local-harness/dynamic-plugins.yaml` (tags on `ghcr.io/redhat-developer/rhdh-plugin-export-overlays/`). If its mount-point config is not in the repo's static `app-config.dynamic-plugins.yaml`, attach the plugin's **canonical `pluginConfig`** (source of truth: `plugins: workspaces//plugins//app-config.dynamic.yaml`) — the harness loads the generated `dynamic-plugins-root/app-config.dynamic-plugins.yaml` last, exactly like the production container. +2. Config that only exists in CI config maps (`rhdh: .ci/pipelines/resources/config_map/*`)? Mirror just the needed keys into `rhdh: app-config.local-e2e.yaml` (objects deep-merge; arrays replace). +3. Tag the test `{ tag: "@cluster-free" }` and add its spec file to the config's `testMatch` allowlist. +4. Repopulate + validate: `./e2e-tests/local-harness/populate.sh`, then `yarn --cwd e2e-tests e2e:legacy-local` (CI runs this in ~4 min). Requires skopeo — preinstalled in CI; on macOS `brew install skopeo`. + +**L4b cluster e2e** (`rhdh: e2e-tests/playwright/e2e/**`) — only when the subject *is* cluster/platform behavior or a real external service. Requirements: `component` annotation in `beforeAll` (see the repo's `ci-e2e-testing` rule), correct config map choice (RBAC vs non-RBAC), project registration in `e2e-tests/playwright/projects.json` if a new project is needed. + +**L3 component tests** — page-level RTL compositions, pattern proposed under RHIDP-13235 in [rhdh#4864](https://github.com/redhat-developer/rhdh/pull/4864) (closed, not merged). Check for merged examples before recommending a concrete template; prefer L3 over L4a when no dynamic-plugin loading is involved. + +**Catalog-index-wide sanity** (nightly, in review — see References) — nothing to write per plugin; it sweeps the whole index. + +## Not possible today (researched — don't burn time) + +- **Rendering a frontend dynamic plugin without an RHDH app** — the artifact is a legacy-frontend Scalprum bundle; no standalone host exists, and building one means maintaining a version-coupled "mini RHDH". +- **`@backstage/frontend-dynamic-feature-loader` for current plugins** — targets the new frontend system (alpha); our exported plugins are legacy-system bundles. Revisit when app-next matures (RHIDP-15082). +- **Catalog-extending modules in a minimal `startTestBackend`** — upstream `catalog-backend` issue (see overlays harness notes). + +## Output format + +Answer with a concrete recommendation: + +- **Repo:** which of the three (or the plugin's own source repo). +- **Layer / harness:** L1–L4b + the specific harness or suite. +- **Location:** the directory/file where the test goes. +- **Scaffolding:** the minimal steps or files to create, referencing an existing neighbor as template. +- **Why not elsewhere:** one line on the layers you rejected (especially if the dev proposed a more expensive one). +- **Cost:** rough feedback time (seconds / ~4 min cluster-free / cluster job). + +## References (status as of 2026-07-07 — verify before citing as merged) + +- Epic **RHIDP-13501** (E2E Test Optimization) — the per-repo responsibility split lives in the epic's comments and its Jira attachment `rhdh-dynamic-plugin-testing-guideline.md` (Jira-only; if unreachable, the decision table above is the summary). +- Layer matrix: — in review in [rhdh#5044](https://github.com/redhat-developer/rhdh/pull/5044) (RHIDP-15076). +- Cluster-free harness + docs: merged in [rhdh#5005](https://github.com/redhat-developer/rhdh/pull/5005) (RHIDP-15075). +- Overlays native smoke: merged in [overlays#2714](https://github.com/redhat-developer/rhdh-plugin-export-overlays/pull/2714). +- Catalog-index sanity check: in review in [rhdh#4967](https://github.com/redhat-developer/rhdh/pull/4967). +- L3 pattern proposal: [rhdh#4864](https://github.com/redhat-developer/rhdh/pull/4864) (closed) under RHIDP-13235. From 091a18810a4ade060ae773dd0891b40499f0536e Mon Sep 17 00:00:00 2001 From: Gustavo Lira Date: Tue, 7 Jul 2026 10:59:41 -0300 Subject: [PATCH 2/3] fix: address PR #58 review feedback - Quote literal trigger phrases in the frontmatter description, matching the nfs-migration/backstage-upgrade convention - Add test-placement to the orchestrator intake menu (item 10) and skills_index; renumber release/general items and routes - Cross-reference skills/rhdh/references/rhdh-repos.md with the standalone-install caveat (backstage-upgrade pattern) - Drop the layer-matrix URL that 404s until rhdh#5044 merges; keep the repo path + PR reference - Remove the hardcoded date from the References header - Add parametrized frontmatter validation for every skills/*/SKILL.md (name matches directory, description within spec limits) Co-Authored-By: Claude Fable 5 --- skills/rhdh/SKILL.md | 35 ++++++++++++++++++------------ skills/test-placement/SKILL.md | 12 +++++----- tests/unit/test_skill_structure.py | 35 ++++++++++++++++++++++++++++++ 3 files changed, 63 insertions(+), 19 deletions(-) diff --git a/skills/rhdh/SKILL.md b/skills/rhdh/SKILL.md index 6425438..9ede658 100644 --- a/skills/rhdh/SKILL.md +++ b/skills/rhdh/SKILL.md @@ -123,16 +123,22 @@ What would you like to do? 9. **Review Test Plan content** — Reviews an RHDH test plan Jira ticket and suggests platform/integration version updates based on support lifecycle pages and RHDH release milestones +### Testing Strategy Tasks + +*For deciding where a test belongs in the RHDH ecosystem* + +10. **Test placement** — Propose the right repo, test layer, location, and scaffolding for a change + ### Release Management Tasks *For RHDH release tracking, status, announcements* -10. **Release management** — Release dates, status, team breakdown, freeze announcements, blocker bugs, CVEs, release notes +11. **Release management** — Release dates, status, team breakdown, freeze announcements, blocker bugs, CVEs, release notes ### General Tasks -11. **Check environment** — Run doctor, configure paths -12. **View/search activity** — Review worklog, todos +12. **Check environment** — Run doctor, configure paths +13. **View/search activity** — Review worklog, todos **Wait for response before proceeding.** @@ -186,36 +192,36 @@ What would you like to do? **To route:** Read `../rhdh-test-plan-review/SKILL.md` and follow its intake process. -### Release Management Routes +### Test Placement Routes | Response | Skill | |----------|-------| -| 10, "release", "release manager", "release dates", "release status", "feature freeze", "code freeze", "blocker bugs", "CVEs", "release notes", "team breakdown", "freeze announcement" | Route to `@rhdh-release` skill | +| 10, "where should I test", "test placement", "does this need a cluster", "which repo does this test belong in", "should this be an e2e test", "test layer" | Route to `test-placement` skill | -**To route:** Read `../rhdh-release/SKILL.md` and follow its intake process. +**To route:** Read `../test-placement/SKILL.md` and follow its instructions. -### Backstage Upgrade Routes +### Release Management Routes | Response | Skill | |----------|-------| -| "upgrade backstage", "bump backstage", "update @backstage", "backstage version", "align deps", "versions:bump" | Route to `backstage-upgrade` skill | +| 11, "release", "release manager", "release dates", "release status", "feature freeze", "code freeze", "blocker bugs", "CVEs", "release notes", "team breakdown", "freeze announcement" | Route to `@rhdh-release` skill | -**To route:** Read `../backstage-upgrade/SKILL.md` and follow its intake process. +**To route:** Read `../rhdh-release/SKILL.md` and follow its intake process. -### Test Placement Routes +### Backstage Upgrade Routes | Response | Skill | |----------|-------| -| "where should I test", "test placement", "does this need a cluster", "which repo does this test belong in", "should this be an e2e test", "test layer" | Route to `test-placement` skill | +| "upgrade backstage", "bump backstage", "update @backstage", "backstage version", "align deps", "versions:bump" | Route to `backstage-upgrade` skill | -**To route:** Read `../test-placement/SKILL.md` and follow its instructions. +**To route:** Read `../backstage-upgrade/SKILL.md` and follow its intake process. ### General Routes | Response | Action | |----------|--------| -| 11, "doctor", "setup", "config" | Use CLI commands below | -| 12, "log", "todo", "activity" | Use tracking commands below | +| 12, "doctor", "setup", "config" | Use CLI commands below | +| 13, "log", "todo", "activity" | Use tracking commands below | @@ -355,6 +361,7 @@ Todos must be **self-contained**—a new session should understand the task with | rhdh-local | Enable/disable/test plugins in local RHDH | `../rhdh-local/SKILL.md` | | rhdh-pr-review | PR code review and live cluster testing | `../rhdh-pr-review/SKILL.md` | | rhdh-test-plan-review | Reviews an RHDH test plan Jira ticket and suggests platform/integration version updates | `../rhdh-test-plan-review/SKILL.md` | +| test-placement | Propose where to test a change: repo, test layer, location, and scaffolding | `../test-placement/SKILL.md` | | rhdh-release | Release dates, status tracking, team coordination, freeze announcements, blocker bugs, CVEs, release notes | `../rhdh-release/SKILL.md` | ### Shared References diff --git a/skills/test-placement/SKILL.md b/skills/test-placement/SKILL.md index 768328c..33fe6c4 100644 --- a/skills/test-placement/SKILL.md +++ b/skills/test-placement/SKILL.md @@ -4,15 +4,17 @@ description: >- Propose where to test a change in the RHDH dynamic-plugin ecosystem: which repo (rhdh-plugins, rhdh-plugin-export-overlays, rhdh), which test layer (unit, integration, component, cluster-free E2E, cluster E2E), where the - test lives, and how to create it. Use when a developer asks where to test - something, whether a test needs a cluster, or which repo a test belongs in + test lives, and how to create it. Use when asked "where should I test + this", "does this need a cluster", "should this be an e2e test", "which + repo does this test belong in", "what test layer", "test placement", or + when reviewing a test added at the wrong layer. --- # Test Placement Advisor Given the context of a change, bug, or new feature in the RHDH dynamic-plugin ecosystem, propose **where** it should be tested: which repository, which test layer, where the test lives, and how to create it. The guiding rule: **pick the cheapest environment that can actually catch the bug — most plugin validation does not need a cluster, and an increasing part doesn't need Docker either.** -Conventions in this skill: paths are prefixed with the repo they live in — `rhdh:`, `overlays:` (= rhdh-plugin-export-overlays), `plugins:` (= rhdh-plugins). Some harnesses referenced here are **still in review** (see References for PR status). Before recommending a harness or script, verify its path exists on the target repo's `main`; if it doesn't, tell the developer it is pending in the corresponding PR instead of asserting it exists. +Conventions in this skill: paths are prefixed with the repo they live in — `rhdh:`, `overlays:` (= rhdh-plugin-export-overlays), `plugins:` (= rhdh-plugins). For broader repo context, consult `../rhdh/references/rhdh-repos.md` (requires the `rhdh` core skill installed alongside; skip if the file is not found). Some harnesses referenced here are **still in review** (see References for PR status). Before recommending a harness or script, verify its path exists on the target repo's `main`; if it doesn't, tell the developer it is pending in the corresponding PR instead of asserting it exists. ## When to Use @@ -109,10 +111,10 @@ Answer with a concrete recommendation: - **Why not elsewhere:** one line on the layers you rejected (especially if the dev proposed a more expensive one). - **Cost:** rough feedback time (seconds / ~4 min cluster-free / cluster job). -## References (status as of 2026-07-07 — verify before citing as merged) +## References (PR statuses are as of the last edit — verify before citing as merged) - Epic **RHIDP-13501** (E2E Test Optimization) — the per-repo responsibility split lives in the epic's comments and its Jira attachment `rhdh-dynamic-plugin-testing-guideline.md` (Jira-only; if unreachable, the decision table above is the summary). -- Layer matrix: — in review in [rhdh#5044](https://github.com/redhat-developer/rhdh/pull/5044) (RHIDP-15076). +- Layer matrix: `rhdh: docs/e2e-tests/layer-migration-matrix.md` — in review in [rhdh#5044](https://github.com/redhat-developer/rhdh/pull/5044) (RHIDP-15076); the path resolves on `main` once that PR merges. - Cluster-free harness + docs: merged in [rhdh#5005](https://github.com/redhat-developer/rhdh/pull/5005) (RHIDP-15075). - Overlays native smoke: merged in [overlays#2714](https://github.com/redhat-developer/rhdh-plugin-export-overlays/pull/2714). - Catalog-index sanity check: in review in [rhdh#4967](https://github.com/redhat-developer/rhdh/pull/4967). diff --git a/tests/unit/test_skill_structure.py b/tests/unit/test_skill_structure.py index 765b4a7..03a6fe8 100644 --- a/tests/unit/test_skill_structure.py +++ b/tests/unit/test_skill_structure.py @@ -1,10 +1,45 @@ """Tests for SKILL.md structure and content validation.""" import re +from pathlib import Path import pytest import yaml +SKILLS_ROOT = Path(__file__).resolve().parents[2] / "skills" +ALL_SKILL_MD_FILES = sorted(SKILLS_ROOT.glob("*/SKILL.md")) + + +class TestAllSkillsFrontmatter: + """Every skills/*/SKILL.md must have frontmatter valid per the Agent Skills spec.""" + + @pytest.fixture(params=ALL_SKILL_MD_FILES, ids=lambda p: p.parent.name) + def skill_file(self, request): + """Each SKILL.md file in the skills directory.""" + return request.param + + @pytest.fixture + def frontmatter(self, skill_file): + """Parse YAML frontmatter from the skill file.""" + content = skill_file.read_text(encoding="utf-8") + match = re.match(r"^---\n(.*?)\n---", content, re.DOTALL) + if not match: + pytest.fail(f"{skill_file} missing YAML frontmatter") + return yaml.safe_load(match.group(1)) + + def test_skills_discovered(self): + """The glob must find the skills (guards against a moved skills/ dir).""" + assert len(ALL_SKILL_MD_FILES) >= 1 + + def test_name_matches_directory(self, skill_file, frontmatter): + """Frontmatter name must match the skill's directory name.""" + assert frontmatter.get("name") == skill_file.parent.name + + def test_description_within_spec_limits(self, frontmatter): + """Description must be meaningful and within the spec's 1024-char limit.""" + description = frontmatter.get("description") or "" + assert 20 < len(description) <= 1024 + class TestOrchestratorSkillMd: """Test that orchestrator SKILL.md (skills/rhdh/SKILL.md) has required structure.""" From edf53d070a3ce67f313c43621eef0f9f7aefd8db Mon Sep 17 00:00:00 2001 From: Gustavo Lira Date: Tue, 7 Jul 2026 13:55:26 -0300 Subject: [PATCH 3/3] =?UTF-8?q?docs:=20refresh=20test-placement=20referenc?= =?UTF-8?q?es=20=E2=80=94=20rhdh#5057=20and=20overlays#2731=20merged?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The cluster-free harness expansion (10 specs / 14 test cases) and the native-smoke workspace mode both merged on 2026-07-07; the References section now cites them so the decision-table capabilities stay backed by merged PRs. Co-Authored-By: Claude Opus 4.8 (1M context) --- skills/test-placement/SKILL.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/skills/test-placement/SKILL.md b/skills/test-placement/SKILL.md index 33fe6c4..327fcae 100644 --- a/skills/test-placement/SKILL.md +++ b/skills/test-placement/SKILL.md @@ -115,7 +115,7 @@ Answer with a concrete recommendation: - Epic **RHIDP-13501** (E2E Test Optimization) — the per-repo responsibility split lives in the epic's comments and its Jira attachment `rhdh-dynamic-plugin-testing-guideline.md` (Jira-only; if unreachable, the decision table above is the summary). - Layer matrix: `rhdh: docs/e2e-tests/layer-migration-matrix.md` — in review in [rhdh#5044](https://github.com/redhat-developer/rhdh/pull/5044) (RHIDP-15076); the path resolves on `main` once that PR merges. -- Cluster-free harness + docs: merged in [rhdh#5005](https://github.com/redhat-developer/rhdh/pull/5005) (RHIDP-15075). -- Overlays native smoke: merged in [overlays#2714](https://github.com/redhat-developer/rhdh-plugin-export-overlays/pull/2714). +- Cluster-free harness + docs: merged in [rhdh#5005](https://github.com/redhat-developer/rhdh/pull/5005) (RHIDP-15075); expanded to 10 specs / 14 test cases in [rhdh#5057](https://github.com/redhat-developer/rhdh/pull/5057) — the richest set of worked enablement examples (config mirrors, catalog file locations, OCI plugin additions). +- Overlays native smoke: merged in [overlays#2714](https://github.com/redhat-developer/rhdh-plugin-export-overlays/pull/2714); the per-workspace mode used in Step 4 merged in [overlays#2731](https://github.com/redhat-developer/rhdh-plugin-export-overlays/pull/2731). - Catalog-index sanity check: in review in [rhdh#4967](https://github.com/redhat-developer/rhdh/pull/4967). - L3 pattern proposal: [rhdh#4864](https://github.com/redhat-developer/rhdh/pull/4864) (closed) under RHIDP-13235.