Invoking RFG APIs

All RFG APIs are invoked in the same manner, described in this section. We encourage developers to separate the code that does the API invocation from the application code that calls the API and processes the response. This will facilitate reuse and make it easy to call other RFG APIs in the future. All API commands are formatted as JSON documents, and are POST'ed in the body of an HTTPS connection. An API command always has 3 parts, separated by a / character (e.g. "test/copy/1"). The first part is the API name, the second part is the command name, and the third part is the version number. This command string must be included in the JSON document, along with any additional parameters needed by that command. E.g.

{
    command: 'test/copy/1',
    data1: 'some test data to copy',
    data2: 'more test data to copy'
}

(white space within the outer { } is ignored.)

Each client is given:

  1. An 'apid' which identifies them in our system
  2. A 128-bit secret used to authenticate, encoded as a 32 character hex string.

The API entry point for all APIs is https://api.researchforgood.com/API/. To invoke the JSON command:

  1. Get the current UNIX timestamp (number of seconds since Jan 1, 1970), e.g. 1382031777

  2. Concatenate the timestamp with the JSON document (making sure that there is no additional whitespace outside of the enclosing { }. E.g.

    1382031777{
        command: 'test/copy/1',
        data1: 'some test data to copy',
        data2: 'more test data to copy'
    }
    
  3. Decode the 32 character secret into a 16 byte array.

  4. Compute the HMAC_SHA1 of the text in #2, using the 16 byte array as the key.

  5. Open an HTTPS connection to the entry point with additional parameters:

    • time: the UNIX timestamp
    • apid: the identifier you were given
    • hash: the HMAC_SHA1 code you computed
    • e.g. https://api.researchforgood.com/API?apid=325f4174fd41a80957ec1b25&time=1382031777&hash=8e56301e9765a9781e7d847057e571e294138671
  6. Set the mime type "application/json". HTTPS POST must be used.

  7. In the POST body, put the original JSON document.

When we receive this command, we repeat the above procedure to authenticate you and validate the JSON message. The timestamp is checked and must be within 60 seconds of the server time, to guard against replay attacks. When this procedure succeeds, the JSON is parsed and the command is processed. The HTTP response will always contain a JSON document containing the result of the command. E.g.

{
    result: 0,
    response: {
        data1: "some test data" ,
        data2: "more test data"
    }
}

The 'result' will be 0 on success. On success, there may also be an embedded 'response' object containing any output from the command. The 'command' will also be sent back to you so you can know the command and the version number that was run. There are three classes of errors: command errors (result=1), protocol errors (result=2), and internal server errors (result=3). A command error occurs when a successfully validated command cannot complete. A protocol error occurs when the server cannot complete the validation and authentication before invoking the command, or any other communications problem. An internal server error indicates a problem in our coding for processing the request. Please contact RFG support. In all cases, a 'message' will accompany the error result telling you the problem. The "test/copy/1" API described above exists for developers to test their API invocation code, before calling other APIs. It simple copies back to you any data that you send it. For the rest of this document "ISO Date" refers to a String that represents a date formatted with the pattern "yyyy-MM- dd'T'HH:mm:ss'Z'". All the data that we publish with this API is cached every minute. All commands, parameter names and parameter values (such as datapoints names) are case sensitive.