Here are some code samples to help you with your RSA Authentication method implementation. These examples are run on the Test endpoint .

Bash

#! /bin/bash

# Put your public key here, keep it on a single line
PUB_KEY="-----BEGIN RSA PUBLIC KEY-----MEgCQQCQyhMk37PWcf8Y/5jbjPxhMw/N35PwCasZUdWvhLWIHf6YqOuyo00Jtc7M0kj3/tybiWAZ1X3NSIvmTXJ5J2ctAgMBAAE=-----END RSA PUBLIC KEY-----"

# Put your private key here, with the line breaks
PRIVATE_KEY="-----BEGIN RSA PRIVATE KEY-----
MIIBOwIBAAJBAJDKEyTfs9Zx/xj/SNuM/GEzD83fk/AJqx
lR1a+EtYgd/pio67KjTQm1zszSSPf+3JuJYBnVfc1Ii+ZN
cnknZy0CAwEAAQJADfghHraikDcRaKUAr4YLt4kIplFC4a
7dHiVCG5wPM6Gj6ghyribNRMXQS0/bsGmsxOsar7dh0Boh
9jLnec56gQIhANJSria/oKfEzdQKTdfMOM9D6Gw1Dd9RWE
L7yih+M1YhAiEAsDvskelGHt6CzK4vyJJabhUdD8vq+78w
ncN9G42kF40CIQC7nvQqLuIDJ4YxtKtyaYT4KG0LMlzYrX
kd7/2MF+B14QIhAKdkc8LwCPt/LEwP0zE22hAfm9gKP6tZ
IWtoaKfINKltAiAqEBbkEM2ZvmU+QMbF1hQxyRENZS0STO
Cy2X53gi/tRg==
-----END RSA PRIVATE KEY-----"

# Get the current UNIX timestamp and generate a random string
TIMESTAMP=$(date +%s)
NONCE=$(openssl rand -hex 8)

# Example body
# Remember to sort this JSON object by key in alphabetical order recursively
# in order to sign your request
BODY='{"testArray":["this","is","an","array"],"testBool":true,"testNumber":123,"testObject":{"a":true,"b":false},"testString":"hello"}'

# Example query params
# Remember to sort this JSON object by key in alphabetical order recursively
# in order to sign your request
QUERY_PARAMS='{"bar":"42","foo":"hi"}'

# JSON object to be signed
# Please respect the order or your signature won't be validated
TO_SIGN=$(printf '{"security":{"nonce":"%s","timestamp":"%s"},"queryParams":%s,"body":%s}' $NONCE $TIMESTAMP $QUERY_PARAMS $BODY)

# Generate the signature
SIGN=$(echo $TO_SIGN | tr -d '\\n' | openssl dgst -sha256 -sign <(echo "${PRIVATE_KEY}") | base64)

# Make the request
curl \\
 -X POST \\
 -d $BODY \\
 '<https://api.e-potek.ch/api/test?foo=hi&bar=42>' \\
 -H 'Content-Type: application/json' \\
 -H "X-RESOLVE-Authorization: RESOLVE ${PUB_KEY}:${SIGN}" \\
 -H "X-RESOLVE-Nonce: ${NONCE}" \\
 -H "X-RESOLVE-Timestamp: ${TIMESTAMP}" \\

Javascript

import https from "https";
import NodeRSA from "node-rsa";
import queryString from "query-string";

// Your API public key
const publicKey =
 "-----BEGIN RSA PUBLIC KEY-----\\n" +
 "MEgCQQCGZse2vDomKwX42nV3ZwJsbw/RGzbtCoz00xnciiHvJOGn\\n" +
 "79MDLQ93aXJVJb0YwqwYIqQHqJI/I1/2inD353lnAgMBAAE=\\n" +
 "-----END RSA PUBLIC KEY-----";

// Your API private key
const privateKey =
 "-----BEGIN RSA PRIVATE KEY-----\\n" +
 "MIIBOQIBAAJAVY6quuzCwyOWzymJ7C4zXjeV/232wt2ZgJZ1kHzjI73wnhQ3WQcL\\n" +
 "DFCSoi2lPUW8/zspk0qWvPdtp6Jg5Lu7hwIDAQABAkBEws9mQahZ6r1mq2zEm3D/\\n" +
 "VM9BpV//xtd6p/G+eRCYBT2qshGx42ucdgZCYJptFoW+HEx/jtzWe74yK6jGIkWJ\\n" +
 "AiEAoNAMsPqwWwTyjDZCo9iKvfIQvd3MWnmtFmjiHoPtjx0CIQCIMypAEEkZuQUi\\n" +
 "pMoreJrOlLJWdc0bfhzNAJjxsTv/8wIgQG0ZqI3GubBxu9rBOAM5EoA4VNjXVigJ\\n" +
 "QEEk1jTkp8ECIQCHhsoq90mWM/p9L5cQzLDWkTYoPI49Ji+Iemi2T5MRqwIgQl07\\n" +
 "Es+KCn25OKXR/FJ5fu6A6A+MptABL3r8SEjlpLc=\\n" +
 "-----END RSA PRIVATE KEY-----";

 // Sorts an object by key in alphabetical order recursively
const sortObject = object => {
 if (!object || typeof object !== "object" || object instanceof Array) {
   return object;
 }

 const sortedObject = {};
 const keys = Object.keys(object);

 keys.sort();

 keys.forEach(key => {
   sortedObject[key] = sortObject(object[key]);
 });

 return sortedObject;
};

// Signs you request with your private key
const signRequest = ({ body, query, timestamp, nonce, privateKey }) => {
 const key = new NodeRSA();
 key.importKey(privateKey.replace(/\\r?\\n|\\r/g, ""), "pkcs1-private-pem");

 let objectToSign = { security: sortObject({ timestamp, nonce }) };

 if (query) {
   objectToSign = { ...objectToSign, queryParams: sortObject(query) };
 }

 if (body) {
   objectToSign = { ...objectToSign, body: sortObject(body) };
 }

 const signature = key.sign(JSON.stringify(objectToSign), "base64", "utf8");
 return signature;
};

// Test body
const BODY = {
 testString: "hello",
 testNumber: 12345,
 testObject: {testArray: ["test1", "test2"]},
};

// Test query params
const QUERY = {
 param1: "hello?this/is=a-test",
 param2: "?yay!this/is/so#cool"
};

// Test id
const ID = "abc123";

// Timestamp and nonce for the request
// Note: always generate different nonce and timestamp for each request !
const TIMESTAMP = Math.round(new Date().valueOf() / 1000).toString();
const NONCE = Math.random()
 .toString(36)
 .substr(2, 8);

// Request signature
const signature = signRequest({
 body: BODY,
 query: QUERY,
 timestamp: TIMESTAMP,
 nonce: NONCE,
 privateKey
});

// Request options
const options = {
 host: "api.resolve.ch",
 port: 443,
 path: `/api/test/${ID}?${queryString.stringify(QUERY, { encode: true })}`,
 method: "POST",
 headers: {
   "Content-Type": "application/json",
   "X-RESOLVE-Authorization": `RESOLVE ${publicKey.replace(
     /\\r?\\n|\\r/g,
     ""
   )}:${signature}`, //Don't forget the signature
   "X-RESOLVE-Nonce": NONCE,
   "X-RESOLVE-Timestamp": TIMESTAMP
 }
};

const req = https.request(options, result => {
 result.setEncoding("utf8");
 result.on("data", chunk => {
   console.log(chunk);
 });
});

req.on("error", error => {
 console.error(error);
});

// Write the body
req.write(JSON.stringify(BODY));
req.end();