Skip to content

test: add opencode HTTP server integration tests + install opencode in CI#6

Merged
JohnnyVicious merged 2 commits intomainfrom
test/opencode-server-integration
Apr 12, 2026
Merged

test: add opencode HTTP server integration tests + install opencode in CI#6
JohnnyVicious merged 2 commits intomainfrom
test/opencode-server-integration

Conversation

@JohnnyVicious
Copy link
Copy Markdown
Owner

Summary

Adds protocol-level integration tests for the OpenCode HTTP wrapper our companion script is built on. None of the existing 57 unit tests touched lib/opencode-server.mjs because running them requires a real opencode serve process. The CI workflow now installs opencode-ai so these tests can run.

What's covered

New file tests/opencode-server.test.mjs spawns opencode serve on a high test port (default 14096, override via OPENCODE_TEST_PORT) so it doesn't collide with a developer's default-port server. Tears the server down via SIGTERM in after(), even on test failure.

Test Asserts
isServerRunning detects the spawned server isServerRunning(host, port) returns true after ensureServer
health() reports healthy with a version string { healthy: true, version: "<non-empty>" }
createSession returns an id non-empty string id
listSessions ... contains a freshly-created session listSessions() includes the new id
createSession -> getSession -> deleteSession roundtrip session is fetchable, then 4xx after delete

What's intentionally NOT covered

  • client.sendPrompt / handleReview / handleAdversarialReview end-to-end. These require a configured AI provider and would burn paid API credits in CI on every PR. Codex's CI doesn't run them either. If we want them, they need a separate workflow with secrets.

Local skipping

The whole suite is gated on isOpencodeInstalled() via describe.skip, so developers without opencode on PATH can still run npm test without failures.

CI changes (.github/workflows/ci.yml)

  • New Install OpenCode CLI step: npm install -g opencode-ai. Modeled after codex-plugin-cc's Install Codex CLI step.
  • timeout-minutes 5 → 10 to absorb the CLI install + server startup overhead.
  • Header comment updated.

Test plan

  • Local: node --check tests/opencode-server.test.mjs passes
  • Local: OPENCODE_TEST_PORT=14096 npm test — 62 tests / 0 failures (was 57 / 0 before)
  • Verified the spawned test server is cleaned up after the run (no leftover listener on 14096)
  • CI green on PR — first run of the new install + integration step

Out of scope

While I was sweeping package.json, I noticed "license": "MIT" contradicts the LICENSE file (Apache 2.0). It's an upstream bug we inherited. Worth a separate one-line fix later — not bundled here to keep this PR focused on tests + CI.

…n CI

Adds protocol-level integration tests for the OpenCode HTTP wrapper our
companion script is built on. These were previously untested — none of
the existing 57 unit tests touched `lib/opencode-server.mjs` because
running them requires a real `opencode serve` process. The CI workflow
now installs `opencode-ai` so these tests can run.

New file: `tests/opencode-server.test.mjs`

Spawns `opencode serve` on a high test port (default 14096, override
via `OPENCODE_TEST_PORT`) so it does not collide with a developer's
default-port server. Tears the server down via SIGTERM in `after()`,
even on test failure.

Coverage:

* `isServerRunning` detects the spawned server
* `health()` returns `{ healthy: true, version: <string> }`
* `createSession` returns an id
* `listSessions` includes a freshly-created session
* `createSession` -> `getSession` -> `deleteSession` roundtrip, with
  the post-delete `getSession` rejected with a 4xx

Intentionally does NOT exercise `sendPrompt` because that would call a
configured AI provider and burn paid API credits in CI. End-to-end
review tests will need a separate workflow with secrets.

Local skipping: the entire suite is gated on `isOpencodeInstalled()`
via `describe.skip`, so developers without `opencode` on their PATH can
still run `npm test` without failures.

CI changes (`.github/workflows/ci.yml`):

* New "Install OpenCode CLI" step running `npm install -g opencode-ai`,
  modeled after codex-plugin-cc's `Install Codex CLI` step.
* `timeout-minutes: 5 -> 10` to absorb the cli install + opencode server
  startup overhead.
* Updated header comment to explain we install opencode (not codex).

Test count: 57 -> 62. All passing locally with `OPENCODE_TEST_PORT=14096`.
CI run 24307439945 reported the integration tests passing in 0.3s, then
node:test sat idle for the full 10-minute job timeout before the runner
was forced to terminate an orphan opencode process. Two bugs:

1. Latent upstream bug in `lib/opencode-server.mjs#ensureServer`. It
   spawned `opencode serve` with `stdio: ["ignore", "pipe", "pipe"]`
   but never read the piped stdout/stderr. Those pipe FDs were ref'd on
   the parent's event loop, so any long-lived parent (notably node:test)
   would deadlock once opencode's log output filled the pipe buffer. In
   normal CLI usage the bug was masked because the companion script
   exited fast enough that the OS reaped the pipes. Switching to
   `stdio: "ignore"` redirects opencode's output to /dev/null, removing
   the parent-side handles entirely. This is a real upstream fix and
   has no production-side downside.

2. The test cleanup in `tests/opencode-server.test.mjs#after` killed
   only the spawned PID, not its process group, and had no SIGKILL
   fallback. Since opencode is spawned with `detached: true` it lives
   in its own group; SIGTERM-ing the leader doesn't guarantee the whole
   tree exits. Now we kill `-pid` (the group), poll for graceful exit
   for 3s via `kill(pid, 0)`, and SIGKILL the group as a last resort.

Verified locally with `time OPENCODE_TEST_PORT=14096 npm test`:

  ℹ tests 62
  ℹ pass 62
  real    0m2.034s

Port 14096 is empty after the run.
@JohnnyVicious JohnnyVicious merged commit 6e1e9f0 into main Apr 12, 2026
1 check passed
@JohnnyVicious JohnnyVicious deleted the test/opencode-server-integration branch April 12, 2026 13:20
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.

1 participant