API reference
Approvals
Approval rules and change requests: list, approve, reject and withdraw.
7 actions · base URL https://api.bizisy.com/v1 · generated from the same definitions as the API.
Get approval settings#
POST/v1/org/approvals.settings.getRead
Returns who must approve each kind of change before it takes effect: job_change (title, team, manager, location, legal entity, employment type, FTE, contract terms; org_people_change_job), termination (org_people_terminate) and pay_change (org_pay_add). Modes: off (no approval: the change applies at once; the default), hr (an owner, admin or HR member), manager (the person's manager today; when they have no manager, the team lead of their team or of a team above it decides; HR when no one of them can sign in, or when the manager proposed the change), manager_then_hr (both, in that order). Pay offers off and hr only. hr_approvers is how many owners, admins and HR members can approve. Owners, admins and HR.
- Who can call it
- Manage key owner admin hr
- MCP tool
org_approvals_settings_geton HR Assistant- Method
POSTwith a JSON body, orGETwith the input as query parameters
Input
No input: send {}.
Returns
job_change"off" | "hr" | "manager" | "manager_then_hr"requiredtermination"off" | "hr" | "manager" | "manager_then_hr"requiredpay_change"off" | "hr" | "manager" | "manager_then_hr"requiredupdated_atstring | nullrequiredhr_approversintegerrequired
Errors
validation_failed unauthenticated forbidden not_found rate_limited internal
curl https://api.bizisy.com/v1/org/approvals.settings.get \
-H "Authorization: Bearer $BIZISY_API_KEY" \
-H "Content-Type: application/json" \
-d '{}'const res = await fetch('https://api.bizisy.com/v1/org/approvals.settings.get', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.BIZISY_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({}),
});
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
console.log(body.data);import os
import requests
res = requests.post(
"https://api.bizisy.com/v1/org/approvals.settings.get",
headers={"Authorization": f"Bearer {os.environ['BIZISY_API_KEY']}"},
json={},
)
body = res.json()
if not res.ok:
raise RuntimeError(f"{body['error']['code']}: {body['error']['message']}")
print(body["data"]){
"data": {
"job_change": "off",
"termination": "off",
"pay_change": "off",
"updated_at": null,
"hr_approvers": 2
}
}Change approval settings#
POST/v1/org/approvals.settings.updateWrite
Sets who approves each kind of change (see org_approvals_settings_get): job_change, termination and pay_change, each off, hr, manager or manager_then_hr (pay: off or hr). Send only what changes. Requests already waiting keep the steps they were created with. Owners and admins only, and only in the app: never over an API key or MCP, so an assistant can never switch approval off.
- Web app only
- Refused for API keys and connected apps. Who approves changes is set in the app only, so an assistant can never switch approval off.
- MCP tool
org_approvals_settings_updateon HR Assistant- Preview
?dry_run=trueruns every check and saves nothing- Retries
- An Idempotency-Key replays the first result
Input
job_change"off" | "hr" | "manager" | "manager_then_hr"termination"off" | "hr" | "manager" | "manager_then_hr"pay_change"off" | "hr"
Returns
job_change"off" | "hr" | "manager" | "manager_then_hr"requiredtermination"off" | "hr" | "manager" | "manager_then_hr"requiredpay_change"off" | "hr" | "manager" | "manager_then_hr"requiredupdated_atstring | nullrequiredhr_approversintegerrequired
Errors
validation_failed unauthenticated forbidden not_found conflict rate_limited internal
curl https://api.bizisy.com/v1/org/approvals.settings.update \
-H "Authorization: Bearer $BIZISY_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{"termination":"manager","pay_change":"hr"}'const res = await fetch('https://api.bizisy.com/v1/org/approvals.settings.update', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.BIZISY_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': crypto.randomUUID(),
},
body: JSON.stringify({
"termination": "manager",
"pay_change": "hr"
}),
});
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
console.log(body.data);import os, uuid
import requests
res = requests.post(
"https://api.bizisy.com/v1/org/approvals.settings.update",
headers={"Authorization": f"Bearer {os.environ['BIZISY_API_KEY']}", "Idempotency-Key": str(uuid.uuid4())},
json={
"termination": "manager",
"pay_change": "hr",
},
)
body = res.json()
if not res.ok:
raise RuntimeError(f"{body['error']['code']}: {body['error']['message']}")
print(body["data"]){
"data": {
"job_change": "manager_then_hr",
"termination": "manager",
"pay_change": "hr",
"updated_at": "2026-10-04T10:00:00.000Z",
"hr_approvers": 2
}
}List approval requests#
POST/v1/org/approvals.listRead
Lists change requests you may see: status open (default: waiting for a decision), closed (approved, rejected, withdrawn, outdated or expired; newest first, at most 100) or all; person_id narrows to one person; waiting_for_me only those you can decide now. waiting_for_me in the result counts requests you can decide (over an API key: that its user can decide in the app). Each request has the change (job_change before/after, termination last day and reason, or pay_change amount), the effective date, the steps with who approved or can approve, and can_decide. You see job and termination requests as HR, as one of the person's managers, as the proposer, or as the team lead deciding it (while it waits for you, and after you decided); pay requests only as HR in the app; never requests about yourself. Approving needs the app (org_approvals_approve refuses API keys).
- Who can call it
- Manage key any Manage role
Me key anyone - MCP tool
org_approvals_liston My Workplace, HR Assistant- Method
POSTwith a JSON body, orGETwith the input as query parameters
Input
status"open" | "closed" | "all"Default
"open".person_idstringwaiting_for_meboolean
Returns
itemsobject[]required19 fields
idstringrequiredkind"job_change" | "termination" | "pay_change"requiredstatus"pending" | "approved" | "rejected" | "cancelled" | "outdated" | "expired"requiredpersonobjectrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
effective_datestringrequiredexpires_onstringrequiredchange"change_job" | "terminate" | "pay_add" | "correct_job" | "rehire" | "pay_remove"requiredjob_changeobject | nullrequired3 fields
reason"change" | "promotion" | "transfer" | "correction" | "rehire"requiredbeforeobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
afterobjectrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
terminationobject | nullrequired4 fields
last_daystringrequiredreasonstring | nullrequiredjobobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
change"end" | "move" | "cancel"required
pay_changeobject | nullrequired6 fields
amountnumberrequiredcurrencystringrequiredperiod"year" | "month" | "hour"requirednotestring | nullrequiredbeforeobject | nullrequired4 fields
amountnumberrequiredcurrencystringrequiredperiodstringrequiredvalid_fromstringrequired
removesbooleanrequired
proposed_byobjectrequired3 fields
namestringrequiredperson_idstring | nullrequiredvia"app" | "api"required
proposed_atstringrequiredstepsobject[]required11 fields
role"manager" | "hr"requiredstate"waiting" | "pending" | "approved" | "rejected"requiredfallbackbooleanrequiredteam_leadobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredreason"no_manager" | "manager_left"required
team_lead_blockedobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredwhat"lead" | "removed" | "moved" | "archived"required
untrusted"no_login" | "invited_by_proposer"requireddecided_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
decided_atstring | nullrequiredcommentstring | nullrequiredauto"proposed_by_approver" | "no_other_approver"requiredapproversobject[]required3 fields
namestringrequiredperson_idstring | nullrequiredis_viewerbooleanrequired
closed_atstring | nullrequiredclosed_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
can_decidebooleanrequiredcan_cancelbooleanrequiredis_proposerbooleanrequiredcan_rejectbooleanrequired
waiting_for_meintegerrequired
Errors
validation_failed unauthenticated forbidden not_found rate_limited internal
curl https://api.bizisy.com/v1/org/approvals.list \
-H "Authorization: Bearer $BIZISY_API_KEY" \
-H "Content-Type: application/json" \
-d '{"status":"closed","person_id":"p1"}'const res = await fetch('https://api.bizisy.com/v1/org/approvals.list', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.BIZISY_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
"status": "closed",
"person_id": "p1"
}),
});
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
console.log(body.data);import os
import requests
res = requests.post(
"https://api.bizisy.com/v1/org/approvals.list",
headers={"Authorization": f"Bearer {os.environ['BIZISY_API_KEY']}"},
json={
"status": "closed",
"person_id": "p1",
},
)
body = res.json()
if not res.ok:
raise RuntimeError(f"{body['error']['code']}: {body['error']['message']}")
print(body["data"]){
"data": {
"items": [
{
"id": "apr1",
"kind": "job_change",
"status": "pending",
"person": {
"id": "p1",
"name": "Ana Ferreira",
"title": "Engineer",
"photo_url": null
},
"effective_date": "2026-11-01",
"expires_on": "2026-12-01",
"change": "change_job",
"job_change": {
"reason": "promotion",
"before": {
"id": "j1",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "hire",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
},
"after": {
"id": "apr1:after",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Senior Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "promotion",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
}
},
"termination": null,
"pay_change": null,
"proposed_by": {
"name": "Hugo Reis",
"person_id": "p4",
"via": "app"
},
"proposed_at": "2026-10-04T10:00:00.000Z",
"steps": [
{
"role": "manager",
"state": "pending",
"fallback": false,
"team_lead": null,
"team_lead_blocked": null,
"untrusted": null,
"decided_by": null,
"decided_at": null,
"comment": null,
"auto": null,
"approvers": [
{
"name": "Bea Silva",
"person_id": "p2",
"is_viewer": true
}
]
}
],
"closed_at": null,
"closed_by": null,
"can_decide": true,
"can_cancel": false,
"is_proposer": false,
"can_reject": true
}
],
"waiting_for_me": 1
}
}Get an approval request#
POST/v1/org/approvals.getRead
Returns one change request (see org_approvals_list) with its change, steps, comments and whether you can decide or withdraw it.
- Who can call it
- Manage key any Manage role
Me key anyone - MCP tool
org_approvals_geton My Workplace, HR Assistant- Method
POSTwith a JSON body, orGETwith the input as query parameters
Input
approval_idstringrequired
Returns
19 fields
idstringrequiredkind"job_change" | "termination" | "pay_change"requiredstatus"pending" | "approved" | "rejected" | "cancelled" | "outdated" | "expired"requiredpersonobjectrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
effective_datestringrequiredexpires_onstringrequiredchange"change_job" | "terminate" | "pay_add" | "correct_job" | "rehire" | "pay_remove"requiredjob_changeobject | nullrequired3 fields
reason"change" | "promotion" | "transfer" | "correction" | "rehire"requiredbeforeobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
afterobjectrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
terminationobject | nullrequired4 fields
last_daystringrequiredreasonstring | nullrequiredjobobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
change"end" | "move" | "cancel"required
pay_changeobject | nullrequired6 fields
amountnumberrequiredcurrencystringrequiredperiod"year" | "month" | "hour"requirednotestring | nullrequiredbeforeobject | nullrequired4 fields
amountnumberrequiredcurrencystringrequiredperiodstringrequiredvalid_fromstringrequired
removesbooleanrequired
proposed_byobjectrequired3 fields
namestringrequiredperson_idstring | nullrequiredvia"app" | "api"required
proposed_atstringrequiredstepsobject[]required11 fields
role"manager" | "hr"requiredstate"waiting" | "pending" | "approved" | "rejected"requiredfallbackbooleanrequiredteam_leadobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredreason"no_manager" | "manager_left"required
team_lead_blockedobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredwhat"lead" | "removed" | "moved" | "archived"required
untrusted"no_login" | "invited_by_proposer"requireddecided_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
decided_atstring | nullrequiredcommentstring | nullrequiredauto"proposed_by_approver" | "no_other_approver"requiredapproversobject[]required3 fields
namestringrequiredperson_idstring | nullrequiredis_viewerbooleanrequired
closed_atstring | nullrequiredclosed_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
can_decidebooleanrequiredcan_cancelbooleanrequiredis_proposerbooleanrequiredcan_rejectbooleanrequired
Errors
validation_failed unauthenticated forbidden not_found rate_limited internal
curl https://api.bizisy.com/v1/org/approvals.get \
-H "Authorization: Bearer $BIZISY_API_KEY" \
-H "Content-Type: application/json" \
-d '{"approval_id":"apr1"}'const res = await fetch('https://api.bizisy.com/v1/org/approvals.get', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.BIZISY_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
"approval_id": "apr1"
}),
});
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
console.log(body.data);import os
import requests
res = requests.post(
"https://api.bizisy.com/v1/org/approvals.get",
headers={"Authorization": f"Bearer {os.environ['BIZISY_API_KEY']}"},
json={
"approval_id": "apr1",
},
)
body = res.json()
if not res.ok:
raise RuntimeError(f"{body['error']['code']}: {body['error']['message']}")
print(body["data"]){
"data": {
"id": "apr1",
"kind": "job_change",
"status": "pending",
"person": {
"id": "p1",
"name": "Ana Ferreira",
"title": "Engineer",
"photo_url": null
},
"effective_date": "2026-11-01",
"expires_on": "2026-12-01",
"change": "change_job",
"job_change": {
"reason": "promotion",
"before": {
"id": "j1",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "hire",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
},
"after": {
"id": "apr1:after",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Senior Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "promotion",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
}
},
"termination": null,
"pay_change": null,
"proposed_by": {
"name": "Hugo Reis",
"person_id": "p4",
"via": "app"
},
"proposed_at": "2026-10-04T10:00:00.000Z",
"steps": [
{
"role": "manager",
"state": "pending",
"fallback": false,
"team_lead": null,
"team_lead_blocked": null,
"untrusted": null,
"decided_by": null,
"decided_at": null,
"comment": null,
"auto": null,
"approvers": [
{
"name": "Bea Silva",
"person_id": "p2",
"is_viewer": true
}
]
}
],
"closed_at": null,
"closed_by": null,
"can_decide": true,
"can_cancel": false,
"is_proposer": false,
"can_reject": true
}
}Approve a change request#
POST/v1/org/approvals.approveWrite
Approves the step of a request that is waiting for you, with an optional comment. On the last step the change is applied exactly as org_people_change_job, org_people_terminate or org_pay_add would apply it (same checks, effective date and warnings); if it can no longer apply (for example the new manager left) approving is refused with the reason, and you can reject it instead. A request whose effective date passed is recorded backdated; 30 days after it, it expires. Only in the app, by the step's approver: the person's manager (with no manager: the team lead the request names in team_lead), or an owner, admin or HR member; never the proposer of an app request, never about yourself. Over an API key or MCP it is refused.
- Web app only
- Refused for API keys and connected apps. Approving needs a person signed in to Bizisy.
- MCP tool
org_approvals_approveon My Workplace, HR Assistant- Preview
?dry_run=trueruns every check and saves nothing- Retries
- An Idempotency-Key prevents a second run, but the result is never stored (it holds a secret or personal data): a retry gets a 409 that points to Activity
Input
approval_idstringrequiredcommentstringUp to 500 characters.
stepintegerFrom 0 to 5.
Returns
20 fields
idstringrequiredkind"job_change" | "termination" | "pay_change"requiredstatus"pending" | "approved" | "rejected" | "cancelled" | "outdated" | "expired"requiredpersonobjectrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
effective_datestringrequiredexpires_onstringrequiredchange"change_job" | "terminate" | "pay_add" | "correct_job" | "rehire" | "pay_remove"requiredjob_changeobject | nullrequired3 fields
reason"change" | "promotion" | "transfer" | "correction" | "rehire"requiredbeforeobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
afterobjectrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
terminationobject | nullrequired4 fields
last_daystringrequiredreasonstring | nullrequiredjobobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
change"end" | "move" | "cancel"required
pay_changeobject | nullrequired6 fields
amountnumberrequiredcurrencystringrequiredperiod"year" | "month" | "hour"requirednotestring | nullrequiredbeforeobject | nullrequired4 fields
amountnumberrequiredcurrencystringrequiredperiodstringrequiredvalid_fromstringrequired
removesbooleanrequired
proposed_byobjectrequired3 fields
namestringrequiredperson_idstring | nullrequiredvia"app" | "api"required
proposed_atstringrequiredstepsobject[]required11 fields
role"manager" | "hr"requiredstate"waiting" | "pending" | "approved" | "rejected"requiredfallbackbooleanrequiredteam_leadobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredreason"no_manager" | "manager_left"required
team_lead_blockedobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredwhat"lead" | "removed" | "moved" | "archived"required
untrusted"no_login" | "invited_by_proposer"requireddecided_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
decided_atstring | nullrequiredcommentstring | nullrequiredauto"proposed_by_approver" | "no_other_approver"requiredapproversobject[]required3 fields
namestringrequiredperson_idstring | nullrequiredis_viewerbooleanrequired
closed_atstring | nullrequiredclosed_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
can_decidebooleanrequiredcan_cancelbooleanrequiredis_proposerbooleanrequiredcan_rejectbooleanrequiredwarningsstring[]required
Errors
validation_failed unauthenticated forbidden not_found conflict rate_limited internal
curl https://api.bizisy.com/v1/org/approvals.approve \
-H "Authorization: Bearer $BIZISY_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{"approval_id":"apr1","comment":"Agreed in the review","step":0}'const res = await fetch('https://api.bizisy.com/v1/org/approvals.approve', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.BIZISY_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': crypto.randomUUID(),
},
body: JSON.stringify({
"approval_id": "apr1",
"comment": "Agreed in the review",
"step": 0
}),
});
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
console.log(body.data);import os, uuid
import requests
res = requests.post(
"https://api.bizisy.com/v1/org/approvals.approve",
headers={"Authorization": f"Bearer {os.environ['BIZISY_API_KEY']}", "Idempotency-Key": str(uuid.uuid4())},
json={
"approval_id": "apr1",
"comment": "Agreed in the review",
"step": 0,
},
)
body = res.json()
if not res.ok:
raise RuntimeError(f"{body['error']['code']}: {body['error']['message']}")
print(body["data"]){
"data": {
"id": "apr1",
"kind": "job_change",
"status": "approved",
"person": {
"id": "p1",
"name": "Ana Ferreira",
"title": "Engineer",
"photo_url": null
},
"effective_date": "2026-11-01",
"expires_on": "2026-12-01",
"change": "change_job",
"job_change": {
"reason": "promotion",
"before": {
"id": "j1",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "hire",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
},
"after": {
"id": "apr1:after",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Senior Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "promotion",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
}
},
"termination": null,
"pay_change": null,
"proposed_by": {
"name": "Hugo Reis",
"person_id": "p4",
"via": "app"
},
"proposed_at": "2026-10-04T10:00:00.000Z",
"steps": [
{
"role": "manager",
"state": "approved",
"fallback": false,
"team_lead": null,
"team_lead_blocked": null,
"untrusted": null,
"decided_by": {
"name": "Bea Silva",
"person_id": "p2"
},
"decided_at": "2026-10-05T09:00:00.000Z",
"comment": null,
"auto": null,
"approvers": []
}
],
"closed_at": "2026-10-05T09:00:00.000Z",
"closed_by": {
"name": "Bea Silva",
"person_id": "p2"
},
"can_decide": false,
"can_cancel": false,
"is_proposer": false,
"can_reject": false,
"warnings": []
}
}Reject a change request#
POST/v1/org/approvals.rejectWrite
Rejects a request; comment (required) says why, for the proposer. Nothing changes on the person. In the app only, by the step's approver, or by any owner, admin or HR member (so a request waiting for a manager never holds the person up), never about yourself.
- Web app only
- Refused for API keys and connected apps. Rejecting needs a person signed in to Bizisy.
- MCP tool
org_approvals_rejecton My Workplace, HR Assistant- Preview
?dry_run=trueruns every check and saves nothing- Retries
- An Idempotency-Key prevents a second run, but the result is never stored (it holds a secret or personal data): a retry gets a 409 that points to Activity
Input
approval_idstringrequiredcommentanyrequiredstepintegerFrom 0 to 5.
Returns
19 fields
idstringrequiredkind"job_change" | "termination" | "pay_change"requiredstatus"pending" | "approved" | "rejected" | "cancelled" | "outdated" | "expired"requiredpersonobjectrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
effective_datestringrequiredexpires_onstringrequiredchange"change_job" | "terminate" | "pay_add" | "correct_job" | "rehire" | "pay_remove"requiredjob_changeobject | nullrequired3 fields
reason"change" | "promotion" | "transfer" | "correction" | "rehire"requiredbeforeobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
afterobjectrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
terminationobject | nullrequired4 fields
last_daystringrequiredreasonstring | nullrequiredjobobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
change"end" | "move" | "cancel"required
pay_changeobject | nullrequired6 fields
amountnumberrequiredcurrencystringrequiredperiod"year" | "month" | "hour"requirednotestring | nullrequiredbeforeobject | nullrequired4 fields
amountnumberrequiredcurrencystringrequiredperiodstringrequiredvalid_fromstringrequired
removesbooleanrequired
proposed_byobjectrequired3 fields
namestringrequiredperson_idstring | nullrequiredvia"app" | "api"required
proposed_atstringrequiredstepsobject[]required11 fields
role"manager" | "hr"requiredstate"waiting" | "pending" | "approved" | "rejected"requiredfallbackbooleanrequiredteam_leadobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredreason"no_manager" | "manager_left"required
team_lead_blockedobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredwhat"lead" | "removed" | "moved" | "archived"required
untrusted"no_login" | "invited_by_proposer"requireddecided_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
decided_atstring | nullrequiredcommentstring | nullrequiredauto"proposed_by_approver" | "no_other_approver"requiredapproversobject[]required3 fields
namestringrequiredperson_idstring | nullrequiredis_viewerbooleanrequired
closed_atstring | nullrequiredclosed_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
can_decidebooleanrequiredcan_cancelbooleanrequiredis_proposerbooleanrequiredcan_rejectbooleanrequired
Errors
validation_failed unauthenticated forbidden not_found conflict rate_limited internal
curl https://api.bizisy.com/v1/org/approvals.reject \
-H "Authorization: Bearer $BIZISY_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{"approval_id":"apr1","comment":"Wait for the budget","step":0}'const res = await fetch('https://api.bizisy.com/v1/org/approvals.reject', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.BIZISY_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': crypto.randomUUID(),
},
body: JSON.stringify({
"approval_id": "apr1",
"comment": "Wait for the budget",
"step": 0
}),
});
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
console.log(body.data);import os, uuid
import requests
res = requests.post(
"https://api.bizisy.com/v1/org/approvals.reject",
headers={"Authorization": f"Bearer {os.environ['BIZISY_API_KEY']}", "Idempotency-Key": str(uuid.uuid4())},
json={
"approval_id": "apr1",
"comment": "Wait for the budget",
"step": 0,
},
)
body = res.json()
if not res.ok:
raise RuntimeError(f"{body['error']['code']}: {body['error']['message']}")
print(body["data"]){
"data": {
"id": "apr1",
"kind": "job_change",
"status": "rejected",
"person": {
"id": "p1",
"name": "Ana Ferreira",
"title": "Engineer",
"photo_url": null
},
"effective_date": "2026-11-01",
"expires_on": "2026-12-01",
"change": "change_job",
"job_change": {
"reason": "promotion",
"before": {
"id": "j1",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "hire",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
},
"after": {
"id": "apr1:after",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Senior Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "promotion",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
}
},
"termination": null,
"pay_change": null,
"proposed_by": {
"name": "Hugo Reis",
"person_id": "p4",
"via": "app"
},
"proposed_at": "2026-10-04T10:00:00.000Z",
"steps": [
{
"role": "manager",
"state": "rejected",
"fallback": false,
"team_lead": null,
"team_lead_blocked": null,
"untrusted": null,
"decided_by": {
"name": "Bea Silva",
"person_id": "p2"
},
"decided_at": "2026-10-05T09:00:00.000Z",
"comment": "Wait for the budget",
"auto": null,
"approvers": []
}
],
"closed_at": "2026-10-05T09:00:00.000Z",
"closed_by": {
"name": "Bea Silva",
"person_id": "p2"
},
"can_decide": false,
"can_cancel": false,
"is_proposer": false,
"can_reject": false
}
}Withdraw a change request#
POST/v1/org/approvals.cancelWrite
Withdraws a request that is waiting (or expired): nothing changes on the person. The proposer, or an owner, admin or HR member who can see it. Works over an API key for job and termination requests.
- Who can call it
- Manage key owner admin hr
- MCP tool
org_approvals_cancelon HR Assistant- Preview
?dry_run=trueruns every check and saves nothing- Retries
- An Idempotency-Key prevents a second run, but the result is never stored (it holds a secret or personal data): a retry gets a 409 that points to Activity
Input
approval_idstringrequired
Returns
19 fields
idstringrequiredkind"job_change" | "termination" | "pay_change"requiredstatus"pending" | "approved" | "rejected" | "cancelled" | "outdated" | "expired"requiredpersonobjectrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
effective_datestringrequiredexpires_onstringrequiredchange"change_job" | "terminate" | "pay_add" | "correct_job" | "rehire" | "pay_remove"requiredjob_changeobject | nullrequired3 fields
reason"change" | "promotion" | "transfer" | "correction" | "rehire"requiredbeforeobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
afterobjectrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
terminationobject | nullrequired4 fields
last_daystringrequiredreasonstring | nullrequiredjobobject | nullrequired17 fields
idstringrequiredvalid_fromstringrequiredvalid_tostring | nullrequiredtitlestringrequiredunitobject | nullrequired2 fields
idstringrequirednamestringrequired
managerobject | nullrequired4 fields
idstringrequirednamestringrequiredtitlestring | nullrequiredphoto_urlstring | nullrequired
locationobject | nullrequired2 fields
idstringrequirednamestringrequired
legal_entityobject | nullrequired2 fields
idstringrequirednamestringrequired
employment_type"full_time" | "part_time" | "contractor" | "intern"requiredftenumberrequiredreasonstringrequiredend_reasonstring | nullrequiredcontract_type"permanent" | "fixed_term" | "temporary" | "internship" | "freelance"requiredcontract_end_datestring | nullrequiredprobation_end_datestring | nullrequiredweekly_hoursnumber | nullrequirednotice_period_daysinteger | nullrequired
change"end" | "move" | "cancel"required
pay_changeobject | nullrequired6 fields
amountnumberrequiredcurrencystringrequiredperiod"year" | "month" | "hour"requirednotestring | nullrequiredbeforeobject | nullrequired4 fields
amountnumberrequiredcurrencystringrequiredperiodstringrequiredvalid_fromstringrequired
removesbooleanrequired
proposed_byobjectrequired3 fields
namestringrequiredperson_idstring | nullrequiredvia"app" | "api"required
proposed_atstringrequiredstepsobject[]required11 fields
role"manager" | "hr"requiredstate"waiting" | "pending" | "approved" | "rejected"requiredfallbackbooleanrequiredteam_leadobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredreason"no_manager" | "manager_left"required
team_lead_blockedobject | nullrequired3 fields
unit_idstringrequiredunit_namestringrequiredwhat"lead" | "removed" | "moved" | "archived"required
untrusted"no_login" | "invited_by_proposer"requireddecided_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
decided_atstring | nullrequiredcommentstring | nullrequiredauto"proposed_by_approver" | "no_other_approver"requiredapproversobject[]required3 fields
namestringrequiredperson_idstring | nullrequiredis_viewerbooleanrequired
closed_atstring | nullrequiredclosed_byobject | nullrequired2 fields
namestringrequiredperson_idstring | nullrequired
can_decidebooleanrequiredcan_cancelbooleanrequiredis_proposerbooleanrequiredcan_rejectbooleanrequired
Errors
validation_failed unauthenticated forbidden not_found conflict rate_limited internal
curl https://api.bizisy.com/v1/org/approvals.cancel \
-H "Authorization: Bearer $BIZISY_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: $(uuidgen)" \
-d '{"approval_id":"apr1"}'const res = await fetch('https://api.bizisy.com/v1/org/approvals.cancel', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.BIZISY_API_KEY}`,
'Content-Type': 'application/json',
'Idempotency-Key': crypto.randomUUID(),
},
body: JSON.stringify({
"approval_id": "apr1"
}),
});
const body = await res.json();
if (!res.ok) throw new Error(`${body.error.code}: ${body.error.message}`);
console.log(body.data);import os, uuid
import requests
res = requests.post(
"https://api.bizisy.com/v1/org/approvals.cancel",
headers={"Authorization": f"Bearer {os.environ['BIZISY_API_KEY']}", "Idempotency-Key": str(uuid.uuid4())},
json={
"approval_id": "apr1",
},
)
body = res.json()
if not res.ok:
raise RuntimeError(f"{body['error']['code']}: {body['error']['message']}")
print(body["data"]){
"data": {
"id": "apr1",
"kind": "job_change",
"status": "cancelled",
"person": {
"id": "p1",
"name": "Ana Ferreira",
"title": "Engineer",
"photo_url": null
},
"effective_date": "2026-11-01",
"expires_on": "2026-12-01",
"change": "change_job",
"job_change": {
"reason": "promotion",
"before": {
"id": "j1",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "hire",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
},
"after": {
"id": "apr1:after",
"valid_from": "2024-01-15",
"valid_to": null,
"title": "Senior Engineer",
"unit": {
"id": "u2",
"name": "Engineering"
},
"manager": {
"id": "p2",
"name": "Rui Costa",
"title": "CTO",
"photo_url": "https://acme.bizisy.com/api/photos/people/p2?v=01k0000000000000000000000b"
},
"location": {
"id": "l1",
"name": "Head office"
},
"legal_entity": {
"id": "e1",
"name": "Acme Lda"
},
"employment_type": "full_time",
"fte": 1,
"reason": "promotion",
"end_reason": null,
"contract_type": "fixed_term",
"contract_end_date": "2026-01-14",
"probation_end_date": "2024-07-14",
"weekly_hours": 40,
"notice_period_days": 30
}
},
"termination": null,
"pay_change": null,
"proposed_by": {
"name": "Hugo Reis",
"person_id": "p4",
"via": "app"
},
"proposed_at": "2026-10-04T10:00:00.000Z",
"steps": [
{
"role": "manager",
"state": "pending",
"fallback": false,
"team_lead": null,
"team_lead_blocked": null,
"untrusted": null,
"decided_by": null,
"decided_at": null,
"comment": null,
"auto": null,
"approvers": []
}
],
"closed_at": "2026-10-05T09:00:00.000Z",
"closed_by": {
"name": "Hugo Reis",
"person_id": "p4"
},
"can_decide": false,
"can_cancel": false,
"is_proposer": false,
"can_reject": false
}
}Something missing or wrong on this page? Write to hello@bizisy.com.