Skip to content

feat(ws): ws test consults adapter, supports Gradle, auto-filters by test name#38

Merged
Cervator merged 6 commits into
mainfrom
feat/ws-test-adapter
Apr 24, 2026
Merged

feat(ws): ws test consults adapter, supports Gradle, auto-filters by test name#38
Cervator merged 6 commits into
mainfrom
feat/ws-test-adapter

Conversation

@agent-refr
Copy link
Copy Markdown

AI-assisted change proposal. Filed by agent driven by @Cervator via GDD.

Summary

  • ws test now consults overlay adapter commands before auto-detection, and adds Gradle as a detected runner
  • Any non-flag argument is treated as a test name and auto-translated to the runner's filter syntax (--tests for Gradle, -run for Go, -k for pytest)
  • Targeted Gradle runs auto-clear the test cache (cleanTest) to avoid stale cached failures
  • Auto-discovers Gradle subproject for a test class via find, with warning on ambiguous matches
  • Help text no longer hardcodes runner priority — points to ws actions instead

Test plan

  • ws test terasology ClientNetworkStateTest — routes through adapter, discovers :engine-tests:test, clears cache, passes
  • ws test with no args shows updated help
  • ws actions terasology shows adapter + auto-detected commands
  • Syntax check passes (bash -n scripts/ws)

Related

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented Apr 19, 2026

Note

Reviews paused

It looks like this branch is under active development. To avoid overwhelming you with review comments due to an influx of new commits, CodeRabbit has automatically paused this review. You can configure this behavior by changing the reviews.auto_review.auto_pause_after_reviewed_commits setting.

Use the following commands to manage reviews:

  • @coderabbitai resume to resume automatic reviews.
  • @coderabbitai review to trigger a single review.

Use the checkboxes below for quick actions:

  • ▶️ Resume reviews
  • 🔍 Trigger review
📝 Walkthrough

Walkthrough

Adds support for --help/-h and an optional leading TestName positional filter to ws test; changes runner detection priority to prefer an overlay adapter, then Gradle, Makefile, Go, and Python; implements runner-specific filter-to-flag mappings and adds _ws_gradle_find_test() to locate Gradle subproject test tasks.

Changes

Cohort / File(s) Summary
CLI test command
scripts/ws
Rewrote ws_test() to accept `ws test [TestName

Sequence Diagram(s)

sequenceDiagram
  autonumber
  participant User as "User"
  participant CLI as "ws CLI"
  participant Adapter as "Overlay Adapter\n(commands.test)"
  participant Gradle as "Gradle (gradlew)"
  participant Makefile as "Makefile (test)"
  participant Go as "Go (go test)"
  participant Py as "Python (pytest)"

  User->>CLI: run `ws test <component> [TestName|args...]`
  CLI->>CLI: parse args -> flags vs test_filter
  CLI->>Adapter: check `commands.test`
  alt Adapter present
    Adapter->>Adapter: run adapter test (pass args/filter)
    Adapter-->>CLI: exit
  else Adapter absent
    CLI->>Gradle: check `gradlew`
    alt Gradle present
      CLI->>Gradle: if test_filter -> _ws_gradle_find_test() -> run `:subproject:cleanTest` then `:subproject:test --tests "*.<filter>"` else run full suite
    else
      CLI->>Makefile: check `make test` target
      alt Makefile present and no filter/extra flags
        Makefile-->>CLI: run `make test`
      else
        CLI->>Go: check `go.mod`
        alt Go present
          Go-->>CLI: run `go test ./... -count=1 -run "$test_filter"` (or full suite)
        else
          CLI->>Py: check `pyproject.toml`
          Py-->>CLI: run `uv run pytest` (with `-k "$test_filter"` if present)
        end
      end
    end
  end
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately summarizes the main changes: adapter consultation, Gradle support, and test name auto-filtering.
Description check ✅ Passed The description is directly related to the changeset, providing context, test plan, and specific examples of the new functionality.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/ws-test-adapter

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@scripts/ws`:
- Around line 347-352: The flags-only branch (elif checking ${`#runner_args`[@]}
-gt 0) currently runs go test "${runner_args[@]}" only in the current package;
change that invocation to run the full module tree with cache disabled by
invoking go test ./... -count=1 "${runner_args[@]}" so that both the flags-only
path and the no-arg / filtered paths behave consistently; update the command in
the elif branch accordingly (the conditional around runner_args and the go test
invocation are the targets).
- Around line 215-220: The current derivation of subproject from matches[0]
fails for root tests because the pattern removal `${subproject%%/src/test/*}`
expects a leading slash; update the logic around the `subproject` variable
assignment so you first normalize or explicitly handle paths that start with
`./src/test/` (or otherwise detect the root-test pattern) and set `subproject`
to "." or empty before the later check, then keep the existing conditional that
echoes `:test` when `subproject` is "." or empty; adjust the code that does
`local subproject="${matches[0]#./}"` and the subsequent
`${subproject%%/src/test/*}` expansion to account for root-test paths.
- Around line 305-317: The argument loop currently splits flags from their
values causing flags like -run, --tests, and -k to be separated into test_filter
and runner_args; modify the parsing in the for-loop that builds test_filter and
runner_args so that when you encounter a flag that expects a value (at minimum
the known set "-run", "--tests", "-k") you consume the next positional argument
as its value and append both the flag and its value to runner_args (leaving
test_filter empty), rather than treating the value as a test_filter; ensure the
logic still handles flags without values and multiple test patterns by checking
the current arg against the known value-taking flags before assigning to
test_filter.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: 3ef24291-206a-417d-868d-57f6ed04e3d8

