AGENT SKILL

qa-targets

Resolve WHERE browser QA runs — named targets in .orc/targets.json (local, staging, preview), the Target gate, credential references (literal | op:// | env:), guard rule

License 许可
MIT
所属仓库
HigorAlves/orc
最近更新
2026-11-07
Stars
★ 7
Forks
0

01 前言 Front Matter

name
qa-targets
description
Resolve WHERE browser QA runs — named targets in .orc/targets.json (local, staging, preview), the Target gate, credential references (literal | op:// | env:), guard rule
when_to_use
Use before env provisioning in /orc:qa, /orc:flow Phase 6, /orc:evidence.

03 SKILL.md 正文

QA targets

Browser QA runs against a target: local (the Docker env orc-env-provisioner boots) or a remote URL such as staging or a preview deploy. Targets live in <repo>/.orc/targets.json (gitignored, repo-level — not per branch), managed by orc-targets (plugin bin/, on PATH while orc is enabled).

Announce at start: "I'm using the qa-targets skill to resolve where browser QA runs."

Registry shape

{ "schema": 1, "targets": {
  "local":   { "kind": "local",  "baseUrl": null, "healthPath": "/", "guard": false, "users": {}, "login": null },
  "staging": { "kind": "remote", "baseUrl": "https://staging.example.com", "healthPath": "/healthz", "guard": true,
               "users": { "admin": { "username": "env:STAGING_ADMIN_USER", "password": "op://Eng/staging-admin/password" } },
               "login": { "path": "/login", "usernameField": "Email", "passwordField": "Password", "submit": "Sign in", "successPath": "/dashboard" } } } }
  • kind — local is provisioned by orc:browser-qa Step 0 (today's path, unchanged); remote is probed, never provisioned.
  • guard: true — a shared environment. The planner is told to tag mutating scenarios @mutating; on a guarded target those run as skipped with note guarded target — never silently dropped, never executed.
  • users.<name>.{username,password} — references, not values: a literal, op://vault/item/field (1Password CLI, op read), or env:VAR. orc-targets resolve <name> substitutes them at run time and prints JSON for ORC_TARGET_JSON; the resolved JSON is never written to disk. Unresolvable ⇒ exit 3 ⇒ an escalation, not a skip.
  • login — the recipe tests/auth.setup.ts follows once per run in the video-off setup project; the session is saved as storageState and reused by every scenario. Field hints match by label or placeholder text.

Resolution order (every caller, same order)

  1. --target <name> flag → use it silently (orc-state decision set target <name> --provenance flag).
  2. --web <url> flag (kept for compatibility) → an ad-hoc remote target: orc-targets resolve local --base-url <url>; recorded as target=adhoc:<url>.
  3. A settled target decision in the session → reuse silently; re-runs keep it.
  4. Otherwise the Target gate below. guided/full autopilot: local (policy decision, printed one-liner) — a remote target is a judgment call and is never auto-picked.

The Target gate (soft-inward, header chip Target)

Run orc-targets init && orc-targets list, then:

> **⛔ Gate — QA target**
>
> Where should browser QA run? `local` boots the Docker env; remote targets are probed first and never provisioned.

AskUserQuestion (header Target), options in this order — local first, each remote row as <name> — <baseUrl> with (read-only) appended when guard is true, and last New remote URL (follow-up free text: URL, optional name to save, guard yes/no, optional user as env:/op:// references — then orc-targets set|user|login and resolve). Record the answer: orc-state decision set target <name> --provenance asked.

After the gate

  • kind: local → continue to orc:browser-qa Step 1 (env attach/provision). appUrl from docker-env-state.json becomes the --base-url override the engine passes to orc-targets resolve local inline.
  • --web <url> / New remote URL without a saved name → an unauthenticated ad-hoc run: resolve local --base-url <url> drops users and login whenever the URL leaves localhost, so local credentials never reach an arbitrary origin. Authenticated remote QA requires a named target.
  • kind: remote → orc-targets probe <name>; failure is an environment escalation (🛑 Escalation — target unreachable: name, URL, curl exit) — stop, never fall back to local silently.
  • Hand the engine the target name (plus the --base-url override when one applies) and guard — never the resolved JSON. Resolution happens inline, inside the same shell command that consumes it: ORC_TARGET_JSON="$(orc-targets resolve <name> [--base-url …])" npx playwright test …. Every tool call is a fresh shell, so an exported variable from an earlier call is gone; and a standalone orc-targets resolve prints plaintext passwords into the conversation transcript, which is written to disk.

Iron rule — never run orc-targets resolve as its own command. It is only ever the $(…) inside the command that needs the JSON. If a step seems to need the resolved values to reason about (which user, which URL), use orc-targets get <name> — it returns the references, not the secrets.

Redaction rules (iron)

  • Resolved credentials appear in no packet file: not steps.md, not qa-manifest.json, not the PR comment, not the explainer script. Reference the user by its registry name (as admin).
  • The setup project records no video and no trace (config template, Slice 2) so the password is never typed on camera; scenario traces contain the session cookie only — acceptable for test environments, noted in steps.md as Auth: storageState from setup project (user: admin).
  • op:// reads go through op read only; orc never caches the value.

04 同仓库更多 Skills