Overview
The flagship feature: a complete, production-ready protocol enabling autonomous agents to discover each other, negotiate rates, open payment streams, meter usage, and settle — entirely programmatically without human involvement.
Scope (~3500 lines)
Protocol Design (docs/AGENT_PAYMENT_PROTOCOL.md)
- Full specification of the handshake, negotiation, and settlement flow
- Rate negotiation: buyer proposes rate, seller accepts/counters, final rate stored off-chain with on-chain commitment
- Metering: each API call decrements an off-chain counter; on-chain settlement happens in batches
Backend Protocol Layer (backend/src/protocol/)
AgentHandshake.js — POST /api/v1/protocol/handshake — buyer agent presents public key + desired asset ID, server returns current price, available license types, and a signed quote (valid 60s)
QuoteManager.js — generates and validates signed quotes using HMAC-SHA256, stores pending quotes in Redis/memory with TTL
StreamNegotiator.js — handles rate negotiation between two agent public keys, stores agreed terms, issues a stream_token JWT
MeteringEngine.js — POST /api/v1/protocol/meter — validates stream_token JWT, decrements call counter atomically (using DB row lock), returns { calls_remaining, settle_now: bool }
BatchSettler.js — runs every 60s, finds streams where calls_used >= batch_size (25), triggers on-chain withdraw for accumulated payments
StreamMonitor.js — watches for streams approaching deposit exhaustion, sends LOW_BALANCE warning event via SSE to the sender agent
Agent SDK (backend/src/sdk/)
CortexAgentSDK.js — full client SDK for agents to use:
discover(filters) — finds assets by type/capability
getQuote(assetId) — fetches a signed price quote
openStream(assetId, depositXlm, durationHours) — handles the full stream opening flow end-to-end
call(streamToken, payload) — makes a metered API call, handles 402 Payment Required
getBalance(streamId) — returns current claimable amount
closeStream(streamId) — cancels stream and reclaims unearned deposit
CortexAgentSDK.d.ts — full TypeScript definitions
README.md — SDK usage guide with 10 worked examples
API Endpoints
POST /api/v1/protocol/handshake — initiate agent session
POST /api/v1/protocol/quote — get signed price quote for an asset
POST /api/v1/protocol/meter — record a usage call against an open stream
GET /api/v1/protocol/stream/:id/balance — real-time claimable balance
POST /api/v1/protocol/stream/:id/settle — trigger manual early settlement
Contract Updates
- Add
batch_settle(env, recipient, stream_ids: Vec<u64>) to micropayments contract — settles multiple streams in one transaction
- Add
get_claimable_batch(env, stream_ids: Vec<u64>) -> Map<u64, i128> view function
Tests
- Full end-to-end test: Agent A discovers Agent B's asset, opens stream, makes 30 metered calls, BatchSettler triggers on-chain withdraw, stream closes
- Test
QuoteManager rejects expired quotes
- Test
MeteringEngine is atomic under concurrent requests (race condition test with 10 parallel calls)
- Test
LOW_BALANCE warning fires at 10% deposit remaining
Acceptance Criteria
- A Node.js script using only the SDK can complete a full buy-and-use cycle on testnet in <60s
- BatchSettler never double-settles the same usage batch
- Stream balance is always accurate within one batch interval
Overview
The flagship feature: a complete, production-ready protocol enabling autonomous agents to discover each other, negotiate rates, open payment streams, meter usage, and settle — entirely programmatically without human involvement.
Scope (~3500 lines)
Protocol Design (
docs/AGENT_PAYMENT_PROTOCOL.md)Backend Protocol Layer (
backend/src/protocol/)AgentHandshake.js—POST /api/v1/protocol/handshake— buyer agent presents public key + desired asset ID, server returns current price, available license types, and a signed quote (valid 60s)QuoteManager.js— generates and validates signed quotes using HMAC-SHA256, stores pending quotes in Redis/memory with TTLStreamNegotiator.js— handles rate negotiation between two agent public keys, stores agreed terms, issues astream_tokenJWTMeteringEngine.js—POST /api/v1/protocol/meter— validates stream_token JWT, decrements call counter atomically (using DB row lock), returns{ calls_remaining, settle_now: bool }BatchSettler.js— runs every 60s, finds streams wherecalls_used >= batch_size (25), triggers on-chainwithdrawfor accumulated paymentsStreamMonitor.js— watches for streams approaching deposit exhaustion, sendsLOW_BALANCEwarning event via SSE to the sender agentAgent SDK (
backend/src/sdk/)CortexAgentSDK.js— full client SDK for agents to use:discover(filters)— finds assets by type/capabilitygetQuote(assetId)— fetches a signed price quoteopenStream(assetId, depositXlm, durationHours)— handles the full stream opening flow end-to-endcall(streamToken, payload)— makes a metered API call, handles 402 Payment RequiredgetBalance(streamId)— returns current claimable amountcloseStream(streamId)— cancels stream and reclaims unearned depositCortexAgentSDK.d.ts— full TypeScript definitionsREADME.md— SDK usage guide with 10 worked examplesAPI Endpoints
POST /api/v1/protocol/handshake— initiate agent sessionPOST /api/v1/protocol/quote— get signed price quote for an assetPOST /api/v1/protocol/meter— record a usage call against an open streamGET /api/v1/protocol/stream/:id/balance— real-time claimable balancePOST /api/v1/protocol/stream/:id/settle— trigger manual early settlementContract Updates
batch_settle(env, recipient, stream_ids: Vec<u64>)tomicropaymentscontract — settles multiple streams in one transactionget_claimable_batch(env, stream_ids: Vec<u64>) -> Map<u64, i128>view functionTests
QuoteManagerrejects expired quotesMeteringEngineis atomic under concurrent requests (race condition test with 10 parallel calls)LOW_BALANCEwarning fires at 10% deposit remainingAcceptance Criteria