json-rpc-cxx

repository·master·Indexed 43 days ago

https://github.com/jsonrpcx/json-rpc-cxx

A C++17 framework for implementing JSON-RPC 2.0 compliant clients and servers. It is transport-agnostic, focuses on type safety, and leverages nlohmann/json for data handling. Key components include JsonRpcClient for sending requests and notifications, and JsonRpc2Server for processing incoming JSON-RPC 2.0 requests and batch processing.

Tokens
2.2K
Snippets
7
Records
11
Agent score
55%

What's inside json-rpc-cxx

  1. Overview of json-rpc-cxx features

    master

    json-rpc-cxx is a C++17 implementation of the JSON-RPC 2.0 protocol. It is designed to be transport-agnostic, meaning it can work over various communication layers (like TCP, WebSockets, etc.) as long as they provide the necessary interface.

    Key features include:

    • JSON-RPC 2.0 Compliance: Fully compliant client and server implementations.
    • Type Safety: Uses compile-time type mapping via nlohmann/json's arbitrary type conversion and provides runtime type checking.
    • Cross-platform: Supports Windows, Linux, and OSX.
    • Minimal Dependencies: Primarily relies on nlohmann/json.
  2. Install json-rpc-cxx

    master

    You can install json-rpc-cxx using one of two methods:

    1. Manual Installation: Copy the contents of the include/jsonrpccxx directory directly into your project's include path.
    2. CMake Installation: Use the CMake build system to install the library to your system.

    Note that the library depends on nlohmann/json.

    mkdir build && cd build
    cmake ..
    sudo make install
  3. Register methods with JsonRpcServer::Add

    master

    To handle incoming JSON-RPC requests, you must register methods with the server using the Add method. The JsonRpcServer class provides two overloads for Add depending on whether the method is a standard request/response method or a notification (which does not require a response).

    Constraints:

    • Method names cannot start with the prefix rpc..
    • If Add returns false, the registration failed (likely due to the name prefix constraint).

    Overloads:

    • bool Add(const std::string &name, MethodHandle callback, const NamedParamMapping &mapping = NAMED_PARAM_MAPPING): Registers a method that expects a response.
    • bool Add(const std::string &name, NotificationHandle callback, const NamedParamMapping &mapping = NAMED_PARAM_MAPPING): Registers a notification handler that does not return a result to the client.
    // Example of adding a method to a server instance
    JsonRpc2Server server;
    
    server.Add("subtract", [](int a, int b) {
        return a - b;
    });
  4. Handle JSON-RPC requests with JsonRpc2Server::HandleRequest

    master

    The JsonRpc2Server class implements the JSON-RPC 2.0 specification. Use HandleRequest to process incoming request strings.

    Behavior:

    • Input: A std::string containing a single JSON object or a JSON array of requests.
    • Output: A std::string containing the JSON-RPC response(s). If the input was an array, the output is an array of responses. If the input was an object, the output is a single response object.
    • Batch Processing: If the input is a JSON array, the server iterates through each request and returns an array of results (excluding null results from notifications).
    • Error Handling: The method catches parse errors, invalid request formats, and internal server errors, returning standard JSON-RPC error objects.

    Error Codes returned by HandleRequest:

    • invalid_request: The request is not properly formatted (e.g., missing jsonrpc version, invalid method type, or invalid params type).
    • parse_error: The input string is not valid JSON.
    • internal_error: An unhandled exception occurred during method execution.
    JsonRpc2Server server;
    // ... register methods ...
    
    std::string request = R!("{""jsonrpc"": ""2.0"", ""method"": ""subtract"", ""params"": [10, 4], ""id"": 1}")!";
    std::string response = server.HandleRequest(request);
    // response will be: {""jsonrpc"": ""2.0"", ""id"": 1, ""result"": 6}
  5. Use JsonRpcClient to send requests

    master

    The JsonRpcClient class is the primary interface for sending JSON-RPC 1.0 or 2.0 requests to a server. It requires an implementation of IClientConnector to handle the actual transport of the JSON strings.

    To use it, instantiate JsonRpcClient with a connector and a version (v1 or v2). You can then call methods using positional parameters, named parameters, or notifications.

    // Assuming an implementation of IClientConnector named 'my_connector' exists
    jsonrpccxx::JsonRpcClient client(my_connector, jsonrpccxx::version::v2);
    
    // Call a method with positional parameters and get a typed result
    int result = client.CallMethod<int>(1, "subtract", {42, 23});
    
    // Call a method with named parameters
    jsonrpccxx::named_parameter params = {{"a", 1}, {"b", 2}};
    int sum = client.CallMethodNamed<int>(2, "add", params);
    
    // Send a notification (no response expected)
    client.CallNotification("update_status", {{"status", "ok"}});
  6. JsonRpcClient Types and Enums

    master

    The following types are used to construct requests in JsonRpcClient:

    • enum class version { v1, v2 }: Specifies the JSON-RPC protocol version.
    • typedef std::vector<json> positional_parameter: Used for array-based parameters.
    • typedef std::map<std::string, json> named_parameter: Used for object-based parameters.
    • typedef std::variant<int, std::string> id_type: The type used for request IDs.
  7. CallMethodNamed<T> for named parameters

    master

    Invokes a JSON-RPC method using a map of named parameters and returns the result cast to type T.

    Signature:

    • T CallMethodNamed(const id_type &id, const std::string &name, const named_parameter &params = {})

    Parameters:

    • id: An id_type (can be int or std::string).
    • name: The name of the method to call.
    • params: A std::map<std::string, json> containing named arguments.
    // Example: Calling 'subtract' with named params {"min": 10, "max": 20}
    jsonrpccxx::named_parameter params = {{"min", 10}, {"max", 20}};
    int result = client.CallMethodNamed<int>(1, "subtract", params);
  8. CallNotification for one-way requests

    master

    Sends a JSON-RPC notification. Notifications do not include an id in the request and do not expect a response from the server.

    Signatures:

    • void CallNotification(const std::string &name, const positional_parameter &params = {})
    • void CallNotificationNamed(const std::string &name, const named_parameter &params = {})

    Parameters:

    • name: The name of the method to notify.
    • params: Either a positional_parameter (vector) or named_parameter (map).
    // Example: Positional notification
    client.CallNotification("log_event", {{"level", "info"}, {"msg", "started"}});
    
    // Example: Named notification
    client.CallNotificationNamed("set_config", {{"timeout", 30}, {"retry", true}});
  9. CallMethod<T> for positional parameters

    master

    Invokes a JSON-RPC method and returns the result cast to type T.

    Signatures:

    • T CallMethod(const id_type &id, const std::string &name)
    • T CallMethod(const id_type &id, const std::string &name, const positional_parameter &params)

    Parameters:

    • id: An id_type (can be int or std::string).
    • name: The name of the method to call.
    • params: A std::vector<json> containing positional arguments.
    // Example: Calling 'add' with positional params [1, 2]
    int result = client.CallMethod<int>(1, "add", {1, 2});
  10. JsonRpcServer base class

    master
    The JsonRpcServer is an abstract base class that provides the core registration logic via a Dispatcher. It defines the interface for handling requests but does not implement the specific JSON-RPC 2.0 parsing logic itself. Users should typically instantiate JsonRpc2Server for standard JSON-RPC 2.0 compliance.
  11. JsonRpc2Server class

    master
    The JsonRpc2Server is a concrete implementation of JsonRpcServer that adheres to the JSON-RPC 2.0 specification. It handles the parsing of JSON strings, validation of the jsonrpc, method, params, and id fields, and manages the distinction between method calls (which require an id) and notifications (which do not).