Hireriv API
Connect your applicant tracking system, HR software or careers site to Hireriv: post and update jobs, read applications, move candidates along your stages and get signed webhooks when something happens.
Machine-readable description: /api/v1/openapi.json (OpenAPI 3.1). Base address: https://hireriv.in/api/v1. Current release: 2026-10-25.
There are no certified third-party integrations yet. The API is for a company's own systems, set up by that company's owners. We will list partner integrations here only after we have tested them.
Getting started
- A company owner signs in to the employer portal and opens Integrations.
- They create an integration, choose its permissions and copy the client secret. It is shown once.
- Your server exchanges the secret for an access token and calls the API. Keep the secret on the server: never in a website, a mobile app or a code repository.
Authentication
Exchange the client secret for an access token that lasts 15 minutes, then send it as Authorization: Bearer <token>. Tokens in the address (?access_token=) are refused, and cookies are never used.
curl -s -X POST https://hireriv.in/api/v1/oauth/token \
-u "$HIRERIV_CLIENT_ID:$HIRERIV_CLIENT_SECRET" \
-d grant_type=client_credentials
{ "access_token": "hrv_at_…", "token_type": "Bearer", "expires_in": 900, "scope": "jobs:read jobs:write" }
curl -s https://hireriv.in/api/v1/jobs -H "Authorization: Bearer $TOKEN"
Permissions (scopes)
| Scope | Allows |
|---|---|
jobs:read | Read the company’s jobs |
jobs:write | Create and edit jobs, send them for review and close them |
applications:read | Read applications to the company’s jobs (without contact details) |
applications:contact | Also read applicants’ email and phone |
applications:status:update | Move applications along the hiring stages |
webhooks:manage | Manage webhook endpoints, see deliveries and replay them |
Ask for a narrower token with scope=jobs:read. Owners can rotate a secret (the old one keeps working for 24 hours, or stops at once) or revoke the integration, which stops its tokens immediately.
Endpoints
Authentication
| Request | What it does | Needs |
|---|---|---|
POST /oauth/token | Get an access token grant_type=client_credentials with the client secret in HTTP Basic (client id as the user) or in the body. Optional scope narrows the token. | — |
GET /me | Who this token belongs to | — |
Jobs
| Request | What it does | Needs |
|---|---|---|
GET /jobs | List the company’s jobs | jobs:read |
POST /jobs | Create a job (a draft, or sent for review) | jobs:write |
GET /jobs/{id} | Read a job | jobs:read |
PATCH /jobs/{id} | Change a job (a live job goes back for review) | jobs:write |
POST /jobs/{id}/submit | Send a job for Hireriv’s review | jobs:write |
POST /jobs/{id}/close | Close a job | jobs:write |
Applications
| Request | What it does | Needs |
|---|---|---|
GET /applications | List applications to the company’s jobs | applications:read |
GET /applications/{id} | Read an application | applications:read |
PATCH /applications/{id}/status | Move an application to another stage | applications:status:update |
Webhooks
| Request | What it does | Needs |
|---|---|---|
GET /webhooks | List webhook endpoints | webhooks:manage |
POST /webhooks | Add a webhook endpoint (the signing secret is shown once) | webhooks:manage |
PATCH /webhooks/{id} | Change, turn on or turn off an endpoint | webhooks:manage |
DELETE /webhooks/{id} | Delete an endpoint | webhooks:manage |
POST /webhooks/{id}/rotate-secret | Rotate the signing secret (the old one also signs for 24 hours) | webhooks:manage |
POST /webhooks/{id}/test | Send a webhook.test event | webhooks:manage |
GET /webhooks/{id}/deliveries | Recent deliveries to an endpoint (30 days) | webhooks:manage |
POST /webhook-deliveries/{id}/replay | Send a delivery again (same event id) | webhooks:manage |
GET /events | The company’s events of the last 30 days | — |
Public
| Request | What it does | Needs |
|---|---|---|
GET /public/jobs | Search live jobs (no token needed) | — |
GET /public/jobs/{slug} | One live job (no token needed) | — |
Jobs sent through the API are reviewed by Hireriv before they go live, exactly like jobs posted in the portal, and must include their responsibilities, pay (or how it is decided) and, for industrial, field and service work, the hours or shift. Lists return { "data": [...], "has_more": true, "next_cursor": "…" }; pass cursor for the next page.
Applications include the candidate's name, experience, location and stage. Email and phone are included only with applications:contact. Resumes are not available through the API.
Webhooks
Add an endpoint (a public https:// address) under Integrations or with POST /webhooks, and choose its events:
| Event | When |
|---|---|
job.submitted | A job was sent for Hireriv’s review |
job.published | A job went live |
job.rejected | A job was sent back with changes to make |
job.closed | A job closed |
application.created | Someone applied to a job |
application.status_changed | An application moved to another stage |
interview.scheduled | An interview was booked |
Each delivery is a POST with a JSON body { "id", "type", "created_at", "api_version", "environment", "data" }. The data holds ids and states, never candidates' contact details: read those through the API with the right permission.
- At least once. The same event can arrive more than once (after a timeout or a replay). Use
Hireriv-Event-Idto ignore repeats. Order is not guaranteed. - Answer quickly with any 2xx within 10 seconds, and do the work afterwards. Redirects other than 307 and 308 count as failures.
- Retries. Failures are retried up to 8 times, waiting about 30 seconds, then doubling up to 6 hours. After 20 failed deliveries in a row the endpoint is turned off and the owners are emailed. Deliveries are kept for 30 days and can be replayed.
- Catching up.
GET /eventslists the last 30 days of events.
Checking the signature
Every delivery has Hireriv-Signature: t=<unix seconds>,v1=<hex>, an HMAC-SHA256 of t + "." + the raw body with your endpoint's signing secret. After a rotation, two v1 values are sent for 24 hours. Reject deliveries older than 5 minutes.
const crypto = require('crypto');
function verify(rawBody, header, secret) {
const parts = Object.groupBy(header.split(','), (p) => p.split('=')[0]);
const t = Number(parts.t?.[0].slice(2));
if (!t || Math.abs(Date.now() / 1000 - t) > 300) return false;
const expected = crypto.createHmac('sha256', secret).update(`${t}.${rawBody}`).digest('hex');
return (parts.v1 || []).some((p) => {
const got = Buffer.from(p.slice(3), 'hex');
return got.length === 32 && crypto.timingSafeEqual(got, Buffer.from(expected, 'hex'));
});
}
Errors and limits
Errors look like { "error": { "code": "validation_failed", "message": "…", "details": ["…"] } }. Codes include unauthorized, invalid_token, insufficient_scope, not_found, validation_failed, idempotency_key_reused and rate_limited. Anything another company owns answers 404.
- Rate limits: 600 requests a minute for a live integration, 120 in the sandbox. Every answer has
RateLimit-Limit,RateLimit-RemainingandRateLimit-Reset; a429hasRetry-After. - Idempotency: send
Idempotency-KeyonPOSTrequests to retry safely. The same key and body return the first answer for 24 hours; a different body is refused with422.
Sandbox
Choose Sandbox when creating an integration. Its secret starts with hrv_test_ and it sees only sample jobs and applications made for it: nothing reaches live jobs, real candidates or our review queue. Sandbox events go only to that integration's sandbox endpoints.
Versions and changes
- The version is in the address (
/api/v1). Within v1 we only add things: new endpoints, optional fields and new event types. Your code should ignore fields it does not know. - A breaking change means a new version. We announce it to the owners of every integration at least 6 months before v1 stops, and old versions answer with
DeprecationandSunsetheaders in that time. - Every answer carries
Hireriv-Api-Versionwith the release date.
Security
- Secrets are stored only as hashes and shown once. If one leaks, rotate it with "stop the old key now", or revoke the integration.
- Owners are emailed when an integration is created. Every change to keys and webhooks is in the company's activity log.
- Webhook addresses must be public: private, local and reserved networks are refused, also after redirects and when a name resolves to one.
- Report a security problem to hello@hireriv.com.