Controls API
This content is not available in your language yet.
Manage your organization’s security controls, policies, procedures, and their effectiveness monitoring.
Control Types
Section titled “Control Types”Available control types (kind):
policy- Organizational policy documentprocedure- Standard operating proceduretechnical- Technical security control
Control States
Section titled “Control States”Available control states:
not_implemented- Control has not been implemented yetimplemented- Control has been implementedfailing- Control is not operating effectively
Relationships
Section titled “Relationships”Controls can be related to:
- Assets - Information assets protected by the control
- Risks - Risks that the control helps mitigate
- Requirements - Compliance requirements the control addresses
- Findings - Audit findings or non-conformities related to the control
- Vendors - Third-party vendors involved in the control
- Tasks - Maintenance, review, or audit tasks for the control
Permissions
Section titled “Permissions”The permissions object indicates what actions the current user can perform:
update- Can modify the controldestroy- Can delete the controlconnect- Can link the control to other objectschangelog- Can view the control’s change history
GET /controls/
Section titled “GET /controls/”List all controls with optional filtering.
Query Parameters
| Parameter | Type | Description |
|---|---|---|
kind[] | array | Filter by control type: policy, procedure, technical, physical. |
state[] | array | Filter by state: not_implemented, implemented, failing. |
owner[] | array | Filter by owner user IDs. |
labels[] | array | Filter by label IDs. Use none for controls without labels. |
curl --location GET \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/" \--header "Authorization: Bearer YOUR-TOKEN"Example with filters:
curl --location GET \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/?state[]=failing&kind[]=policy&kind[]=procedure" \--header "Authorization: Bearer YOUR-TOKEN"Example Response
Status: 200
{ "data": [ { "id": "18211d00-904f-4ca9-a212-1e616a687d83", "assets": [], "begins_at": "2025-03-24T00:00:00+00:00", "created_at": "2025-03-24T09:02:24+00:00", "description": "<p><strong>1. Purpose</strong></p><p>The purpose of this Acceptable Use Policy is to establish guidelines for the appropriate use of the Company's information systems...</p>", "findings": [ { "id": "064ad39e-0f7f-479f-a239-5b4e30713a16", "kind": "ncr", "state": "open", "title": "Start monitoring controls effect on risks in Kordon" } ], "kind": "policy", "labels": [], "owner": { "id": "58e7bf6e-618e-4c87-81fb-31b5ecee2d41", "active": true, "color": "#F5222D", "kind": "person", "name": "Rusty Ryan" }, "permissions": { "update": true, "destroy": true, "connect": true, "changelog": true }, "requirements": [ { "id": "9c70579f-fc76-4908-af69-7d9fdb3e8bf2", "is_applicable": true, "regulations": [ { "id": "f1c874ec-4dcf-4603-a339-767094cdc5ce", "is_custom": false, "title": "ISO 27001:2022" } ], "title": "Actions to address risks and opportunities" } ], "risks": [], "state": "not_implemented", "tasks": [], "title": "Acceptable Use Policy", "updated_at": "2025-10-29T15:14:06+00:00", "vendors": [] } ], "meta": { "total_count": 60, "page": 1, "permissions": { "create": true }, "per_page": "10" }}GET /controls/:id
Section titled “GET /controls/:id”Retrieve a specific control by ID.
curl --location GET \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/18211d00-904f-4ca9-a212-1e616a687d83" \--header "Authorization: Bearer YOUR-TOKEN"Example Response
Status: 200
{ "data": { "id": "5e440b94-87c9-4bd9-9b04-65095439760e", "assets": [], "begins_at": "2024-05-16T00:00:00+00:00", "created_at": "2024-05-15T09:15:34+00:00", "description": "<p><strong>1. Purpose</strong></p><p>The purpose of this Code of Conduct is to outline the ethical principles...</p>", "findings": [ { "id": "064ad39e-0f7f-479f-a239-5b4e30713a16", "kind": "ncr", "state": "open", "title": "Start monitoring controls effect on risks in Kordon" } ], "kind": "policy", "labels": [], "owner": { "id": "58e7bf6e-618e-4c87-81fb-31b5ecee2d41", "active": true, "color": "#F5222D", "kind": "person", "name": "Rusty Ryan" }, "permissions": { "update": true, "destroy": true, "connect": true, "changelog": true }, "requirements": [ { "id": "690a7009-38ea-4935-a139-f1b495e46d56", "is_applicable": true, "regulations": [ { "id": "fce9d4d7-ffae-4aa1-84ac-941288d75ba4", "is_custom": false, "title": "SOC 2" } ], "title": "Attract, Develop, Retain Personnel in Line with Security Objectives" } ], "risks": [ { "id": "3efe0045-3562-4aa5-96bd-b17f13c4de79", "state": "acceptable", "title": "DDoS attack" } ], "state": "failing", "tasks": [ { "id": "365077f9-028c-4162-8477-3b85fcfd86ac", "assignee": { "id": "58e7bf6e-618e-4c87-81fb-31b5ecee2d41", "active": true, "color": "#F5222D", "kind": "person", "name": "Rusty Ryan" }, "kind": "review", "state": "new", "title": "Annual review of Code of Conduct" } ], "title": "Code of Conduct", "updated_at": "2025-11-13T12:32:25+00:00", "vendors": [] }}POST /controls/
Section titled “POST /controls/”Create a new control.
Required Parameters:
title- Control titleowner_id- User ID of the control ownerkind- Control type (policy,procedure, ortechnical)begins_at- Date when the control begins (ISO 8601 format)
Optional Parameters:
description- Detailed description of the control (HTML supported)state- Control state (defaults tonot_implemented)
curl --location POST \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/" \--header "Authorization: Bearer YOUR-TOKEN" \--header "Content-Type: application/json" \--data '{ "control": { "title": "Data Encryption Policy", "begins_at": "2025-11-12T00:00:00+00:00", "kind": "policy", "owner_id": "844596ff-8942-4704-b0cd-3e853921d71b" }}'PATCH /controls/:id
Section titled “PATCH /controls/:id”Update an existing control.
curl --location PATCH \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/18211d00-904f-4ca9-a212-1e616a687d83" \--header "Authorization: Bearer YOUR-TOKEN" \--header "Content-Type: application/json" \--data '{ "state": "operating_effectively"}'Example Response
Status: 200
The response will include the full data of the updated control.
Connect a Task to a Control
To connect a task to a control, update the task’s taskable_id to reference the control ID. See the Tasks API for full details.
PATCH /tasks/:task_id
Section titled “PATCH /tasks/:task_id”curl --location PATCH \--url "https://YOUR_KORDON_DOMAIN/api/v1/tasks/task-id-here" \--header "Authorization: Bearer YOUR-TOKEN" \--header "Content-Type: application/json" \--data '{ "task": { "taskable_id": "18211d00-904f-4ca9-a212-1e616a687d83" }}'This will link the task to the control, making it appear in the control’s tasks list.
DELETE /controls/:id
Section titled “DELETE /controls/:id”Remove a control.
curl --location DELETE \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/18211d00-904f-4ca9-a212-1e616a687d83" \--header "Authorization: Bearer YOUR-TOKEN"Example Response
Status: 200
{ "data": { "id": "18211d00-904f-4ca9-a212-1e616a687d83" }}Managing Control Connections
Section titled “Managing Control Connections”Controls can be connected to Requirements, Assets, Vendors, Risks, Business Processes, and Findings.
Viewing Connections
Section titled “Viewing Connections”When retrieving a control via GET /controls/:id, all connections are included in the response:
{ "data": { "id": "ad784c35-c246-4441-b07f-bcf89731db99", "title": "Automated Capacity Adjustment", "assets": [ { "id": "0fb11fe0-85de-423d-ba63-b76598a9c743", "state": "deprecated", "title": "Web app" }, { "id": "16615652-dcea-4250-8068-ab19e0dc046d", "state": "live", "title": "AWS environment" } ], "business_processes": [ { "id": "5a35e67e-f6b7-488d-86a2-6d7943ea6119", "title": "Sales" }, { "id": "3c041e93-a87d-4d4e-a247-c8ad6afbc3e7", "title": "Marketing" } ], "findings": [ { "id": "0177187d-9000-4d2a-bad4-c1506a207086", "kind": "incident", "state": "resolved", "title": "Delayed Security Patch Deployment" } ], "requirements": [ { "id": "64fd3076-c1ff-4b05-9a96-aae96f3443dc", "is_applicable": true, "regulations": [ { "id": "fce9d4d7-ffae-4aa1-84ac-941288d75ba4", "is_custom": false, "title": "SOC 2" } ], "title": "Capacity monitoring" } ], "risks": [ { "id": "3efe0045-3562-4aa5-96bd-b17f13c4de79", "state": "acceptable", "title": "DDoS attack" } ], "vendors": [ { "id": "b00f71e5-9cb4-4995-96e6-0e5710f85e0a", "title": "Pipedrive" } ] }}PATCH /controls/:id/connections
Section titled “PATCH /controls/:id/connections”Update the connections for a control.
Connection Parameters
| Parameter | Type | Description |
|---|---|---|
requirement_ids | array | IDs of requirements to connect |
asset_ids | array | IDs of assets to connect |
vendor_ids | array | IDs of vendors to connect |
risk_ids | array | IDs of risks to connect |
business_process_ids | array | IDs of business processes to connect |
finding_ids | array | IDs of findings to connect |
Example: Add a new risk connection
If a control is currently connected to 2 risks and you want to add a third:
curl --location PATCH \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/ad784c35-c246-4441-b07f-bcf89731db99/connections" \--header "Authorization: Bearer YOUR-TOKEN" \--header "Content-Type: application/json" \--data '{ "connections": { "risk_ids": [ "3efe0045-3562-4aa5-96bd-b17f13c4de79", "6d59f166-a777-40a2-8c1e-bbf79bb0fda4", "8c8d2bd2-2373-401b-9c53-d2200183c136" ] }}'Example: Update multiple connection types at once
curl --location PATCH \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/ad784c35-c246-4441-b07f-bcf89731db99/connections" \--header "Authorization: Bearer YOUR-TOKEN" \--header "Content-Type: application/json" \--data '{ "connections": { "requirement_ids": [ "64fd3076-c1ff-4b05-9a96-aae96f3443dc", "a41a8208-4c0d-4103-9e53-04cb45930c70" ], "asset_ids": [ "0fb11fe0-85de-423d-ba63-b76598a9c743", "16615652-dcea-4250-8068-ab19e0dc046d" ], "vendor_ids": [ "b00f71e5-9cb4-4995-96e6-0e5710f85e0a" ], "risk_ids": [ "3efe0045-3562-4aa5-96bd-b17f13c4de79" ], "business_process_ids": [ "5a35e67e-f6b7-488d-86a2-6d7943ea6119" ], "finding_ids": [ "0177187d-9000-4d2a-bad4-c1506a207086" ] }}'Example: Remove all vendor connections
curl --location PATCH \--url "https://YOUR_KORDON_DOMAIN/api/v1/controls/ad784c35-c246-4441-b07f-bcf89731db99/connections" \--header "Authorization: Bearer YOUR-TOKEN" \--header "Content-Type: application/json" \--data '{ "connections": { "vendor_ids": [] }}'Example Response
Status: 200
The response returns the full control object with all updated connections.