When a JSON-RPC server's API is expressed as a .NET interface, StreamJsonRpc can dynamically create a proxy that implements that interface
to expose a strongly-typed client for your service. These proxies can be created using either the static JsonRpc.Attach<T>(Stream)
method
or the instance JsonRpc.Attach<T>()
method.
Generated proxies have the following behaviors:
- They always pass arguments using positional arguments rather than named arguments.
- Methods are sent as ordinary requests (not notifications).
- Events on the interface are raised locally when a notification with the same name is received from the other party.
- Implement
IDisposable
if created using the staticJsonRpc.Attach<T>
method, and terminate the connection whenDispose()
is invoked.
A proxy can only be dynamically generated for an interface that meets these requirements:
- No properties
- No generic methods
- All methods return
Task
orTask<T>
- All events are typed with
EventHandler
orEventHandler<T>
- Methods may accept a
CancellationToken
as the last parameter.
An interface used to generate a dynamic client proxy must return Task
or Task<T>
from all methods.
This allows the client proxy to be generated with asynchronous methods as appropriate for JSON-RPC (and IPC in general)
which is fundamentally asynchronous.
On the server side, these same methods may be simple and naturally synchronous. Returning values from the server wrapped
in a Task
may seem unnatural.
The server need not itself explicitly implement the interface -- it could implement the same method signatures as are
found on the interface except return void
(or whatever your T
is in your Task<T>
method signature on the interface)
and it would be just fine. Of course implementing the interface may make it easier to maintain a consistent contract
between client and server.
Sometimes a client may need to block its caller until a response to a JSON-RPC request comes back.
The dynamic proxy maintains the same async-only contract that is exposed by the JsonRpc
class itself.
Learn more about sending requests, particularly under the heading about async responses.