Echo Server
A high-performance async echo server library built with Tokio, supporting TCP, UDP, HTTP, and Unix domain socket protocols. Perfect for development, testing, and when you need a network service with predictable, verifiable behavior.
Why Echo Server?
- Multi-Protocol: Supports TCP, UDP, HTTP, and Unix domain sockets (stream and datagram)
- Predictable: Always echoes back exactly what you send - no surprises
- Simple: Minimal configuration, just start it and it works
- Verifiable: Easy to test - send data, get the same data back
- Flexible: Use as a library in your Rust projects or standalone executable
- Reliable: Built with proper error handling and connection management
- High Performance: Async I/O with Tokio runtime
- Extensible: Generic architecture supports future protocols
Quick Start
As a Standalone Server
# Run TCP server on default port 8080
# Run UDP server on default port 8080
# Run TCP server on specific port
# Run UDP server on specific port
# Run Unix domain stream server
# Run Unix domain datagram server
# Run HTTP server on default port 8080
# Run HTTP server on specific port
# Test TCP with netcat
|
# Test UDP with netcat
|
# Test Unix domain socket with socat
|
# Test HTTP with curl
As a Library
TCP Server
use ;
use Duration;
async
UDP Server
use ;
use Duration;
async
HTTP Server
use ;
use Duration;
async
Note: The HTTP echo server only accepts POST requests and echoes back only the request body content (no HTTP headers). Non-POST requests receive a 405 Method Not Allowed response.
Unix Domain Stream Server
use ;
use Duration;
async
Unix Domain Datagram Server
use ;
use Duration;
async
Features
- Multi-Protocol Support: TCP, UDP, and Unix domain sockets (stream and datagram)
- High Performance: Async I/O with Tokio runtime
- Connection Limits: Configurable maximum concurrent connections (TCP/Unix stream)
- Timeouts: Configurable read/write timeouts for all protocols
- Graceful Shutdown: Responds to SIGINT/SIGTERM
- Binary Data Support: Handles any data type, not just text
- Unicode Support: Full UTF-8 support
- Structured Logging: Built-in observability with tracing
- Common Interface: Shared traits for consistent API across protocols
- Generic Architecture: Extensible for future protocols (WebSockets, TLS, etc.)
- Unix Domain Sockets: Efficient inter-process communication on Unix systems
Use Cases
- Integration Testing: When your application requires a network service to be running
- Network Validation: Verify network connectivity and port availability
- Client Testing: Test network clients that need a server to connect to
- Development: Quick setup when you need a service listening on a port
- Learning: Understand how TCP/UDP/Unix domain servers work with predictable behavior
- Protocol Comparison: Test and compare different transport protocols
- Inter-Process Communication: Unix domain sockets for efficient local communication
- Container Communication: Unix domain sockets for container-to-container communication
Configuration
TCP Configuration
let config = TcpConfig ;
UDP Configuration
let config = UdpConfig ;
Unix Domain Stream Configuration
let config = UnixStreamConfig ;
Unix Domain Datagram Configuration
let config = UnixDatagramConfig ;
Testing
The library includes test clients for both protocols:
TCP Client
use TcpEchoClient;
async
UDP Client
use UdpEchoClient;
async
Unix Domain Stream Client
use UnixStreamEchoClient;
use PathBuf;
async
HTTP Client
use HttpEchoClient;
async
Note: The HTTP client sends POST requests and receives only the body content in response.
Unix Domain Datagram Client
use UnixDatagramEchoClient;
use PathBuf;
async
Generic Clients
For extensibility, you can also use the generic client implementations:
use StreamEchoClient;
use DatagramEchoClient;
use TcpProtocol;
use UdpProtocol;
// Generic stream client with TCP protocol
let mut tcp_client: = connect.await?;
// Generic datagram client with UDP protocol
let mut udp_client: = connect.await?;
// Both work identically to the concrete clients
let response = client.echo_string.await?;
Architecture
The library uses a clean, generic architecture for maximum extensibility:
Module Structure
src/
├── common/ # Shared components
│ ├── traits.rs # Core traits (EchoServerTrait, EchoClient)
│ └── test_utils.rs # Test utilities
├── stream/ # Generic stream implementation
│ ├── client.rs # Generic stream client
│ ├── server.rs # Generic stream server
│ ├── protocol.rs # StreamProtocol trait
│ └── config.rs # StreamConfig
├── datagram/ # Generic datagram implementation
│ ├── client.rs # Generic datagram client
│ ├── server.rs # Generic datagram server
│ ├── protocol.rs # DatagramProtocol trait
│ └── config.rs # DatagramConfig
├── tcp/ # TCP-specific implementation
│ ├── mod.rs # Type aliases for TCP
│ ├── server.rs # Type alias: TcpEchoServer = StreamEchoServer<TcpProtocol>
│ ├── config.rs # TcpConfig
│ └── stream_protocol.rs # TcpProtocol implementation
├── udp/ # UDP-specific implementation
│ ├── mod.rs # Type aliases for UDP
│ ├── server.rs # Type alias: UdpEchoServer = DatagramEchoServer<UdpProtocol>
│ ├── config.rs # UdpConfig
│ └── datagram_protocol.rs # UdpProtocol implementation
├── unix/ # Unix domain socket implementation
│ ├── mod.rs # Module exports and type aliases
│ ├── config.rs # UnixStreamConfig, UnixDatagramConfig
│ ├── server.rs # UnixStreamEchoServer, UnixDatagramEchoServer
│ ├── client.rs # UnixStreamEchoClient, UnixDatagramEchoClient
│ ├── stream_protocol.rs # UnixStreamProtocol implementation
│ ├── datagram_protocol.rs # UnixDatagramProtocol implementation
│ └── tests.rs # Unix domain socket tests
├── http/ # HTTP protocol implementation
│ ├── mod.rs # Module exports and type aliases
│ ├── config.rs # HttpConfig
│ ├── protocol.rs # HttpProtocol implementation
│ ├── client.rs # HttpEchoClient type alias
│ └── tests.rs # HTTP protocol unit tests
├── lib.rs # Main library exports
└── main.rs # Binary entry point
Design Philosophy
- Generic Architecture: Stream and datagram clients/servers are generic over protocol implementations
- Type Aliases: Concrete clients (
TcpEchoClient,UdpEchoClient) are type aliases to generic implementations - Protocol Traits:
StreamProtocolandDatagramProtocoltraits define the interface for protocol implementations - Extensibility: Easy to add new protocols (Unix streams, WebSockets, etc.) by implementing the protocol traits
Common Traits
Both TCP and UDP implementations share common traits for consistency:
use ;
// Both TcpEchoServer and UdpEchoServer implement EchoServerTrait
// Both TcpEchoClient and UdpEchoClient implement EchoClient
Installation
Add to your Cargo.toml:
[]
= "0.1.0"
License
MIT License - see LICENSE file for details.