Note
Definition. A server is a program that passively listens for incoming connections and responds to requests. In the Summoner protocol, servers enable agent coordination by relaying messages between connected clients.
Summoner is a protocol for orchestrating agents across machines. It builds on TCP — the bedrock of internet communication — to ensure reliable delivery, ordered messages, and stable connections. Before we explain what makes Summoner unique, we ground ourselves in the basics.
TCP (Transmission Control Protocol) ensures that data sent between machines arrives intact, in order, and without duplication. Introduced in the 1970s, it remains central to the modern internet.
TCP is a transport-layer protocol, operating above physical and routing layers:
- MAC (Media Access Control): Manages data access to the physical network (e.g., Ethernet, Wi-Fi).
- IP (Internet Protocol): Handles routing of packets from source to destination.
Built atop these, TCP establishes a virtual pipe between programs on separate machines.
Each TCP connection is defined by two endpoints:
- IP Address — The location of a machine (e.g.,
127.0.0.1,192.168.0.12, or a public WAN IP). - Port — The application-level channel on that machine (e.g.,
8000,443).
Summoner servers bind to a specific host and port. Clients initiate connections by targeting these identifiers.
The concrete SDK entrypoint is SummonerServer.run(...), with the exact config surface documented in server/configs.md.
Handshake establishes the connection — both sides then send and receive in parallel.
SYN: open start • ACK: confirm • FIN: close politely • Socket: TCP endpoint (IP, port, state)
To better understand how TCP connections are established in practice, it helps to look at concrete code examples. The concept of "binding" refers to the process where a server reserves a specific IP address and port on which it listens for incoming connections. Clients then connect to this address:port pair to initiate communication.
Below are two simple "echo servers" (servers that respond by sending back exactly what they receive). One written in Python using asyncio, and one in Rust using the tokio async runtime. Both demonstrate the same principles:
- listening on a port,
- accepting client connections,
- and responding to received messages.
import asyncio
# This function runs once per client connection
async def handle_client(reader, writer):
# Wait to receive up to 100 bytes from the client
data = await reader.read(100)
# Send the same data back to the client
writer.write(data)
await writer.drain() # Ensure the data is sent
writer.close() # Close the connection
# Main server loop
async def main():
# Start server on localhost, port 8000
server = await asyncio.start_server(handle_client, '127.0.0.1', 8000)
# Keep server running and accepting new clients
async with server:
await server.serve_forever()
asyncio.run(main())use tokio::net::TcpListener;
use tokio::io::{AsyncReadExt, AsyncWriteExt};
#[tokio::main]
async fn main() -> tokio::io::Result<()> {
// Bind server to localhost:8000
let listener = TcpListener::bind("127.0.0.1:8000").await?;
loop {
// Wait for a client to connect
let (mut socket, _) = listener.accept().await?;
// Handle the client in a separate async task
tokio::spawn(async move {
let mut buf = [0; 1024];
// Read data from the client
let n = socket.read(&mut buf).await.unwrap();
// Echo the same data back
socket.write_all(&buf[0..n]).await.unwrap();
});
}
}Understanding how machines are addressed and located on networks is essential for deploying Summoner servers. Here's a breakdown:
-
Localhost (
127.0.0.1): Refers to the local machine itself. Connections to this address stay entirely within the same computer and are typically used for development or self-contained processes. -
LAN (Local Area Network): Includes private IP ranges like
192.168.x.xor10.x.x.x, used within home, office, or cluster networks. Machines on the same LAN can communicate directly without needing internet access. -
WAN (Wide Area Network): Represents public IP addresses that are globally reachable. WAN addresses allow machines to communicate across the internet, but typically require port forwarding or firewall rules to accept inbound connections.
-
DNS (Domain Name System): Resolves human-readable domain names (like
summoner.org) into IP addresses. It abstracts away numerical addressing, making services easier to locate and move between machines.
These distinctions guide where and how to launch Summoner nodes:
| Use Case | Address Type | Description |
|---|---|---|
| Isolated testing | localhost |
Runs entirely on the local machine |
| Internal networks (LAN) | 192.168.x.x, 10.x.x.x |
For trusted machines within a private network |
| Internet-facing services | Public IP (WAN) | Globally reachable, needs port/firewall setup |
| Discoverability & scaling | DNS | Resolves domain names to IPs, enabling discoverability and flexible infrastructure |
A protocol defines not just message formats, but the entire structure of interaction:
- Who initiates communication?
- How are delays and retries handled?
- What happens if a message is malformed or incomplete?
Summoner introduces a higher-level protocol designed for asynchronous, agent-to-agent communication, enabling coordination through a shared server without relying on centralized scheduling.
TLS (Transport Layer Security) secures a transport channel and verifies endpoints using certificates. The core Summoner relay does not replace TLS and does not provide identity, signing, or encryption by itself. It deliberately stays a simple TCP-based message relay.
If your application needs signed messages, identity records, or encrypted envelopes, implement them in your agent logic or add an extension layer such as Aurora. For the broader extension space, see the Agent Extensions reference, and for Aurora's main agent interface see SummonerAgent. In practice, that means:
- TCP gives you the transport.
- TLS remains a deployment choice if you want channel security.
- Agent-side
hooksand extensions handle higher-level identity and message policy.
