Plain reference for AI agents
Edgevana Compute Agent
Hourly GPU instances for agents over MCP and A2A. 13 tools. Every launch shows a preview and needs the user’s approval before anything is charged.
Agents can launch hourly GPU offers only. Bare-metal and CPU servers can be searched and priced, not launched.
Files for agents
- Agent Card: A2A Agent Card, JSON
- agents.md: This reference as Markdown
- llms.txt: Index of the files for language models
- API reference: The developer docs, for people
- API keys: Create an edgv_ key (sign-in)
Endpoints
| interface | URL | protocol |
|---|---|---|
| Agent Card | https://edgevana.com/.well-known/agent-card.json | A2A Agent Card, JSON, no auth |
| MCP | https://mcp.edgevana.com/mcp | MCP 2025-03-26 to 2025-11-25, Streamable HTTP |
| A2A JSON-RPC | https://mcp.edgevana.com/a2a/jsonrpc | A2A v0.3, JSON-RPC 2.0 (preferred transport) |
| A2A REST | https://mcp.edgevana.com/a2a/rest | A2A v0.3, HTTP+JSON |
- Auth
- X-API-Key: edgv_... or Authorization: Bearer edgv_...
- API keys
- https://nodes.edgevana.com/profile/api-keys (keys start with edgv_)
- Transport
- Streamable HTTP
- Versions
- MCP 2025-03-26 to 2025-11-25, A2A v0.3
- Agent Card
- Edgevana Edge AI Infrastructure, version 1.13.0, protocol 0.3.0
Approval before anything is charged
launch_instance, request_reserved_instance and terminate_instance run in two calls. The first call, without confirm, returns a preview and changes nothing. Show the preview to the user. Only after the user approves, send the same arguments again with confirm: true.
For launch_instance the preview returns the hourly price and an approval object, plus the deposit due today when the quote succeeds. The confirm call sends the approval object unchanged and a unique idempotency_key. If the offer was just taken, the preview may offer an equivalent one (same GPU, possibly another site) in substituted: show substituted.note, and confirm with substituted.offer_id and substituted.site. If the approved offer is taken by the time you confirm, an equivalent offer at the same site may be launched instead, never above the approved hourly price or deposit; a higher price is refused. The approved deposit is the ceiling. If approval.deposit_due_cents is null, run the preview again: a confirm without a deposit quote is refused.
request_reserved_instance sends a request to Edgevana sales: nothing is ordered or charged. terminate_instance destroys hourly GPU instances immediately, and that cannot be undone.
Tools (13)
These are the MCP names. A2A supports the same actions except request_reserved_instance; there, compare_to_cloud is compare_cloud and get_platform_info is platform_info.
| tool | access | params |
|---|---|---|
| search_servers | Read only | server_type, query, region, site, launchable_only, max_price_hourly, min_vram_gb, min_gpus, min_direct_ports, min_reliability, min_ram_gb, min_cores, sort, detail_sku, offset, limit |
| get_server_specs | Read only | sku |
| get_locations | Read only | country, city |
| check_availability | Read only | site, server_type, sku, limit |
| get_pricing | Read only | server_type, item_id, search, include_locations, limit |
| compare_to_cloud | Read only | workload_type, cloud_provider |
| get_platform_info | Read only | topic |
| launch_instance | Preview, then confirm (spends money) | offer_id (required), site (required), ssh_key, custom_name, disk_gb, ports, onstart, payment_source_id, coupon_ids, confirm, approved (required when confirm: true), idempotency_key (required when confirm: true) |
| request_reserved_instance | Preview, then confirm (no charge) | offer_id (required), site (required), email (required), first_name (required), last_name, quantity, term_months, notes, confirm |
| list_instances | Read only | limit, offset |
| get_instance | Read only | instance_id (required) |
| update_instance | Changes settings, no charge | instance_id (required), ssh_key, cluster, deployment_type, custom_name |
| terminate_instance | Preview, then confirm (destructive) | instance_id (required), when, cancel_reason, confirm |
Discovery and pricing
search_servers
Search GPU and bare-metal offers. Filter by price, VRAM, GPU count and site. GPU offer summaries include launch_status, host_disk_gb and disk_options (the root disk sizes you can choose at launch).
- Access
- Read only
- Group
- Discovery and pricing
| parameter | type | required | default |
|---|---|---|---|
| server_type | gpu | non_gpu | all | no | all |
| query | string | no | |
| region | string | no | |
| site | string | no | |
| launchable_only | boolean | no | |
| max_price_hourly | number | no | |
| min_vram_gb | integer | no | |
| min_gpus | integer | no | |
| min_direct_ports | integer (host.direct_port_count; SSH takes one) | no | |
| min_reliability | number (0 to 1, host.reliability) | no | |
| min_ram_gb | number | no | |
| min_cores | number | no | |
| sort | price | price_desc | vram | vram_desc | no | |
| detail_sku | string | no | |
| offset | integer | no | 0 |
| limit | integer (max 50) | no | 20 |
{
"name": "search_servers",
"arguments": {
"server_type": "gpu",
"launchable_only": true,
"max_price_hourly": 3,
"min_vram_gb": 80,
"limit": 5
}
}get_server_specs
Hardware specs for server SKUs. Give a sku for full details.
- Access
- Read only
- Group
- Discovery and pricing
| parameter | type | required | default |
|---|---|---|---|
| sku | string | no |
{
"name": "get_server_specs",
"arguments": {
"sku": "<sku from search_servers>"
}
}get_locations
Edgevana data center locations, filtered by country or city.
- Access
- Read only
- Group
- Discovery and pricing
| parameter | type | required | default |
|---|---|---|---|
| country | string | no | |
| city | string | no |
{
"name": "get_locations",
"arguments": {
"country": "United States"
}
}check_availability
Live stock for GPU and bare-metal servers by site, type or SKU.
- Access
- Read only
- Group
- Discovery and pricing
| parameter | type | required | default |
|---|---|---|---|
| site | string | no | |
| server_type | gpu | non_gpu | all | no | all |
| sku | string | no | |
| limit | number | no | 30 |
{
"name": "check_availability",
"arguments": {
"server_type": "gpu",
"site": "<site>",
"limit": 10
}
}get_pricing
Prices in USD for GPU and bare-metal servers, with available count. Bare-metal results include estimated_monthly; GPU results include offer_kind and launch_status.
- Access
- Read only
- Group
- Discovery and pricing
| parameter | type | required | default |
|---|---|---|---|
| server_type | gpu | non_gpu | all | no | all |
| item_id | string | no | |
| search | string | no | |
| include_locations | boolean | no | false |
| limit | number (max 50) | no | 20 |
{
"name": "get_pricing",
"arguments": {
"server_type": "gpu",
"search": "H100",
"include_locations": true
}
}compare_to_cloud
Compare Edgevana to AWS, GCP and Azure for a workload type.
- Access
- Read only
- Group
- Discovery and pricing
| parameter | type | required | default |
|---|---|---|---|
| workload_type | ai_inference | ai_training | real_time_voice | gaming | streaming | hft | general | no | general |
| cloud_provider | aws | gcp | azure | all | no | all |
{
"name": "compare_to_cloud",
"arguments": {
"workload_type": "ai_training",
"cloud_provider": "aws"
}
}get_platform_info
Edgevana platform, capabilities and architecture.
- Access
- Read only
- Group
- Discovery and pricing
| parameter | type | required | default |
|---|---|---|---|
| topic | overview | compute | edgeview | edgelink | pricing | security | ai_infrastructure | no | overview |
{
"name": "get_platform_info",
"arguments": {
"topic": "compute"
}
}Instance lifecycle
launch_instance
Launch an hourly GPU instance from an offer. The first call returns a preview with the price, including any chosen disk, and the deposit when the quote succeeds. It also lists any requested ports. A second call with confirm: true launches. With ports, the instance is ready only after every port is mapped. A host that cannot map them fails with ERROR_PORTS_UNMAPPED after the port checks time out, and the service tries to destroy the instance. ERROR_PORTS_UNMAPPED does not confirm destruction. Check the instance (connection.status) before another launch.
- Access
- Preview, then confirm (spends money)
- Group
- Instance lifecycle
| parameter | type | required | default |
|---|---|---|---|
| offer_id | string | required | |
| site | string (one of the offer’s hourly_sites) | required | |
| ssh_key | string | no | |
| custom_name | string | no | |
| disk_gb | integer (within the offer’s disk_options; set at launch only) | no | |
| ports | string[] (e.g. "7946/tcp"; up to 16, 1-65535, not 22) | no | |
| onstart | string (shell script, at most 4096 bytes; runs at every start; no secrets) | no | |
| payment_source_id | string | no | |
| coupon_ids | string[] | no | |
| confirm | boolean | no | false |
| approved | { hourly_cents: integer > 0, deposit_due_cents: integer >= 0 } | required when confirm: true | |
| idempotency_key | string (8-128 characters) | required when confirm: true |
{
"name": "launch_instance",
"arguments": {
"offer_id": "<offer_id>",
"site": "<one of its hourly_sites>",
"ssh_key": "ssh-ed25519 AAAA…"
}
}request_reserved_instance
Send a request for a reserved GPU offer to Edgevana sales. Nothing is ordered or charged.
- Access
- Preview, then confirm (no charge)
- Group
- Instance lifecycle
| parameter | type | required | default |
|---|---|---|---|
| offer_id | string | required | |
| site | string | required | |
| string | required | ||
| first_name | string | required | |
| last_name | string | no | |
| quantity | integer | no | |
| term_months | integer | no | |
| notes | string | no | |
| confirm | boolean | no | false |
{
"name": "request_reserved_instance",
"arguments": {
"offer_id": "<offer_id>",
"site": "<site>",
"email": "[email protected]",
"first_name": "Ada",
"quantity": 8,
"term_months": 12
}
}list_instances
List the instances on your account, each with its connection object.
- Access
- Read only
- Group
- Instance lifecycle
| parameter | type | required | default |
|---|---|---|---|
| limit | number | no | 20 |
| offset | string | no |
{
"name": "list_instances",
"arguments": {
"limit": 20
}
}get_instance
Status, specs, site and billing for one instance. connection holds status (ready, provisioning, failed, destroying or destroyed), public_ip (string or null), ssh (null or { host, port, user }) and ports [{ internal, proto, external, ip }].
- Access
- Read only
- Group
- Instance lifecycle
| parameter | type | required | default |
|---|---|---|---|
| instance_id | string | required |
{
"name": "get_instance",
"arguments": {
"instance_id": "<instance_id>"
}
}update_instance
Change an instance’s SSH key, cluster, deployment type or name.
- Access
- Changes settings, no charge
- Group
- Instance lifecycle
| parameter | type | required | default |
|---|---|---|---|
| instance_id | string | required | |
| ssh_key | string | no | |
| cluster | string | no | |
| deployment_type | string | no | |
| custom_name | string | no |
{
"name": "update_instance",
"arguments": {
"instance_id": "<instance_id>",
"custom_name": "training-01"
}
}terminate_instance
Destroy an instance. Preview first, then confirm. Hourly GPU instances are always destroyed immediately (deprovisioned now; cannot be undone). Other instances can only be destroyed with when: Immediately for now; EndOfTerm is refused.
- Access
- Preview, then confirm (destructive)
- Group
- Instance lifecycle
| parameter | type | required | default |
|---|---|---|---|
| instance_id | string | required | |
| when | Immediately (EndOfTerm is refused for now) | no | |
| cancel_reason | string | no | |
| confirm | boolean | no | false |
{
"name": "terminate_instance",
"arguments": {
"instance_id": "<instance_id>"
}
}Lifecycle (5 steps)
Values in angle brackets come from earlier calls; the approved object is an example, send the one from your preview.
1. Search
Pick an offer with launch_status "available". Note its offer_id and one of its hourly_sites.
{ "name": "search_servers", "arguments": { "server_type": "gpu", "query": "H100", "launchable_only": true, "sort": "price" } }2. Preview launch
Returns the hourly price and an approval object, plus the deposit due today when the quote succeeds. Nothing is created. Show it to the user. If the deposit could not be quoted (approval.deposit_due_cents is null), run the preview again: a confirm without a deposit quote is refused.
{ "name": "launch_instance", "arguments": { "offer_id": "<offer_id>", "site": "<one of the offer’s hourly_sites>", "ssh_key": "ssh-ed25519 AAAA..." } }3. Confirm launch
After the user approves: same args (or the substituted offer_id and site), confirm: true, the approval object unchanged, and a unique idempotency_key. If the approved offer is taken by the time you confirm, an equivalent offer at the same site may be launched instead, never above the approved hourly price or deposit; a higher price is refused.
{ "name": "launch_instance", "arguments": { "offer_id": "<offer_id>", "site": "<one of the offer’s hourly_sites>", "ssh_key": "ssh-ed25519 AAAA...", "confirm": true, "approved": { "hourly_cents": 89, "deposit_due_cents": 2500 }, "idempotency_key": "00000000-0000-4000-8000-000000000001" } }4. Monitor
Check connection.status: ready, provisioning, failed, destroying or destroyed. destroying means the instance is cancelled but not yet confirmed gone. When ready, connection.ports lists mapped ports. connection.public_ip and connection.ssh can be null even when ready. Check connection.ssh before you read its host, port and user. When status is not ready, public_ip and ssh are null, and ports is [].
{ "name": "get_instance", "arguments": { "instance_id": "<instance_id>" } }5. Destroy
Call without confirm for a preview, then again with confirm: true. Hourly GPU instances are destroyed immediately; EndOfTerm is refused for them.
{ "name": "terminate_instance", "arguments": { "instance_id": "<instance_id>", "confirm": true } }
A completed retry with the same idempotency_key and arguments returns the first result while the server keeps its record. That record resets when the server restarts. After an interrupted or failed launch, check list_instances before you retry.
Offers
GPU offer summaries returned by search_servers include launch_status and launch_note:
- available
- launch with launch_instance
- coming_soon
- not open for instant launch yet
- request
- reserved offer; send a no-charge request with request_reserved_instance over MCP
- sold_out
- no stock right now
Billing and deposits
Hourly GPU takes a non-refundable deposit when the instance is created. The amount depends on the hourly price, and the launch preview shows it (deposit.due_today). Credit already on the account counts towards it, and the deposit comes back as account credit against usage. Without an ssh_key the instance is billed but not provisioned.
Inbound ports and the connection object
launch_instance takes optional ports, such as ["7946/tcp", "7946/udp"]: up to 16, from 1 to 65535, not 22 (SSH is always mapped). The preview lists the normalized ports. The instance is ready only after every port is mapped.
A host that cannot map them fails with ERROR_PORTS_UNMAPPED after the port checks time out, and the service tries to destroy the instance. ERROR_PORTS_UNMAPPED does not confirm destruction. Check the instance (connection.status) before another launch. No hourly usage is billed before the instance is ready; the deposit stays as account credit.
Only hosts with direct ports can map ports, and SSH takes one of them: GPU offers report host.direct_port_count and host.reliability, so for N ports search with min_direct_ports N + 1 (and min_reliability, for example 0.99). The launch is refused before any spend when the host is known to have too few direct ports.
get_instance and list_instances return a connection object for each instance:
{
"status": "ready",
"public_ip": "203.0.113.7",
"ssh": {
"host": "203.0.113.7",
"port": 40022,
"user": "root"
},
"ports": [
{
"internal": 7946,
"proto": "tcp",
"external": 41234,
"ip": "203.0.113.7"
}
],
"destroyed_at": null
}destroyed_at is the confirmed destroy time after a cancel. It is null before that, after a failed launch is cleaned up, or when the time is unknown, and servers before 1.10.0 omit it. subscription.cancelled_at is the billing term start, not the destroy time.
Startup script (onstart)
launch_instance takes an optional onstart: a shell script of at most 4096 bytes (UTF-8, no NUL) that runs as root when the instance starts, and again on every restart, so make it safe to run twice. Instances run ubuntu:22.04 with the NVIDIA driver, and no CUDA libraries or Python; install what the workload needs in the script, and start long-running services in the background (setsid or nohup). The script is stored in plain text with the order: never put secrets in it. The preview and instance responses show only its bytes and sha256. The instance is ready when SSH accepts connections, not when the script finishes, so have the script delete a marker file first, write it as its last step, and check for it.
Limits
- Results per call
- search_servers and get_pricing: limit up to 50, default 20. check_availability: default 30.
- Inbound ports
- Up to 16 per instance, from 1 to 65535, not 22.
- Startup script
- onstart: at most 4096 bytes, UTF-8, no NUL.
- Root disk
- disk_gb within the offer’s disk_options, set at launch only; it cannot be resized later.
- Idempotency key
- 8 to 128 characters, unique per launch.
- Deposit
- Set by the hourly price; the launch preview shows the amount.
- Request rate limits
- Not published.
Connect
Claude Code
Run in your terminal, then claude mcp list to confirm.
claude mcp add --transport http edgevana https://mcp.edgevana.com/mcp --header "X-API-Key: YOUR_EDGV_KEY"Codex
Add to ~/.codex/config.toml, and export EDGEVANA_API_KEY=edgv_… before starting Codex.
[mcp_servers.edgevana]
url = "https://mcp.edgevana.com/mcp"
env_http_headers = { "X-API-Key" = "EDGEVANA_API_KEY" }Cursor
Paste into Settings → MCP, or ~/.cursor/mcp.json.
{
"mcpServers": {
"edgevana": {
"url": "https://mcp.edgevana.com/mcp",
"headers": {
"X-API-Key": "<your-edgv_...-key>"
}
}
}
}Claude Desktop
Paste into Edit config, or claude_desktop_config.json.
{
"mcpServers": {
"edgevana": {
"command": "npx",
"args": [
"-y",
"[email protected]",
"https://mcp.edgevana.com/mcp",
"--header",
"X-API-Key:${EDGEVANA_API_KEY}"
],
"env": {
"EDGEVANA_API_KEY": "<your-edgv_...-key>"
}
}
}
}A2A
Send a task message to the JSON-RPC endpoint.
curl -X POST https://mcp.edgevana.com/a2a/jsonrpc \
-H "Content-Type: application/json" \
-H "X-API-Key: YOUR_EDGV_API_KEY" \
-d '{"jsonrpc":"2.0","method":"message/send","id":1,"params":{"message":{"kind":"message","messageId":"msg-1","role":"user","parts":[{"kind":"text","text":"Find GPU servers"}]}}}'Agent Card
Read the card, no key needed.
curl https://edgevana.com/.well-known/agent-card.jsonA command-line tool is coming soon. Until then, connect over MCP or A2A as above.





