Merit Palk API Authentication

Overview

All Merit Palk API requests require authentication using HMAC-SHA256 signatures. This ensures message integrity and authenticates requests to specific companies.

Prerequisites

  • Merit Palk PRO license
  • API credentials (API ID and API Key) generated from Merit Palk Settings > API Settings.

Credentials

CredentialFormatDescription
API IDGUIDUnique identifier for your API access
API KeyBase64 string (256-bit)Secret key for signature calculation

Admin users can generate and manage API credentials in Merit Palk Settings > API Settings.

  1. Navigate to API Settings
  2. Click “New API key” to create new credentials
  3. Store the API Key securely – it cannot be retrieved after creation
  4. Add optional comments to identify the credential purpose

Keep your Api ID and Api Key secret. They should be guarded just as you would your regular account password. If you feel your ID and Key has been compromised, you can reset it by deleting and re creating a new ID and Key.

Request Authentication

Required Query Parameters

All API endpoints require these query string parameters:

ParameterFormatDescription
apiIdGUIDYour API ID credential
timestampyyyyMMddHHmmssCurrent UTC time
signatureBase64 string (URL-encoded)HMAC-SHA256 signature

Timestamp Requirements

  • Format: yyyyMMddHHmmss (numeric, 14 digits)
  • Timezone: Must be UTC
  • Validity: Use current time – requests with old or future timestamps are rejected

Signature Calculation

The signature is calculated using HMAC-SHA256 (RFC-2104):

dataToSign = UTF8_bytes(ApiId + Timestamp + RequestBody)
signature = Base64(HMAC-SHA256(ApiKey, dataToSign))

Important: The signature must be URL-encoded when passed as a query parameter.
The + character in Base64 must be encoded as %2B.

Example Request

POST 
/api/v1/getemployees?apiId=670fe52f-558a-4be8-ade0-526e01a106d0&timestamp=20240624205902&signature=dt6dkfuj%2BOfX01YkvvAoN%2FfekAUGr6AvVlQhUUja9Qc%3D
Content-Type: application/json

{"OnlyActive": true}

Request Format

AspectRequirement
MethodHTTP POST (for most endpoints)
Content-Typeapplication/json
EncodingUTF-8
Date formatyyyy-mm-dd
Decimal separator. (dot)
Boolean valuestrue / false (lowercase)
Null valuesnull (lowercase)
PercentagesWhole numbers (5 for 5%, not 0.05)

Response Codes

CodeDescription
200Success – response contains requested data
400Bad Request – invalid request data or business rule violation
401Unauthorized – invalid credentials, signature, or missing PRO license

Code Examples

C#

public string CalculateSignature(string apiId, string apiKey, string timestamp, string requestBody)
{
    byte[] keyBytes = Convert.FromBase64String(apiKey);
    byte[] dataBytes = Encoding.UTF8.GetBytes(apiId + timestamp + requestBody);

    using (var hmac = new HMACSHA256(keyBytes))
    {
        byte[] signatureBytes = hmac.ComputeHash(dataBytes);
        return Convert.ToBase64String(signatureBytes);
    }
}

// Usage
string apiId = "your-api-id";
string apiKey = "your-api-key";
string timestamp = DateTime.UtcNow.ToString("yyyyMMddHHmmss");
string requestBody = "{\"OnlyActive\":true}";

string signature = CalculateSignature(apiId, apiKey, timestamp, requestBody);
string signatureEncoded = WebUtility.UrlEncode(signature);

string url = $"https://palk.merit.ee/api/v1/getemployees?apiId={apiId}&timestamp={timestamp}&signature={signatureEncoded}";

Python

import hmac
import hashlib
import base64
from datetime import datetime
from urllib.parse import quote

def calculate_signature(api_id: str, api_key: str, timestamp: str, request_body: str) -> str:
    key_bytes = base64.b64decode(api_key)
    data_to_sign = (api_id + timestamp + request_body).encode('utf-8')
    signature = hmac.new(key_bytes, data_to_sign, hashlib.sha256).digest()
    return base64.b64encode(signature).decode('utf-8')

# Usage
api_id = "your-api-id"
api_key = "your-api-key"
timestamp = datetime.utcnow().strftime("%Y%m%d%H%M%S")
request_body = '{"OnlyActive":true}'

signature = calculate_signature(api_id, api_key, timestamp, request_body)
signature_encoded = quote(signature, safe='')

url = f"https://palk.merit.ee/api/v1/getemployees?apiId={api_id}&timestamp={timestamp}&signature={signature_encoded}"

Security Best Practices

  1. Protect your API Key – treat it like a password
  2. Use HTTPS – all communication is encrypted
  3. Regenerate credentials if compromised – delete and create new ones in API Settings
  4. Limit credential sharing – create separate credentials for different integrations

Troubleshooting

ErrorCauseSolution
Missing URL parameterapiId, timestamp, or signature not providedEnsure all three parameters are in the query string
Timestamp not validTimestamp too old or in futureUse current UTC time in yyyyMMddHHmmss format
UnauthorizedInvalid API IDVerify API ID in Settings > API Settings
Incorrect signatureSignature calculation errorVerify: correct API Key, UTF-8 encoding, exact concatenation order (ApiId + Timestamp + Body)
PRO licence neededNo active PRO licenseUpgrade to Merit Palk PRO package