Tip of the day: Exempt your IP address from bans, just in case you or a fellow IRCOp accidentally GLINES you.

JSON-RPC

From UnrealIRCd documentation wiki
Jump to navigation Jump to search

UnrealIRCd 6.0.5 will have a JSON-RPC API. This allows remote endpoints to query and control UnrealIRCd. For example for statistics.

This page starts with Configuration and Transport to quickly get you started. More details about the format are provided in the section JSON-RPC Protocol and the list of all API calls is in JSON-RPC Methods.

Configuration[edit]

You need to load the requires JSON-RPC modules. Simply put this in your unrealircd.conf:

include "rpc.modules.default.conf";

Then you need to create a listen block with listen::options::rpc, and for HTTPS you would also have to create one or more api-user blocks. This is explained in Transport, see next.

Transport[edit]

UNIX domain socket[edit]

This is for local connections only. On the server side you have this:

listen {
        file "/home/xyz/unrealircd/data/rpc.sock";
        options { rpc; }
}

Then simply connect to the socket and you can issue JSON-RPC requests directly. Example:

$ nc -U ~/unrealircd/data/rpc.sock
{"jsonrpc": "2.0", "method": "channel.list", "params": {}, "id": 123}
{"jsonrpc": "2.0", "method": "channel.list", "id": 123, "response": {"list": []}}

There is no authentication being done, as only local users can use this and the socket is only readable/writable by the user running UnrealIRCd by default (rwx------).

You can issue multiple requests (even in parallel, no need to wait for the response). The connection is not closed. The connection is only closed if some fatal JSON parsing error is encountered such as a missing }. Normally that should never happen. Other errors such as an unknown method being called, invalid parameter count, etc. are not fatal.

HTTPS POST[edit]

On the server side this requires you to open up a port (Listen block) and add at least one api user (Rpc-user block):

listen {
        ip *;
        port 8000;
        options { rpc; }
}

rpc-user apiuser {
        match { ip 192.168.*; }
        password "password";
}

Then do a POST request to /api with the JSON request. You must do this over https.

Example:

curl -s --insecure -X POST -d '{"jsonrpc": "2.0", "method": "channel.list", "params": {}, "id": 123}' https://apiuser:password@127.0.0.1:8000/api

The connection is closed after processing the request. If you want to issue another API call then do a new HTTPS POST. If you want streaming requests/responses, use HTTPS Websocket (see next section).

HTTPS Websocket[edit]

On the server side the config is the same as for HTTPS POST. You open up a port (Listen block) and add at least one api user (Rpc-user block):

listen {
        ip *;
        port 8000;
        options { rpc; }
}

rpc-user apiuser {
        match { ip 192.168.*; }
        password "password";
}

Make a HTTPS websocket connection (not HTTP!) and then you can send JSON requests. Eg:

{"jsonrpc": "2.0", "method": "channel.list", "params": {}, "id": 123}

The connection is kept open so you can issue more JSON-RPC requests. You may also send multiple requests in parallel, you don't have to wait for a response. The connection is only closed upon:

  • A fatal error, such as a JSON parsing error (obviously should never happen)
  • A certain timeout (currently rather low!)

JSON-RPC Protocol[edit]

The JSON request/responses follow the JSON-RPC 2.0 specification.

Request[edit]

This is an example query. It calls the channel.list method with empty parameters:

{"jsonrpc": "2.0", "method": "channel.list", "params": {}, "id": 123}

Response[edit]

If succesful, UnrealIRCd will reply with a response object. Here's an example if there are 0 channels:

{"jsonrpc": "2.0", "method": "channel.list", "id": 123, "response": {"list": []}}

The response will naturally be different for each method. And as you can see, the id is included so the client application can track request/responses.

Error[edit]

A request may also result in an error instead of a response object. Here's an example error object that UnrealIRCd may send:

{"jsonrpc": "2.0", "method": "qwerty", "id": 123, "error": {"code": -32601, "message": "Unsupported method"}}

Error codes:

typedef enum JsonRpcError {
       // Official JSON-RPC error codes:
       JSON_RPC_ERROR_PARSE_ERROR      = -32700, /**< JSON parse error (fatal) */
       JSON_RPC_ERROR_INVALID_REQUEST  = -32600, /**< Invalid JSON-RPC Request */
       JSON_RPC_ERROR_METHOD_NOT_FOUND = -32601, /**< Method not found */
       JSON_RPC_ERROR_INVALID_PARAMS   = -32602, /**< Method parameters invalid */
       JSON_RPC_ERROR_INTERNAL_ERROR   = -32603, /**< Internal server error */
       // UnrealIRCd JSON-RPC server specific error codes:
       JSON_RPC_ERROR_API_CALL_DENIED  = -32000, /**< The api user does not have enough permissions to do this call */
       // UnrealIRCd specific application error codes:
       JSON_RPC_ERROR_NOT_FOUND        =  -1000, /**< Target not found (no such nick / channel / ..) */
       JSON_RPC_ERROR_ALREADY_EXISTS   =  -1001, /**< Resource already exists by that name (eg on nickchange request, a gline, etc) */
       JSON_RPC_ERROR_INVALID_NAME     =  -1002, /**< Name is not permitted (eg: nick, channel, ..) */
       JSON_RPC_ERROR_USERNOTINCHANNEL =  -1003, /**< The user is not in the channel */
       JSON_RPC_ERROR_TOO_MANY_ENTRIES =  -1004, /**< Too many entries (eg: banlist, ..) */
       JSON_RPC_ERROR_DENIED           =  -1005, /**< Permission denied for user (unrelated to api user permissions) */
} JsonRpcError;

JSON-RPC Methods[edit]

The following methods are currently implemented:

  • user.list
  • user.get
  • channel.list
  • server_ban.list
  • server_ban.get
  • server_ban.add
  • server_ban.del

TODO: document parameters etc.

Examples with parameters:

{"jsonrpc": "2.0", "method": "server_ban.add", "params": {"name":"*@1.2.3.4","type":"gline","reason":"go away please"}, "id": 123}
{"jsonrpc": "2.0", "method": "server_ban.del", "params": {"name":"*@1.2.3.4","type":"gline"}, "id": 123}