Secure agent-to-agent communication over the Internet.
A communication protocol for agent-to-agent transfer.
DNS-based discovery, mandatory Ed25519 signing, server-mediated delivery.
Agent A ATP Server A ATP Server B Agent B
| | | |
|---[1. Submit]----->| | |
| (unsigned+cred) | | |
| 2. Credential Verify | |
| | | |
| 3. DNS SVCB Discover | |
| 4. Domain-key Sign (ATK) | |
| | | |
| |--[5. Transfer]----->| |
| | TLS 1.3 + POST | |
| | (signed message) | |
| | | |
| | 6. ATS+ATK Verify (DNS) |
| | 7. Sender Authenticated |
| | | |
|<---[202 Accepted]--| |---[8. Deliver]--->|
| | | |
Agents need a standard way to communicate across the Internet: securely, without a central registry, using infrastructure that already exists.
| Feature | How |
|---|---|
| Identity | local@domain format, powered by DNS |
| Discovery | DNS SVCB records, no central registry needed |
| Signing | Ed25519 on every message, verified on cross-domain transfer |
| Authorization | ATS policies in DNS, control who can send for your domain |
| Delivery | Store-and-forward with retry, messages don't get lost |
pip install agent-transfer-protocolRequires Python 3.11+
# 1. Start a server
atp server start --domain example.com --port 7443
# 2. Register an agent (will prompt for password)
atp agent register mybot --server example.com
# Or non-interactively: atp agent register mybot --server example.com -p mypassword
# 3. Send a message (from another terminal)
atp send agent@remote.org \
--from mybot \
--password mypassword \
--server example.com \
--body "Hello!"
# 4. Check server status
atp status --server example.comRun two servers locally and send messages between them, no DNS needed:
# Terminal 1: Start Server A
atp server start --domain alice.local --port 7443
# Terminal 2: Start Server B
atp server start --domain bob.local --port 7444
# Register agents
atp agent register agent --server 127.0.0.1:7443 --no-verify -p alice_pass
atp agent register agent --server 127.0.0.1:7444 --no-verify -p bob_pass
# Terminal 3: Alice sends to Bob
atp send agent@bob.local \
--from agent \
--password alice_pass \
--server 127.0.0.1:7443 \
--no-verify \
--body "Hello Bob!"
# Terminal 4: Bob receives
atp recv \
--agent-id agent \
--password bob_pass \
--server 127.0.0.1:7444 \
--no-verifyimport asyncio
from atp.client import ATPClient
async def main():
client = ATPClient(
agent_id="mybot",
password="mypassword",
server="example.com",
)
# Send
result = await client.send("target@remote.org", body="Hello from SDK")
print(result) # {"status": "accepted", "nonce": "msg-..."}
# Receive
messages = await client.recv()
for msg in messages:
print(f"{msg.from_id}: {msg.payload}")
await client.close()
asyncio.run(main())| Command | Description |
|---|---|
atp server start |
Start ATP server |
atp send <to> |
Send a message |
atp recv |
Receive messages |
| Command | Description |
|---|---|
atp agent register <name> |
Register an agent with credentials |
atp agent list |
List registered agents |
Ed25519 signing keys are auto-generated on first server startup. These commands are for manual control.
| Command | Description |
|---|---|
atp keys generate |
Generate Ed25519 key pair |
atp keys show |
Show key info |
atp keys list |
List all keys |
atp keys rotate |
Rotate to a new key |
| Command | Description |
|---|---|
atp status |
Show server status and metrics |
atp inspect <nonce> |
Inspect a specific message |
| Command | Description |
|---|---|
atp dns generate |
Generate DNS records for your domain |
atp dns check |
Verify DNS records are configured |
Run atp <command> --help for options.
--server format |
Protocol | Port |
|---|---|---|
example.com |
HTTPS | 7443 (default) |
example.com:8443 |
HTTPS | 8443 |
https://example.com |
HTTPS | 7443 |
http://example.com |
HTTP (warns) | 7443 |
- Default: verify TLS certificates. Invalid cert prompts for confirmation.
--no-verify: skip certificate verification silently.- Agent names without
@are auto-completed with the server domain.
For production, configure DNS records. ATP generates them for you:
# Step 1: Generate the records
atp dns generate --domain example.com --ip 203.0.113.1
# Step 2: Add them to your DNS provider (Cloudflare, Route53, etc.)
# Step 3: Verify
atp dns check --domain example.com
# Step 4: Start with TLS
atp server start --domain example.com --cert server.crt --key server.keySee the DNS Setup Guide for details.
ATP provides four layers of security, inspired by email's battle-tested approach:
| Layer | ATP | Email Equivalent | Purpose |
|---|---|---|---|
| Transport | TLS 1.3 | STARTTLS | Encrypted connections |
| Authentication | Credential | SMTP AUTH | Agent identity (username + password) |
| Authorization | ATS | SPF | Who can send for a domain |
| Integrity | ATK (Ed25519) | DKIM | Message signing & verification |
Agents authenticate to their server with credentials (password). The server signs messages with its domain-level Ed25519 key before forwarding. Remote servers verify independently via ATS+ATK.
| Quick Start | Full walkthrough with two servers |
| Configuration | CLI options, config file, retry policy |
| DNS Setup | Production DNS configuration |
| Security Model | ATS, ATK, TLS explained in depth |
| Python SDK | API reference for developers |
| Architecture | Module design for contributors |
ATP is defined as an IETF Internet-Draft (Standards Track):
Agent Transfer Protocol (ATP) draft-li-atp · March 2026 Xiang Li, Lu Sun, Yuqi Qiu, Nankai University, AOSP Laboratory
git clone https://github.com/NKU-AOSP-Lab/AgentTransferProtocol.git
cd atp
pip install -e ".[dev]"
python -m pytest tests/ -v # 227 testsSee Architecture for module design and development guide.