Zard HTTP
Lightning-fast, boilerplate-free HTTP networking for Dart. Designed for AI synergy and model-less data access.
Features
- Pure Model-less Data: JSON is kept as
Map<String, dynamic>. No code generation orfromJson/toJsonboilerplate. - Edge Validation: Every request is strictly validated at the network boundary (client-side pre-flight and server-side ingestion) using Zard.
- CQRS Contracts: API boundaries are defined as singleton contracts, separating Queries (GET), Commands (JSON POST), and Uploads (Byte POST).
- Zero-Copy Performance: Response wrappers are implemented as extension types on
http.StreamedResponsefor maximum efficiency. - Framework Agnostic: The core library works in any environment; includes a first-class Shelf adapter.
Quick Start
1. Define a Contract (Shared)
import 'package:zard/zard.dart';
import 'package:zard_http/zard_http.dart';
// R = ({String id, String name})
final createUser = ObjectCommand<({String id, String name})>(
path: '/users',
body: z.map({
'name': z.string(),
}),
);
2. Client Usage
final client = HttpContractClient('https://api.example.com');
final response = await client.request(createUser, body: {'name': 'Jane Doe'});
if (response.statusCode == 201) {
final data = await response.json(); // Awaited stream consumption
print(data.get<String>('name')); // Model-less access
}
3. Server Usage (Shelf)
import 'package:zard_http/shelf.dart';
final router = Router();
// request.body is non-nullable and guaranteed safe by Zard
router.addCommand(createUser, (request) async {
final name = request.body.get<String>('name');
return Response.ok(jsonEncode({
'id': '123',
'name': name,
}));
});
4. Upload Usage
// 1. Define Upload Contract
final uploadImage = RawUpload<String>(path: '/upload');
// 2. Client
await client.request(uploadImage, body: myImageBytes);
// 3. Server
router.addUpload(uploadImage, (request) async {
final bytes = await request.read().toBytes(); // Use helper or stream manually
// Validation is handler's responsibility
return Response.ok('Saved ${bytes.length} bytes');
});
Installation
dart pub add zard_http
Documentation
For a full list of classes, methods, and extensions, see the API Reference.
In-depth
Singleton Contracts
Endpoints are defined as global constants. This allows both the client and server to share the same validation logic and routing metadata. Phantom record types (R) are used to document the expected JSON shape for developers and AI agents.
Strict Request Validation
When using client.request, the provided body, query, or headers maps are validated against the contract's Zard schemas before the request is even sent. On the server, the adapter validates the incoming data before your handler is ever called, automatically returning a 400 Bad Request with descriptive Zard issues on failure.
Asynchronous Data Access
To maintain zero-copy performance, ObjectResponse and ListResponse wrap the raw http.StreamedResponse. Calling .json() asynchronously consumes the stream and decodes the JSON into an ObjectData accessor.
Model-less Extraction
ObjectData provides a robust API for extracting data without classes:
get<T>(key): Strict extraction.parseDateTime(key): Handles ISO 8601 strings and epoch integers.parseEnumByName(key, values): Safe enum mapping.parseBySchema(key, schema): Nested validation for complex structures.
License
MIT