## File: README.md

## Why DBX?



| 🪶 20 MB, zero runtime bloat
      No Java JRE. No Python venv. No bundled Chromium. DBX ships as a single small binary — download, install, connect. DBeaver needs Java; TablePlus is macOS-only. DBX runs everywhere with nothing extra. | 🤖 AI that lives in your editor
      Highlight a table, describe what you want, get SQL back — no copy-paste between tools. Works with Claude, OpenAI, or local models via Ollama. Built-in safety checks review AI-generated SQL before it runs. |
| --- | --- |
| 🔌 MCP: your databases, AI-ready
      DBX speaks the Model Context Protocol. Claude Code, Cursor, Windsurf, and other AI coding agents can query your databases through connections you already set up. One config, everywhere. | 🌐 Desktop + Docker + Web
      Native app on macOS, Windows, and Linux. Self-host via Docker for team access. Web version for browser-only environments. Same feature set. Same connections. |



## Features

### 90+ Databases, One Tool

MySQL, PostgreSQL, SQLite, Cloudflare D1, Redis, MongoDB, DuckDB, ClickHouse, SQL Server, Oracle, Elasticsearch, Easysearch, Meilisearch, Qdrant, Milvus, Weaviate, MariaDB, TiDB, OceanBase, openGauss, GaussDB, KWDB, KingbaseES, Vastbase, GoldenDB, Doris, SelectDB, StarRocks, Manticore Search, Redshift, DM, TDengine, XuguDB, CockroachDB, Access, HighGo, UXDB, Dolt, and more. Agent-based profiles extend DBX to H2, Snowflake, Trino, PrestoSQL, Hive, DB2, Informix, Neo4j, Cassandra, BigQuery, Cloud Spanner, Kylin, SunDB, JDBCX, and custom JDBC connections. New native and agent-driven drivers also cover Databricks, SAP HANA, Teradata, Vertica, Firebird, Exasol, YashanDB, GBase 8a/8s, Databend, RQLite, Turso, InfluxDB, QuestDB, IoTDB, etcd, ZooKeeper, Nacos, Consul KV, IRIS, and more. Message queue admin is also available for Pulsar, Kafka, and RocketMQ. All in a single ~20 MB app. No bundled Chromium.

### Query Editor

CodeMirror 6 with SQL syntax highlighting, metadata-aware autocomplete, `Cmd+Enter` execution, selected SQL execution, SQL formatting, diagnostics, and 9 editor themes. Persistent query history, saved SQL snippets, tab restore, and SQL file execution keep repeat work close at hand.

### AI SQL Assistant

Describe what you want in plain language — get SQL back. DBX can explain queries, optimize SQL, fix errors, and run AI-generated SQL through built-in safety checks. Works with Claude, OpenAI, local models, or any OpenAI-compatible endpoint.

### Data Grid

Virtual-scrolled table that handles large result sets. Inline editing, SQL preview before save, WHERE / ORDER BY controls, DataGrip-style filters, LIKE / NOT LIKE context filters, sorting, full-text search, pagination, column resize, auto-fit, row numbers, zebra stripes, and full cell details. Export or copy as CSV, JSON, Markdown, XLSX, or INSERT statements.

### Schema Tools

- **Schema browser** — databases, schemas, tables, columns, indexes, foreign keys, triggers, with sidebar search & pin
- **Object browser** — grouped procedures, functions, views, and source editing where supported
- **Table structure editor** — reviewable column and index changes for supported engines
- **ER diagram** — visualize table relationships
- **Schema diff** — compare structures across connections
- **Explain plan** — visual query execution plan
- **Field lineage** — column-level lineage analysis
- **Database search** — find objects across large schemas

### Data Operations

- **Table import** — CSV, Excel
- **Data transfer** — migrate between databases
- **Database export** — full database dump
- **Data compare** — compare table data and review synchronization output
- **SQL file execution** — run `.sql` files directly
- **File preview** — drag & drop Parquet, CSV, JSON to preview instantly (powered by DuckDB)
- **Connection import** — bring connection profiles from DBeaver or Navicat

### Specialized Browsers

- **Redis** — key pattern search, batch key operations, command runner, TTL editing, and all data types (String, Hash, List, Set, ZSet, Stream)
- **MongoDB** — document CRUD with pagination, Atlas & replica set URL connection

### Safety & Connectivity

SSH tunnel (key & password) · database and AI proxy settings · auto-reconnect on connection loss · confirmation dialogs for destructive operations · encrypted config export/import · color-coded connections · driver store and optional JDBC plugin

### Polished UI

Dark mode with native title bar sync · 9 editor themes · English, 简体中文 & Español · layout preferences · built-in auto-update

## AI Agent Integration (MCP)

DBX provides a separate [Rust-powered MCP server](packages/mcp-server/) that lets AI coding agents query databases using connections configured in DBX. The MCP server is distributed independently from the desktop application, so installing DBX does not automatically install the MCP executable.

```bash
npx @dbx-app/mcp-server
```

Add to your `.mcp.json`:

```json
{
  "mcpServers": {
    "dbx": { "command": "npx", "args": ["-y", "@dbx-app/mcp-server"] }
  }
}
```

Manage the connection allowlist and the **Read only**, **Data read/write**, and **Full access** modes in **DBX Settings → MCP**. The machine-readable values remain `read_only`, `safe_write`, and `high_risk_write`; client configs do not need permission or connection-scope environment variables.

For upgrade compatibility, an existing `DBX_MCP_ALLOW_WRITES=0` (or `false`) remains a read-only restriction only until a central MCP policy is saved for the first time; it can never enable writes or override a saved policy.

Windows portable builds need `DBX_DATA_DIR` in the MCP config, pointing to the `data` directory next to `DBX.exe` (the folder that contains `dbx.db`).

For DBX Web or Docker deployments, point the MCP server at the Web backend API. If the Web login page requires a password, set `DBX_WEB_PASSWORD` to the same password used there:

```json
{
  "mcpServers": {
    "dbx": {
      "command": "npx",
      "args": ["-y", "@dbx-app/mcp-server"],
      "env": {
        "DBX_WEB_URL": "http://localhost:4224",
        "DBX_WEB_PASSWORD": "your-web-login-password"
      }
    }
  }
}
```

Works with Claude Code, Cursor, Windsurf, and any MCP-compatible agent. Supports listing connections, browsing tables, executing SQL, and opening tables directly in DBX's UI.

