Development Toolkit
Manifest
An add-on manifest is used to describe how your CAKE.com Marketplace add-on integrates with the Clockify app. Your add-on can contain some additional UI elements that will be added by installing that add-on and manifest file can define details regarding those elements.
Manifest is a JSON file that needs to be hosted on a path to an add-on URL app and included in the add-on URL root folder.
When creating an add-on at CAKE.com Marketplace, manifest URL is required. You need to enter it in a form at the first step of creating an add-on.
Top-level properties
Property | Required | Description |
schemaVersion | no | Version of Clockify JSON manifest scheme according to which manifest is validated. Multiple versions are supported, version: “1.0”, “1.0.1”, “1.0.2”, “1.1”, “1.2” and current version: “1.3”. If not defined, last version is used. |
key | yes | Unique key chosen by developer, can’t be changed (2-50 characters) |
name | yes | Same as the one submitted for review (1-50 characters) |
baseUrl | yes | URL of an add-on |
description | no | Brief description of add-on |
iconPath | no | Path to add-on hosted image which will serve as an add-on icon. Path is part of the URL from which the image will be served. Full URL is constructed by concatenating add-on ‘baseUrl’ and path. |
lifecycle | no | List of defined lifecycle hooks defined for a specific add-on. Possible values: INSTALLED, SETTINGS-UPDATED, SETTINGS-CHANGED and DELETED |
webhooks | no | Contain details about events that trigger the webhook requests |
components | no | Specified UI components |
settings | no* | Can be additional settings for UI elements organized by nesting tabs and Group, or URL path Possible values: TXT, NUMBER, DROPDOWN_SINGLE, DROPDOWN_MULTIPLE, CHECKBOX, LINK Possible value for URL path: e.g. settings: “/settings” Note: When updating the value, change ID or type, e.g. URL in the settings can’t be changed with an update unless you change type or ID of the settings. *Required if defined |
minimalSubscriptionPlan | yes | Minimal Clockify’s subscription plan that is required for add-on. This plan is used when checking if user’s current plan is at least equal to the plan required by add-on. Possible values: FREE, BASIC, STANDARD, PRO, ENTERPRISE |
scopes | no | List of Clockify’s API scopes that add-on is using. Scope is specified by Clockify’s endpoint group, and READ/WRITE permission where WRITE consists of PUT/POST/DELETE and CREATE endpoints that belong to a certain scope. WRITE permission doesn’t automatically imply READ permission. Possible values: CLIENT_READ, CLIENT_WRITE, PROJECT_READ, PROJECT_WRITE, TAG_READ, TAG_WRITE, TASK_READ, TASK_WRITE, TIME_ENTRY_READ, TIME_ENTRY_WRITE, EXPENSE_READ, EXPENSE_WRITE, INVOICE_READ, INVOICE_WRITE, USER_READ, USER_WRITE, GROUP_READ, GROUP_WRITE, WORKSPACE_READ, WORKSPACE_WRITE, CUSTOM_FIELDS_READ, CUSTOM_FIELDS_WRITE, APPROVAL_READ, APPROVAL_WRITE, SCHEDULING_READ, SCHEDULING_WRITE, REPORTS_READ, REPORTS_WRITE, TIME_OFF_READ, TIME_OFF_WRITE |
Components
Components contain details about your add-ons UI elements such as their type, e.g. tab, widget, sidebar, or permission access level, e.g. component can be accessed by admin or everyone.
Property | Required | Description |
type | yes | Specifies which kind of component will be rendered. If component is ‘tab’, it also comes with the name of Clockify page where ‘tab’ component will be rendered. Add-on cannot define two components of the same type e.g. no two components of “sidebar” type. Possible values: sidebar, widget, timeoff.tab, schedule.tab, approvals.tab, reports.tab, activity.tab, team.tab, projects.tab |
options | no | Here you can define some component-specific options for a component that holds add-on app. |
label | yes | Custom label for component. For example, if component is ‘tab’, value of ‘label’ property will be displayed in UI. |
path | yes | Defines an add-on server path that will display an iFrame content in a component. Path is part of the URL from which a component content will be served. Full URL is constructed by concatenating add-on ‘baseUrl’ and path. Possible values: /sidebar |
iconPath | no | Path to add-on hosted image which will serve as an icon for a Clockify component. Path is part of the URL from which the image will be served. Full URL is constructed by concatenating add-on ‘baseUrl’ and path. |
accessLevel | yes | Specifies who can access add-on component. You can either choose to give access only to Clockify workspace admins, or everyone. Possible values: ADMINS, EVERYONE |
width | no | Specifies the width of a widget. Possible value: integer |
height | no | Specifies the height of a widget. Possible value: integer |
Example
"components": [
{
"type": "sidebar",
"label": "${sidebarLabel}",
"accessLevel": "ADMINS",
"path": "${sidebarPath}",
"options": {
"option 1": "option 1 value",
"option 2": "option 2 value"
},
"iconPath": "/trt"
]
Lifecycles
Lifecycles contain events add-on receives when installed, deleted, or when its settings are updated.
Property | Required | Description |
path | yes | Path to add-on endpoint designated for receiving lifecycle hooks from the Clockify side. Path is a part of URL to which a lifecycle hook will be sent. A full URL is constructed by concatenating add-on ‘baseUrl’ and path. |
type | yes | Specifies and add-on lifecycle event you want to be notified by Clockify. Possible values: INSTALLED, SETTINGS_UPDATED, STATUS_CHANGED, DELETED |
Example
"lifecycle": [
{
"path": "/postinstall",
"type": "INSTALLED"
},
{
"path": "/uninstalled",
"type": "DELETED"
}
]
Webhooks
Webhooks contain details about events that trigger the webhook requests. There can be various types of webhooks, depending on the events.
Property | Required | Description |
path | yes | Path to add-on endpoint designated for receiving webhooks from the Clockify side. Path is just part of URL to which the webhook will be sent. Full URL is constructed by concatenating add-on ‘baseUrl’ and path. e.g. /clockify/webhooks |
event | yes | Clockify event that triggers webhook is sent to a specified URL. This URL is constructed by concatenating add-on ‘baseUrl’ and ‘webhook.path’. Possible values: NEW_PROJECT, PROJECT_UPDATED, PROJECT_DELETED, NEW_TASK, TASK_UPDATED, TASK_DELETED, NEW_CLIENT, CLIENT_UPDATED, CLIENT_DELETED, NEW_TAG, TAG_UPDATED, TAG_DELETED, NEW_TIMER_STARTED, TIMER_STOPPED, TIME_ENTRY_UPDATED, TIME_ENTRY_DELETED, NEW_TIME_ENTRY, NEW_INVOICE, INVOICE_UPDATED, USER_JOINED_WORKSPACE, USER_DELETED_FROM_WORKSPACE, USER_DEACTIVATED_ON_WORKSPACE, USER_ACTIVATED_ON_WORKSPACE, USER_EMAIL_CHANGED, USER_UPDATED, NEW_APPROVAL_REQUEST, APPROVAL_REQUEST_STATUS_UPDATED, TIME_OFF_REQUESTED, TIME_OFF_REQUEST_APPROVED, TIME_OFF_REQUEST_REJECTED, TIME_OFF_REQUEST_WITHDRAWN, BALANCE_UPDATED, USER_GROUP_CREATED, USER_GROUP_UPDATED, USER_GROUP_DELETED, EXPENSE_CREATED, EXPENSE_UPDATED, EXPENSE_DELETED, ASSIGNMENT_CREATED, ASSIGNMENT_UPDATED, ASSIGNMENT_DELETED, ASSIGNMENT_PUBLISHED |
Example
"webhooks": [
{
"event": "NEW_TIME_ENTRY",
"path": "/clockify/time-entry"
},
{
"event": "NEW_CLIENT",
"path": "clockify/client"
}
],
Settings
Settings contain details about additional settings for UI elements (e.g. dropdown with options 1, 2, 3). Settings are organized by nesting tabs and groups. Each setting must have id, name, type, value and access level. Value and type of setting must be compatible.
If the value of settings is a URL path (e.g. /settings), settings are taken from an add-on and displayed in Clockify app via iFrame. These types of settings are hosted on an add-on.
If empty, there are no settings for that add-on.
Property | Required | Description |
id | yes | Settings unique identifier |
name | yes | Settings name |
value | yes | Specifies settings’ value. Each value is displayed differently in UI and the value must be compatible with a specified type. Possible values: string |
type | yes | Specifies settings’ value type. Possible values: TXT |
accessLevel | yes | Specifies who can access add-on settings. You can either choose to give access only to Clockify workspace admins, or everyone. Possible values: ADMINS, EVERYONE |
Example
"settings": [
{
"id": "sidebarLabel",
"accessLevel": "ADMINS",
"value": "Custom label",
"name": "Custom label for component",
"type": "TXT"
},
{
"id": "sidebarPath",
"accessLevel": "ADMINS",
"value": "/sidebar",
"name": "Custom label for component",
"type": "TXT"
}
]
Tabs
Tabs are at the top level of hierarchy when defining settings.
Tabs cannot be nested in other tabs or groups and they need to have at least one type of settings defined, whether it’s a “settings” or a “groups” property. If “groups” property is the one defined, it needs to have at least one “settings” property defined in it.
For more information on “groups”, check out Groups section.
Property | Required | Description |
id | yes | Tab identifier e.g. tab_one |
name | yes | Tab name displayed in UI e.g. Tab one |
header | no | Banner with info text shown before all settings and groups contained in tab |
settings | no | List of settings contained in tab |
groups | no | Settings grouped by certain criteria |
Example
"settings": {
"tabs": [
{
"id": "Tab id",
"name": "Tab one title",
"header": {
"title": "Title text"
},
"groups": [
{
"id": "Group id",
"title": "Group one title",
"description": "Group description",
"header": {
"title": "Header title"
},
"settings": [
{
"id": "Setting id",
"name": "Default setting",
"description": "Description of default setting",
"placeholder": "Default setting here...",
"type": "TXT",
"value": "Value of default setting",
"required": true,
"copyable": true,
"readOnly": false,
"accessLevel": "ADMINS"
}
]
}
],
"settings": [
{
"id": "Tab setting",
"name": "Tab setting",
"type": "TXT",
"value": "Some value",
"required": true,
"accessLevel": "EVERYONE"
}
]
}
]}
]
Groups
Serves as another level of hierarchy when defining settings. Group can be part of tabs, and one tab can contain multiple groups. Each group needs to have its “id” and can have “title”, “description”, “header” and “settings”.
Property | Required | Description |
id | yes | Group identifier e.g. “group_one” |
title | yes | Group title. Displayed in UI. e.g. “Group one title” |
description | no | Brief description of the settings that a given group contains. e.g. “Group description” |
header | no | Banner with an info text displayed above all the settings that a given group contains. e.g. Group info text |
settings | yes | List of settings the group contains |
Example
"groups": [
{
"id": "Group id",
"title": "Group one title",
"description": "Group description",
"header": {
"title": "Header title"
},
"settings": [
{
"id": "Setting id",
"name": "Default setting",
"description": "Description of default setting",
"placeholder": "Default setting here...",
"type": "TXT",
"value": "Value of default setting",
"required": true,
"copyable": true,
"readOnly": false,
"accessLevel": "ADMINS"
}
]
}
]
Settings
These settings are defined in “settings” or “groups” properties.
Property | Required | Description |
id | yes | Settings unique identifier |
name | yes | Settings name |
description | no | Brief description of settings. It states settings’ purpose, affect, etc. |
palceholder | no | Text displayed in UI form field if settings have no value. |
type | yes | Specifies settings’ value type. Each type is displayed differently in UI and the value must be compatible with a specified type e.g. if ‘type’ is TXT, ‘value’ must be ‘string’, if ‘type’ is DROPDOWN, ‘value’ must be ‘array’. Possible value for Group type: TXT / NUMBER / DROPDOWN_SINGLE / DROPDOWN_MULTIPLE / CHECKBOX / LINK Note: Checkbox is switch. In case settings type is changed in an add-on update, the user selected value will be removed and the default value will be set. |
key | no | Serves as a key for settings that represent a key-value pair e.g. if you have documentation add-on which shows document corresponding to the Clockify page i.e. you need to match the Clockify page to the URL of the document describing how to use that page. In that case, key would be ‘Clockify page’, and ‘value’ would be ‘URL of the document’. |
value | yes | Settings’ value. It must correspond to the type of settings which is defined in the “type” property |
allowedValues | no* | Specifies which options will be displayed in dropdown. * Required if type of settings defined in the “type” property is DROPDOWN_SINGLE or DROPDOWN_MULTIPLE. |
required | no | Defines if setting is required for add-on to work Possible values: true/false |
copyable | no | Defines if setting value will be displayed with ‘Copy’ button for easier copying. |
readOnly | no | Defines if setting value is read-only i.e. setting value cannot be updated. |
accessLevel | yes | Defines if settings can be viewed by regular users, or admins only. Possible values: ADMINS or EVERYONE |
Example
"settings": [
{
"id": "Setting id",
"name": "Default setting",
"description": "Description of default setting",
"placeholder": "Default setting here...",
"type": "TXT",
"value": "Value of default setting",
"required": true,
"copyable": true,
"readOnly": false,
"accessLevel": "ADMINS"
}
]