Changelog
View SourceAll notable changes to this project are documented here. The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.
[Unreleased]
[0.1.1] - 2026-06-13
Added
- Client interop check against a real grpc-go server
(
make interop-client, skipped without Go), provinglivery_grpc_clientcalls services that are not written in Erlang (unary and server-streaming over the standard health service).
Fixed
- A request message compressed with an unsupported
grpc-encodingnow returnsunimplemented(as the gRPC spec requires) instead ofinternal. Addedlivery_grpc_compression:request_algorithm/1.
[0.1.0] - 2026-06-13
First release. gRPC for Erlang on the livery HTTP/2 stack: server and client, all four call types, and the surrounding ecosystem.
Added
- Project scaffold: OTP application, supervisor, build pipeline with
gpbandrebar3_gpb_plugin, samplehelloworld.proto. - Wire layer:
livery_grpc_frame(length-prefixed framing + streaming decoder),livery_grpc_status(canonical codes, grpc-message encoding, trailers),livery_grpc_compression(identity + gzip),livery_grpc_codec(gpb glue + content-type checks). Property and unit tests. livery_grpc_service: method descriptors derived from gpb introspection (wire path, message types, call kind, snake_case callback name) and a path-keyed routing index.- Server:
livery_grpc:start_server/1runs gRPC on a dedicated h2 listener;livery_grpc_serverdispatchesPOST /pkg.Svc/Methodto the bound callback module. Unary and server-streaming, with status in trailers (and Trailers-Only for pre-dispatch errors). End-to-end tests over h2c cover success, error status, handler crash, unknown method, and streaming. - Client:
livery_grpc_clientcalls gRPC services over the h2 client (unary and server-streaming), with metadata and gzip.livery_grpc_wirecentralises message encode/decode for both sides. In-tree client tests cover unary, error status, server-streaming, and gzip both directions. - Cross-cutting:
grpc-timeoutdeadlines (client sends and bounds the wait; server parses, exposes in the context, and aborts a unary handler that overruns), error details viagrpc-status-details-bin, request metadata, and livery middleware as gRPC interceptors. - Health: the standard
grpc.health.v1.Healthservice (livery_grpc_health:service/0), with per-service serving status.Checkis unary;Watchemits the current status once (live updates follow the bidirectional work). - gRPC-Web:
livery_grpc_webframing on the same server (binary and text), with the status delivered as an in-body trailer frame. Unary and server-streaming. Reflection is deferred: its RPC is bidirectional and waits on the h2 bidi work. - Example (
greeter_example), a quickstart guide, and agrpcurlinterop smoke test (make interop) confirming on-the-wire compliance with an external gRPC client. - Client-streaming and bidirectional streaming on both sides, on h2
0.10.0. The server reads requests through a
livery_grpc_streamhandle and interleaves replies in the chunked producer; the client addsclient_stream/3,4andopen/2,3+send/2+send_end/1+recv/1,2. All four call types are verified against grpcurl. - Client interceptor stack, the outbound twin of livery's server
middleware:
interceptorsonconnect/3or per call, withbefore/1,after_response/1, andwrap/1, matching thelivery_clientlayer shape (Tower layers on the BEAM). - Server reflection (
grpc.reflection.v1): enable withreflection => trueand tools like grpcurl discover services and message schemas at runtime, with no local.proto. Verified with grpcurllist,describe, and a fully reflective call. - Health
Watchnow streams live updates: it emits the current status and a new message on every change until the client disconnects, backed by a small subscription store (livery_grpc_health_store). - Code generation (
livery_grpc_codegen,make stubs): per service, anerpc-style client stub (greeter_client:say_hello/2) and a service behaviour (-behaviour(greeter_service)) for compiler-checked handlers.
Changed
- Servers are now owned by a supervised process (
livery_grpc_listenerunderlivery_grpc_server_sup) instead of the caller, so a server started from a short-lived process keeps running.start_server/1returns the listener owner pid.
Added (testing)
livery_grpc_e2e_SUITE, a Common Test end-to-end suite against a real running server: the full journey with the in-tree client, and the same calls driven by grpcurl over reflection (skipped if grpcurl is absent).
Added (docs and example)
- A documentation set in the style of grpc.io with Erlang snippets: Introduction, Core concepts, Getting started, a Basics tutorial built on a real RouteGuide example, a Design guide for the Erlang integration, an Erlang-integration how-to, and task-oriented guides modeled on the gRPC guides (streaming, metadata, interceptors, deadlines, cancellation, error handling, status codes, compression, authentication, health, reflection, retry, graceful shutdown, flow control, wait-for-ready, gRPC-Web, generated stubs, testing). All wired into ex_doc.
examples/route_guide.erl+proto/route_guide.proto: the RouteGuide example, exercising all four call types, with an eunit suite.livery_grpc_client:cancel/1cancels a streaming call.