Precompiled native binaries are also published for macOS, Linux, and Windows in [package releases](https://github.com/t8y2/dbx/releases?q=packages-v). They run without Node.js and are suitable for offline or server environments. The npm installation uses the same Rust binary through a small Node.js launcher.

DBX also provides a dedicated CLI package for terminal, script, and Codex workflows:

```bash
npm install @dbx-app/cli
# or via Homebrew
brew tap t8y2/tap && brew install dbx-cli
dbx connections list --json
dbx query local "select 1" --json
```

See the [MCP server README](packages/mcp-server/README.md) and [CLI README](packages/cli/README.md) for details.

## Install

Download the latest release from the [Releases](https://github.com/t8y2/dbx/releases/latest) page.

**Homebrew (macOS):**

```bash
brew install --cask dbx
```

**Scoop (Windows):**

```bash
scoop bucket add dbx https://github.com/t8y2/scoop-bucket
scoop install dbx
```

**WinGet (Windows):**

```
winget install t8y2.dbx
```

**Flatpak (Linux):**

```bash
flatpak remote-add --if-not-exists flatpark https://dl.flatpark.org/flatpark.flatpakrepo
flatpak install flatpark com.dbxio.dbx
```

Updates then arrive through the regular `flatpak update`. See the [DBX page on FlatPark](https://flatpark.org/apps/com.dbxio.dbx/) for details.

## Self-Hosted (Docker)

DBX provides a web version that can be deployed via Docker. The examples use
the `latest` tag to pull the current release.

```bash
docker run -d --pull=always --name dbx -p 4224:4224 -v dbx-data:/app/data t8y2/dbx:latest
```

This uses the cross-platform `dbx-data` named volume. Users in China can use
the CNB image, `docker.cnb.cool/dbxio.com/dbx:latest`, for faster pulls.

For Docker Compose, `deploy/docker-compose.yml` remains the source-build
configuration. To deploy a published image, use
`deploy/docker-compose.release.yml`:

```bash
docker compose -f deploy/docker-compose.release.yml up -d
```

```yaml
services:
  dbx:
    image: t8y2/dbx:latest
    # For faster pulls in China, use the CNB image instead:
    # image: docker.cnb.cool/dbxio.com/dbx:latest
    pull_policy: always
    ports:
      - "4224:4224"
    volumes:
      - dbx-data:/app/data
    restart: unless-stopped

volumes:
  dbx-data:
```

Open `http://localhost:4224` in your browser. Multi-arch images (amd64 / arm64) are available.

To publish DBX under a reverse-proxy context path such as `/dbx`, set the
runtime base path and proxy the same prefix to the container:

```yaml
environment:
  - DBX_PUBLIC_BASE_PATH=/dbx
```

When building the frontend yourself with an absolute asset base, set
`VITE_DBX_BASE_PATH=/dbx/` before `pnpm build`.

## Getting Started

### Prerequisites

- [Node.js](https://nodejs.org/) >= 18
- [pnpm](https://pnpm.io/)
- [Rust](https://www.rust-lang.org/tools/install) >= 1.88

#### System Dependencies

**macOS:**

No additional dependencies required.

**Linux (Ubuntu/Debian):**

```bash
sudo apt-get install -y libwebkit2gtk-4.1-dev libgtk-3-dev libappindicator3-dev librsvg2-dev patchelf libssl-dev
```

**NIXOS/NIX :** 

[See README-NIX.md](README-NIX.md)

**Windows:**

No additional dependencies required.

### Development

```bash
make
```

`make` installs root dependencies when needed and starts the local Tauri desktop development environment.

Development builds can run alongside an installed DBX instance and share its local data, including connections and history. Avoid changing the same connection or global setting in both windows at once.

> [!TIP]
> DuckDB compilation takes a while. If you're not working on DuckDB features,
> skip it to speed up local builds:
>
> ```bash
> # Fast checks (skip DuckDB)
> make cargo-check-fast
> make cargo-test-fast
>
> # Tauri dev without DuckDB
> make dev-fast
> ```
>
> The `--no-default-features` flag only affects local development.
> Release builds (`pnpm tauri build`) always include DuckDB.

Web version:

```bash
make dev-web       # frontend
make dev-backend   # backend
```

Documentation site:

```bash
make docs
```

The official DBX documentation site lives in `docs/`. If you want to improve the website content or documentation pages, edit the files under `docs/` and run `make docs` to preview the site locally.

For clean, reproducible local database instances, use the versioned Docker Compose recipes under [`deploy/database/`](deploy/database/README.md):

```bash
make db-list
make db-verify DB=mysql@8.4
```

JDBC agent driver development projects live in `agents/`:

```bash
cd agents
./gradlew test
```

Build artifacts from `agents/drivers/<db-type>/build/libs/` are picked up by local driver install flows when available.

### Build

```bash
make package
```

The installer will be in `src-tauri/target/release/bundle/`.

## Tech Stack

| Layer     | Technology                                                                                                                                                                                                       |
| --------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| Framework | [Tauri 2](https://tauri.app/)                                                                                                                                                                                    |
| Frontend  | [Vue 3](https://vuejs.org/) + TypeScript                                                                                                                                                                         |
| UI        | [shadcn-vue](https://www.shadcn-vue.com/) + Tailwind CSS                                                                                                                                                         |
| Editor    | [CodeMirror 6](https://codemirror.net/)                                                                                                                                                                          |
| Backend   | Rust + [sqlx](https://github.com/launchbadge/sqlx) / [tiberius](https://github.com/prisma/tiberius) / [redis-rs](https://github.com/redis-rs/redis-rs) / [mongodb](https://github.com/mongodb/mongo-rust-driver) |

## Documentation

- [Official docs](https://dbxio.com/en/docs/what-is-dbx) — feature guides and tutorials
- [Database Test Lab](https://dbxio.com/en/docs/database-lab) — local database recipes for development and verification
- [Contributing](CONTRIBUTING.md) — how to pick up issues and open PRs
- [Web API reference](docs/content/docs/web-api.mdx) — HTTP API for Docker/Web deployments
- [Examples](examples/) — CLI, MCP, Docker, and API samples

## Support DBX

DBX is free and open source, but ongoing maintenance, database compatibility testing, infrastructure, and release work require sustained time and resources.

### Sponsors & Partners



|  | RainYun is a cloud service provider offering cloud servers, physical servers, game hosting, and developer-friendly infrastructure services. | [Visit RainYun](https://www.rainyun.com/MTE5Mjc4Ng==_) |
| --- | --- | --- |
|  | Qiniu Cloud provides DBX with object storage, CDN, and other cloud infrastructure resources. | [Visit Qiniu Cloud](https://www.qiniu.com/) |
|  | Easysearch is an enterprise-grade distributed search engine compatible with Elasticsearch APIs, combining full-text, vector, geospatial search, real-time analytics, and AI capabilities in one platform. | [Visit Easysearch](https://easysearch.cn) |
|  | Atlas Cloud gives developers one unified API for 400+ AI models across chat, image, video, and audio. | [Visit Atlas Cloud](https://www.atlascloud.ai/?ref=6YYXWA) |



- [Support DBX](https://my.feishu.cn/wiki/WMTkwdATDiiu4rk14JMcoyhTnoh) — voluntary donations via WeChat or Alipay
- [Sponsors & Partners](https://my.feishu.cn/wiki/CgOWwwTzzify79k9Oq8cXpUNn6e) — sponsorship, infrastructure, tools, and community collaboration

## Contributors

<a href="https://github.com/t8y2/dbx/graphs/contributors">
  
</a>

## Community

[](https://discord.gg/W7NyVDRt6a)
[](https://qm.qq.com/q/1087880322)
[](https://docs.qq.com/doc/DVVhMY0h1ekJqc0tz)
[](https://linux.do)

## Star History

<a href="https://star-history.dera.page/#t8y2/dbx&type=date">
 
   
   
   
 
</a>

## License

[Apache-2.0](LICENSE)

---

## File: agents/docs/examples/jdbc-agent-template/README.md

# JDBC Agent Template

Copy this directory when adding a new JDBC-based DBX agent.

Recommended flow:

1. Rename `template` paths, package names, class names, and artifact names to the new agent name.
2. Replace the driver class and JDBC URL builder.
3. Implement metadata SQL using the target database system catalogs or `DatabaseMetaData`.
4. Keep `executeQuery` delegated to `JdbcExecutor`.
5. Place the module under `drivers/`, then add it to `settings.gradle`, `versions.json`, and the root README support table.
6. Run `./gradlew :<agent>:test :<agent>:shadowJar`.

To verify this template before copying it, run:

```bash
./gradlew -p docs/examples/jdbc-agent-template clean test shadowJar
```

See `docs/agent-authoring.md` for the full checklist.

---

## File: agents/docs/agent-authoring.md

# Agent Authoring Guide

This guide defines the expected shape of a DBX agent. Treat it as the checklist for adding or reviewing an agent.

## Agent Contract

Every agent is a standalone JVM process that:

- Implements `com.dbx.agent.DatabaseAgent`.
- Prefer extending `com.dbx.agent.ConfiguredJdbcAgent` for standard JDBC agents.
- Extend `com.dbx.agent.AbstractJdbcAgent` when the database needs custom metadata SQL but can still share lifecycle and execution behavior.
- Starts with `new JsonRpcServer(new <Agent>()).run()` in its `main` method.
- Talks to DBX over stdin/stdout JSON-RPC 2.0.
- Uses JDBC for database access unless the module is explicitly designed around a non-JDBC protocol.
- Produces one shadow JAR named `dbx-agent-<agent-name>.jar`.

The public behavior should be consistent across agents even when each database has different SQL dialects.

## Required Methods

Each agent must implement these capabilities:

- `connect(params)`: handled by the shared JDBC foundation for JDBC agents.
- `testConnection(params)`: handled by the shared JDBC foundation for JDBC agents.
- `listDatabases()`: return visible catalogs/databases when the database supports them; otherwise return one sensible default database.
- `listSchemas()`: return schemas in stable order.
- `listTables(schema)`: return table-like objects for the selected schema, with normalized `type` values where possible.
- `getColumns(schema, table)`: return column metadata, nullability, defaults, key flags, numeric precision/scale, character length, and comments when available.
- `listIndexes(schema, table)`: return one `IndexInfo` per index, preserving column order.
- `listForeignKeys(schema, table)`: return outbound foreign keys when available.
- `listTriggers(schema, table)`: return triggers when available; return an empty list if the database has no trigger metadata.
- `executeQuery(sql, schema, options)`: inherited from the shared JDBC foundation unless the agent has a documented custom execution behavior.
- `disconnect()`: inherited from the shared JDBC foundation.
- `getConnection()`: inherited from the shared JDBC foundation.

Throw `IllegalStateException("Not connected")` when a method requires a connection and none exists.

## SQL Execution Rules

Do not classify statements by SQL prefix inside individual agents.

For most JDBC agents, inherit this from `AbstractJdbcAgent` or `ConfiguredJdbcAgent`. Do not copy the execution method into the agent class. If a custom value reader is required, override `resultValue(...)`:

```java
@Override
protected Object resultValue(ResultSet rs, int index, int sqlType) {
    return unchecked(() -> rs.getString(index));
}
```

For simple standard JDBC metadata agents, start with a profile:

```java
public final class ExampleAgent extends ConfiguredJdbcAgent {
    public static final JdbcAgentProfile EXAMPLE_PROFILE = new JdbcAgentProfile(
        "com.example.Driver",
        "jdbc:example://{host}:{port}/{database}",
        1234
    );

    public ExampleAgent() {
        super(EXAMPLE_PROFILE);
    }
}
```

`JdbcExecutor` owns these behaviors:

- Trims a trailing semicolon before execution.
- Handles `BEGIN`, `COMMIT`, and `ROLLBACK`.
- Runs schema switching SQL before the user statement.
- Executes statements with `Statement.execute(...)`.
- Reads `ResultSet` output for any statement type, not only `SELECT`.
- Returns update counts for update statements.
- Caps result rows at `options.maxRows`, defaulting to `JdbcExecutor.DEFAULT_MAX_ROWS`.
- Applies `options.fetchSize` to the JDBC statement when provided.
- Marks `truncated = true` only when more rows exist beyond the cap.

An agent must not reintroduce local copies of:

- `QUERY_PREFIXES`
- `MAX_ROWS`
- `executeUpdate(trimmedSql)` in `executeQuery`
- result truncation based on `rows.size >= MAX_ROWS`
- `Class.forName(...)` / `DriverManager.getConnection(...)` lifecycle boilerplate outside shared foundation extension points
- local `disconnect()` copies for JDBC agents
- local `JdbcExecutor.INSTANCE.execute(...)` copies for standard query execution

## Schema And Identifier Rules

Override `setSchemaSQL(schema)` for the database dialect, or configure the profile dialect options when standard quoting is enough.

Use `JdbcIdentifiers` helpers when quoting identifiers:

```java
@Override
public String setSchemaSQL(String schema) {
    return "SET SCHEMA " + JdbcIdentifiers.INSTANCE.doubleQuote(schema);
}
```

If the database does not support a schema switching statement, return an empty string:

```java
@Override
public String setSchemaSQL(String schema) {
    return "";
}
```

Never concatenate unquoted user-provided schema names into schema-switching SQL unless the target database requires unquoted identifiers and the value has already been validated.

For metadata queries, prefer prepared statements for `schema`, `table`, and other user-controlled values.

## Shared JDBC Foundation

Use the smallest shared base that matches the database:

- `ConfiguredJdbcAgent`: standard JDBC lifecycle, execution, and standard `DatabaseMetaData`-based metadata.
- `PostgresLikeAgent`: PostgreSQL-family metadata with shared lifecycle and execution.
- `AbstractJdbcAgent`: custom metadata SQL with shared lifecycle, execution, paging, transactions, result conversion, and DDL fallback.

If a database cannot yet use the shared foundation, add it to the validation allowlist with a specific reason and tests covering the custom behavior. Remove the allowlist entry when the module migrates.

## Driver Packaging

Each module chooses one of two driver modes.

### Bundled Driver

Use this when the driver is redistributable from Maven Central or another permitted repository:

```groovy
dependencies {
    implementation 'com.example:example-jdbc:1.2.3'
}
```

The root Gradle convention supplies `project(':common')`, `project(':test-support')`, JUnit, Java toolchains, the Shadow plugin, and the `dbx-agent-<module>` archive name for included agent modules.

No manifest flag is needed.

### External Driver

Use this when the driver cannot be redistributed or must be supplied by the user:

```groovy
dependencies {
    implementation fileTree(dir: 'libs', include: ['*.jar'])
}

tasks.named('shadowJar') {
    manifest {
        attributes(
            'Agent-Label': 'Example DB',
            'Agent-External-Driver': 'true',
            'Main-Class': 'com.dbx.agent.example.ExampleAgent'
        )
    }
}
```

The release workflow reads `Agent-External-Driver: true` and emits `external_driver_required: true` in `agent-registry.json`.

## Module Registration

When adding an agent named `exampledb`:

- Create the module under `drivers/exampledb`.
- Add `exampledb` to `driverModules` in `settings.gradle`.
- Add `"exampledb": "0.1.0"` to `versions.json`.
- Set `Agent-Label` to the user-facing database name.
- Set `Main-Class` to the Java agent class, usually `com.dbx.agent.exampledb.ExampledbAgent`.
- Add the database to the README support table.

The root `build.gradle` convention derives the archive name from the module name, so `exampledb` builds `dbx-agent-exampledb.jar` without per-module archive configuration.

`versions.json` must contain only modules included in `settings.gradle`, excluding infrastructure modules such as `common` and `test-support`.

## Runtime Selection

Default to:

```groovy
subprojects {
    java {
        toolchain {
            languageVersion = JavaLanguageVersion.of(21)
        }
    }
}
```

All Java agent modules and shared infrastructure modules use Java 21. If an agent needs a special runtime, update the root Gradle convention, the release workflow JRE detection logic, and document the reason in the module.

## Tests

Every JDBC agent should have at least one execution-path regression test.

For agents that can run with an embedded or in-memory database, prefer both shared behavior contracts:

```
/* Detailed source-code truncated for AI context efficiency. */
```

`JdbcExecutionBehaviorTest` verifies non-`SELECT` result set execution, max-row truncation boundaries, and transaction control statements. `JdbcMetadataBehaviorTest` verifies stable metadata ordering. Agents with limited local test infrastructure can adopt the execution contract first and add the metadata contract later.

For agents that need unavailable commercial or external drivers, use the fake execution contract:

```java
class ExampleAgentTest extends JdbcFakeExecutionBehaviorTest {
    @Override
    protected DatabaseAgent createAgent() {
        return new ExampleAgent();
    }

    @Override
    protected String resultSetSql() {
        return "SHOW TABLES";
    }
}
```

`JdbcFakeExecutionBehaviorTest` injects a fake JDBC connection and verifies that `executeQuery` uses `Statement.execute`, reads the returned `ResultSet`, and does not fall back to `executeQuery` or `executeUpdate`. Use `testImplementation project(':test-support')` for this contract.

## Review Checklist

Before opening a PR or release:

- `executeQuery` delegates to `JdbcExecutor.execute`.
- No local SQL-prefix classifier exists.
- No local result row cap exists unless there is a database-specific reason documented in code.
- Metadata methods use prepared statements for user-controlled schema/table inputs.
- `setSchemaSQL` quotes identifiers or returns an empty string.
- `disconnect` closes and clears the connection.
- `testConnection` closes its temporary connection.
- Root `build.gradle` conventions cover Java plugin, toolchain, JUnit, common/test-support dependencies, Shadow plugin, and archive name.
- Module `build.gradle` has correct driver dependencies, `Agent-Label`, `Main-Class`, and external driver flag.
- `settings.gradle`, `versions.json`, and README are updated together.
- At least one execution-path regression test exists.
- `python3 scripts/validate_agents.py` passes.
- `./gradlew test shadowJar --continue` passes.

---

## File: agents/docs/release-checklist.md

# Release Checklist

Use this checklist before pushing release tags or publishing DBX agent jars.

## 1. Confirm Scope

- Review the recent commits:

```bash
git log --oneline -10
```

- Confirm the working tree is clean before tagging:

```bash
git status --short
```

- Check that each intended agent change touches the right module directory, `common`, `test-support`, docs, or workflows.
- Avoid mixing unrelated driver updates, behavior changes, and release-only edits in the same commit.

## 2. Local Verification

On this workspace, use the local JDKs under `/private/tmp`:

```bash
env JAVA_HOME=/private/tmp/dbx-jdk/jdk-21.0.11+10/Contents/Home \
  ./gradlew \
  -Dorg.gradle.java.installations.paths=/private/tmp/dbx-jdk/jdk-21.0.11+10/Contents/Home,/private/tmp/dbx-jdk8/jdk8/Contents/Home \
  test shadowJar --continue
```

Also run the lightweight validation gates:

```bash
python3 -m unittest discover -s scripts -p '*_test.py'
python3 scripts/validate_agents.py
python3 scripts/validate_agent_jars.py
git diff --check
```

The package tests require the `zstd` CLI.

Expected result:

- Python script tests pass.
- `Agent validation passed`.
- `Agent jar validation passed` after `shadowJar` has produced jars.
- `git diff --check` prints nothing.
- Gradle finishes with `BUILD SUCCESSFUL`.

## 3. Agent Contract Checks

For changed agent modules:

- `executeQuery` delegates to `JdbcExecutor.execute`.
- No module-local SQL prefix classifier is present.
- No module-local result row cap is present.
- `Statement.execute(...)` is used for arbitrary user SQL.
- Metadata methods return stable ordering for schemas, tables, columns, indexes, foreign keys, and triggers.
- User-controlled schema and table names are passed through prepared statements or quoted with `JdbcIdentifiers`.
- `connect` stores one connection, `disconnect` closes and clears it, and `testConnection` closes its temporary connection.
- A behavior test exists:
  - Use `JdbcExecutionBehaviorTest` and `JdbcMetadataBehaviorTest` for agents with a local/embedded test database.
  - Use `JdbcFakeExecutionBehaviorTest` for agents that require unavailable external drivers.
  - Use targeted `JdbcMetadataSqlFake` tests for metadata SQL that must interpolate quoted identifiers.

## 4. Registry And Module Checks

Run:

```bash
python3 scripts/validate_agents.py
```

This checks:

- `versions.json` keys match included agent modules in `settings.gradle`.
- Root Gradle conventions define agent archive names.
- Agent manifests define `Agent-Label`.
- Agent manifests define `Main-Class`.
- Agent `Main-Class` source exists and the built jar contains the matching `.class`.
- Forbidden legacy execution patterns are absent.
- Disallowed JVM source/build DSL residue is absent outside Gradle output directories.

When adding or removing an agent, update these files together:

- `settings.gradle`
- `versions.json`
- `README.md`
- Agent module `build.gradle` for driver dependencies and manifest attributes
- Root `build.gradle` only when the module needs non-standard shared build behavior

## 5. Driver Packaging

For bundled drivers:

- Verify the dependency is redistributable.
- Prefer Maven dependencies over checked-in jars.

For external drivers:

- Use `implementation fileTree(dir: 'libs', include: ['*.jar'])`.
- Set the manifest attribute:

```groovy
attributes(
    'Agent-External-Driver': 'true'
)
```

- Confirm release registry generation emits `external_driver_required: true`.

Current external-driver agents include BigQuery and SunDB.

## 6. JRE Selection

Java agents are built for the default JRE key `21`, backed by JDK 21 in the release workflow. Native agents do not require a JRE.

If another agent needs a different runtime, update the release workflow JRE detection logic.
- Document why in the module or release notes.
- Verify DBX can download the matching runtime artifact.

## 7. CI Expectations

The CI workflow runs on `main` and pull requests:

```bash
python3 -m unittest discover -s scripts -p '*_test.py'
python3 scripts/validate_agents.py
./gradlew test shadowJar --continue
python3 scripts/validate_agent_jars.py
```

Do not tag a release while CI is failing on `main`.

## 8. Release Tag Flow

Release workflow runs on tags matching `agents-v*`.

Before tagging:

```bash
git status --short
git log --oneline -5
git tag --list 'agents-v*' --sort=-creatordate | head
```

Choose a new tag that does not already exist locally or on GitHub. For example:

```bash
RELEASE_TAG=agents-v0.3.0
git tag --list "$RELEASE_TAG"
git ls-remote --tags origin "$RELEASE_TAG"
```

Both commands should print nothing before you create the tag.

Create and push the tag:

```bash
git tag "$RELEASE_TAG"
git push origin main
git push origin "$RELEASE_TAG"
```

The release workflow will:

- Resolve the effective previous module versions from the post-release version-sync commit after the previous `agents-v*` tag.
- Bump and build only changed Java or native agent modules.
- Download unchanged single-driver packages and JRE archives from the previous immutable release, then verify filenames, versions, platform coverage, sizes, and SHA-256 digests before reuse.
- Generate `agent-registry.json`.
- Create full offline platform ZIPs from raw staging files.
- Create one `.tar.zst` package per Java or native driver.
- Publish offline ZIPs, single-driver packages, JRE archives, and the registry.

## 9. Post-Release Verification

After the GitHub release finishes:

- Download or inspect `agent-registry.json`.
- Confirm every expected agent appears under `drivers`.
- Confirm labels preserve spaces, for example `Google BigQuery`.
- Confirm Java agents use JRE key `21`.
- Confirm `external_driver_required` is correct.
- Confirm every jar URL, sha256, and size is present.
- Spot-check at least one agent jar manifest:

```bash
unzip -p dbx-agent-h2.jar META-INF/MANIFEST.MF
```

## 10. Known Follow-Ups

- Gradle currently reports deprecated features that will be incompatible with Gradle 10. Use `--warning-mode all` in a separate cleanup task.
- Commercial or external-driver agents still need manual smoke tests with real driver jars and databases.
- Add real containerized smoke tests only one database family at a time.

---

## File: agents/drivers/xugu/README.md

# DBX Xugu Agent

Native XuguDB agent for DBX using `gitee.com/XuguDB/go-xugu-driver`.

## Build

```bash
go build -o agent .
```

Cross-compile release builds use pure Go output:

```bash
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -trimpath -ldflags="-s -w" -o dbx-agent-xugu-linux-x64 .
CGO_ENABLED=0 GOOS=darwin GOARCH=arm64 go build -trimpath -ldflags="-s -w" -o dbx-agent-xugu-macos-aarch64 .
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -trimpath -ldflags="-s -w" -o dbx-agent-xugu-windows-x64.exe .
```

## Local DBX Test

Build the binary, then copy it into DBX's installed XuguDB driver directory:

```bash
mkdir -p ~/.dbx/agents/drivers/xugu
cp agent ~/.dbx/agents/drivers/xugu/agent
chmod +x ~/.dbx/agents/drivers/xugu/agent
```

DBX prefers `agent` over `agent.jar`, so XuguDB connections will use this Go
agent until the file is removed.

To restore the Java/JDBC agent:

```bash
rm ~/.dbx/agents/drivers/xugu/agent
```

---

## File: agents/drivers/oracle-go/README.md

# DBX Oracle Go Agent

Experimental native Oracle agent for DBX using `github.com/sijms/go-ora/v2`.

## Build

```bash
go build -o agent .
```

Cross-compile release builds use pure Go output:

```bash
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -trimpath -ldflags="-s -w" -o dbx-agent-oracle-linux-x64 .
CGO_ENABLED=0 GOOS=darwin GOARCH=arm64 go build -trimpath -ldflags="-s -w" -o dbx-agent-oracle-macos-aarch64 .
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -trimpath -ldflags="-s -w" -o dbx-agent-oracle-windows-x64.exe .
```

## Local DBX Test

Build the binary, then copy it into DBX's installed Oracle driver directory:

```bash
mkdir -p ~/.dbx/agents/drivers/oracle
cp agent ~/.dbx/agents/drivers/oracle/agent
chmod +x ~/.dbx/agents/drivers/oracle/agent
```

DBX prefers `agent` over `agent.jar`, so Oracle connections will use this Go
agent until the file is removed.

To restore the Java agent:

```bash
rm ~/.dbx/agents/drivers/oracle/agent
```

---

## File: agents/README.md

# DBX Agents

English | [简体中文](README.zh-CN.md)

Agent drivers for [DBX](https://github.com/t8y2/dbx) — database support via JDBC and native database drivers.

Each agent runs as a standalone process and communicates with DBX via stdin/stdout JSON-RPC 2.0.

## Supported Databases

| Agent | Database | Driver |
|-------|----------|-------------|
| access | Microsoft Access | UCanAccess |
| dameng | 达梦 DM8 | DM JDBC |
| kingbase | 金仓KingbaseES | gokb Go native agent |
| vastbase | Vastbase | openGauss Go native agent |
| uxdb | UXDB | UXDB JDBC |
| goldendb | GoldenDB | MySQL Connector/J |
| databend | Databend | Databend JDBC |
| databricks | Databricks SQL | Databricks JDBC |
| saphana | SAP HANA | SAP HANA JDBC |
| teradata | Teradata | Teradata JDBC |
| vertica | Vertica | Vertica JDBC |
| firebird | Firebird | Jaybird JDBC |
| exasol | Exasol | Exasol JDBC |
| oceanbase-oracle | OceanBase Oracle Mode | OceanBase JDBC |
| gbase8a | GBase 8a | External GBase 8a JDBC |
| gbase8s | GBase 8s | External GBase 8s JDBC |
| oracle | Oracle 10g+ | go-ora native agent |
| h2 | H2 | H2 JDBC |
| snowflake | Snowflake | Snowflake JDBC |
| trino | Trino (Presto) | Trino JDBC |
| hive | Apache Hive | Native Go HS2 agent |
| db2 | IBM DB2 | DB2 JDBC |
| informix | IBM Informix | Informix JDBC |
| neo4j | Neo4j | Official Neo4j Go Driver native agent |
| cassandra | Apache Cassandra 2.1+ | Apache cassandra-gocql-driver native agent |
| bigquery | Google BigQuery | BigQuery JDBC |
| spanner | Google Cloud Spanner | Google Cloud Spanner JDBC |
| kylin | Apache Kylin | Kylin JDBC |
| ignite | Apache Ignite | Ignite JDBC thin (ignite-core) |
| ignite3 | Apache Ignite 3 | Ignite 3 JDBC thin (ignite-jdbc) |
| sundb | SunDB | SunDB JDBC |
| tdengine | TDengine 2.4+ | taos-connector-rust native WebSocket agent |
| yashandb | 崖山 YashanDB | YashanDB JDBC |
| xugu | 虚谷 XuguDB | XuguDB Go native agent |
| iotdb | Apache IoTDB | Apache IoTDB Go Client native agent |
| etcd | etcd | jetcd |
| zookeeper | Apache ZooKeeper | go-zookeeper native agent |
| rabbitmq | RabbitMQ | amqp091-go native agent |
| rocketmq | Apache RocketMQ | rocketmq-admin-go native agent |


## Multi-JRE Support

Most Java agents target JRE 21. Native agents, such as `cassandra`, `duckdb`, `hive`, `iotdb`, `oracle`, `kingbase`, `tdengine`, `xugu`, `rabbitmq`, `rocketmq`, and `zookeeper`, do not require a JRE. DBX downloads and manages the JRE 21 installation automatically for Java agents.

## JDBC Connection Pooling

All multi-session Java JDBC agents share HikariCP pools inside one Agent runtime through `AbstractJdbcAgent`. Ordinary metadata and short query requests borrow and return a connection, while paged cursors and explicit session-state SQL keep their connection pinned until the cursor or logical session closes. Stateful connections are evicted instead of being reused by another session. Agent-specific URL, transport fallback, encrypted-file, and native-driver behavior is preserved through shared lifecycle hooks.

The default maximum is 8 physical connections per immutable connection identity, with 0 minimum idle connections. This keeps short-query connection pressure bounded while allowing up to 8 concurrently pinned paged cursors or stateful sessions. The defaults can be overridden with JVM system properties or environment variables:

| System property | Environment variable | Default |
|---|---|---:|
| `dbx.agent.jdbc.pool.enabled` | `DBX_AGENT_JDBC_POOL_ENABLED` | `true` |
| `dbx.agent.jdbc.pool.maximumPoolSize` | `DBX_AGENT_JDBC_POOL_MAXIMUM_POOL_SIZE` | `8` |
| `dbx.agent.jdbc.pool.minimumIdle` | `DBX_AGENT_JDBC_POOL_MINIMUM_IDLE` | `0` |
| `dbx.agent.jdbc.pool.connectionTimeoutMillis` | `DBX_AGENT_JDBC_POOL_CONNECTION_TIMEOUT_MILLIS` | `30000` |
| `dbx.agent.jdbc.pool.validationTimeoutMillis` | `DBX_AGENT_JDBC_POOL_VALIDATION_TIMEOUT_MILLIS` | `5000` |
| `dbx.agent.jdbc.pool.idleTimeoutMillis` | `DBX_AGENT_JDBC_POOL_IDLE_TIMEOUT_MILLIS` | `120000` |
| `dbx.agent.jdbc.pool.maxLifetimeMillis` | `DBX_AGENT_JDBC_POOL_MAX_LIFETIME_MILLIS` | `1800000` |
| `dbx.agent.jdbc.pool.retireMillis` | `DBX_AGENT_JDBC_POOL_RETIRE_MILLIS` | `300000` |

HikariCP is shaded into each pooled Agent JAR. Existing installations already using the managed JRE 21 do not need to reinstall or replace the JRE.
Set `DBX_AGENT_JDBC_POOL_ENABLED=false` for a runtime-level compatibility fallback to the previous one-connection-per-logical-session behavior.

## Choosing a Driver Language

For new agents, prefer a **native (Go or Rust) driver** over a Java/JDBC agent whenever a mature, license-compatible native driver is available. Native agents ship as a single self-contained executable with no JRE, which significantly reduces memory footprint and startup time — the JVM baseline that every Java agent pays even when idle is avoided entirely.

- **Native (C++/Go/Rust)** — preferred when a usable native driver exists. See `drivers/cassandra-go` (Apache cassandra-gocql-driver), `drivers/duckdb`, `drivers/hive-go` (native HS2), `drivers/iotdb` (Apache IoTDB Go Client), `drivers/oracle-go` (go-ora), `drivers/kingbase-go` (gokb), `drivers/vastbase-go` (openGauss connector), `drivers/tdengine` (taos-connector-rust), `drivers/xugu`, `drivers/rabbitmq` (amqp091-go), `drivers/rocketmq` (rocketmq-admin-go), and `drivers/zookeeper` (go-zookeeper) as reference implementations. No JRE download or management is needed.
- **Java/JDBC** — the default fallback when only a JDBC driver exists for the database, or when the native driver is immature or unmaintained. Most agents still fall in this category.

Native agents implement the same JSON-RPC contract and `versions.json` registration as Java agents; they ship an `agent` executable instead of `agent.jar`. If both native and Java source implementations exist for the same database, publish only the native artifact unless the Java variant has a separately registered compatibility profile, such as `oracle-legacy` / `oracle-10g`.

## Build

Requires JDK 21 (Gradle toolchain auto-downloads if needed).

```bash
./gradlew shadowJar
(cd drivers/oracle-go && go build -o agent .)
(cd drivers/cassandra-go && go build -o agent .)
(cd drivers/hive-go && go build -o agent .)
(cd drivers/iotdb && go build -o agent .)
(cd drivers/kingbase-go && go build -o agent .)
(cd drivers/vastbase-go && go build -o agent .)
(cargo build --manifest-path drivers/tdengine/Cargo.toml --release --locked)
(cd drivers/xugu && go build -o agent .)
(cd drivers/rabbitmq && go build -o agent .)
(cd drivers/rocketmq && go build -o agent .)
(cd drivers/zookeeper && go build -o agent .)
```

Output JARs are in `drivers/{module}/build/libs/`. Native agents build from `drivers/cassandra-go`, `drivers/duckdb`, `drivers/hive-go`, `drivers/iotdb`, `drivers/oracle-go`, `drivers/kingbase-go`, `drivers/vastbase-go`, `drivers/tdengine`, `drivers/xugu`, `drivers/rabbitmq`, `drivers/rocketmq`, and `drivers/zookeeper`.

### Local DBX Runtime Test

When changing a Java agent under `agents/drivers/<db_type>/` or shared Java agent protocol code, rebuild the target agent and replace the runtime JAR used by the local DBX app:

```bash
./gradlew :<db_type>:shadowJar
cp ~/.dbx/agents/drivers/<db_type>/agent.jar ~/.dbx/agents/drivers/<db_type>/agent.jar.bak
cp agents/drivers/<db_type>/build/libs/*-all.jar ~/.dbx/agents/drivers/<db_type>/agent.jar
```

Restart DBX or disconnect and reconnect the database so the new agent process loads the replacement JAR.

Native agents such as `cassandra`, `hive`, `iotdb`, `oracle`, `kingbase`, `tdengine`, `xugu`, `rabbitmq`, `rocketmq`, and `zookeeper` use an `agent` executable instead of `agent.jar`. TDengine builds `target/release/dbx-tdengine-driver` from `drivers/tdengine/Cargo.toml`.

## Versioning

Agent module versions are tracked in [`versions.json`](versions.json).

- **Changing an existing driver** — do not edit `versions.json` manually. The release CI diffs each `drivers/<module>/` directory against the previous tag and auto-bumps the patch version for every changed module (see [`bump-agent-versions.mjs`](../.github/scripts/bump-agent-versions.mjs)). A change to the shared `agents/common` runtime bumps every module that packages it.
- **Adding a new driver** — add an entry to `versions.json`, e.g. `"rabbitmq": "0.1.0"`. The CI only bumps keys already present in the file, so a new module is invisible to versioning until it is registered here. Java modules must also be added to `settings.gradle`; native modules must be registered in the release version script and workflow. Update the support table in the same change.

## Development

- Agent authoring guide: [docs/agent-authoring.md](docs/agent-authoring.md)
- JDBC agent template: [docs/examples/jdbc-agent-template](docs/examples/jdbc-agent-template)
- Release checklist: [docs/release-checklist.md](docs/release-checklist.md)

## Architecture

```
DBX Main Process (Rust/Tauri)
    │ stdin/stdout (JSON-RPC 2.0)
    ▼
agent / java -jar dbx-agent-{type}.jar
    │
    ▼
Native driver / JDBC → Database
```

## License

[AGPL-3.0](https://github.com/t8y2/dbx/blob/main/LICENSE)

---

## File: agents/README.zh-CN.md

# DBX Agents

[English](README.md) | 简体中文

DBX 的 Agent 驱动 —— 通过 JDBC 和原生数据库驱动支持各种数据库。

每个 agent 作为独立进程运行，通过 stdin/stdout 与 DBX 进行 JSON-RPC 2.0 通信。

## 支持的数据库

| Agent | 数据库 | 驱动 |
|-------|----------|-------------|
| access | Microsoft Access | UCanAccess |
| dameng | 达梦 DM8 | DM JDBC |
| kingbase | 金仓KingbaseES | gokb Go 原生 agent |
| vastbase | Vastbase | openGauss Go 原生 agent |
| uxdb | 优炫 UXDB | UXDB JDBC |
| goldendb | GoldenDB | MySQL Connector/J |
| databend | Databend | Databend JDBC |
| databricks | Databricks SQL | Databricks JDBC |
| saphana | SAP HANA | SAP HANA JDBC |
| teradata | Teradata | Teradata JDBC |
| vertica | Vertica | Vertica JDBC |
| firebird | Firebird | Jaybird JDBC |
| exasol | Exasol | Exasol JDBC |
| oceanbase-oracle | OceanBase Oracle 模式 | OceanBase JDBC |
| gbase8a | GBase 8a | 外部 GBase 8a JDBC |
| gbase8s | GBase 8s | 外部 GBase 8s JDBC |
| oracle | Oracle 10g+ | go-ora 原生 agent |
| h2 | H2 | H2 JDBC |
| snowflake | Snowflake | Snowflake JDBC |
| trino | Trino (Presto) | Trino JDBC |
| hive | Apache Hive | 原生 Go HS2 agent |
| db2 | IBM DB2 | DB2 JDBC |
| informix | IBM Informix | Informix JDBC |
| neo4j | Neo4j | 官方 Neo4j Go Driver 原生 Agent |
| cassandra | Apache Cassandra 2.1+ | Apache cassandra-gocql-driver 原生 Agent |
| bigquery | Google BigQuery | BigQuery JDBC |
| spanner | Google Cloud Spanner | Google Cloud Spanner JDBC |
| kylin | Apache Kylin | Kylin JDBC |
| ignite | Apache Ignite | Ignite JDBC thin（ignite-core） |
| ignite3 | Apache Ignite 3 | Ignite 3 JDBC thin（ignite-jdbc） |
| sundb | SunDB | SunDB JDBC |
| tdengine | TDengine 2.4+ | taos-connector-rust 原生 WebSocket agent |
| yashandb | 崖山 YashanDB | YashanDB JDBC |
| xugu | 虚谷 XuguDB | XuguDB Go 原生 agent |
| iotdb | Apache IoTDB | Apache IoTDB Go Client 原生 Agent |
| etcd | etcd | jetcd |
| zookeeper | Apache ZooKeeper | go-zookeeper 原生 Agent |
| rabbitmq | RabbitMQ | amqp091-go 原生 agent |
| rocketmq | Apache RocketMQ | rocketmq-admin-go 原生 agent |


## 多 JRE 支持

多数 Java agent 以 JRE 21 为目标。原生 agent（如 `cassandra`、`duckdb`、`hive`、`iotdb`、`oracle`、`kingbase`、`tdengine`、`xugu`、`rabbitmq`、`rocketmq` 和 `zookeeper`）不需要 JRE。对 Java agent，DBX 会自动下载并管理 JRE 21 安装。

## JDBC 连接池

所有多会话 Java JDBC agent 都通过 `AbstractJdbcAgent` 在同一个 Agent 运行时内共享 HikariCP 连接池。普通元数据请求和短查询按请求借还连接；分页游标和显式会话态 SQL 会固定连接，直到游标或逻辑会话关闭。带有会话状态的连接会直接淘汰，不会复用于其他会话。各 Agent 特有的 URL、传输协议兜底、加密文件和原生驱动行为通过共享生命周期钩子保留。

默认每个不可变连接身份最多建立 8 个物理连接，最小空闲连接数为 0。该默认值在限制短查询连接压力的同时，允许最多 8 个分页游标或会话态逻辑会话并发固定连接。可通过 JVM system property 或环境变量覆盖：

| System property | 环境变量 | 默认值 |
|---|---|---:|
| `dbx.agent.jdbc.pool.enabled` | `DBX_AGENT_JDBC_POOL_ENABLED` | `true` |
| `dbx.agent.jdbc.pool.maximumPoolSize` | `DBX_AGENT_JDBC_POOL_MAXIMUM_POOL_SIZE` | `8` |
| `dbx.agent.jdbc.pool.minimumIdle` | `DBX_AGENT_JDBC_POOL_MINIMUM_IDLE` | `0` |
| `dbx.agent.jdbc.pool.connectionTimeoutMillis` | `DBX_AGENT_JDBC_POOL_CONNECTION_TIMEOUT_MILLIS` | `30000` |
| `dbx.agent.jdbc.pool.validationTimeoutMillis` | `DBX_AGENT_JDBC_POOL_VALIDATION_TIMEOUT_MILLIS` | `5000` |
| `dbx.agent.jdbc.pool.idleTimeoutMillis` | `DBX_AGENT_JDBC_POOL_IDLE_TIMEOUT_MILLIS` | `120000` |
| `dbx.agent.jdbc.pool.maxLifetimeMillis` | `DBX_AGENT_JDBC_POOL_MAX_LIFETIME_MILLIS` | `1800000` |
| `dbx.agent.jdbc.pool.retireMillis` | `DBX_AGENT_JDBC_POOL_RETIRE_MILLIS` | `300000` |

HikariCP 会直接打进启用连接池的 Agent JAR。已经使用 DBX 托管 JRE 21 的安装无需重新安装或替换 JRE。
如遇特定老驱动兼容问题，可设置 `DBX_AGENT_JDBC_POOL_ENABLED=false`，让该运行时回退到原来的“每个逻辑会话一个连接”行为。

## 选择驱动实现语言

对于新 agent，只要存在成熟、许可证兼容的原生驱动，优先选择**原生（Go 或 Rust）驱动**而非 Java/JDBC agent。原生 agent 以单一自包含可执行文件发布，无需 JRE，可显著降低内存占用和启动时间 —— 完全避开 Java agent 即便空闲也要付出的 JVM 基线开销。

- **原生（Go/Rust）** —— 存在可用原生驱动时首选。参考 `drivers/cassandra-go`（Apache cassandra-gocql-driver）、`drivers/duckdb`、`drivers/hive-go`（原生 HS2）、`drivers/iotdb`（Apache IoTDB Go Client）、`drivers/oracle-go`（go-ora）、`drivers/kingbase-go`（gokb）、`drivers/vastbase-go`（openGauss connector）、`drivers/tdengine`（taos-connector-rust）、`drivers/xugu`、`drivers/rabbitmq`（amqp091-go）、`drivers/rocketmq`（rocketmq-admin-go）和 `drivers/zookeeper`（go-zookeeper）。无需 JRE 下载与管理。
- **Java/JDBC** —— 当某数据库只有 JDBC 驱动，或原生驱动不成熟、缺乏维护时的默认兜底方案。多数 agent 仍属此类。

原生 agent 实现与 Java agent 相同的 JSON-RPC 契约和 `versions.json` 登记；它发布的是 `agent` 可执行文件而非 `agent.jar`。若同一数据库同时保留原生和 Java 源码实现，默认只发布原生产物；只有 Java 变体以独立兼容配置登记时才同时发布，例如 `oracle-legacy` / `oracle-10g`。

## 构建

需要 JDK 21（Gradle toolchain 会自动下载）。

```bash
./gradlew shadowJar
(cd drivers/oracle-go && go build -o agent .)
(cd drivers/cassandra-go && go build -o agent .)
(cd drivers/hive-go && go build -o agent .)
(cd drivers/iotdb && go build -o agent .)
(cd drivers/kingbase-go && go build -o agent .)
(cd drivers/vastbase-go && go build -o agent .)
(cargo build --manifest-path drivers/tdengine/Cargo.toml --release --locked)
(cd drivers/xugu && go build -o agent .)
(cd drivers/rabbitmq && go build -o agent .)
(cd drivers/rocketmq && go build -o agent .)
(cd drivers/zookeeper && go build -o agent .)
```

产物 JAR 在 `drivers/{module}/build/libs/`。原生 agent 从 `drivers/cassandra-go`、`drivers/duckdb`、`drivers/hive-go`、`drivers/iotdb`、`drivers/oracle-go`、`drivers/kingbase-go`、`drivers/vastbase-go`、`drivers/tdengine`、`drivers/xugu`、`drivers/rabbitmq`、`drivers/rocketmq` 和 `drivers/zookeeper` 构建。

### 本地 DBX 运行时测试

修改 `agents/drivers/<db_type>/` 下的 Java agent 或共享 Java agent 协议代码后，需重新构建目标 agent 并替换本地 DBX 应用使用的运行时 JAR：

```bash
./gradlew :<db_type>:shadowJar
cp ~/.dbx/agents/drivers/<db_type>/agent.jar ~/.dbx/agents/drivers/<db_type>/agent.jar.bak
cp agents/drivers/<db_type>/build/libs/*-all.jar ~/.dbx/agents/drivers/<db_type>/agent.jar
```

重启 DBX 或断开重连数据库，使新 agent 进程加载替换后的 JAR。

`cassandra`、`hive`、`iotdb`、`oracle`、`kingbase`、`tdengine`、`xugu`、`rabbitmq`、`rocketmq` 和 `zookeeper` 等原生 agent 使用可执行文件而非 `agent.jar`。TDengine 从 `drivers/tdengine/Cargo.toml` 构建 `target/release/dbx-tdengine-driver`。

## 版本管理

Agent 模块的版本记录在 [`versions.json`](versions.json) 中，遵循以下规则：

- **修改现有驱动**：无需手动编辑 `versions.json`。发版 CI 会把每个 `drivers/<module>/` 目录与上一个 tag 做对比，对有变更的模块自动 bump patch 版本号（见 [`bump-agent-versions.mjs`](../.github/scripts/bump-agent-versions.mjs)）。若改动的是共享运行时 `agents/common`，所有依赖它的模块会一并 bump。
- **新增驱动**：在 `versions.json` 中新增一行，例如 `"rabbitmq": "0.1.0"`。CI 只 bump 文件里已存在的 key，所以新模块在登记到这里之前对版本管理完全不可见。Java 模块还要加入 `settings.gradle`；原生模块要在发版版本脚本与 workflow 中登记，并同步更新上方支持表。

## 开发

- Agent 编写指南：[docs/agent-authoring.md](docs/agent-authoring.md)
- JDBC agent 模板：[docs/examples/jdbc-agent-template](docs/examples/jdbc-agent-template)
- 发布检查清单：[docs/release-checklist.md](docs/release-checklist.md)

## 架构

```
DBX 主进程 (Rust/Tauri)
    │ stdin/stdout (JSON-RPC 2.0)
    ▼
agent / java -jar dbx-agent-{type}.jar
    │
    ▼
原生驱动 / JDBC → 数据库
```

## 许可证

[AGPL-3.0](https://github.com/t8y2/dbx/blob/main/LICENSE)

---

## File: apps/desktop/src/components/mq/README.md

# Message Queue Admin Components

消息队列管理 UI 组件集。

## 组件列表

- **MqAdminConsole.vue** - 主控制台框架
- **TenantsPanel.vue** - 租户管理
- **NamespacesPanel.vue** - 命名空间管理
- **TopicsPanel.vue** - 主题管理
- **SubscriptionsPanel.vue** - 订阅管理
- **MonitoringPanel.vue** - 监控统计

## 使用方式

```vue
<template>
  <MqAdminConsole :connection-id="connectionId" />
</template>

<script setup lang="ts">
import MqAdminConsole from "@/components/mq/MqAdminConsole.vue";

const connectionId = "your-mq-connection-id";
</script>
```

## 文档

完整文档请参考：`docs/mq-index.md`

---

## File: apps/desktop/src/lib/sql/semantic/README.md

# SQL Semantic

This directory owns the pure frontend SQL semantic layer used by editor completion, diagnostics, and navigation.

- `tokens.ts`: span-preserving SQL tokenization and active statement detection.
- `dialect.ts`: dialect adapters for identifier normalization, quoting, qualifier roles, and projection alias visibility.
- `model.ts`: active-statement semantic model, row-source parsing, cursor intent, and confidence/fallback output.
- `completion.ts`: compatibility adapter from semantic intent to the existing SQL completion item builder.
- `references.ts`: shared row-source references for completion, diagnostics, and navigation.
- `diagnostics.ts`: SQL semantic diagnostic helpers and viewport range selection.
- `fixtures.ts` and `types.ts`: test fixtures and shared semantic types.

The older `sqlCompletion.ts` and `sqlNavigation.ts` files remain at `lib/` for now because they are broad public editor utilities. Move them only with a separate behavior-preserving migration.