Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,25 @@ All notable changes to qmax-code. Versions follow [Semantic Versioning](https://

## [Unreleased]

## [1.22.0] - 2026-07-24

### Added
- Added supported standalone local-only mode (`--local`,
`qmax-code config set local_only true`, or `QMAX_LOCAL_ONLY=1`). It skips
QualityMax onboarding and credential loading while retaining local
repository work across built-in and CLI orchestration backends.
- Standalone tool catalogs now expose only planning/workspace file operations
and allowlisted local commands. MCP children inherit the mode, and
execution-time checks reject direct calls to hidden QualityMax tools.

### Documentation
- Updated the README and contributor/security documentation for the v1.21
feature set, including current backends, QA skills, Exposure Receipts, live
feeds, native test execution, sessions, and configuration.
- Added orchestration-mode and command references, and corrected the in-app
`/help` and slash-menu descriptions to reflect the unified backend/model/
effort picker.

## [1.21.2] - 2026-07-22

### Fixed
Expand Down
95 changes: 59 additions & 36 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,13 +27,14 @@ Thanks for your interest in improving `qmax-code`. This document covers everythi
| Requirement | Notes |
|---|---|
| **Go 1.24+** | See `go.mod` for the exact version. `go version` to check. |
| **Anthropic API key** | Required for agent mode. Set via `qmax-code config set anthropic_key <key>` or `ANTHROPIC_API_KEY` env var. |
| **QualityMax account** | Required for cloud tools (test generation, crawl, repo review). Run `qmax-code login` after [signing up](https://app.qualitymax.io). Most unit tests run without one. |
| **Inference backend** | The direct API path needs an Anthropic key. You can instead develop against a logged-in Claude Code/Codex CLI, an enabled OpenCode provider, Cerebras, or Ollama. |
| **QualityMax account** | Required only for connected cloud tools (test generation, crawl, repo review). Standalone `--local` development and most unit tests do not need one. |

Optional but useful:

- [golangci-lint](https://golangci-lint.run/usage/install/) — the CI linter; run it locally to catch issues before pushing
- [Ollama](https://ollama.com) — only needed if working on the local-model (`/ollama`) code path
- [Claude Code](https://claude.ai/download), [Codex](https://github.com/openai/codex), or [OpenCode](https://opencode.ai) — only needed when working on that CLI orchestration backend
- [Ollama](https://ollama.com) or a Cerebras key — only needed when working on that inference adapter

---

Expand Down Expand Up @@ -86,29 +87,40 @@ Tests that hit the QualityMax API or a live Anthropic model are skipped when the

## Architecture overview

```text
main.go Process entry, flags, subcommands, backend startup
internal/repl/repl.go REPL, slash commands, queue, backend switching
internal/agent/agent.go Built-in streaming loop and history compression
internal/agent/tools.go Tool definitions, dispatch, safety, local execution
internal/agent/cc_agent.go Claude Code subprocess backend
internal/agent/codex_agent.go Codex subprocess backend
internal/agent/opencode_agent.go OpenCode subprocess backend
internal/agent/cerebras_agent.go Cerebras native function-calling loop
internal/agent/ollama_agent.go Ollama full-agent mode
internal/api/client.go QualityMax REST client
internal/api/auth.go QualityMax auth and keychain helpers
internal/api/config.go Persistent user configuration
internal/api/providers.go Opt-in OpenCode provider registry
internal/mcp/server.go Embedded stdio MCP server
internal/setup/orch.go MCP registration and skill installation
internal/skills/ Backend-neutral 27-skill catalog/materializer
internal/session/ Local/cloud sessions and prompt queue
internal/tui/ Bubble Tea input, output, themes, media, pickers
internal/security/ Command validation and credential redaction
internal/httpx/ and receipt.go Guarded egress and Exposure Receipts
```
main.go Entry point, flag parsing, REPL bootstrap
agent.go Core Anthropic streaming loop, tool dispatch, history compression
tools.go Tool definitions (BuildToolDefs) and ExecuteTool dispatcher
api_client.go REST client for the QualityMax cloud API
input.go Bubbletea TUI input model, slash-command menu
terminal.go Output rendering, theme application, progress display
theme.go Named color schemes and live-preview theme picker
queue.go Prompt queue — accepts input while the agent is running
mcp_server.go MCP server mode (native tool-use, no Anthropic tokens)
ollama.go Ollama provider adapter
ollama_agent.go Ollama full-agent mode (prompt-based tool dispatch)
cc_agent.go Claude Code sub-agent integration
codex_agent.go Codex/OpenAI-compatible sub-agent integration
auth.go QualityMax login, API key storage, keychain helpers
config.go Config struct, load/save, defaults
security.go Command validation, credential redaction
error_reporting.go Optional Sentry-compatible telemetry (opt-in only)
session.go Session persistence and history
context.go SessionContext — shared state threaded through the agent
```

The main loop lives in `runREPL` (`main.go`). Each user prompt goes to `Agent.RunStreaming` → `runStreamingLoop` → `callStreamingAPI` → `executeToolCallsWithUI`. Tools are defined declaratively in `BuildToolDefs` and dispatched by name in `ExecuteTool`.
The interactive loop lives in `internal/repl/repl.go`. Built-in backend prompts
flow through `Agent.RunStreaming`, while CLI backends implement
`agent.CLIAgent` and receive qmax tools from `internal/mcp/server.go`. Tools are
declared in `BuildToolDefs` and dispatched by `ExecuteTool` in
`internal/agent/tools.go`.

Standalone mode is an explicit capability boundary. New tools must not be added
to `localOnlyToolNames` unless they work without QualityMax credentials, API
calls, the legacy `qmax` CLI, or cloud result reporting. Keep tool discovery
and execution-time rejection tests in sync; MCP clients can call tool names
that were never advertised.

---

Expand All @@ -118,15 +130,16 @@ The main loop lives in `runREPL` (`main.go`). Each user prompt goes to `Agent.Ru

Slash commands are handled in two places — miss either one and the command either won't work or won't appear in the autocomplete menu.

**1. Register the handler** in `runREPL` (`main.go`):
**1. Register the handler** in `runREPL` (`internal/repl/repl.go`):

```go
case input == "/mycommand":
handleMyCommand(agent, term)
continue
```

**2. Add a menu entry** in `input.go` so it appears in the `/` autocomplete:
**2. Add a menu entry** in `internal/tui/input.go` so it appears in the `/`
autocomplete:

```go
var slashMenuItems = []SlashMenuItem{
Expand All @@ -141,7 +154,8 @@ Both steps are required. The menu entry is what users see when they type `/`; th

### Adding an agent tool

Tools are declared in `BuildToolDefs` (`tools.go`) and dispatched in `ExecuteTool`. To add one:
Tools are declared in `BuildToolDefs` (`internal/agent/tools.go`) and dispatched
in `ExecuteTool`. To add one:

**1. Declare the tool** in `buildAllToolDefs`:

Expand All @@ -162,7 +176,8 @@ case "my_tool":
return api.MyTool(ctx, strVal(input, "param_name"))
```

**3. Add the API method** in `api_client.go` if it calls the QualityMax backend:
**3. Add the API method** in `internal/api/client.go` if it calls the QualityMax
backend:

```go
func (c *APIClient) MyTool(ctx context.Context, param string) string {
Expand All @@ -172,13 +187,16 @@ func (c *APIClient) MyTool(ctx context.Context, param string) string {

**4. Assign a cost tier** in `ToolCost` (`tools.go`) — `"low"`, `"medium"`, or `"high"`. This is shown to the user before expensive operations.

Write a test in `api_client_native_test.go` covering the request shape if the tool hits the network.
Write a focused test in `internal/api/` covering the request shape if the tool
hits the network. Outbound HTTP must go through `internal/httpx`; the static
egress guard fails CI if a package constructs an unreceipted raw HTTP client or
request.

---

### Adding a theme

Themes are defined in `theme.go`. Add an entry to the `themes` map:
Themes are defined in `internal/tui/theme.go`. Add an entry to the `themes` map:

```go
"mytheme": {
Expand All @@ -192,7 +210,8 @@ Themes are defined in `theme.go`. Add an entry to the `themes` map:
},
```

Run `go test ./...` — `theme_test.go` validates that all registered themes have complete field sets.
Run `go test ./...` — `internal/tui/theme_test.go` validates that all registered
themes have complete field sets.

---

Expand All @@ -211,14 +230,18 @@ Run `go test ./...` — `theme_test.go` validates that all registered themes hav

Read [SECURITY.md](SECURITY.md) before touching:

- auth or credential storage (`auth.go`, `keychain.go`)
- telemetry or error reporting (`error_reporting.go`)
- `read_file`, `write_file`, `run_command`, or `run_local_test` tool implementations
- command validation logic (`security.go`)
- auth or credential storage (`internal/api/auth.go`, `internal/api/keychain.go`)
- provider configuration or subprocess credential injection
- telemetry or error reporting (`internal/sysutil/error_reporting.go`)
- Exposure Receipts or outbound HTTP (`receipt.go`, `internal/httpx/`)
- `read_file`, `edit_file`, `write_file`, `run_command`, or `run_local_test` tool implementations
- command validation logic (`internal/security/`)
- orchestration consent, global MCP configuration, or skill materialization
- script healing, backup, or rollback behavior
- API error handling or any code path that might log user data

For any of the above, add or update tests in `security_test.go` and note the security impact in your PR description.
For any of the above, add or update focused tests in the owning package and
note the security impact in your PR description.

---

Expand Down
41 changes: 28 additions & 13 deletions OPEN_SOURCE_SCOPE.md
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,12 @@ Public `qmax-code` may contain:

- Terminal UX, command parsing, install/build/release scripts, and docs.
- Client-side auth flows and cloud API calls that are intentionally supported.
- LLM orchestration, tool definitions, local execution helpers, and safety
guards that define the CLI behavior.
- Provider adapters for Anthropic/Ollama and public configuration.
- LLM orchestration, MCP integration, managed QA skills, tool definitions,
local execution helpers, and safety guards that define the CLI behavior.
- Provider adapters for Anthropic, Cerebras, Ollama, Claude Code, Codex, and
OpenCode, including the public opt-in provider registry.
- Exposure Receipt generation and verification, provided that receipts contain
structural egress metadata rather than user content or credentials.

Closed QualityMax monorepo should retain:

Expand Down Expand Up @@ -49,15 +52,19 @@ Before public release, every cloud route/tool should be classified as:

Needs change before opening:

- `error_reporting.go` now requires `QMAX_CODE_TELEMETRY=1` and
- `internal/sysutil/error_reporting.go` now requires `QMAX_CODE_TELEMETRY=1` and
`QMAX_CODE_TELEMETRY_DSN` before initializing Sentry-compatible reporting.
Before release, confirm this opt-in behavior is documented wherever binaries
are distributed.
- `auth.go` stores QualityMax API credentials in `~/.qmax-code/auth.json`
- `internal/api/auth.go` stores QualityMax API credentials in
`~/.qmax-code/auth.json`
with `0600` permissions. `README.md` now documents storage and `/disconnect`
cleanup.
- Known credential patterns are redacted from API errors, command output, local
test output, and optional telemetry before display/reporting.
- `internal/httpx/guard_test.go` keeps outbound HTTP on the receipted transport;
signed manifests are stored under `~/.qmax-code/receipts/` and can be
verified offline.

Likely okay with docs:

Expand All @@ -68,10 +75,11 @@ Likely okay with docs:

Needs product review:

- `api_client.go` publishes the complete client-side REST route map for
- `internal/api/client.go` publishes the complete client-side REST route map for
QualityMax projects, crawls, repository review, k6, QTML, framework export,
PR creation, and background jobs.
- `tools.go` publishes the LLM tool schema, capability descriptions, cost
- `internal/agent/tools.go` publishes the LLM tool schema, capability
descriptions, cost
categories, and agent-facing workflow assumptions.
- `ImportRepo` no longer sends `training_consent` by default. It only sends
`opt_in` or `opt_out` when the user/tool call explicitly provides one.
Expand All @@ -94,6 +102,10 @@ Proposed launch classification:
| Surface | Suggested class | Notes |
| --- | --- | --- |
| Auth and config | public-core | Browser login, API-key login, env/keychain config. |
| Inference backends and orch | public-core | Direct adapters, CLI subprocesses, MCP wiring, permission consent, opt-in providers. |
| Exposure Receipts | public-core | Signed local egress manifests and offline verification. |
| Managed QA skills | public-core | Public catalog materialized into supported coding-agent CLIs. |
| Standalone local-only mode | public-core | No QualityMax auth; exact local tool allowlist enforced at discovery and execution. |
| Projects and test cases | public-core | Basic CRUD/listing is expected client behavior. |
| Automation scripts | public-core | List/get/update plus security scanning are core to the agent. |
| Test generation and execution | public-cloud | Public client can call closed generation/execution services. |
Expand Down Expand Up @@ -134,8 +146,9 @@ Likely okay:

Needs security review:

- The agent exposes `read_file`, `write_file`, and `run_command` tools. There is
some validation, and `SECURITY.md` now documents the trusted-local model.
- The agent exposes `read_file`, `edit_file`, `write_file`, and `run_command`
tools. There is some validation, and `SECURITY.md` now documents the
trusted-local model.
- `runLocalTest` downloads test code from QualityMax and executes Python or
Playwright locally, then reports results back. This is powerful and should be
treated as a prominent security notice; `SECURITY.md` now calls this out.
Expand All @@ -156,7 +169,8 @@ Phase 3 cleanup completed:

Needs product/legal review:

- `agent.go` contains the full system prompt and autonomous healing policy.
- `internal/agent/agent.go` contains the full system prompt and autonomous
healing policy.
This may be acceptable, but it is product-defining behavior and should be
intentionally open-sourced rather than leaked accidentally.
- The system prompt includes product behavior: capability lanes, review
Expand All @@ -175,7 +189,8 @@ Phase 4 cleanup completed:

Likely okay with docs:

- Anthropic and Ollama provider adapters are client behavior and can be public.
- Anthropic, Cerebras, and Ollama adapters plus the Claude Code, Codex, and
OpenCode orchestration paths are client behavior and can be public.
- Prompt-based local-model tool dispatch is publishable as long as the enabled
tool surface is intentionally classified in Phase 2.

Expand All @@ -187,8 +202,8 @@ Likely okay with docs:
- QualityMax reporting in CI now skips when the reporting secret is unavailable,
which keeps public forks cleaner.
- Split private release publishing from public release workflows.
- Decide whether public builds include telemetry, direct QualityMax cloud API,
or only an OSS/local mode.
- Public builds include both the direct QualityMax API path and an explicit
standalone `--local` mode; telemetry remains opt-in.
- Create an issue checklist for any intentionally deferred proprietary cleanup.

Phase 5 cleanup completed:
Expand Down
Loading
Loading