mirror of
https://github.com/chainbase-labs/Agentkey.git
synced 2026-09-20 14:20:23 +08:00
feat: add Cursor, Gemini CLI, and Antigravity plugin support (#91)
## Summary - add the Cursor-native plugin manifest and marketplace metadata with inline AgentKey MCP OAuth - add the root Gemini CLI extension manifest using Streamable HTTP and native OAuth discovery - add one root Antigravity plugin package for both Antigravity 2.0 and Antigravity CLI - configure Antigravity remote MCP with the required `serverUrl` field and automatic OAuth discovery - reuse the existing `skills/agentkey/` package across Gemini and Antigravity without duplication - keep endpoint and release/version synchronization across every client - document Cursor, Gemini, Antigravity 2.0, and Antigravity CLI onboarding in English and Chinese ## Validation - `npx -y bats@1.12.0 tests/` (20/20 passing) - `npx -y @google/gemini-cli@0.54.4 extensions validate .` - verified all eight version values match `1.13.1` - verified Claude, Codex, Cursor, Kimi, Gemini, and Antigravity MCP endpoints remain synchronized - verified the AgentKey endpoint advertises OAuth protected-resource metadata - verified the branch merges cleanly with `chainbase-labs/main` ## Antigravity validation boundary The `agy` binary is not installed in the current environment, so a live CLI install was not run. The plugin layout, manifest fields, `serverUrl`, OAuth configuration, and shared Skill discovery are covered by automated assertions against the current Antigravity documentation. The documentation-prescribed `$schema` URL currently returns HTTP 404; the manifest retains the prescribed value while tests enforce the published schema locally. --------- Co-authored-by: Allen <0xfatdog@gmail.com>
This commit is contained in:
+40
-5
@@ -17,8 +17,14 @@ The same repo also works as a Claude Code plugin (via `.claude-plugin/plugin.jso
|
||||
|
||||
It additionally works as a **Codex plugin** (via `.codex-plugin/plugin.json` + `.codex-plugin/mcp.json`, distributed through `.agents/plugins/marketplace.json` — the repo is its own marketplace, added with `codex plugin marketplace add chainbase-labs/agentkey`). Codex plugins have no `userConfig`/header-interpolation mechanism, so auth uses MCP OAuth instead: the server's `/v1/mcp` endpoint advertises `WWW-Authenticate: Bearer resource_metadata=…` (RFC 9728) and supports dynamic client registration, so `.codex-plugin/mcp.json` needs only `type` + `url` — discovery does the rest. In that mode the OAuth sign-in substitutes for step 2.
|
||||
|
||||
It also works as a **Cursor plugin** (`.cursor-plugin/plugin.json`). The Cursor-native manifest bundles `skills/` and an inline remote-HTTP MCP entry. Cursor authenticates through the server's MCP OAuth discovery, substituting for step 2.
|
||||
|
||||
It also works as a **Kimi Code plugin** (`.kimi-plugin/plugin.json`). Kimi requires `mcpServers` to be an inline object in the manifest. The remote AgentKey endpoint uses Kimi's native MCP OAuth flow; after install Kimi shows the standard `/reload` hint, then the user signs in with `/mcp-config login plugin-agentkey:agentkey` when Kimi reports that OAuth is required.
|
||||
|
||||
It also works as a **Gemini CLI extension** (root `gemini-extension.json` + `skills/`). Gemini requires the manifest at the extension root, discovers bundled agent skills automatically, and connects to AgentKey with `httpUrl` plus native MCP OAuth discovery. `/mcp auth agentkey` substitutes for step 2.
|
||||
|
||||
It also works as an **Antigravity 2.0 and Antigravity CLI plugin** (root `plugin.json` + `mcp_config.json` + `skills/`). Both runtimes use the same package, require `serverUrl` for remote MCP, and authenticate through automatic OAuth discovery.
|
||||
|
||||
## Directory Structure
|
||||
|
||||
```
|
||||
@@ -27,10 +33,15 @@ agentkey/
|
||||
├── .codex-plugin/
|
||||
│ ├── plugin.json # Codex plugin manifest (skills + mcpServers + interface metadata)
|
||||
│ └── mcp.json # Codex MCP entry — http + oauth_resource (NOT the root .mcp.json)
|
||||
├── .cursor-plugin/
|
||||
│ └── plugin.json # Cursor manifest with skills + inline HTTP MCP entry (OAuth)
|
||||
├── .kimi-plugin/
|
||||
│ └── plugin.json # Kimi Code manifest with inline HTTP MCP entry (OAuth)
|
||||
├── .agents/plugins/marketplace.json # Codex marketplace listing this repo as a local-source plugin
|
||||
├── .mcp.json # Auto-registers AgentKey MCP when installed as a Claude Code plugin
|
||||
├── gemini-extension.json # Gemini CLI extension — Streamable HTTP + OAuth discovery
|
||||
├── plugin.json # Antigravity desktop/CLI plugin marker
|
||||
├── mcp_config.json # Antigravity remote MCP entry — serverUrl + OAuth discovery
|
||||
├── skills/agentkey/
|
||||
│ ├── SKILL.md # Decision tree + routing rules (end-user facing)
|
||||
│ ├── scripts/ # check-update helper
|
||||
@@ -58,11 +69,11 @@ git tag -d vX.Y.Z && git push origin :refs/tags/vX.Y.Z
|
||||
gh release delete vX.Y.Z --repo chainbase-labs/agentkey --yes
|
||||
```
|
||||
|
||||
Releases are driven by [release-please](https://github.com/googleapis/release-please): merged PRs with Conventional Commit messages (`feat:`, `fix:`, `feat!:`, etc.) update an open Release PR that bumps `skills/agentkey/version.txt`, all three plugin manifest versions, and `CHANGELOG.md`. Merging the Release PR tags the release and creates the GitHub Release, which in turn triggers plugin updates for users.
|
||||
Releases are driven by [release-please](https://github.com/googleapis/release-please): merged PRs with Conventional Commit messages (`feat:`, `fix:`, `feat!:`, etc.) update an open Release PR that bumps `skills/agentkey/version.txt`, all four versioned plugin manifest versions, `gemini-extension.json`, and `CHANGELOG.md`. The Antigravity manifest has no version field. Merging the Release PR tags the release and creates the GitHub Release, which in turn triggers plugin updates for users.
|
||||
|
||||
## Version & Release Rules
|
||||
|
||||
- `skills/agentkey/version.txt`, the versions in `.claude-plugin/plugin.json`, `.codex-plugin/plugin.json`, and `.kimi-plugin/plugin.json`, plus `CHANGELOG.md`, are managed by release-please based on Conventional Commits — never edit manually except via PR that intentionally amends them.
|
||||
- `skills/agentkey/version.txt`, the versions in `.claude-plugin/plugin.json`, `.codex-plugin/plugin.json`, `.cursor-plugin/plugin.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`, plus `CHANGELOG.md`, are managed by release-please based on Conventional Commits — never edit manually except via PR that intentionally amends them.
|
||||
- `version.txt` lives inside `skills/agentkey/` (not at repo root) so it travels with the skill when the Skills CLI copies the subdirectory. `release-please-config.json` points at this path via `version-file`.
|
||||
- Tag format: `v` prefix (e.g. `v0.4.5`)
|
||||
- Plugin updates trigger on **GitHub Release** publication, not on plain commits
|
||||
@@ -71,7 +82,7 @@ Releases are driven by [release-please](https://github.com/googleapis/release-pl
|
||||
## Change Checklists
|
||||
|
||||
**Changes to any `plugin.json`:**
|
||||
- release-please automatically bumps all three manifest versions + `CHANGELOG.md` from merged conventional-commit PRs; maintainers review + merge the generated Release PR rather than editing these files directly
|
||||
- release-please automatically bumps all four manifest versions + `CHANGELOG.md` from merged conventional-commit PRs; maintainers review + merge the generated Release PR rather than editing these files directly
|
||||
|
||||
**Changes to `.mcp.json`:**
|
||||
- The MCP server is `type: http` (remote endpoint, no subprocess), so inject the API key by interpolating the userConfig value as `${user_config.AGENTKEY_API_KEY}` in the `Authorization` header — the key name MUST match the `plugin.json` `userConfig` key. Do NOT use `${CLAUDE_PLUGIN_OPTION_<KEY>}`: those env vars are only exported to stdio/subprocess servers and hook/monitor commands, and are not interpolated into an http server's headers.
|
||||
@@ -80,14 +91,35 @@ Releases are driven by [release-please](https://github.com/googleapis/release-pl
|
||||
**Changes to `.codex-plugin/mcp.json`:**
|
||||
- Codex plugin MCP config does NOT support `${user_config.*}` interpolation — a literal `${…}` would be sent as the Authorization header. Auth is MCP OAuth via RFC 9728 discovery: the server's 401 advertises `resource_metadata`, and the rmcp client automatically appends `resource=<server url>` to the authorization request.
|
||||
- Do NOT set `oauth_resource`: rmcp already sends `resource` on its own, and Codex appends `oauth_resource` as a *second* `resource` query param without deduplication (`codex-rs/rmcp-client/src/perform_oauth_login.rs`). Clerk enforces RFC 6749 (no repeated params) and rejects the request with `invalid_request: The request includes the parameter 'resource' more than once`. The official Notion/Figma plugins get away with it only because their authorization servers tolerate duplicates.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json` — both must point at the same `/v1/mcp` endpoint.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json`, `.cursor-plugin/plugin.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
|
||||
**Changes to `.cursor-plugin/plugin.json`:**
|
||||
- The manifest MUST stay at `.cursor-plugin/plugin.json`; component paths resolve from the plugin root.
|
||||
- Use only fields documented by the Cursor plugin reference. Do not copy Codex/Kimi-only metadata such as `interface` into this manifest.
|
||||
- Keep `skills` pointed at `./skills/` and `mcpServers` as the minimal inline `{"agentkey":{"url":"https://api.agentkey.app/v1/mcp"}}` entry. Do not add static credentials or `${user_config.*}` interpolation; Cursor handles MCP OAuth itself.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json`, `.codex-plugin/mcp.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
- This repository is a single Cursor plugin, so `.cursor-plugin/marketplace.json` is not required. Submit the public repository URL through Cursor's marketplace publisher.
|
||||
|
||||
**Changes to `.kimi-plugin/plugin.json`:**
|
||||
- `mcpServers` MUST be an inline object. Kimi does not accept a path such as `"./mcp.json"` for this field.
|
||||
- Keep the HTTP entry minimal: `{"agentkey":{"url":"https://api.agentkey.app/v1/mcp"}}`. Kimi infers the transport from `url`.
|
||||
- Do not add `userConfig`, a static Authorization header, or `${user_config.*}` interpolation. Kimi discovers and persists MCP OAuth credentials itself.
|
||||
- Kimi displays `Run /new or /reload to apply plugin changes.` after install. Once reloaded, the user completes native MCP OAuth with `/mcp-config login plugin-agentkey:agentkey` when Kimi reports that authentication is required.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json` and `.codex-plugin/mcp.json`.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json`, `.codex-plugin/mcp.json`, `.cursor-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
|
||||
**Changes to `gemini-extension.json`:**
|
||||
- The manifest MUST remain at the repository root because Gemini installs the repository as the extension root and expects the extension name to match its install directory.
|
||||
- Keep `mcpServers.agentkey` inline and use `httpUrl` for the Streamable HTTP endpoint. Do not use the SSE-only `url` field for `/v1/mcp`.
|
||||
- Do not add static credentials, `settings`, custom headers, or `trust`. Gemini discovers the AgentKey OAuth metadata after the server's 401, and users authenticate with `/mcp auth agentkey`.
|
||||
- Do not duplicate `skills/agentkey/` or add an always-loaded `GEMINI.md`; Gemini discovers the existing skill automatically.
|
||||
- Keep the endpoint URL in sync with `.mcp.json`, `.codex-plugin/mcp.json`, `.cursor-plugin/plugin.json`, and `.kimi-plugin/plugin.json`.
|
||||
|
||||
**Changes to root `plugin.json` / `mcp_config.json`:**
|
||||
- Keep both files at the repository root so Antigravity 2.0 and Antigravity CLI share one plugin package and reuse `skills/agentkey/` without duplication.
|
||||
- Keep `plugin.json` limited to the documented `$schema`, `name`, and `description` fields. The Antigravity schema has no `version` field, so release-please must not add one.
|
||||
- Keep `mcpServers.agentkey` inline in `mcp_config.json` and use `serverUrl`; legacy `url` and `httpUrl` fields are unsupported.
|
||||
- Do not add static credentials, headers, or manual OAuth client secrets. AgentKey supports dynamic client registration, so Antigravity performs automatic OAuth discovery.
|
||||
- Keep the endpoint URL in sync with `.mcp.json`, `.codex-plugin/mcp.json`, `.cursor-plugin/plugin.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
|
||||
**Changes to install/uninstall docs:**
|
||||
- Update both `README.md` and `docs/README_zh.md` together — they mirror each other
|
||||
@@ -99,5 +131,8 @@ Releases are driven by [release-please](https://github.com/googleapis/release-pl
|
||||
- Setup mode in SKILL.md runs `! npx -y @agentkey/cli --auth-login` to authenticate via browser — same command as step 2 of the public install
|
||||
- `@agentkey/cli --auth-login` auto-writes MCP configs for 16 agents (canonical list lives in `AGENT_REGISTRY` in `../AgentKey-Server/cli/src/lib/mcp-clients.ts`): Claude Code, Claude Desktop, Cursor, Codex, Gemini CLI, OpenCode, Qwen Code, iFlow CLI, Kimi CLI, Kiro CLI, Windsurf, Warp, Amp, Crush, droid, openclaw. The `--only <ids>` flag (used by install.sh's `MCP_TARGETS` and install.ps1's `$McpTargets`) filters this list — its id values MUST match `npx skills add -a` ids, with `claude-desktop` as the one documented MCP-only exception. Goose / kode / kilo still need a manual JSON paste (see SKILL.md's "Fallback" section); when adding more agents server-side, keep `MCP_AUTO_AGENTS` in both install scripts and the cleanup list in both uninstall scripts in sync.
|
||||
- `.mcp.json` registers the remote-HTTP MCP endpoint (`https://api.agentkey.app/v1/mcp`) in Claude Code plugin mode; the API key flows from plugin userConfig into the `Authorization: Bearer ${user_config.AGENTKEY_API_KEY}` header (no stdio binary is launched)
|
||||
- `.cursor-plugin/plugin.json` registers the same endpoint inline in Cursor plugin mode, authenticated through Cursor's native MCP OAuth flow
|
||||
- `.kimi-plugin/plugin.json` registers the same endpoint inline in Kimi Code plugin mode. After reloading, the user starts Kimi's native MCP OAuth flow with `/mcp-config login plugin-agentkey:agentkey`.
|
||||
- `gemini-extension.json` registers the same endpoint through `httpUrl` in Gemini CLI extension mode. Gemini discovers the existing `skills/agentkey/` tree and authenticates through `/mcp auth agentkey`.
|
||||
- Root `plugin.json` and `mcp_config.json` package the existing skill and the same endpoint for both Antigravity 2.0 and Antigravity CLI; remote MCP uses `serverUrl` and automatic OAuth discovery.
|
||||
- `README.md` / `docs/README_zh.md` are the public-facing docs; keep them in sync with any structural changes
|
||||
|
||||
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"name": "agentkey",
|
||||
"description": "One-stop live data marketplace for your agent: web search, web scraping, social media, finance, crypto, e-commerce, business data, weather/maps, and travel",
|
||||
"owner": {
|
||||
"name": "Chainbase Labs",
|
||||
"url": "https://agentkey.app"
|
||||
},
|
||||
"plugins": [
|
||||
{
|
||||
"name": "agentkey",
|
||||
"description": "AgentKey — one-stop live data marketplace for your agent: web search, web scraping, social media, finance, crypto, e-commerce, business data, weather/maps, and travel through a single MCP server. No API keys to manage, auto failover across providers, free to start.",
|
||||
"source": "./",
|
||||
"category": "data",
|
||||
"homepage": "https://github.com/chainbase-labs/agentkey",
|
||||
"tags": ["agentkey", "web-search", "scraping", "social-media", "finance", "crypto", "blockchain", "e-commerce", "business-data", "weather", "maps", "travel", "real-time-data"]
|
||||
}
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
{
|
||||
"name": "agentkey",
|
||||
"version": "1.13.1",
|
||||
"description": "AgentKey — one-stop live data marketplace for your agent: web search, web scraping, social media, finance, crypto, e-commerce, business data, weather/maps, and travel through a single MCP server. No API keys to manage, auto failover across providers, free to start.",
|
||||
"author": {
|
||||
"name": "Chainbase Labs"
|
||||
},
|
||||
"homepage": "https://agentkey.app",
|
||||
"license": "MIT",
|
||||
"keywords": [
|
||||
"agentkey",
|
||||
"web-search",
|
||||
"scraping",
|
||||
"social-media",
|
||||
"finance",
|
||||
"crypto",
|
||||
"blockchain",
|
||||
"e-commerce",
|
||||
"business-data",
|
||||
"weather",
|
||||
"maps",
|
||||
"travel",
|
||||
"real-time-data"
|
||||
],
|
||||
"skills": "./skills/",
|
||||
"mcpServers": {
|
||||
"agentkey": {
|
||||
"url": "https://api.agentkey.app/v1/mcp"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -192,7 +192,8 @@ jobs:
|
||||
from release-please itself, which won't trigger this
|
||||
review since author.type == Bot)
|
||||
- `.claude-plugin/plugin.json`, `.codex-plugin/plugin.json`,
|
||||
and `.kimi-plugin/plugin.json` version fields — managed
|
||||
`.cursor-plugin/plugin.json`, and `.kimi-plugin/plugin.json`
|
||||
version fields — managed
|
||||
|
||||
### 4c. Repo invariants
|
||||
- `skills/agentkey/scripts/check-update.sh` REPO line
|
||||
|
||||
@@ -3,11 +3,17 @@ on:
|
||||
push:
|
||||
paths:
|
||||
- 'skills/agentkey/scripts/**'
|
||||
- 'gemini-extension.json'
|
||||
- 'plugin.json'
|
||||
- 'mcp_config.json'
|
||||
- 'tests/**'
|
||||
- '.github/workflows/scripts-test.yml'
|
||||
pull_request:
|
||||
paths:
|
||||
- 'skills/agentkey/scripts/**'
|
||||
- 'gemini-extension.json'
|
||||
- 'plugin.json'
|
||||
- 'mcp_config.json'
|
||||
- 'tests/**'
|
||||
|
||||
jobs:
|
||||
|
||||
@@ -13,7 +13,9 @@ on:
|
||||
- 'skills/agentkey/SKILL.md'
|
||||
- '.claude-plugin/plugin.json'
|
||||
- '.codex-plugin/plugin.json'
|
||||
- '.cursor-plugin/plugin.json'
|
||||
- '.kimi-plugin/plugin.json'
|
||||
- 'gemini-extension.json'
|
||||
- 'release-please-config.json'
|
||||
pull_request:
|
||||
paths:
|
||||
@@ -22,7 +24,9 @@ on:
|
||||
- 'skills/agentkey/SKILL.md'
|
||||
- '.claude-plugin/plugin.json'
|
||||
- '.codex-plugin/plugin.json'
|
||||
- '.cursor-plugin/plugin.json'
|
||||
- '.kimi-plugin/plugin.json'
|
||||
- 'gemini-extension.json'
|
||||
- 'release-please-config.json'
|
||||
|
||||
jobs:
|
||||
@@ -38,19 +42,25 @@ jobs:
|
||||
| head -1 | sed -E 's/^LOCAL_VERSION="([^"]+)".*/\1/')
|
||||
claude_plugin=$(python3 -c 'import json; print(json.load(open(".claude-plugin/plugin.json"))["version"])')
|
||||
codex_plugin=$(python3 -c 'import json; print(json.load(open(".codex-plugin/plugin.json"))["version"])')
|
||||
cursor_plugin=$(python3 -c 'import json; print(json.load(open(".cursor-plugin/plugin.json"))["version"])')
|
||||
kimi_plugin=$(python3 -c 'import json; print(json.load(open(".kimi-plugin/plugin.json"))["version"])')
|
||||
gemini_extension=$(python3 -c 'import json; print(json.load(open("gemini-extension.json"))["version"])')
|
||||
skill=$(awk '/^---/{c++; next} c==1 && /^version:/{print $2; exit}' skills/agentkey/SKILL.md)
|
||||
echo "version.txt: $canonical"
|
||||
echo "check-update.sh: $script"
|
||||
echo "Claude plugin: $claude_plugin"
|
||||
echo "Codex plugin: $codex_plugin"
|
||||
echo "Cursor plugin: $cursor_plugin"
|
||||
echo "Kimi plugin: $kimi_plugin"
|
||||
echo "Gemini extension: $gemini_extension"
|
||||
echo "SKILL.md: $skill"
|
||||
if [ "$canonical" != "$script" ] \
|
||||
|| [ "$canonical" != "$claude_plugin" ] \
|
||||
|| [ "$canonical" != "$codex_plugin" ] \
|
||||
|| [ "$canonical" != "$cursor_plugin" ] \
|
||||
|| [ "$canonical" != "$kimi_plugin" ] \
|
||||
|| [ "$canonical" != "$gemini_extension" ] \
|
||||
|| [ "$canonical" != "$skill" ]; then
|
||||
echo "::error::Version drift detected. release-please syncs all six values from version.txt — re-run release-please or restore the values manually."
|
||||
echo "::error::Version drift detected. release-please syncs all eight values from version.txt — re-run release-please or restore the values manually."
|
||||
exit 1
|
||||
fi
|
||||
|
||||
@@ -17,7 +17,10 @@ The same repo also works as:
|
||||
|
||||
- a **Claude Code plugin** (`.claude-plugin/plugin.json` + root `.mcp.json`) — the plugin's `userConfig` injects the API key via `${user_config.AGENTKEY_API_KEY}`, substituting for step 2.
|
||||
- a **Codex plugin** (`.codex-plugin/plugin.json` + `.codex-plugin/mcp.json`, distributed through `.agents/plugins/marketplace.json`; the repo is its own marketplace: `codex plugin marketplace add chainbase-labs/agentkey`). Codex plugins have no `userConfig`/header-interpolation mechanism, so auth uses MCP OAuth via the server's RFC 9728 metadata discovery (`type` + `url` only in mcp.json), substituting for step 2.
|
||||
- a **Cursor plugin** (`.cursor-plugin/plugin.json`). The Cursor-native manifest bundles `skills/` and an inline remote-HTTP MCP entry. Cursor authenticates through the server's MCP OAuth discovery, substituting for step 2.
|
||||
- a **Kimi Code plugin** (`.kimi-plugin/plugin.json`). Kimi requires `mcpServers` to be an inline object in the manifest. The remote AgentKey endpoint uses Kimi's native MCP OAuth flow; after install Kimi shows the standard `/reload` hint, then the user signs in with `/mcp-config login plugin-agentkey:agentkey` when Kimi reports that OAuth is required.
|
||||
- a **Gemini CLI extension** (root `gemini-extension.json` + `skills/`). Gemini requires the manifest at the extension root, discovers bundled agent skills automatically, and connects to AgentKey with `httpUrl` plus native MCP OAuth discovery. `/mcp auth agentkey` substitutes for step 2.
|
||||
- an **Antigravity 2.0 and Antigravity CLI plugin** (root `plugin.json` + `mcp_config.json` + `skills/`). Both runtimes use the same package, require `serverUrl` for remote MCP, and authenticate through automatic OAuth discovery.
|
||||
|
||||
## Directory Structure
|
||||
|
||||
@@ -27,10 +30,15 @@ agentkey/
|
||||
├── .codex-plugin/
|
||||
│ ├── plugin.json # Codex plugin manifest (skills + mcpServers + interface metadata)
|
||||
│ └── mcp.json # Codex MCP entry — http + oauth_resource (NOT the root .mcp.json)
|
||||
├── .cursor-plugin/
|
||||
│ └── plugin.json # Cursor manifest with skills + inline HTTP MCP entry (OAuth)
|
||||
├── .kimi-plugin/
|
||||
│ └── plugin.json # Kimi Code manifest with inline HTTP MCP entry (OAuth)
|
||||
├── .agents/plugins/marketplace.json # Codex marketplace listing this repo as a local-source plugin
|
||||
├── .mcp.json # Auto-registers AgentKey MCP when installed as a Claude Code plugin
|
||||
├── gemini-extension.json # Gemini CLI extension — Streamable HTTP + OAuth discovery
|
||||
├── plugin.json # Antigravity desktop/CLI plugin marker
|
||||
├── mcp_config.json # Antigravity remote MCP entry — serverUrl + OAuth discovery
|
||||
├── skills/agentkey/
|
||||
│ ├── SKILL.md # Decision tree + routing rules (end-user facing)
|
||||
│ ├── scripts/ # check-update helper
|
||||
@@ -58,11 +66,11 @@ git tag -d vX.Y.Z && git push origin :refs/tags/vX.Y.Z
|
||||
gh release delete vX.Y.Z --repo chainbase-labs/agentkey --yes
|
||||
```
|
||||
|
||||
Releases are driven by [release-please](https://github.com/googleapis/release-please): merged PRs with Conventional Commit messages (`feat:`, `fix:`, `feat!:`, etc.) update an open Release PR that bumps `skills/agentkey/version.txt`, all three plugin manifest versions, and `CHANGELOG.md`. Merging the Release PR tags the release and creates the GitHub Release, which in turn triggers plugin updates for users.
|
||||
Releases are driven by [release-please](https://github.com/googleapis/release-please): merged PRs with Conventional Commit messages (`feat:`, `fix:`, `feat!:`, etc.) update an open Release PR that bumps `skills/agentkey/version.txt`, all four versioned plugin manifest versions, `gemini-extension.json`, and `CHANGELOG.md`. The Antigravity manifest has no version field. Merging the Release PR tags the release and creates the GitHub Release, which in turn triggers plugin updates for users.
|
||||
|
||||
## Version & Release Rules
|
||||
|
||||
- `skills/agentkey/version.txt`, the versions in `.claude-plugin/plugin.json`, `.codex-plugin/plugin.json`, and `.kimi-plugin/plugin.json`, plus `CHANGELOG.md`, are managed by release-please based on Conventional Commits — never edit manually except via PR that intentionally amends them.
|
||||
- `skills/agentkey/version.txt`, the versions in `.claude-plugin/plugin.json`, `.codex-plugin/plugin.json`, `.cursor-plugin/plugin.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`, plus `CHANGELOG.md`, are managed by release-please based on Conventional Commits — never edit manually except via PR that intentionally amends them.
|
||||
- `version.txt` lives inside `skills/agentkey/` (not at repo root) so it travels with the skill when the Skills CLI copies the subdirectory. `release-please-config.json` points at this path via `version-file`.
|
||||
- Tag format: `v` prefix (e.g. `v0.4.5`)
|
||||
- Plugin updates trigger on **GitHub Release** publication, not on plain commits
|
||||
@@ -71,7 +79,7 @@ Releases are driven by [release-please](https://github.com/googleapis/release-pl
|
||||
## Change Checklists
|
||||
|
||||
**Changes to any `plugin.json`:**
|
||||
- release-please automatically bumps all three manifest versions + `CHANGELOG.md` from merged conventional-commit PRs; maintainers review + merge the generated Release PR rather than editing these files directly
|
||||
- release-please automatically bumps all four manifest versions + `CHANGELOG.md` from merged conventional-commit PRs; maintainers review + merge the generated Release PR rather than editing these files directly
|
||||
|
||||
**Changes to the root `.mcp.json` (Claude Code plugin path):**
|
||||
- The MCP server is `type: http` (remote endpoint, no subprocess), so inject the API key by interpolating the userConfig value as `${user_config.AGENTKEY_API_KEY}` in the `Authorization` header — the key name MUST match the `.claude-plugin/plugin.json` `userConfig` key. Do NOT use `${CLAUDE_PLUGIN_OPTION_<KEY>}`: those env vars are only exported to stdio/subprocess servers and hook/monitor commands, and are not interpolated into an http server's headers.
|
||||
@@ -80,14 +88,35 @@ Releases are driven by [release-please](https://github.com/googleapis/release-pl
|
||||
**Changes to `.codex-plugin/mcp.json` (Codex plugin path):**
|
||||
- Codex plugin MCP config does NOT support `${user_config.*}` interpolation — a literal `${…}` would be sent as the Authorization header. Auth is MCP OAuth via RFC 9728 discovery: the server's 401 advertises `resource_metadata`, and the rmcp client automatically appends `resource=<server url>` to the authorization request.
|
||||
- Do NOT set `oauth_resource`: rmcp already sends `resource` on its own, and Codex appends `oauth_resource` as a *second* `resource` query param without deduplication (`codex-rs/rmcp-client/src/perform_oauth_login.rs`). Clerk enforces RFC 6749 (no repeated params) and rejects the request with `invalid_request: The request includes the parameter 'resource' more than once`. The official Notion/Figma plugins get away with it only because their authorization servers tolerate duplicates.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json` — both must point at the same `/v1/mcp` endpoint.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json`, `.cursor-plugin/plugin.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
|
||||
**Changes to `.cursor-plugin/plugin.json` (Cursor plugin path):**
|
||||
- The manifest MUST stay at `.cursor-plugin/plugin.json`; component paths resolve from the plugin root.
|
||||
- Use only fields documented by the Cursor plugin reference. Do not copy Codex/Kimi-only metadata such as `interface` into this manifest.
|
||||
- Keep `skills` pointed at `./skills/` and `mcpServers` as the minimal inline `{"agentkey":{"url":"https://api.agentkey.app/v1/mcp"}}` entry. Do not add static credentials or `${user_config.*}` interpolation; Cursor handles MCP OAuth itself.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json`, `.codex-plugin/mcp.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
- This repository is a single Cursor plugin, so `.cursor-plugin/marketplace.json` is not required. Submit the public repository URL through Cursor's marketplace publisher.
|
||||
|
||||
**Changes to `.kimi-plugin/plugin.json` (Kimi Code plugin path):**
|
||||
- `mcpServers` MUST be an inline object. Kimi does not accept a path such as `"./mcp.json"` for this field.
|
||||
- Keep the HTTP entry minimal: `{"agentkey":{"url":"https://api.agentkey.app/v1/mcp"}}`. Kimi infers the transport from `url`.
|
||||
- Do not add `userConfig`, a static Authorization header, or `${user_config.*}` interpolation. Kimi discovers and persists MCP OAuth credentials itself.
|
||||
- Kimi displays `Run /new or /reload to apply plugin changes.` after install. Once reloaded, the user completes native MCP OAuth with `/mcp-config login plugin-agentkey:agentkey` when Kimi reports that authentication is required.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json` and `.codex-plugin/mcp.json`.
|
||||
- Keep the endpoint URL in sync with the root `.mcp.json`, `.codex-plugin/mcp.json`, `.cursor-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
|
||||
**Changes to `gemini-extension.json` (Gemini CLI extension path):**
|
||||
- The manifest MUST remain at the repository root because Gemini installs the repository as the extension root and expects the extension name to match its install directory.
|
||||
- Keep `mcpServers.agentkey` inline and use `httpUrl` for the Streamable HTTP endpoint. Do not use the SSE-only `url` field for `/v1/mcp`.
|
||||
- Do not add static credentials, `settings`, custom headers, or `trust`. Gemini discovers the AgentKey OAuth metadata after the server's 401, and users authenticate with `/mcp auth agentkey`.
|
||||
- Do not duplicate `skills/agentkey/` or add an always-loaded `GEMINI.md`; Gemini discovers the existing skill automatically.
|
||||
- Keep the endpoint URL in sync with `.mcp.json`, `.codex-plugin/mcp.json`, `.cursor-plugin/plugin.json`, and `.kimi-plugin/plugin.json`.
|
||||
|
||||
**Changes to root `plugin.json` / `mcp_config.json` (Antigravity plugin path):**
|
||||
- Keep both files at the repository root so Antigravity 2.0 and Antigravity CLI share one plugin package and reuse `skills/agentkey/` without duplication.
|
||||
- Keep `plugin.json` limited to the documented `$schema`, `name`, and `description` fields. The Antigravity schema has no `version` field, so release-please must not add one.
|
||||
- Keep `mcpServers.agentkey` inline in `mcp_config.json` and use `serverUrl`; legacy `url` and `httpUrl` fields are unsupported.
|
||||
- Do not add static credentials, headers, or manual OAuth client secrets. AgentKey supports dynamic client registration, so Antigravity performs automatic OAuth discovery.
|
||||
- Keep the endpoint URL in sync with `.mcp.json`, `.codex-plugin/mcp.json`, `.cursor-plugin/plugin.json`, `.kimi-plugin/plugin.json`, and `gemini-extension.json`.
|
||||
|
||||
**Changes to install/uninstall docs:**
|
||||
- Update both `README.md` and `docs/README_zh.md` together — they mirror each other
|
||||
@@ -100,5 +129,8 @@ Releases are driven by [release-please](https://github.com/googleapis/release-pl
|
||||
- `@agentkey/cli --auth-login` auto-writes MCP configs for 16 agents (canonical list lives in `AGENT_REGISTRY` in `../AgentKey-Server/cli/src/lib/mcp-clients.ts`): Claude Code, Claude Desktop, Cursor, Codex, Gemini CLI, OpenCode, Qwen Code, iFlow CLI, Kimi CLI, Kiro CLI, Windsurf, Warp, Amp, Crush, droid, openclaw. The `--only <ids>` flag (used by install.sh's `MCP_TARGETS` and install.ps1's `$McpTargets`) filters this list — its id values MUST match `npx skills add -a` ids, with `claude-desktop` as the one documented MCP-only exception. Goose / kode / kilo still need a manual JSON paste (see SKILL.md's "Fallback" section); when adding more agents server-side, keep `MCP_AUTO_AGENTS` in both install scripts and the cleanup list in both uninstall scripts in sync.
|
||||
- Root `.mcp.json` registers the remote-HTTP MCP endpoint (`https://api.agentkey.app/v1/mcp`) in Claude Code plugin mode; the API key flows from plugin userConfig into the `Authorization: Bearer ${user_config.AGENTKEY_API_KEY}` header (no stdio binary is launched)
|
||||
- `.codex-plugin/mcp.json` registers the same endpoint in Codex plugin mode, authenticated via MCP OAuth (RFC 9728 discovery; no `oauth_resource` — see checklist above)
|
||||
- `.cursor-plugin/plugin.json` registers the same endpoint inline in Cursor plugin mode, authenticated through Cursor's native MCP OAuth flow
|
||||
- `.kimi-plugin/plugin.json` registers the same endpoint inline in Kimi Code plugin mode. After reloading, the user starts Kimi's native MCP OAuth flow with `/mcp-config login plugin-agentkey:agentkey`.
|
||||
- `gemini-extension.json` registers the same endpoint through `httpUrl` in Gemini CLI extension mode. Gemini discovers the existing `skills/agentkey/` tree and authenticates through `/mcp auth agentkey`.
|
||||
- Root `plugin.json` and `mcp_config.json` package the existing skill and the same endpoint for both Antigravity 2.0 and Antigravity CLI; remote MCP uses `serverUrl` and automatic OAuth discovery.
|
||||
- `README.md` / `docs/README_zh.md` are the public-facing docs; keep them in sync with any structural changes
|
||||
|
||||
@@ -380,6 +380,43 @@ Kimi copies local plugins into its managed plugin directory. Re-run `/plugins in
|
||||
|
||||
If you previously worked around an older AgentKey plugin by adding a user-global `agentkey` entry through `/mcp-config`, remove that old entry once with `/mcp-config remove agentkey` before reloading. The plugin now owns its namespaced MCP entry; keeping both would create duplicate tools and authentication attempts.
|
||||
|
||||
**Cursor plugin mode** — install AgentKey from the Cursor Marketplace after the listing is published. The Cursor-native manifest at `.cursor-plugin/plugin.json` bundles the same Skill and an inline remote-HTTP MCP entry, so there is **no API key to paste and no second `@agentkey/cli` step**. When Cursor prompts for MCP authentication, approve the AgentKey browser sign-in.
|
||||
|
||||
For maintainers, push the plugin to a public Git repository and submit the repository URL at [cursor.com/marketplace/publish](https://cursor.com/marketplace/publish). Before submitting, test the plugin in the current Cursor release and confirm that both the `agentkey` Skill and MCP server load successfully after OAuth. The manifest follows the [Cursor plugin reference](https://cursor.com/docs/reference/plugins); keep its component paths relative to the plugin root.
|
||||
|
||||
**Gemini CLI extension mode** — install the repository as an extension. The root `gemini-extension.json` bundles the existing AgentKey skill and the remote Streamable HTTP MCP server, so there is **no API key to paste and no second `@agentkey/cli` step**:
|
||||
|
||||
```bash
|
||||
# Public install
|
||||
gemini extensions install https://github.com/chainbase-labs/agentkey
|
||||
|
||||
# Or link a local checkout for development
|
||||
gemini extensions link /absolute/path/to/agentkey
|
||||
```
|
||||
|
||||
Restart Gemini CLI after installing or linking. If the MCP server requires authentication, run `/mcp auth agentkey` and approve the browser authorization; Gemini then stores and refreshes the OAuth tokens. Use `/mcp reload` after changing the server configuration.
|
||||
|
||||
**Antigravity 2.0 / Antigravity CLI plugin mode** — both runtimes use the root `plugin.json`, `mcp_config.json`, and existing `skills/` directory. The MCP entry uses Antigravity's `serverUrl` schema and automatic OAuth discovery, so there is **no API key to paste and no second `@agentkey/cli` step**.
|
||||
|
||||
For Antigravity 2.0, place the repository at workspace scope or global scope, then restart Antigravity:
|
||||
|
||||
```bash
|
||||
# Workspace scope
|
||||
git clone https://github.com/chainbase-labs/agentkey.git /path/to/workspace/.agents/plugins/agentkey
|
||||
|
||||
# Or global scope
|
||||
git clone https://github.com/chainbase-labs/agentkey.git ~/.gemini/config/plugins/agentkey
|
||||
```
|
||||
|
||||
For Antigravity CLI, install a local checkout and verify it is registered:
|
||||
|
||||
```bash
|
||||
agy plugin install /absolute/path/to/agentkey
|
||||
agy plugin list
|
||||
```
|
||||
|
||||
Antigravity 2.0 exposes OAuth through **Settings → Customizations → Authenticate**. In Antigravity CLI, open `/mcp` to inspect or reload the server and follow the authentication prompt when it first connects.
|
||||
|
||||
**Repo layout:**
|
||||
|
||||
```
|
||||
@@ -388,10 +425,15 @@ agentkey/
|
||||
├── .codex-plugin/
|
||||
│ ├── plugin.json # Codex plugin manifest
|
||||
│ └── mcp.json # Codex MCP entry (OAuth, no user_config)
|
||||
├── .cursor-plugin/
|
||||
│ └── plugin.json # Cursor manifest with Skill + inline MCP OAuth
|
||||
├── .kimi-plugin/
|
||||
│ └── plugin.json # Kimi manifest with inline MCP OAuth entry
|
||||
├── .agents/plugins/marketplace.json # Codex marketplace (this repo is its own marketplace)
|
||||
├── .mcp.json # Used when installed as a Claude Code plugin
|
||||
├── gemini-extension.json # Gemini CLI extension manifest (MCP OAuth + skills)
|
||||
├── plugin.json # Antigravity desktop/CLI plugin manifest
|
||||
├── mcp_config.json # Antigravity remote MCP entry (serverUrl + OAuth)
|
||||
├── skills/agentkey/
|
||||
│ ├── SKILL.md # Decision tree + routing rules
|
||||
│ ├── scripts/ # check-update helper
|
||||
@@ -403,7 +445,7 @@ agentkey/
|
||||
└── uninstall.ps1 # Windows PowerShell uninstaller
|
||||
```
|
||||
|
||||
**Release a new version (maintainers):** releases are cut automatically by [release-please](https://github.com/googleapis/release-please). Merging a PR with a `feat:` or `fix:` title opens a Release PR that bumps `skills/agentkey/version.txt`, all three plugin manifests, and `CHANGELOG.md`. Merging the Release PR creates the tag + GitHub Release + uploads the `agentkey.skill` asset.
|
||||
**Release a new version (maintainers):** releases are cut automatically by [release-please](https://github.com/googleapis/release-please). Merging a PR with a `feat:` or `fix:` title opens a Release PR that bumps `skills/agentkey/version.txt`, all four versioned plugin manifests, `gemini-extension.json`, and `CHANGELOG.md`. The Antigravity schema has no `version` field, so its root `plugin.json` is not part of version syncing. Merging the Release PR creates the tag + GitHub Release + uploads the `agentkey.skill` asset.
|
||||
|
||||
</details>
|
||||
|
||||
|
||||
+43
-1
@@ -380,6 +380,43 @@ Kimi 会把本地插件复制到自己的托管目录。修改原 checkout 后
|
||||
|
||||
如果你曾为旧版 AgentKey plugin 手工通过 `/mcp-config` 添加过用户全局的 `agentkey` 条目,请在 reload 前执行一次 `/mcp-config remove agentkey` 删除旧条目。现在 plugin 会维护自己的命名空间 MCP;同时保留两份会造成工具和鉴权流程重复。
|
||||
|
||||
**Cursor 插件模式** —— 插件上架后,从 Cursor Marketplace 安装 AgentKey。`.cursor-plugin/plugin.json` 这个 Cursor 原生清单会同时捆绑同一个 Skill 和内联的远程 HTTP MCP 配置,因此**不用粘贴 API Key,也不需要再单独运行 `@agentkey/cli`**。Cursor 提示 MCP 需要认证时,在浏览器完成 AgentKey 登录即可。
|
||||
|
||||
维护者需要先把插件推送到公开 Git 仓库,再到 [cursor.com/marketplace/publish](https://cursor.com/marketplace/publish) 提交仓库地址。提交前请使用当前版本 Cursor 实际安装测试,确认 OAuth 完成后 `agentkey` Skill 和 MCP server 都能正常加载。清单遵循 [Cursor 插件参考](https://cursor.com/cn/docs/reference/plugins),其中所有组件路径都必须相对于插件根目录。
|
||||
|
||||
**Gemini CLI 扩展模式** —— 把本仓库直接安装为 extension。根目录的 `gemini-extension.json` 会捆绑现有 AgentKey skill 和远程 Streamable HTTP MCP server,**不用粘贴 API Key,也不需要再单独跑 `@agentkey/cli`**:
|
||||
|
||||
```bash
|
||||
# 公开安装
|
||||
gemini extensions install https://github.com/chainbase-labs/agentkey
|
||||
|
||||
# 或链接本地 checkout,用于开发
|
||||
gemini extensions link /absolute/path/to/agentkey
|
||||
```
|
||||
|
||||
安装或链接后重启 Gemini CLI。如果 MCP server 提示需要认证,执行 `/mcp auth agentkey` 并在浏览器完成授权;之后 Gemini 会保存并自动刷新 OAuth token。修改 server 配置后可执行 `/mcp reload`。
|
||||
|
||||
**Antigravity 2.0 / Antigravity CLI 插件模式** —— 两个运行时共用根目录的 `plugin.json`、`mcp_config.json` 和现有 `skills/`。MCP 配置使用 Antigravity 规定的 `serverUrl` 并依赖自动 OAuth discovery,**不用粘贴 API Key,也不需要再单独运行 `@agentkey/cli`**。
|
||||
|
||||
Antigravity 2.0 可按 workspace 或全局范围放置插件,完成后重启 Antigravity:
|
||||
|
||||
```bash
|
||||
# Workspace 范围
|
||||
git clone https://github.com/chainbase-labs/agentkey.git /path/to/workspace/.agents/plugins/agentkey
|
||||
|
||||
# 或全局范围
|
||||
git clone https://github.com/chainbase-labs/agentkey.git ~/.gemini/config/plugins/agentkey
|
||||
```
|
||||
|
||||
Antigravity CLI 使用本地 checkout 安装并确认注册结果:
|
||||
|
||||
```bash
|
||||
agy plugin install /absolute/path/to/agentkey
|
||||
agy plugin list
|
||||
```
|
||||
|
||||
Antigravity 2.0 在 **Settings → Customizations → Authenticate** 中完成 OAuth。Antigravity CLI 首次连接时按认证提示操作;需要检查状态或重新加载 server 时打开 `/mcp`。
|
||||
|
||||
**仓库结构:**
|
||||
|
||||
```
|
||||
@@ -388,10 +425,15 @@ agentkey/
|
||||
├── .codex-plugin/
|
||||
│ ├── plugin.json # Codex 插件清单
|
||||
│ └── mcp.json # Codex MCP 配置(OAuth,无 user_config)
|
||||
├── .cursor-plugin/
|
||||
│ └── plugin.json # Cursor 清单,捆绑 Skill 与内联 MCP OAuth
|
||||
├── .kimi-plugin/
|
||||
│ └── plugin.json # Kimi 清单,内联 MCP OAuth 配置
|
||||
├── .agents/plugins/marketplace.json # Codex marketplace(本仓库即自己的 marketplace)
|
||||
├── .mcp.json # 作为 Claude Code 插件安装时使用
|
||||
├── gemini-extension.json # Gemini CLI 扩展清单(MCP OAuth + skills)
|
||||
├── plugin.json # Antigravity 桌面端/CLI 插件清单
|
||||
├── mcp_config.json # Antigravity 远程 MCP 配置(serverUrl + OAuth)
|
||||
├── skills/agentkey/
|
||||
│ ├── SKILL.md # 决策树 & 路由规则
|
||||
│ ├── scripts/ # check-update 辅助脚本
|
||||
@@ -403,7 +445,7 @@ agentkey/
|
||||
└── uninstall.ps1 # Windows PowerShell 卸载脚本
|
||||
```
|
||||
|
||||
**发布新版本(Maintainer):** 发版由 [release-please](https://github.com/googleapis/release-please) 自动触发。合并一个 `feat:` 或 `fix:` 的 PR 后,release-please 会开一个 Release PR,自动 bump `skills/agentkey/version.txt`、三个插件清单和 `CHANGELOG.md`。合并这个 Release PR 即会创建 tag + GitHub Release + 上传 `agentkey.skill` 产物。
|
||||
**发布新版本(Maintainer):** 发版由 [release-please](https://github.com/googleapis/release-please) 自动触发。合并一个 `feat:` 或 `fix:` 的 PR 后,release-please 会开一个 Release PR,自动 bump `skills/agentkey/version.txt`、四个带版本号的插件清单、`gemini-extension.json` 和 `CHANGELOG.md`。Antigravity schema 没有 `version` 字段,因此根目录 `plugin.json` 不参与版本同步。合并这个 Release PR 即会创建 tag + GitHub Release + 上传 `agentkey.skill` 产物。
|
||||
|
||||
</details>
|
||||
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
{
|
||||
"name": "agentkey",
|
||||
"version": "1.13.1",
|
||||
"description": "AgentKey gives Gemini CLI one-stop access to live web, social, finance, crypto, e-commerce, business, weather, maps, and travel data.",
|
||||
"mcpServers": {
|
||||
"agentkey": {
|
||||
"httpUrl": "https://api.agentkey.app/v1/mcp"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"mcpServers": {
|
||||
"agentkey": {
|
||||
"serverUrl": "https://api.agentkey.app/v1/mcp"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
{
|
||||
"$schema": "https://antigravity.google/schemas/v1/plugin.json",
|
||||
"name": "agentkey",
|
||||
"description": "AgentKey gives Antigravity one-stop access to live web, social, finance, crypto, e-commerce, business, weather, maps, and travel data."
|
||||
}
|
||||
@@ -20,11 +20,21 @@
|
||||
"path": ".codex-plugin/plugin.json",
|
||||
"jsonpath": "$.version"
|
||||
},
|
||||
{
|
||||
"type": "json",
|
||||
"path": ".cursor-plugin/plugin.json",
|
||||
"jsonpath": "$.version"
|
||||
},
|
||||
{
|
||||
"type": "json",
|
||||
"path": ".kimi-plugin/plugin.json",
|
||||
"jsonpath": "$.version"
|
||||
},
|
||||
{
|
||||
"type": "json",
|
||||
"path": "gemini-extension.json",
|
||||
"jsonpath": "$.version"
|
||||
},
|
||||
{
|
||||
"type": "generic",
|
||||
"path": "skills/agentkey/scripts/check-update.sh"
|
||||
|
||||
@@ -0,0 +1,98 @@
|
||||
#!/usr/bin/env bats
|
||||
|
||||
setup() {
|
||||
REPO_ROOT="$(cd "$BATS_TEST_DIRNAME/.." && pwd)"
|
||||
MANIFEST="$REPO_ROOT/plugin.json"
|
||||
MCP_CONFIG="$REPO_ROOT/mcp_config.json"
|
||||
}
|
||||
|
||||
@test "Antigravity plugin manifest follows the documented schema" {
|
||||
python3 - "$MANIFEST" <<'PY'
|
||||
import json
|
||||
import re
|
||||
import sys
|
||||
|
||||
with open(sys.argv[1], encoding="utf-8") as handle:
|
||||
manifest = json.load(handle)
|
||||
|
||||
assert manifest["$schema"] == "https://antigravity.google/schemas/v1/plugin.json"
|
||||
assert re.fullmatch(r"[a-zA-Z0-9-_]+", manifest["name"])
|
||||
assert manifest["name"] == "agentkey"
|
||||
assert manifest["description"]
|
||||
assert set(manifest) == {"$schema", "name", "description"}
|
||||
assert "version" not in manifest
|
||||
PY
|
||||
}
|
||||
|
||||
@test "Antigravity plugin declares remote MCP with serverUrl" {
|
||||
python3 - "$MCP_CONFIG" <<'PY'
|
||||
import json
|
||||
import sys
|
||||
|
||||
with open(sys.argv[1], encoding="utf-8") as handle:
|
||||
config = json.load(handle)
|
||||
|
||||
assert config == {
|
||||
"mcpServers": {
|
||||
"agentkey": {
|
||||
"serverUrl": "https://api.agentkey.app/v1/mcp",
|
||||
}
|
||||
}
|
||||
}
|
||||
server = config["mcpServers"]["agentkey"]
|
||||
assert "url" not in server
|
||||
assert "httpUrl" not in server
|
||||
PY
|
||||
}
|
||||
|
||||
@test "Antigravity plugin relies on automatic OAuth discovery" {
|
||||
python3 - "$MCP_CONFIG" <<'PY'
|
||||
import json
|
||||
import sys
|
||||
|
||||
with open(sys.argv[1], encoding="utf-8") as handle:
|
||||
server = json.load(handle)["mcpServers"]["agentkey"]
|
||||
|
||||
assert "headers" not in server
|
||||
assert "oauth" not in server
|
||||
assert "authProviderType" not in server
|
||||
PY
|
||||
}
|
||||
|
||||
@test "Antigravity desktop and CLI share the existing AgentKey skill" {
|
||||
[ -f "$REPO_ROOT/skills/agentkey/SKILL.md" ]
|
||||
|
||||
python3 - "$REPO_ROOT/skills/agentkey/SKILL.md" <<'PY'
|
||||
import sys
|
||||
|
||||
with open(sys.argv[1], encoding="utf-8") as handle:
|
||||
skill = handle.read()
|
||||
|
||||
frontmatter = skill.split("---", 2)[1]
|
||||
assert "\nname: agentkey\n" in f"\n{frontmatter}\n"
|
||||
PY
|
||||
}
|
||||
|
||||
@test "Antigravity endpoint stays synchronized with every plugin client" {
|
||||
python3 - "$REPO_ROOT" <<'PY'
|
||||
import json
|
||||
import os
|
||||
import sys
|
||||
|
||||
root = sys.argv[1]
|
||||
configs = {
|
||||
"claude": (".mcp.json", "url"),
|
||||
"codex": (".codex-plugin/mcp.json", "url"),
|
||||
"cursor": (".cursor-plugin/plugin.json", "url"),
|
||||
"kimi": (".kimi-plugin/plugin.json", "url"),
|
||||
"gemini": ("gemini-extension.json", "httpUrl"),
|
||||
"antigravity": ("mcp_config.json", "serverUrl"),
|
||||
}
|
||||
endpoints = {}
|
||||
for client, (relative_path, field) in configs.items():
|
||||
with open(os.path.join(root, relative_path), encoding="utf-8") as handle:
|
||||
endpoints[client] = json.load(handle)["mcpServers"]["agentkey"][field]
|
||||
|
||||
assert set(endpoints.values()) == {"https://api.agentkey.app/v1/mcp"}, endpoints
|
||||
PY
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
#!/usr/bin/env bats
|
||||
|
||||
setup() {
|
||||
REPO_ROOT="$(cd "$BATS_TEST_DIRNAME/.." && pwd)"
|
||||
MANIFEST="$REPO_ROOT/gemini-extension.json"
|
||||
}
|
||||
|
||||
@test "Gemini extension declares the AgentKey Streamable HTTP server inline" {
|
||||
python3 - "$MANIFEST" <<'PY'
|
||||
import json
|
||||
import sys
|
||||
|
||||
with open(sys.argv[1], encoding="utf-8") as handle:
|
||||
manifest = json.load(handle)
|
||||
|
||||
assert manifest["name"] == "agentkey"
|
||||
assert manifest["description"]
|
||||
assert manifest["mcpServers"] == {
|
||||
"agentkey": {
|
||||
"httpUrl": "https://api.agentkey.app/v1/mcp",
|
||||
}
|
||||
}
|
||||
PY
|
||||
}
|
||||
|
||||
@test "Gemini extension relies on native OAuth discovery" {
|
||||
python3 - "$MANIFEST" <<'PY'
|
||||
import json
|
||||
import sys
|
||||
|
||||
with open(sys.argv[1], encoding="utf-8") as handle:
|
||||
manifest = json.load(handle)
|
||||
|
||||
assert "settings" not in manifest
|
||||
server = manifest["mcpServers"]["agentkey"]
|
||||
assert "headers" not in server
|
||||
assert "oauth" not in server
|
||||
assert "authProviderType" not in server
|
||||
assert "trust" not in server
|
||||
PY
|
||||
}
|
||||
|
||||
@test "Gemini extension bundles the existing AgentKey skill" {
|
||||
[ -f "$REPO_ROOT/skills/agentkey/SKILL.md" ]
|
||||
|
||||
python3 - "$REPO_ROOT/skills/agentkey/SKILL.md" <<'PY'
|
||||
import sys
|
||||
|
||||
with open(sys.argv[1], encoding="utf-8") as handle:
|
||||
skill = handle.read()
|
||||
|
||||
frontmatter = skill.split("---", 2)[1]
|
||||
assert "\nname: agentkey\n" in f"\n{frontmatter}\n"
|
||||
PY
|
||||
}
|
||||
Reference in New Issue
Block a user