Binding Dev Guide
Thanks for your interest in writing a new language binding for Barrister. This guide outlines
some things to keep in mind while writing your binding.
Before we go further
Barrister is really a layer on JSON-RPC 2.0. If you are familiar with
a JSON-RPC library for your favorite language, you could try overlaying the Barrister IDL discovery and
type validation onto that library.
That might save you some time. Or it might not.
Considerations
- Requests and responses are encoded using the JSON-RPC 2.0 format. Take a moment to familiarize yourself with that document.
- Write a README that explains:
- How to install the binding -- ideally using the language package manager if one exists
- How to write a client
- How to write a server
- Should pass the conformance test suite (see below)
Type Validation
- Client and server code should validate that request / response payloads match the type definitions specified in the IDL
- JSON-RPC error codes should be used to express errors. For example, invalid params passed to the server should result in an error with code=-32602
- Null value rules
- Top level function parameters may never be null
- Struct fields flagged as
optional=true
may be null
- Return types flagged as
optional=true
may be null
- Non-null values should be validated against the type specified in the IDL (recursively)
Client
- Provide a HTTP transport that given an URL, loads the IDL contract for that endpoint
- Send a request to the endpoint with the JSON-RPC method:
barrister-idl
- Provide batch support so that clients can invoke multiple methods in a single RPC call
- Clients are responsible for correlating the responses with the requests based on ID
- Reponses should be ordered to match the order of the requests made against the batch
- Ideally provides an "in process" transport that skips the serialization code but still performs type validation.
Server
- Provide a way to associate interface implementations with a given IDL
- Provide a transport independent dispatching mechanism that parses the JSON-RPC request and invokes the correct method on the registered interface implementation
- Implement the
barrister-idl
method, which returns the IDL JSON associated with the server instance
- Provide batch request support.
- Per the JSON-RPC spec, servers may parallelize execution of individual requests in the batch, but are not required to.
Code Generation
- If the language is static, we encourage you to provide a command line code generator that takes a IDL JSON file as input and produces stubs for that interface
- See the barrister-java implementation as an example
- Interfaces, Structs, and Enums should all be supported
- Consider writing the comments in the IDL as comments in the generated source code that match the convention of the host language (e.g. Javadoc style for Java)
Jenkins Continuous Integration
I have a Jenkins server that runs the test suite for Barrister and the supported language bindings.
Once your binding is far enough along I'd like to add it to the Jenkins server and integrate it into the
conformance test suite. Please ping me on the
mailing list when you're ready.
Conformance Tests
In the python tree there is a
conformance test that runs all the clients and servers against each other in a pair-wise fashion
using a common text input file. The output from each client is checked and any anomolies are
logged as failures.
Each language runtime needs to provide a client and server implementation that can be run by the
test suite. Look at the python code as a reference:
To add your implementation to the suite:
- Open
conform_test.py
- Add the client to the
clients
block which starts around line 39
- Format:
[ "name", [ "command", "line", "to", "start", "client" ] ]
- Add a new test method to the
ConformTest
class
- See
test_python_server
as an example
- Should provide a
cmd
array that can start the server
- Can optionally sleep for x seconds to give server time to start and bind to port
- To run:
python conform_test.py
- The conformance test will run each client against each server
- Any output from the clients that deviates from the expectation in
conform.in
will trigger a failure