📥 Commits

Reviewing files that changed from the base of the PR and between ae010ac and 07591a8.

📒 Files selected for processing (1)
  • scripts/ws

Comment thread scripts/ws
Comment thread scripts/ws Outdated
Comment thread scripts/ws Outdated
Comment thread scripts/ws
Cervator added a commit that referenced this pull request Apr 22, 2026
…, safe exec

Address four CodeRabbit findings on PR #38:

1. Root-project Gradle test path derivation: strip pattern expected a
   leading slash, breaking root-level tests. Detect `src/test/*` prefix
   explicitly and emit `:test`.

2. Arg parser split value-expecting flags from their values. `-run TestFoo`
   became `runner_args=(-run)` + `test_filter=TestFoo`. Track known
   value-expecting flags (`-run`, `--tests`, `-k`, etc.) and keep the pair
   together.

3. Adapter Gradle invocation used `bash -c` with unquoted substitution,
   enabling command injection via crafted test filter. Replace with
   direct exec using array expansion.

4. Go flags-only branch ran `go test "${runner_args[@]}"` without
   `./... -count=1`, inconsistent with the other Go branches. Add them.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@Cervator Cervator force-pushed the feat/ws-test-adapter branch from 07591a8 to 104950a Compare April 22, 2026 20:15
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@scripts/ws`:
- Around line 326-329: The case block that sets expect_value=true incorrectly
treats Gradle's --parallel as a value-taking flag; update the case in the
scripts/ws loop (the case that assigns expect_value=true) to remove --parallel
and instead add Go flags that do consume values (e.g., -count, -bench,
-benchtime, -cpu, -shuffle) so the parser doesn't swallow the next token; keep
the expect_value mechanic and only list flags that actually take an argument.
- Around line 356-358: The current replacement for clean_task uses global
substitution on gradle_task which can mangle project names containing ":test";
instead, derive clean_task by removing only the trailing ":test" suffix from
gradle_task and then appending ":cleanTest" (so only the task suffix is
changed), and keep using that clean_task when invoking ./gradlew with
gradle_task, test_filter and runner_args; update the code around the gradle_task
-> clean_task assignment to perform suffix-stripping (for example using shell
parameter expansion to remove the trailing ":test") before appending
":cleanTest".
- Around line 352-364: The targeted-task branch is calling ./gradlew directly
and drops adapter-provided base args; instead reuse gradle_argv so overlay args
(like --no-daemon or init scripts) are preserved. Change the branch where
gradle_task and clean_task are used to invoke the command via gradle_argv: build
a base array from gradle_argv with any trailing task element removed (so you can
append "$clean_task" and "$gradle_task"), then execute "${base[@]}"
"$clean_task" "$gradle_task" --tests "*.$test_filter" "${runner_args[@]}";
reference symbols: _ws_gradle_find_test, gradle_task, clean_task, gradle_argv,
test_filter, runner_args.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: 852b3508-2e1b-48a3-b9c1-fffb4a2e04eb

📥 Commits

Reviewing files that changed from the base of the PR and between 07591a8 and 104950a.

📒 Files selected for processing (1)
  • scripts/ws

Comment thread scripts/ws
Comment thread scripts/ws Outdated
Cervator added a commit that referenced this pull request Apr 23, 2026
…fix sub

Address 3 CodeRabbit findings on PR #38:

1. --parallel was wrongly listed as value-consuming; it's a Gradle
   boolean flag. Also add Go flags that DO take values (-count, -bench,
   -benchtime, -cpu, -shuffle, etc.) and Gradle init/project flags
   (-I, --init-script, --build-file, --project-dir).

2. Targeted-Gradle branch hardcoded ./gradlew, dropping adapter base
   args like --no-daemon or -I init.gradle. Reuse gradle_argv minus
   the trailing task so adapter flags flow through. Also: guard the
   Gradle path for non-Gradle adapters (just run the adapter with
   runner_args, no task substitution).

3. Use suffix substitution (${gradle_task%:test}:cleanTest) instead
   of global substitution to avoid mangling subproject names that
   happen to contain ':test' (e.g., :testSupport:test).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Cervator and others added 3 commits April 23, 2026 23:07
…test name

- Check overlay adapter test command before auto-detection
- Add Gradle runner (gradlew) to auto-detection chain
- Any non-flag arg is treated as a test name and translated to the
  runner's filter syntax (--tests for Gradle, -run for Go, -k for pytest)
- Targeted Gradle runs auto-clear test cache (cleanTest) to avoid
  stale cached failures
- Auto-discover Gradle subproject for a test class via find, with
  warning on ambiguous multi-match
- Help text no longer hardcodes runner priority order — points to
  ws actions instead

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…, safe exec

Address four CodeRabbit findings on PR #38:

1. Root-project Gradle test path derivation: strip pattern expected a
   leading slash, breaking root-level tests. Detect `src/test/*` prefix
   explicitly and emit `:test`.

2. Arg parser split value-expecting flags from their values. `-run TestFoo`
   became `runner_args=(-run)` + `test_filter=TestFoo`. Track known
   value-expecting flags (`-run`, `--tests`, `-k`, etc.) and keep the pair
   together.

3. Adapter Gradle invocation used `bash -c` with unquoted substitution,
   enabling command injection via crafted test filter. Replace with
   direct exec using array expansion.

4. Go flags-only branch ran `go test "${runner_args[@]}"` without
   `./... -count=1`, inconsistent with the other Go branches. Add them.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
…fix sub

Address 3 CodeRabbit findings on PR #38:

1. --parallel was wrongly listed as value-consuming; it's a Gradle
   boolean flag. Also add Go flags that DO take values (-count, -bench,
   -benchtime, -cpu, -shuffle, etc.) and Gradle init/project flags
   (-I, --init-script, --build-file, --project-dir).

2. Targeted-Gradle branch hardcoded ./gradlew, dropping adapter base
   args like --no-daemon or -I init.gradle. Reuse gradle_argv minus
   the trailing task so adapter flags flow through. Also: guard the
   Gradle path for non-Gradle adapters (just run the adapter with
   runner_args, no task substitution).

3. Use suffix substitution (${gradle_task%:test}:cleanTest) instead
   of global substitution to avoid mangling subproject names that
   happen to contain ':test' (e.g., :testSupport:test).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@agent-refr agent-refr force-pushed the feat/ws-test-adapter branch from 8169481 to 4c2de87 Compare April 24, 2026 03:07
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 4

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@scripts/ws`:
- Around line 285-301: The nested-Go detection currently prefers a single entry
in go_candidates and sets runner="go" before ever checking for a top-level
pyproject.toml, which makes Python ignored in mixed repos; update the logic
around go_candidates so the existence of a top-level pyproject.toml is
considered at the same precedence as a single nested go.mod (e.g., check for -f
pyproject.toml alongside the single go_candidates case or explicitly test for
pyproject.toml before setting runner="go"), and if you keep Go precedence emit a
clear informational message indicating Go was chosen; reference the
go_candidates array and the runner variable and ensure the pyproject.toml check
is hoisted out of the sole-else branch so Python projects aren’t silently
ignored.
- Around line 348-359: The non-Gradle branch in the case for "adapter|gradle"
drops test_filter when it runs the adapter directly; update the branch where it
currently executes `"${adapter_argv[@]}" "${runner_args[@]}"` and returns so
that it either appends the test_filter as a trailing positional argument (e.g.,
include test_filter after runner_args when non-empty) or, alternatively, fail
fast with a clear message instructing users to use `ws exec` for filtered runs;
modify the logic around adapter_argv, runner_args and test_filter in the
non-Gradle path to implement one of these behaviors and ensure the command
invocation and return remain consistent.
- Around line 199-227: _ws_gradle_find_test currently only searches
src/test/java for "${class_name}.java" so it misses tests in other JVM source
dirs (kotlin, groovy, scala); update the find invocation in _ws_gradle_find_test
to match any file under */src/test/*/${class_name}.* (or explicitly include
.java .kt .kts .groovy .scala) so it discovers tests regardless of language;
keep the existing subproject extraction logic (subproject="${matches[0]#./}" and
subproject="${subproject%%/src/test/*}") as-is since it already strips the
language directory correctly.
- Around line 341-346: The adapter command string splitting using read -r -a
adapter_argv on adapter_cmd breaks quoted arguments (e.g., "*.Foo Bar") — either
change the contract to require commands be provided as YAML sequences (consume
them as arrays directly into adapter_argv) or replace the naive whitespace split
with a shell-safe tokenizer: feed adapter_cmd through a safe splitter (e.g., use
printf '%s\n' "$adapter_cmd" piped into xargs/while-read to preserve quoted
tokens) and populate adapter_argv from those tokens; update code paths that
reference adapter_cmd and adapter_argv accordingly and add a note in the adapter
contract if you keep the simple whitespace-split behavior.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: 9fdf1ac0-545b-4f1d-8427-68cbb451eb33

📥 Commits

Reviewing files that changed from the base of the PR and between 104950a and 4c2de87.

📒 Files selected for processing (1)
  • scripts/ws

Comment thread scripts/ws
Comment thread scripts/ws Outdated
Comment thread scripts/ws
Comment thread scripts/ws
…adapter

Address 3 CodeRabbit findings on PR #38:

1. _ws_gradle_find_test only searched src/test/java, missing Kotlin
   (.kt), Groovy (.groovy), and Scala (.scala) test sources. Loop over
   all four language directories.

2. Non-Gradle adapter path silently dropped test_filter, running the
   full suite with no warning. Now errors with guidance pointing to
   'ws exec' when a filter is provided against a non-Gradle adapter.

3. Document the "no quoted args" contract on adapter_cmd parsing —
   adapter commands are whitespace-separated tokens; use a wrapper
   script if complex quoting is needed.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@scripts/ws`:
- Around line 240-257: The usage/help block in the ws test command currently
treats explicit help and missing-argument cases the same and always exits with
1; split the conditional so that the no-argument case (check on $# -lt 1) prints
the usage to stderr and exits 1, while the explicit help case (when "$1" ==
"--help" or "$1" == "-h") prints the same usage text to stdout and exits 0;
update the conditional around the existing usage text in the scripts/ws file
(the block that checks "$#" and "$1") to handle these two branches separately
and preserve the existing messages and formatting.
- Around line 337-343: The case block inside the argument parsing logic in
scripts/ws currently lists pytest flags that consume a value (the pattern
matching for -run|--tests|... leading to expect_value=true) but omits the pytest
marker flag -m, causing markers to be misparsed; update that case pattern to
include -m so the parser sets expect_value=true for -m (consider also adding
other value-taking pytest flags like -o, -r, --tb, --maxfail if desired) so that
when parsing in the function handling args (where expect_value is used to
collect runner_args/test_filter) the marker expression is consumed as the flag's
value instead of being treated as a test name.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: 3aada9f1-7034-432e-b7d9-fe6a0f0a4791

📥 Commits

Reviewing files that changed from the base of the PR and between 4c2de87 and d28df5f.

📒 Files selected for processing (1)
  • scripts/ws

Comment thread scripts/ws Outdated
Comment thread scripts/ws
Copy link
Copy Markdown

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Updates the workspace CLI’s ws test subcommand to better integrate overlay adapters and support more ecosystems (notably Gradle), while adding a convenience “test name” positional argument that’s translated into runner-specific filter flags.

Changes:

  • Detects and prefers overlay adapter commands.test before falling back to auto-detected runners.
  • Adds Gradle runner support (including subproject discovery for test classes and targeted --tests execution).
  • Treats the first non-flag argument as a test filter and passes runner flags through.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment thread scripts/ws Outdated
Comment thread scripts/ws
Comment thread scripts/ws Outdated
Comment thread scripts/ws Outdated
Comment thread scripts/ws Outdated
…lags

Address 5 review findings on PR #38 (CodeRabbit + Copilot):

- Runner precedence: Gradle before Make, match ws-overlay.sh
  ws_actions ordering (was Make → Gradle → Go → Python, now
  Gradle → Make → Go → Python)
- pyproject.toml detection hoisted above nested go.mod search so
  mixed Go+Python repos don't silently pick Go
- --help / -h now exits 0 and prints to stdout (was exit 1, stderr)
- Gradle --tests pattern: pass FQNs (org.foo.Bar) and wildcards
  through as-is; only prefix *. for bare class names
- Add pytest value-taking flags to expect_value list: -m, -r, -o,
  --maxfail, --tb
- Remove 2>/dev/null suppression on ws_detect_overlay so YAML
  parse errors surface to the user

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
coderabbitai[bot]
coderabbitai Bot previously requested changes Apr 24, 2026
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@scripts/ws`:
- Line 18: The header line in the script's help output still documents the old
runner precedence "(adapter > Makefile > Gradle > Go > Python)"; update that
help/header string in the scripts/ws file to match the actual runner order
implemented in ws_test (adapter > Gradle > Makefile > Go > Python) so the "ws
help" output reflects the true precedence. Locate the help/header comment that
begins with "#   test <comp> [TestName|args...] Run tests" and change the
parenthetical runner order to "adapter > Gradle > Makefile > Go > Python" so it
aligns with the ws_test implementation.
- Around line 411-414: The slice that builds gradle_base can produce an empty
array if gradle_argv contains a single token; add a defensive guard after
computing gradle_base to handle that case: if ${`#gradle_base`[@]} -eq 0 then set
gradle_base to the single token (e.g., gradle_base=("${gradle_argv[0]}")) so the
invocation uses the adapter executable rather than trying to execute a task as a
program; refer to gradle_argv, gradle_base, clean_task and gradle_task when
making this change.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: 4b488a6a-8679-40d9-9fb3-c4c47f1cd83f

📥 Commits

Reviewing files that changed from the base of the PR and between d28df5f and f118755.

📒 Files selected for processing (1)
  • scripts/ws

Comment thread scripts/ws Outdated
Comment thread scripts/ws
@Cervator
Copy link
Copy Markdown
Member

This is turning into another GDD-showcase PR, I think. It highlights some benefits:

  • The agent-assisted code review process in general
  • Detecting and clarifying false alarms between LLMs via agent-posted comments like feat(ws): ws test consults adapter, supports Gradle, auto-filters by test name #38 (comment)
  • That the local agent was able to use a different component entirely (Terasology) to justify that a change (to GDD) is actually correct
  • The new ws test wrapper can make automated testing much easier for both humans and agents to interact with (and if tests are easier to run then that lowers the barrier to do more testing!)

To also show a snippet of what happens in the local GDD workspace here's a bit of session content:

● Verify the test flow still works:

● Bash(bash scripts/ws test terasology ClientNetworkStateTest 2>&1 | tail -5)    
  ⎿  Running in the background (↓ to manage)

● While that runs — here's the triage decisions:

  ┌─────┬─────────────────────────────┬──────────────────────────────────────┐   
  │  #  │            Issue            │               Decision               │   
  ├─────┼─────────────────────────────┼──────────────────────────────────────┤   
  │ 1   │ Glob only covers            │ Fixed — widened to                   │   
  │     │ src/test/java/              │ Java/Kotlin/Groovy/Scala             │   
  ├─────┼─────────────────────────────┼──────────────────────────────────────┤   
  │ 2   │ Go detection shortcircuits  │ Skip — hypothetical, inconsistency   │   
  │     │ Python in monorepos         │ noted in Thalamus-worthy style       │   
  ├─────┼─────────────────────────────┼──────────────────────────────────────┤   
  │ 3   │ read -r -a splits on IFS,   │ Documented — added contract comment  │   
  │     │ breaks quoted adapter args  │ explaining the limitation            │   
  ├─────┼─────────────────────────────┼──────────────────────────────────────┤   
  │     │ Non-Gradle adapter +        │ Fixed — now errors with clear        │   
  │ 4   │ test_filter silently runs   │ guidance pointing to ws exec         │   
  │     │ full suite                  │                                      │   
  └─────┴─────────────────────────────┴──────────────────────────────────────┘   

✻ Baked for 1m 35s · 1 shell still running

● Background command "Verify test still works with Kotlin/Groovy/Scala glob      
additions" completed (exit code 0)
● Passes. Commit:

● Write(.commits\ws-test-review-round3.md)
  ⎿  Wrote 19 lines to .commits\ws-test-review-round3.md
       2 message: "fix(ws): review round 3 — widen JVM langs, fail loudly        
         on non-Gradle adapter"
       3 add:
       5 --- scripts/ws
       6
       7 Address 3 CodeRabbit findings on PR #38:
       9 1. _ws_gradle_find_test only searched src/test/java, missing Kotl       
         in
      10    (.kt), Groovy (.groovy), and Scala (.scala) test sources. Loop       
          over
     … +11 lines (ctrl+o to expand)

● Bash(bash scripts/ws commit yggdrasil .commits/ws-test-review-round3.md)       
  ⎿  Staging files from bodyfile frontmatter...
     [feat/ws-test-adapter d28df5f] fix(ws): review round 3 — widen JVM lang     
     s, fail loudly on non-Gradle adapter
      1 file changed, 25 insertions(+), 6 deletions(-)

..........

● Let me verify the key claims before fixing:

  Searched for 1 pattern (ctrl+o to expand)

● The current glob works — find -path "*" matches across slashes (unlike shell   
  globs), and ClientNetworkStateTest.java is in
  org/terasology/engine/integrationenvironment/ (4 segments) and still got found.   Let me verify Copilot's claim more carefully:

● Bash(cd D:/Dev/GitWS/yggdrasil/components/terasology && find . -path
      "*/src/test/java/*/ClientNetworkStateTest.java" -type f 2>/dev/null)       
  ⎿  ./engine-tests/src/test/java/org/terasology/engine/integrationenvironme     
     nt/ClientNetworkStateTest.java

● Copilot #5 is wrong — find -path treats * as matching across slashes. The      
  current glob works for multi-segment packages. Let me check the others:        

  Searched for 2 patterns, read 1 file (ctrl+o to expand)

● Let me fix all the legitimate issues:

  Read 1 file (ctrl+o to expand)

● Now let me apply all the fixes:

..........

● Now test various scenarios:

● Bash(cd D:/Dev/GitWS/yggdrasil && bash scripts/ws test --help 2>&1 | head -3 &&       echo "---exit=$?")
  ⎿  Usage: ws test <component> [test-name | args...]

     Run tests for a component. The test runner is detected automatically        
     ---exit=0

● Good — --help exits 0 and prints to stdout. Now test the actual flow:

● Bash(cd D:/Dev/GitWS/yggdrasil && bash scripts/ws test terasology
      ClientNetworkStateTest 2>&1 | tail -5)
  ⎿  Running in the background (↓ to manage)

● While that runs, let me address the two Copilot findings that are actually     
  incorrect by resolving them with justification. They're #4 (help hardcodes     
  runner priority — it doesn't, points to ws actions) and #5 (multi-segment glob 
  — find -path handles it fine). Also the Go/Python precedence thread is now     
  actually addressed, not rejected.

● Bash(cd D:/Dev/GitWS/yggdrasil && bash scripts/ws review yggdrasil reply 38    
      PRRT_kwDOQoGMSs59ST6c "Verified the help text at lines 243-256 — it says   
      'detected automa…)
  ⎿  Replied to thread on CR #38 (SiliconSaga/yggdrasil).
     Thread resolved.

● Bash(cd D:/Dev/GitWS/yggdrasil && bash scripts/ws review yggdrasil reply 38    
      PRRT_kwDOQoGMSs59ST6m "find -path treats * as matching across slashes      
      (unlike shell globs…)
  ⎿  Replied to thread on CR #38 (SiliconSaga/yggdrasil).
     Thread resolved.

✻ Churned for 4m 4s · 1 shell still running

● Background command "Verify end-to-end" completed (exit code 0)

  Read 1 file (ctrl+o to expand)

● Passes. Commit:

● Write(.commits\ws-test-review-round4.md)
  ⎿  Wrote 20 lines to .commits\ws-test-review-round4.md
       2 message: "fix(ws): review round 4 — precedence, --help UX, FQN fi       
         lter, pytest flags"
       3 add:
       4   - scripts/ws
       5 ---
       6
       7 Address 5 review findings on PR #38 (CodeRabbit + Copilot):
       8
       9 - Runner precedence: Gradle before Make, match ws-overlay.sh
      10   ws_actions ordering (was Make → Gradle → Go → Python, now
     … +11 lines (ctrl+o to expand)

● Bash(cd D:/Dev/GitWS/yggdrasil && bash scripts/ws commit yggdrasil
      .commits/ws-test-review-round4.md)
  ⎿  Staging files from bodyfile frontmatter...
     [feat/ws-test-adapter f118755] fix(ws): review round 4 — precedence, --     
     help UX, FQN filter, pytest flags
      1 file changed, 51 insertions(+), 28 deletions(-)

● Bash(cd D:/Dev/GitWS/yggdrasil && bash scripts/ws push yggdrasil)
  ⎿  Pushing feat/ws-test-adapter → siliconsaga (SiliconSaga/yggdrasil)
     To https://github.com/SiliconSaga/yggdrasil.git
        d28df5f..f118755  feat/ws-test-adapter -> feat/ws-test-adapter

● Pushed — normal push, no force needed. Summary of this round:

  ┌─────┬───────────────────────────────┬───────────────────────────────────┐    
  │  #  │            Finding            │             Decision              │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CR  │ Go/Python precedence          │ Fixed — hoisted pyproject.toml    │    
  │ #1  │                               │ before nested go.mod              │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CR  │ --help exits 1 to stderr      │ Fixed — explicit help now exits 0 │    
  │ #2  │                               │  to stdout                        │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ #2  │                               │  to stdout                        │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CR  │ -m and other pytest           │ Fixed — added -m, -r, -o,         │    
  │ #3  │ value-flags missing           │ --maxfail, --tb                   │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CP  │ Help text hardcodes priority  │ Resolved — false alarm, help      │    
  │ #4  │                               │ already points to ws actions      │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CP  │ Glob doesn't match            │ Resolved — false alarm, find      │    
  │ #5  │ multi-segment packages        │ -path handles slashes             │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CP  │ Silenced errors hide          │ Fixed — removed 2>/dev/null from  │    
  │ #6  │ misconfigurations             │ ws_detect_overlay                 │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CP  │ Runner precedence disagrees   │ Fixed — same fix as CR #1         │    
  │ #7  │ with ws-overlay.sh            │ extended to Make ordering         │    
  ├─────┼───────────────────────────────┼───────────────────────────────────┤    
  │ CP  │ Gradle filter mangles FQNs    │ Fixed — pass FQNs and wildcards   │    
  │ #8  │ with *. prefix                │ through unchanged                 │    
  └─────┴───────────────────────────────┴───────────────────────────────────┘    

  2 false-alarm Copilot threads already resolved via ws review reply. The rest   
  will be addressed by the push triggering re-review.

Not sure what happened to that bare #2 in the issue table, looks like the prior row partially repeated in the output. Hey nothing's perfect! :-)

Address 2 CodeRabbit findings on PR #38:

- Header comment (rendered by 'ws help') listed the old runner
  precedence. Align with the implementation: adapter > Gradle >
  Makefile > Go > Python.

- Targeted-Gradle branch assumed the adapter's last token is a
  strippable task. If an adapter is misconfigured with a single
  token (e.g. just './gradlew'), the base slice would be empty
  and the next exec would try to run ':subproject:cleanTest' as a
  program. Add a guard that errors with a clear format hint.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@Cervator Cervator dismissed coderabbitai[bot]’s stale review April 24, 2026 14:30

Dismissing stale review that didn't auto-resolve

@Cervator Cervator merged commit 64f2d1b into main Apr 24, 2026
1 check passed
@Cervator Cervator deleted the feat/ws-test-adapter branch April 24, 2026 14:31
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants