Introduction
The Fibery API provides a way to integrate Fibery with your external systems and automate routine tasks. While the public API is not yet complete, it’s already capable of performing most of the tasks at hand:
- Customize apps by creating, renaming and deleting Types and Fields.
- Read, create, update and delete Entities.
- Work with rich text Documents.
- Upload, attach and download Files.
- Update other tools when something changes in Fibery using webhooks.
- Automate routine actions with programmable action buttons and rules.
- Integrate your custom data into Fibery database using custom apps.
If something is missing, please describe your use case in Fibery dev community — we’ll try our best to help.
Getting started
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d '[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "fibery/user",
"q/select": ["fibery/id","user/name"],
"q/limit": 1
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const users = await fibery.entity.query({
"q/from": "fibery/user",
"q/select": ["fibery/id","user/name"],
"q/limit": 1
});
Here’s the result:
[
{
"success": true,
"result": [
{
"fibery/id": "7dcf4730-82d2-11e9-8a28-82a9c787ee9d",
"user/name": "Arthur Dent"
}
]
}
]
[
{
"fibery/id": "7dcf4730-82d2-11e9-8a28-82a9c787ee9d",
"user/name": "Arthur Dent"
}
]
Fibery API is JSON-RPC-like and is based on commands.
Both reading and editing data means sending a POST request to https://YOUR_ACCOUNT.fibery.io/api/commands
endpoint.
The endpoint works with batches of commands. The request should contain an array of commands with their names and arguments. You'll get an array back too. Take a look at the example on the right in which we retrieve the basic info about a user.
While there are no official clients for any platform, there is an unofficial API client for Node.js. It mostly follows the API functionality, but makes it easier to create a domain Type, a relation or a single-select Field.
Authentication
Fibery API uses token-based authentication. That means you need to pass your API token with every request. This token should be the same for all requests, there is no need to generate a new one each time. Your API token carries the same privileges as your user, so be sure to keep it secret.
# To authenticate set the Authorization header in this way:
curl -X POST "https://YOUR_ACCOUNT.fibery.io/api/commands" \
-H "Authorization: Token YOUR_TOKEN" \
-H "Content-Type: application/json" \
...
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
Make sure to replace your account name and token with the actual values
Managing tokens
The number of tokens is limited to 2 per user.
You can generate, list and delete tokens on the "API Tokens" page available from the workspace menu.
You can also manage the tokens directly using the API. The following endpoints are available to manage access tokens:
GET /api/tokens — lists all access tokens that were given to current user POST /api/tokens — creates new token for current user DELETE /api/tokens/:token_id — deletes token by id
You need to be authenticated with a browser cookie or with an already existing token when accessing these endpoints 🤷.
Schema
Fibery Schema is the metadata describing Types and their Fields.
Basically, it's everything you see on the Customize Apps
screen and a few auxiliary Types:
Get Schema
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d '[{ "command": "fibery.schema/query" }]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const schema = await fibery.getSchema();
Result:
[
{
"success": true,
"result": {
"fibery/id": "fd5d9550-3779-11e9-9162-04d77e8d50cb",
"fibery/types": [
{
"fibery/name": "software-development/user-story",
"fibery/fields": [
{
"fibery/name": "fibery/modification-date",
"fibery/type": "fibery/date-time",
"fibery/meta": {
"fibery/modification-date?": true,
"fibery/readonly?": true,
"fibery/default-value": "$now",
"fibery/secured?": false,
"fibery/required?": true,
"ui/object-editor-order": 8
},
"fibery/id": "e36a91b1-3f4b-11e9-8051-8fb5f642f8a5"
},
{
"fibery/name": "assignments/assignees",
"fibery/type": "fibery/user",
"fibery/meta": {
"fibery/collection?": true,
"ui/object-editor-order": 4,
"fibery/relation": "c3e75ca4-8d15-11e9-b98a-9abbdf4720ab"
},
"fibery/id": "2cd92374-3839-11e9-9162-04d77e8d50cb"
}
#...other Fields
],
"fibery/meta": {
"fibery/primitive?": false,
"fibery/domain?": true,
"ui/color": "#068cba",
"app/mixins": {
"fibery/rank-mixin": true,
"assignments/assignments-mixin": true,
"Files/Files-mixin": true,
"workflow/workflow": true,
"comments/comments-mixin": true
},
"fibery/secured?": true
},
"fibery/id": "2c4213ae-3839-11e9-9162-04d77e8d50cb"
}
#...other Types
],
"fibery/meta": {
"fibery/version": "1.0.62",
"fibery/rel-version": "1.0.6",
"fibery/maintenance?": false,
"maintenance?": false
}
}
}
]
[
{
"fibery/name": "software-development/user-story",
"fibery/fields": [
{
"fibery/name": "fibery/modification-date",
"fibery/type": "fibery/date-time",
"fibery/meta": {
"fibery/modification-date?": true,
"fibery/readonly?": true,
"fibery/default-value": "$now",
"fibery/secured?": false,
"fibery/required?": true,
"ui/object-editor-order": 8
},
"fibery/id": "e36a91b1-3f4b-11e9-8051-8fb5f642f8a5"
},
{
"fibery/name": "assignments/assignees",
"fibery/type": "fibery/user",
"fibery/meta": {
"fibery/collection?": true,
"ui/object-editor-order": 4,
"fibery/relation": "c3e75ca4-8d15-11e9-b98a-9abbdf4720ab"
},
"fibery/id": "2cd92374-3839-11e9-9162-04d77e8d50cb"
}
//...other Fields
],
"fibery/meta": {
"fibery/primitive?": false,
"fibery/domain?": true,
"ui/color": "#068cba",
"app/mixins": {
"fibery/rank-mixin": true,
"assignments/assignments-mixin": true,
"Files/Files-mixin": true,
"workflow/workflow": true,
"comments/comments-mixin": true
},
"fibery/secured?": true
},
"fibery/id": "2c4213ae-3839-11e9-9162-04d77e8d50cb"
}
//...other Types
]
Get all Types, Fields and their metadata.
Take a look at the Type and Field sections for the metadata description.
Command parameters
Parameter (required in bold) |
Default | Description | Example |
---|---|---|---|
with-description? |
false | Whether to include type descriptions in response | true |
Type
Type is a template for Entities of some kind: Bugs, Teams, Objectives, etc. It consists of metadata and Fields.
Create Type
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.type/create",
"args": {
"fibery/name": "Cricket/Player",
"fibery/meta": {
"fibery/domain?": true,
"fibery/secured?": true,
"ui/color": "#F7D130"
},
"fibery/fields": [
{
"fibery/name": "Cricket/name",
"fibery/type": "fibery/text",
"fibery/meta": {
"fibery/secured?": false,
"ui/title?": true
}
},
{
"fibery/name": "fibery/id",
"fibery/type": "fibery/uuid",
"fibery/meta": {
"fibery/secured?": false,
"fibery/id?": true,
"fibery/readonly?": true
}
},
{
"fibery/name": "fibery/public-id",
"fibery/type": "fibery/text",
"fibery/meta": {
"fibery/secured?": false,
"fibery/public-id?": true,
"fibery/readonly?": true
}
},
{
"fibery/name": "fibery/creation-date",
"fibery/type": "fibery/date-time",
"fibery/meta": {
"fibery/secured?": false,
"fibery/creation-date?": true,
"fibery/readonly?": true,
"fibery/default-value": "$now"
}
},
{
"fibery/name": "fibery/modification-date",
"fibery/type": "fibery/date-time",
"fibery/meta": {
"fibery/modification-date?": true,
"fibery/required?": true,
"fibery/readonly?": true,
"fibery/default-value": "$now",
"fibery/secured?": false
}
},
{
"fibery/name": "user/salary",
"fibery/type": "fibery/int",
"fibery/meta": {
"fibery/secured?": true
}
}
]
}
},
{
"command": "fibery.app/install-mixins",
"args": {
"types": {
"Cricket/Player": [
"fibery/rank-mixin"
]
}
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
// 5 primitive fields are created and rank Mixin is installed automatically for domain Types
await fibery.type.createBatch([
{
'fibery/name': 'Cricket/Player',
'fibery/meta': {
'fibery/domain?': true,
'fibery/secured?': true,
'ui/color': '#F7D130'
},
'fibery/fields': [
{
"fibery/name": 'user/salary',
"fibery/type": 'fibery/int',
"fibery/meta": {
"fibery/secured?": true
}
}
]
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
To create a fully functional Type, we'll execute two commands:
schema.type/create
to create a Type with at least five mandatory primitive Fields:fibery/id
fibery/public-id
fibery/creation-date
fibery/modification-date
${app}/name
fibery.app/install-mixins
to be able to prioritize Type's Entities.
Command parameters
Parameter (required in bold) |
Default | Description | Example |
---|---|---|---|
fibery/name |
Type name in ${app}/${name} format |
CRM/Lead |
|
fibery/id |
Auto-generated | UUID | fd5d9550-3779... |
meta.fibery/domain? |
false | Domain Types appear in Customize Apps screen and are available as cards on Views |
true |
meta.fibery/secured? |
Permissions apply to secured Types only | true | |
meta.ui/color? |
#000000 | HEX color to use in Entity badges | #F7D130 |
meta.fibery/fields |
Array of Fields including 5 primitive ones above |
Rename Type
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.type/rename",
"args": {
"from-name": "Cricket/Referee",
"to-name": "Cricket/Umpire"
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.type.renameBatch([
{
'from-name': 'Cricket/Referee',
'to-name': 'Cricket/Umpire'
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
Command parameters
Parameter (required in bold) |
Description | Example |
---|---|---|
from-name |
Current Type name in ${app}/${name} format |
Cricket/Referee |
to-name |
New Type name in ${app}/${name} format |
Cricket/Umpire |
Delete Type
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.type/delete",
"args": {
"name": "Cricket/Umpire",
"delete-entities?": true,
"delete-related-fields?": true
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.type.deleteBatch([
{
'name': 'Cricket/Umpire',
'delete-entities?': true,
'delete-related-fields?': true
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
Command parameters
Parameter (required in bold) |
Default | Description | Example |
---|---|---|---|
name |
Type name in ${app}/${name} format |
Cricket/Umpire |
|
delete-entities? |
false | Delete all Entities of this Type? See the behavior in the table below. | true |
delete-related-fields? |
false | Delete all related Fields like Criket/Favourite Umpire in Cricket/Player ? See the behavior in the table below. |
true |
delete?
parameter behavior
delete? parameter |
|||
false | true | ||
Entities (or related Fields) | don't exist | Type is deleted | Type is deleted |
exist | Error is thrown | Type and Entities (or related Fields) are deleted |
Field
Create
- primitive Field
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.field/create",
"args": {
"fibery/holder-type": "Cricket/Player",
"fibery/name": "Cricket/Salary",
"fibery/type": "fibery/int",
"fibery/meta": {
"fibery/readonly?": false,
"fibery/default-value": 1000,
"ui/number-unit": "USD"
}
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.field.createBatch([
{
'fibery/holder-type': 'Cricket/Player',
'fibery/name': 'Cricket/Salary',
'fibery/type': 'fibery/int',
'fibery/meta': {
'fibery/readonly?': false,
'fibery/default-value': 1000,
'ui/number-unit': 'USD'
}
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
Primitive Field types
Field type | Example |
---|---|
fibery/int |
42 |
fibery/decimal |
0.33 |
fibery/bool |
true |
fibery/text |
Don't panic |
fibery/email |
contact@megadodo.com |
fibery/emoji |
🏏 |
fibery/date |
1979-10-12 |
fibery/date-time |
2019-06-24T12:25:20.812Z |
fibery/date-range |
{ "start": "2019-06-27", "end": "2019-06-30" } |
fibery/date-time-range |
{ "start": "2019-06-18T02:40:00.000Z", "end": "2019-07-25T11:40:00.000Z" } |
fibery/uuid |
acb5ef80-9679-11e9-bc42-526af7764f64 |
fibery/rank |
1000 |
fibery/json-value |
{ "paranoid?": true } |
Command parameters
Parameter (required in bold) |
Description | Example |
---|---|---|
fibery/holder-type |
Holder Type name in ${app}/${name} format |
Cricket/Player |
fibery/name |
Field name in ${app}/${name} format. |
Cricket/Salary |
fibery/type |
One of the primitive Field types above or a Type for a one-way relation. | fibery/int |
meta.fibery/readonly? |
If users are able to change value from UI | true |
meta.fibery/default-value |
The value automatically set when a new entity is created | "(empty)" |
- relation (entity [collection] Field)
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.field/create",
"args": {
"fibery/holder-type": "Cricket/Player",
"fibery/name": "Cricket/Current Team",
"fibery/type": "Cricket/Team",
"fibery/meta": {
"fibery/relation": "d9e9ec34-9685-11e9-8550-526af7764f64"
}
}
},
{
"command": "schema.field/create",
"args": {
"fibery/holder-type": "Cricket/Team",
"fibery/name": "Cricket/Current Roster",
"fibery/type": "Cricket/Player",
"fibery/meta": {
"fibery/collection?": true,
"fibery/relation": "d9e9ec34-9685-11e9-8550-526af7764f64"
}
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
// The unofficial client is closer to UI than to API here.
// Note the missing 'fibery/' namespace in Field type name and meta parameter —
// these things are unique to the client.
await fibery.field.createBatch([
{
'fibery/holder-type': 'Cricket/Player',
'fibery/name': 'Cricket/Current Team',
'fibery/type': 'relation',
meta: {
to: 'Cricket/Team',
toName: 'Cricket/Current Roster',
isFromMany: true,
isToMany: false
}
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
To create a relation between two Types we create a pair of entity [collection] Fields and connect them with a unique identifier.
The relation is to-one by default.
Set entity Field's meta.fibery/collection?
to true
for to-many relation.
Command parameters
Parameter (required in bold) |
Description | Example |
---|---|---|
fibery/holder-type |
Holder Type name in ${app}/${name} format |
Cricket/Player |
fibery/name |
Field name in ${app}/${name} format. |
Cricket/Current Team |
fibery/type |
Related Type name in ${app}/${name} format |
Cricket/Team |
meta.fibery/relation |
UUID shared between the pair of Fields. | d9e9ec34-96... |
meta.fibery/collection? |
true for to-many relation (entity collection Field) |
true |
meta.fibery/readonly? |
If users are able to change value from UI | true |
- single-select Field
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.command/batch",
"args": {
"commands": [
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.enum/create",
"args": {
"fibery/name": "Cricket/Batting Hand_Cricket/Player"
}
},
{
"command": "schema.field/create",
"args": {
"fibery/holder-type": "Cricket/Player",
"fibery/name": "Cricket/Batting Hand",
"fibery/type": "Cricket/Batting Hand_Cricket/Player"
}
}
]
}
},
{
"command": "fibery.entity/create",
"args": {
"type": "Cricket/Batting Hand_Cricket/Player",
"entity": {
"enum/name": "Right",
"fibery/id": "4a3ffb10-9747-11e9-9def-016e5ea5e162",
"fibery/rank": 0
}
}
},
{
"command": "fibery.entity/create",
"args": {
"type": "Cricket/Batting Hand_Cricket/Player",
"entity": {
"enum/name": "Left",
"fibery/id": "4a402220-9747-11e9-9def-016e5ea5e162",
"fibery/rank": 1000000
}
}
},
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.field/set-meta",
"args": {
"name": "Cricket/Batting Hand",
"holder-type": "Cricket/Player",
"key": "fibery/default-value",
"value": {
"fibery/id": "4a3ffb10-9747-11e9-9def-016e5ea5e162"
}
}
},
{
"command": "schema.field/set-meta",
"args": {
"name": "Cricket/Batting Hand",
"holder-type": "Cricket/Player",
"key": "fibery/required?",
"value": true
}
}
]
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
// The unofficial client is closer to UI than to API here.
// Note the missing 'fibery/' namespace in Field type name and meta parameter —
// these things are unique to the client.
await fibery.field.createBatch([
{
'fibery/holder-type': 'Cricket/Player',
'fibery/name': 'Cricket/Batting Hand',
'fibery/type': 'single-select',
meta: {
options: [
{ name: 'Right' },
{ name: 'Left' }
]
}
}
]);
Result:
[
{
"success": true,
"result": [
{
"success": true,
"result": "ok"
},
{
"success": true,
"result": {
"fibery/id": "4a3ffb10-9747-11e9-9def-016e5ea5e162",
"fibery/public-id": "1",
"enum/name": "Right",
"fibery/rank": 0
}
},
{
"success": true,
"result": {
"fibery/id": "4a402220-9747-11e9-9def-016e5ea5e162",
"fibery/public-id": "2",
"enum/name": "Left",
"fibery/rank": 1000000
}
},
{
"success": true,
"result": "ok"
}
]
}
]
[ { success: true, result: 'ok' },
{ success: true,
result:
{ 'fibery/id': '2d4aedf0-9e48-11e9-84ac-fd78950b4910',
'fibery/public-id': '1',
'enum/name': 'Right',
'fibery/rank': 0 } },
{ success: true,
result:
{ 'fibery/id': '2d4b1500-9e48-11e9-84ac-fd78950b4910',
'fibery/public-id': '2',
'enum/name': 'Left',
'fibery/rank': 1000000 } },
{ success: true, result: 'ok' } ]
A single-select Field is not what it seems to be. Actually, every single-select option is an Entity of a newly created special Type.
This way unlocks 'name on UI + value in Formula' scenario (think Self conviction
→ 0.01
in GIST) and enables an easy transition to a fully functional Type.
To create a single-select Field we should:
- Create a new
enum
Type - Create a Field of the newly created
enum
Type - Create an Entity for each single-select option
- Make the selection required and set the default value
The new enum
Type name is built using this format: ${app}/${field}_${app}/${holder-type}
.
- rich text Field
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.field/create",
"args": {
"fibery/holder-type": "Cricket/Player",
"fibery/name": "Cricket/Bio",
"fibery/type": "Collaboration~Documents/Document",
"fibery/meta": {
"fibery/entity-component?": true,
},
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
// The unofficial client is closer to UI than to API here.
// Note the missing 'fibery/' namespace in Field type name and meta parameter —
// these things are unique to the client.
await fibery.field.createBatch([
{
'fibery/holder-type': 'Cricket/Player',
'fibery/name': 'Cricket/Bio',
'fibery/type': 'Collaboration~Documents/Document',
'fibery/meta': {
'fibery/entity-component?': true,
}
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
In Fibery every rich text Field instance is, in fact, a collaborative document.
It means that for each Entity with N rich text Fields Fibery automatically creates N documents.
Each of these documents is stored in Document Storage
and is connected to its Entity through an auxiliary Collaboration~Documents/Document
Entity:
Entity --- (magic) ---> Collab Doc/Document
--- (fibery/secret
) ---> Document in Storage
So to create a rich text Field we just connect our Type with Collaboration~Documents/Document
Type.
Type Collaboration~Documents/Document
has a special property, namely, the entities of this Type inherit access from their Parent Entity.
To indicate that Parent-Child relationship we pass fibery/entity-component?
meta flag, but only for ordinary Fields (e.g. not Lookup and not Formula)
Selecting and updating a rich text Field is a two-step process:
- Get
fibery/secret
of the related Document. - Work with this Document via
api/documents
Storage endpoint.
Rename Field
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.field/rename",
"args": {
"holder-type": "Cricket/Player",
"from-name": "Cricket/Position",
"to-name": "Cricket/Role"
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.field.renameBatch([
{
'holder-type': 'Cricket/Player',
'from-name': 'Cricket/Position',
'to-name': 'Cricket/Role'
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
Command parameters
Parameter (required in bold) |
Description | Example |
---|---|---|
holder-type |
Holder Type name in ${app}/${name} format |
Cricket/Player |
from-name |
Current Field name in ${app}/${name} format |
Cricket/Position |
to-name |
New Field name in ${app}/${name} format |
Cricket/Role |
Delete Field
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.schema/batch",
"args": {
"commands": [
{
"command": "schema.field/delete",
"args": {
"holder-type": "Cricket/Player",
"name": "Cricket/Role",
"delete-values?": true
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.field.deleteBatch([
{
'holder-type': 'Cricket/Player',
'name': 'Cricket/Role',
'delete-values?': true
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
'ok'
Command parameters
Parameter (required in bold) |
Default | Description | Example |
---|---|---|---|
holder-type |
Holder Type name in ${app}/${name} format |
Cricket/Player |
|
name |
Field name in ${app}/${name} format |
Cricket/Role |
|
delete-values? |
false | See the behavior in the table below | true |
delete-values?
parameter behavior
delete-values? |
|||
false | true | ||
Field type | Empty primitive Field | Field is deleted | Field is deleted |
Non-empty primitive Field | Error is thrown | Field and values are deleted | |
Empty entity [collection] Field | Field is deleted | Field is deleted | |
Non-empty entity [collection] Field | Error is thrown | Field and links (but not related Entities) are deleted |
Entity
Get Entities
Get info about cricket players born since 1986 ordered by height and age:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": [
"fibery/id",
"fibery/public-id",
"Cricket/name",
"Cricket/Full Name",
"Cricket/Born",
"Cricket/Shirt Number",
"Cricket/Height",
"Cricket/Retired?",
{ "Cricket/Batting Hand": ["enum/name"] },
{ "Cricket/Current Team": ["Cricket/name"] },
{ "user/Former Teams": { "q/select": ["Cricket/name"], "q/limit": "q/no-limit" } },
{ "# of former teams": [ "q/count", ["user/Former Teams", "fibery/id"] ] }
],
"q/where": [">=", ["Cricket/Born"], "$birthday" ],
"q/order-by": [
[["Cricket/Height"], "q/desc"],
[["Cricket/Born"], "q/asc"]
],
"q/limit": 3
},
"params": {
"$birthday": "1986-01-01"
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': [
'fibery/id',
'fibery/public-id',
'Cricket/name',
'Cricket/Full Name',
'Cricket/Born',
'Cricket/Shirt Number',
'Cricket/Height',
'Cricket/Retired?',
{ 'Cricket/Batting Hand': ['enum/name'] },
{ 'Cricket/Current Team': ['Cricket/name'] },
{ 'user/Former Teams': { 'q/select': ['Cricket/name'], 'q/limit': 'q/no-limit' } },
{ '# of former teams': [ 'q/count', ['user/Former Teams', 'fibery/id'] ] }
],
'q/where': ['>=', ['Cricket/Born'], '$birthday' ],
'q/order-by': [
[['Cricket/Height'], 'q/desc'],
[['Cricket/Born'], 'q/asc']
],
'q/limit': 3
}, { '$birthday': '1986-01-01' });
Result:
[
{
"success": true,
"result": [
{
"# of former teams": 6,
"Cricket/Height": "1.79",
"user/Former Teams": [
{ "Cricket/name": "Royal Challengers Bangalore" },
{ "Cricket/name": "Yorkshire" },
{ "Cricket/name": "Kolkata Knight Riders" },
{ "Cricket/name": "Kings XI Punjab" },
{ "Cricket/name": "Derbyshire" },
{ "Cricket/name": "Nottinghamshire" }
],
"Cricket/Born": "1988-01-25",
"fibery/id": "21e578b0-9752-11e9-81b9-4363f716f666",
"Cricket/Shirt Number": 15,
"Cricket/Full Name": "Cheteshwar Arvind Pujara",
"fibery/public-id": "3",
"Cricket/Retired?": false,
"Cricket/Current Team": {
"Cricket/name": "Saurashtra"
},
"Cricket/Batting Hand": {
"enum/name": "Right"
},
"Cricket/name": "Cheteshwar Pujara"
},
{
"# of former teams": 1,
"Cricket/Height": "1.75",
"user/Former Teams": [
{ "Cricket/name": "Delhi" }
],
"Cricket/Born": "1988-11-05",
"fibery/id": "20f9b920-9752-11e9-81b9-4363f716f666",
"Cricket/Shirt Number": 18,
"Cricket/Full Name": "Virat 'Chikoo' Kohli",
"fibery/public-id": "1",
"Cricket/Retired?": false,
"Cricket/Current Team": {
"Cricket/name": "Delhi"
},
"Cricket/Batting Hand": {
"enum/name": "Right"
},
"Cricket/name": "Virat Kohli"
},
{
"# of former teams": 4,
"Cricket/Height": "1.75",
"user/Former Teams": [
{ "Cricket/name": "Northern Districts" },
{ "Cricket/name": "Gloucestershire" },
{ "Cricket/name": "Yorkshire" },
{ "Cricket/name": "Barbados Tridents" }
],
"Cricket/Born": "1990-08-08",
"fibery/id": "216c2a00-9752-11e9-81b9-4363f716f666",
"Cricket/Shirt Number": 22,
"Cricket/Full Name": "Kane Stuart Williamson",
"fibery/public-id": "2",
"Cricket/Retired?": false,
"Cricket/Current Team": {
"Cricket/name": "Sunrisers Hyderabad"
},
"Cricket/Batting Hand": {
"enum/name": "Right"
},
"Cricket/name": "Kane Williamson"
}
]
}
]
[ { '# of former teams': 6,
'Cricket/Height': '1.79',
'user/Former Teams':
[ [Object], [Object], [Object], [Object], [Object], [Object] ],
'Cricket/Born': '1988-01-25',
'fibery/id': '21e578b0-9752-11e9-81b9-4363f716f666',
'Cricket/Shirt Number': 15,
'Cricket/Full Name': 'Cheteshwar Arvind Pujara',
'fibery/public-id': '3',
'Cricket/Retired?': false,
'Cricket/Current Team': { 'Cricket/name': 'Saurashtra' },
'Cricket/Batting Hand': { 'enum/name': 'Right' },
'Cricket/name': 'Cheteshwar Pujara' },
{ '# of former teams': 1,
'Cricket/Height': '1.75',
'user/Former Teams': [ [Object] ],
'Cricket/Born': '1988-11-05',
'fibery/id': '20f9b920-9752-11e9-81b9-4363f716f666',
'Cricket/Shirt Number': 18,
'Cricket/Full Name': 'Virat \'Chikoo\' Kohli',
'fibery/public-id': '1',
'Cricket/Retired?': false,
'Cricket/Current Team': { 'Cricket/name': 'Delhi' },
'Cricket/Batting Hand': { 'enum/name': 'Right' },
'Cricket/name': 'Virat Kohli' },
{ '# of former teams': 4,
'Cricket/Height': '1.75',
'user/Former Teams': [ [Object], [Object], [Object], [Object] ],
'Cricket/Born': '1990-08-08',
'fibery/id': '216c2a00-9752-11e9-81b9-4363f716f666',
'Cricket/Shirt Number': 22,
'Cricket/Full Name': 'Kane Stuart Williamson',
'fibery/public-id': '2',
'Cricket/Retired?': false,
'Cricket/Current Team': { 'Cricket/name': 'Sunrisers Hyderabad' },
'Cricket/Batting Hand': { 'enum/name': 'Right' },
'Cricket/name': 'Kane Williamson' } ]
This section describes a comprehensive example. See the sections below for a more detailed explanation:
Command parameters
Parameter (required in bold) |
Description |
---|---|
query.q/from |
Type name in ${app}/${name} format. |
query.q/select |
Array of primitive Fields, entity Field objects, objects with entity collection Fields subqueries and entity collection Field aggregates. |
query.q/where |
Filter expression represented as an array. |
query.q/order-by |
Array of sorting expressions — sorting by multiple Fields is supported. |
query.q/limit |
How many Entities to get. Pass q/no-limit to get all entities. In entity collection Fields subqueries only q/no-limit is supported . |
query.q/offset |
How many Entities to skip — useful for pagination. |
params |
Object of parameters for filter expressions in { "$param": value } format. |
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
fibery/id |
fibery/uuid |
fibery/public-id |
fibery/text |
Cricket/name |
fibery/text |
Cricket/Full Name |
fibery/text |
Cricket/Born |
fibery/date |
Cricket/Shirt Number |
fibery/int |
Cricket/Height |
fibery/decimal |
Cricket/Retired? |
fibery/bool |
Cricket/Batting Hand |
single-select |
Cricket/Current Team |
entity Field |
user/Former Teams |
entity collection Field |
- Select Fields
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": [
"Cricket/Full Name",
{ "Cricket/Batting Hand": [
"fibery/id",
"enum/name"
] },
{ "Cricket/Current Team": [
"fibery/id",
"Cricket/name"
] },
{ "user/Former Teams": {
"q/select": [
"Cricket/name",
"Cricket/Year Founded"
],
"q/limit": "q/no-limit" }
},
{ "oldest former team founded": [ "q/min", ["user/Former Teams", "Cricket/Year Founded"] ] }
],
"q/limit": 2
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': [
'Cricket/Full Name',
{ 'Cricket/Batting Hand': [
'fibery/id',
'enum/name'
] },
{ 'Cricket/Current Team': [
'fibery/id',
'Cricket/name'
] },
{ 'user/Former Teams': {
'q/select': [
'Cricket/name',
'Cricket/Year Founded'
],
'q/limit': 'q/no-limit'
} },
{ 'oldest former team founded': [ 'q/min', ['user/Former Teams', 'Cricket/Year Founded'] ] }
],
'q/limit': 2
});
Result:
[
{
"success": true,
"result": [
{
"Cricket/Current Team": {
"Cricket/name": "Delhi",
"fibery/id": "d328b7b0-97fa-11e9-81b9-4363f716f666"
},
"Cricket/Batting Hand": {
"enum/name": "Right",
"fibery/id": "b0ed1370-9747-11e9-9f03-fd937c4ecf3b"
},
"Cricket/Full Name": "Virat 'Chikoo' Kohli",
"user/Former Teams": [
{
"Cricket/name": "Delhi",
"Cricket/Year Founded": 1934
}
],
"oldest former team founded": 1934
},
{
"Cricket/Current Team": {
"Cricket/name": "Sunrisers Hyderabad",
"fibery/id": "2456d780-97fa-11e9-81b9-4363f716f666"
},
"Cricket/Batting Hand": {
"enum/name": "Right",
"fibery/id": "b0ed1370-9747-11e9-9f03-fd937c4ecf3b"
},
"Cricket/Full Name": "Kane Stuart Williamson",
"user/Former Teams": [
{
"Cricket/name": "Northern Districts",
"Cricket/Year Founded": 1955
},
{
"Cricket/name": "Gloucestershire",
"Cricket/Year Founded": 1870
},
{
"Cricket/name": "Yorkshire",
"Cricket/Year Founded": 1863
},
{
"Cricket/name": "Barbados Tridents",
"Cricket/Year Founded": 2013
}
],
"oldest former team founded": 1863
}
]
}
]
[ { 'Cricket/Current Team':
{ 'Cricket/name': 'Delhi',
'fibery/id': 'd328b7b0-97fa-11e9-81b9-4363f716f666' },
'Cricket/Batting Hand':
{ 'enum/name': 'Right',
'fibery/id': 'b0ed1370-9747-11e9-9f03-fd937c4ecf3b' },
'Cricket/Full Name': 'Virat \'Chikoo\' Kohli',
'user/Former Teams': [ [Object] ],
'oldest former team founded': 1934 },
{ 'Cricket/Current Team':
{ 'Cricket/name': 'Sunrisers Hyderabad',
'fibery/id': '2456d780-97fa-11e9-81b9-4363f716f666' },
'Cricket/Batting Hand':
{ 'enum/name': 'Right',
'fibery/id': 'b0ed1370-9747-11e9-9f03-fd937c4ecf3b' },
'Cricket/Full Name': 'Kane Stuart Williamson',
'user/Former Teams': [ [Object], [Object], [Object], [Object] ],
'oldest former team founded': 1863 } ]
In this example we select:
- a primitive Field (full name)
- a single-select (batting hand)
- an entity Field (current Team)
- an entity collection Field (former Teams)
- an aggregate (the oldest former team year of foundation)
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
Cricket/Full Name |
fibery/text |
Cricket/Batting Hand |
single-select |
Cricket/Current Team |
entity Field |
user/Former Teams |
entity collection Field |
Available entity collection Field aggregates
q/count
q/sum
q/avg
q/min
q/max
- Select rich text Field
Get the related collaborative documents
fibery/secret
:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": [
"Cricket/name",
{ "Cricket/Bio": [ "Collaboration~Documents/secret" ] }
],
"q/limit": 2
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': [
'Cricket/name',
{ 'Cricket/Bio': [ 'Collaboration~Documents/secret' ] }
],
'q/where': ['=', ['fibery/id'], '$id'],
'q/limit': 2
});
Grab the secrets:
[
{
"success": true,
"result": [
{
"Cricket/name": "Virat Kohli",
"Cricket/Bio": {
"Collaboration~Documents/secret": "b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb"
}
},
{
"Cricket/name": "Kane Williamson",
"Cricket/Bio": {
"Collaboration~Documents/secret": "b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb"
}
}
]
}
]
[ { 'Cricket/name': 'Virat Kohli',
'Cricket/Bio':
{ 'Collaboration~Documents/secret': 'b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb' } },
{ 'Cricket/name': 'Kane Williamson',
'Cricket/Bio':
{ 'Collaboration~Documents/secret': 'b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb' } } ]
Get the documents one-by-one:
curl -X GET https://YOUR_ACCOUNT.fibery.io/api/documents/b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb?format=html \
-H 'Authorization: Token YOUR_TOKEN' \
curl -X GET https://YOUR_ACCOUNT.fibery.io/api/documents/b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb?format=html \
-H 'Authorization: Token YOUR_TOKEN' \
const virat_bio = await fibery.document.get('b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb', 'md');
const kane_bio = await fibery.document.get('b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb', 'md');
Result:
{
"secret": "b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb",
"content": "<p>Virat Kohli (born 5 November 1988) is an Indian <a href=\"https://en.wikipedia.org/wiki/Cricket\">cricketer</a> who currently captains the India national team.\nHe plays for Royal Challengers Bangalore in the Indian Premier League.</p>"
}
{
"secret": "b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb",
"content": "<p><strong>Kane Stuart Williamson</strong> (born 8 August 1990) is a New Zealand international <a href=\"https://en.wikipedia.org/wiki/Cricket\" title=\"Cricket\">cricketer</a> who is currently the <a href=\"https://en.wikipedia.org/wiki/Captain_(cricket)\" title=\"Captain (cricket)\">captain</a> of the <a href=\"https://en.wikipedia.org/wiki/New_Zealand_national_cricket_team\" title=\"New Zealand national cricket team\">New Zealand national team</a>.</p><p>He is a right-handed batsman and an occasional <a href=\"https://en.wikipedia.org/wiki/Off_spin\" title=\"Off spin\">off spin</a> bowler and is considered to be one of the best batsmen in the world.</p>"
}
{"secret":"b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb","content":"Virat Kohli (born 5 November 1988) is an Indian [cricketer](https://en.wikipedia.org/wiki/Cricket) who currently captains the India national team.\nHe plays for Royal Challengers Bangalore in the Indian Premier League."}
{"secret":"b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb","content":"**Kane Stuart Williamson** (born 8 August 1990) is a New Zealand international [cricketer](https://en.wikipedia.org/wiki/Cricket \"Cricket\") who is currently the [captain](https://en.wikipedia.org/wiki/Captain_(cricket) \"Captain (cricket)\") of the [New Zealand national team](https://en.wikipedia.org/wiki/New_Zealand_national_cricket_team \"New Zealand national cricket team\").\n\nHe is a right-handed batsman and an occasional [off spin](https://en.wikipedia.org/wiki/Off_spin \"Off spin\") bowler and is considered to be one of the best batsmen in the world."}
Get multiple documents in a single batch request:
curl --location --request POST 'https://YOUR_ACCOUNT.fibery.io/api/documents/commands' \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--data-raw '{
"command": "get-documents",
"args": [
{
"secret": "b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb"
},
{
"secret": "b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb"
}
]
}'
Result:
[
{
"secret": "b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb",
"content": "..."
},
{
"secret": "b33a25d3-99ba-11e9-8c59-09d0cb6f3aeb",
"content": "..."
}
]
Take a look how rich text Fields work in Fibery, if you haven't yet.
To select a rich text Field we should:
- Get
fibery/secret
of the corresponding collaborative document. - Get the document via
api/documents
endpoint using thisfibery/secret
.
Supported document formats:
- Markdown (md) — default
- HTML (html)
- JSON of a particular structure (json)
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
Cricket/Bio |
rich text (Collaboration~Documents/Document ) |
- Filter Entities
Get players taller than 1.75 meters — primitive Field:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": ["Cricket/name", "Cricket/Height"],
"q/where": [">", ["Cricket/Height"], "$height" ],
"q/limit": 2
},
"params": {
"$height": "1.75"
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': ['Cricket/name', 'Cricket/Height'],
'q/where': ['>', ['Cricket/Height'], '$height' ],
'q/limit': 2
}, { '$height': '1.75' });
Result:
[
{
"success": true,
"result": [
{
"Cricket/name": "Cheteshwar Pujara",
"Cricket/Height": "1.79"
}
]
}
]
[ {
'Cricket/name': 'Cheteshwar Pujara',
'Cricket/Height': '1.79'
} ]
Get players who started their youth career before 2004 and haven't retired yet — two primitive Fields:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": ["Cricket/name", "Cricket/Youth Career", "Cricket/Retired?"],
"q/where": [
"q/and",
["<", ["q/start", ["Cricket/Youth Career"]], "$date"],
["=", ["Cricket/Retired?"], "$retired?"]
],
"q/limit": 2
},
"params": {
"$date": "2004-01-01",
"$retired?": false
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': ['Cricket/name', 'Cricket/Youth Career', 'Cricket/Retired?'],
'q/where': [
'q/and',
['<', ['q/start', ['Cricket/Youth Career']], '$date'],
['=', ['Cricket/Retired?'], '$retired?']
],
'q/limit': 2
}, {
'$date': '2004-01-01',
'$retired?': false
});
Result:
[
{
"success": true,
"result": [
{
"Cricket/name": "Virat Kohli",
"Cricket/Youth Career": {
"start": "2002-10-01",
"end": "2008-07-01"
},
"Cricket/Retired?": false
}
]
}
]
[ { 'Cricket/name': 'Virat Kohli',
'Cricket/Youth Career': { start: '2002-10-01', end: '2008-07-01' },
'Cricket/Retired?': false } ]
Get right-handed players — single-select:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": ["Cricket/name", { "Cricket/Batting Hand": ["enum/name"] } ],
"q/where": ["=", ["Cricket/Batting Hand", "enum/name"], "$hand" ],
"q/limit": 2
},
"params": {
"$hand": "Right"
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': ['Cricket/name', { 'Cricket/Batting Hand': ['enum/name'] }],
'q/where': ['=', ['Cricket/Batting Hand', 'enum/name'], '$hand' ],
'q/limit': 2
}, { '$hand': 'Right' });
Result:
[
{
"success": true,
"result": [
{
"Cricket/name": "Virat Kohli",
"Cricket/Batting Hand": {
"enum/name": "Right"
}
},
{
"Cricket/name": "Kane Williamson",
"Cricket/Batting Hand": {
"enum/name": "Right"
}
}
]
}
]
[ { 'Cricket/name': 'Virat Kohli',
'Cricket/Batting Hand': { 'enum/name': 'Right' } },
{ 'Cricket/name': 'Kane Williamson',
'Cricket/Batting Hand': { 'enum/name': 'Right' } } ]
Get players whose current team was founded before 2000 — entity Field:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": ["Cricket/name", { "Cricket/Current Team": ["Cricket/name"] } ],
"q/where": ["<", ["Cricket/Current Team", "Cricket/Year Founded"], "$year" ],
"q/limit": 2
},
"params": {
"$year": 2000
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': ['Cricket/name', { 'Cricket/Current Team': ['Cricket/name'] }],
'q/where': ['<', ['Cricket/Current Team', 'Cricket/Year Founded'], '$year' ],
'q/limit': 2
}, { '$year': 2000 });
Result:
[
{
"success": true,
"result": [
{
"Cricket/name": "Virat Kohli",
"Cricket/Current Team": {
"Cricket/name": "Delhi"
}
},
{
"Cricket/name": "Cheteshwar Pujara",
"Cricket/Current Team": {
"Cricket/name": "Saurashtra"
}
}
]
}
]
[ { 'Cricket/name': 'Virat Kohli',
'Cricket/Current Team': { 'Cricket/name': 'Delhi' } },
{ 'Cricket/name': 'Cheteshwar Pujara',
'Cricket/Current Team': { 'Cricket/name': 'Saurashtra' } } ]
Get players who previously played for Yorkshire or Derbyshire — entity collection Field:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": ["Cricket/name", { "user/Former Teams": { "q/select": ["Cricket/name"], "q/limit": "q/no-limit" } } ],
"q/where": ["q/in", ["user/Former Teams", "Cricket/name"], "$teams" ],
"q/limit": 2
},
"params": {
"$teams": ["Yorkshire", "Derbyshire"]
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': ['Cricket/name', { 'user/Former Teams': { 'q/select': ['Cricket/name'], 'q/limit': 'q/no-limit' } } ],
'q/where': ['q/in', ['user/Former Teams', 'Cricket/name'], '$teams' ],
'q/limit': 2
}, { '$teams': ['Yorkshire', 'Derbyshire'] });
Result:
[
{
"success": true,
"result": [
{
"Cricket/name": "Kane Williamson",
"user/Former Teams": [
{ "Cricket/name": "Northern Districts" },
{ "Cricket/name": "Gloucestershire" },
{ "Cricket/name": "Yorkshire" },
{ "Cricket/name": "Barbados Tridents" }
]
},
{
"Cricket/name": "Cheteshwar Pujara",
"user/Former Teams": [
{ "Cricket/name": "Royal Challengers Bangalore" },
{ "Cricket/name": "Yorkshire" },
{ "Cricket/name": "Kolkata Knight Riders" },
{ "Cricket/name": "Kings XI Punjab" },
{ "Cricket/name": "Derbyshire" },
{ "Cricket/name": "Nottinghamshire" }
]
}
]
}
]
[ { 'Cricket/name': 'Kane Williamson',
'user/Former Teams': [ [Object], [Object], [Object], [Object] ] },
{ 'Cricket/name': 'Cheteshwar Pujara',
'user/Former Teams':
[ [Object], [Object], [Object], [Object], [Object], [Object] ] } ]
In these examples we filter by:
- a primitive Field (height)
- two primitive Fields (birth date and retirement status)
- a single-select (batting hand)
- an entity Field (current team)
- an entity collection Field (former teams)
We don't compare Entity's Field to a value directly, but use a $param
instead.
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
Cricket/Height |
fibery/decimal |
Cricket/Youth Career |
fibery/date-range |
Cricket/Retired? |
fibery/bool |
Cricket/Batting Hand |
single-select |
Cricket/Current Team |
entity Field |
user/Former Teams |
entity collection Field |
Operators
=
!=
<
<=
>
>=
q/contains
q/not-contains
q/in
q/not-in
q/and
q/or
- Order Entities
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": [
"Cricket/name",
"Cricket/Height",
{ "Cricket/Current Team": ["Cricket/name"] }
],
"q/order-by": [
[["Cricket/Height"], "q/desc"],
[["Cricket/Current Team", "Cricket/name"], "q/asc"]
],
"q/limit": 3
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': [
'Cricket/name',
'Cricket/Height',
{ 'Cricket/Current Team': ['Cricket/name'] }
],
'q/order-by': [
[['Cricket/Height'], 'q/desc'],
[['Cricket/Current Team', 'Cricket/name'], 'q/asc']
],
'q/limit': 3
});
Result:
[
{
"success": true,
"result": [
{
"Cricket/Current Team": {
"Cricket/name": "Saurashtra"
},
"Cricket/Height": "1.79",
"Cricket/name": "Cheteshwar Pujara"
},
{
"Cricket/Current Team": {
"Cricket/name": "Royal Challengers Bangalore"
},
"Cricket/Height": "1.75",
"Cricket/name": "Virat Kohli"
},
{
"Cricket/Current Team": {
"Cricket/name": "Sunrisers Hyderabad"
},
"Cricket/Height": "1.75",
"Cricket/name": "Kane Williamson"
}
]
}
]
[ { 'Cricket/Current Team': { 'Cricket/name': 'Saurashtra' },
'Cricket/Height': '1.79',
'Cricket/name': 'Cheteshwar Pujara' },
{ 'Cricket/Current Team': { 'Cricket/name': 'Royal Challengers Bangalore' },
'Cricket/Height': '1.75',
'Cricket/name': 'Virat Kohli' },
{ 'Cricket/Current Team': { 'Cricket/name': 'Sunrisers Hyderabad' },
'Cricket/Height': '1.75',
'Cricket/name': 'Kane Williamson' } ]
Sort Entities by multiple primitive and entity Fields.
The default sorting is by creation date and UUID:
[ [["fibery/creation-date"], "q/asc"], [["fibery/id"], "q/asc"] ]
Sorting by fibery/id
guarantees that Entities order won't change on different executions of the same query.
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
Cricket/Height |
fibery/decimal |
Cricket/Current Team |
entity Field |
Create Entity
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/create",
"args": {
"type": "Cricket/Player",
"entity": {
"fibery/id": "d17390c4-98c8-11e9-a2a3-2a2ae2dbcce4",
"Cricket/name": "Curtly Ambrose",
"Cricket/Full Name": "Curtly Elconn Lynwall Ambrose",
"Cricket/Born": "1963-09-21",
"Cricket/Youth Career": {
"start": "1985-01-01",
"end": "1986-01-01"
},
"Cricket/Shirt Number": 1,
"Cricket/Height": "2.01",
"Cricket/Retired?": true,
"Cricket/Batting Hand": { "fibery/id": "b0ed3a80-9747-11e9-9f03-fd937c4ecf3b" }
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.entity.createBatch([
{
'type': 'Cricket/Player',
'entity': {
'fibery/id': 'd17390c4-98c8-11e9-a2a3-2a2ae2dbcce4',
'Cricket/name': 'Curtly Ambrose',
'Cricket/Full Name': 'Curtly Elconn Lynwall Ambrose',
'Cricket/Born': '1963-09-21',
'Cricket/Youth Career': {
'start': '1985-01-01',
'end': '1986-01-01'
},
'Cricket/Shirt Number': 1,
'Cricket/Height': '2.01',
'Cricket/Retired?': true,
'Cricket/Batting Hand': { 'fibery/id': 'b0ed3a80-9747-11e9-9f03-fd937c4ecf3b' }
}
}
]);
Result with all primitive Fields, single-selects and entity Fields:
[
{
"success": true,
"result": {
"Cricket/Height": "2.01",
"fibery/modification-date": "2019-06-27T10:44:53.860Z",
"Cricket/Born": "1963-09-21",
"fibery/id": "98fd77a0-98c8-11e9-8af8-976831879f29",
"fibery/creation-date": "2019-06-27T10:44:53.860Z",
"Cricket/Shirt Number": 1,
"Cricket/Full Name": "Curtly Elconn Lynwall Ambrose",
"fibery/public-id": "6",
"Cricket/Retired?": true,
"Cricket/Current Team": null,
"Cricket/Batting Hand": {
"fibery/id": "b0ed3a80-9747-11e9-9f03-fd937c4ecf3b"
},
"Cricket/Youth Career": {
"start": "1985-01-01",
"end": "1986-01-01"
},
"Cricket/name": "Curtly Ambrose"
}
}
]
[
{ 'Cricket/Height': '2.01',
'fibery/modification-date': '2019-06-27T11:41:19.131Z',
'Cricket/Born': '1963-09-21',
'fibery/id': 'd17390c4-98c8-11e9-a2a3-2a2ae2dbcce4',
'fibery/creation-date': '2019-06-27T11:41:19.131Z',
'Cricket/Shirt Number': 1,
'Cricket/Full Name': 'Curtly Elconn Lynwall Ambrose',
'fibery/public-id': '7',
'Cricket/Retired?': true,
'Cricket/Current Team': null,
'Cricket/Batting Hand': { 'fibery/id': 'b0ed3a80-9747-11e9-9f03-fd937c4ecf3b' },
'Cricket/Youth Career': { 'start': '1985-01-01', 'end': '1986-01-01' },
'Cricket/name': 'Curtly Ambrose'
}
]
Create Entities with primitive, single-select and entity Fields.
Setting fibery/id
is optional and might be useful for working with Entity right after creation.
To set a single-select or an entity Field we'll need the target Entity's fibery/id
.
We can get fibery/id
either via API or
by opening the relevant Entity on UI and exploring the command response in browser's Network tab.
Note that the target Entity should already exist.
Setting entity collection Fields on Entity creation is not supported. Instead we suggest updating entity collection Fields after the Entity is created.
Setting a rich text Field on creation is not possible either. Update rich text Field once the Entity is created instead.
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
fibery/id |
fibery/uuid |
fibery/public-id |
fibery/text |
Cricket/name |
fibery/text |
Cricket/Full Name |
fibery/text |
Cricket/Born |
fibery/date |
Cricket/Youth Career |
fibery/date-range |
Cricket/Shirt Number |
fibery/int |
Cricket/Height |
fibery/decimal |
Cricket/Retired? |
fibery/bool |
Cricket/Batting Hand |
single-select |
Cricket/Current Team |
entity Field |
user/Former Teams |
entity collection Field |
Update Entity
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/update",
"args": {
"type": "Cricket/Player",
"entity": {
"fibery/id": "20f9b920-9752-11e9-81b9-4363f716f666",
"Cricket/Full Name": "Virat \"Chikoo\" Kohli",
"Cricket/Current Team": { "fibery/id": "d328b7b0-97fa-11e9-81b9-4363f716f666" }
}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.entity.updateBatch([
{
'type': 'Cricket/Player',
'entity': {
'fibery/id': '20f9b920-9752-11e9-81b9-4363f716f666',
'Cricket/Full Name': 'Virat \"Chikoo\" Kohli',
'Cricket/Current Team': { 'fibery/id': 'd328b7b0-97fa-11e9-81b9-4363f716f666' }
}
}
]);
Result with all primitive Fields, single-select and entity Fields:
[
{
"success": true,
"result": {
"Cricket/Height": "1.75",
"fibery/modification-date": "2019-06-27T12:17:02.842Z",
"Cricket/Born": "1988-11-05",
"fibery/id": "20f9b920-9752-11e9-81b9-4363f716f666",
"fibery/creation-date": "2019-06-25T14:04:20.988Z",
"Cricket/Shirt Number": 18,
"Cricket/Full Name": "Virat \"Chikoo\" Kohli",
"fibery/public-id": "1",
"Cricket/Retired?": false,
"Cricket/Current Team": {
"fibery/id": "d328b7b0-97fa-11e9-81b9-4363f716f666"
},
"Cricket/Batting Hand": {
"fibery/id": "b0ed1370-9747-11e9-9f03-fd937c4ecf3b"
},
"Cricket/Youth Career": {
"start": "2002-10-01",
"end": "2008-07-01"
},
"Cricket/name": "Virat Kohli"
}
}
]
[
{
'Cricket/Height': '1.75',
'fibery/modification-date': '2019-06-27T12:48:56.451Z',
'Cricket/Born': '1988-11-05',
'fibery/id': '20f9b920-9752-11e9-81b9-4363f716f666',
'fibery/creation-date': '2019-06-25T14:04:20.988Z',
'Cricket/Shirt Number': 18,
'Cricket/Full Name': 'Virat \"Chikoo\" Kohli',
'fibery/public-id': '1',
'Cricket/Retired?': false,
'Cricket/Current Team': [Object],
'Cricket/Batting Hand': [Object],
'Cricket/Youth Career': [Object],
'Cricket/name': 'Virat Kohli'
}
]
Update primitive, single-select and entity Fields this way. For updating entity collection Fields check out the section below.
To update a single-select or an entity Field we'll need the target Entity's fibery/id
.
We can get fibery/id
either via API or
by opening the relevant Entity on UI and exploring the command response in browser's Network tab.
Note that the target Entity should already exist.
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
fibery/id |
fibery/uuid |
fibery/public-id |
fibery/text |
Cricket/name |
fibery/text |
Cricket/Full Name |
fibery/text |
Cricket/Born |
fibery/date |
Cricket/Youth Career |
fibery/date-range |
Cricket/Shirt Number |
fibery/int |
Cricket/Height |
fibery/decimal |
Cricket/Retired? |
fibery/bool |
Cricket/Batting Hand |
single-select |
Cricket/Current Team |
entity Field |
user/Former Teams |
entity collection Field |
- Update entity collection Field
Add two existing Teams to Player's "Former Teams" entity collection Field:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/add-collection-items",
"args": {
"type": "Cricket/Player",
"field": "user/Former Teams",
"entity": { "fibery/id": "216c2a00-9752-11e9-81b9-4363f716f666" },
"items": [
{ "fibery/id": "0a3ae1c0-97fa-11e9-81b9-4363f716f666" },
{ "fibery/id": "17af8db0-97fa-11e9-81b9-4363f716f666" }
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.entity.addToEntityCollectionFieldBatch([
{
'type': 'Cricket/Player',
'field': 'user/Former Teams',
'entity': { 'fibery/id': '216c2a00-9752-11e9-81b9-4363f716f666' },
'items': [
{ 'fibery/id': '0a3ae1c0-97fa-11e9-81b9-4363f716f666' },
{ 'fibery/id': '17af8db0-97fa-11e9-81b9-4363f716f666' }
]
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
[ 'ok' ]
Remove two Teams from Player's "Former Teams" entity collection Field:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/remove-collection-items",
"args": {
"type": "Cricket/Player",
"field": "user/Former Teams",
"entity": { "fibery/id": "216c2a00-9752-11e9-81b9-4363f716f666" },
"items": [
{ "fibery/id": "0a3ae1c0-97fa-11e9-81b9-4363f716f666" },
{ "fibery/id": "17af8db0-97fa-11e9-81b9-4363f716f666" }
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.entity.removeFromEntityCollectionFieldBatch([
{
'type': 'Cricket/Player',
'field': 'user/Former Teams',
'entity': { 'fibery/id': '216c2a00-9752-11e9-81b9-4363f716f666' },
'items': [
{ 'fibery/id': '0a3ae1c0-97fa-11e9-81b9-4363f716f666' },
{ 'fibery/id': '17af8db0-97fa-11e9-81b9-4363f716f666' }
]
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
[ 'ok' ]
Add already existing Entities to an entity collection Field by providing their fibery/id
.
Remove Entities from the collection in a similar way.
Get fibery/id
either via API or
by opening the relevant Entity on UI and exploring the command response in browser's Network tab.
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
fibery/id |
fibery/uuid |
user/Former Teams |
entity collection Field |
- Update rich text Field
Get collaborative document's
fibery/secret
:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": [
"fibery/id",
{ "Cricket/Bio": [ "Collaboration~Documents/secret" ] }
],
"q/where": ["=", ["fibery/id"], "$id"],
"q/limit": 1
},
"params": { "$id": "20f9b920-9752-11e9-81b9-4363f716f666" }
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const players = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': [
'fibery/id',
{ 'Cricket/Bio': [ 'Collaboration~Documents/secret' ] }
],
'q/where': ['=', ['fibery/id'], '$id'],
'q/limit': 1
}, { '$id': '20f9b920-9752-11e9-81b9-4363f716f666' });
Grab the secret:
[
{
"success": true,
"result": [
{
"fibery/id": "20f9b920-9752-11e9-81b9-4363f716f666",
"Cricket/Bio": {
"Collaboration~Documents/secret": "b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb"
}
}
]
}
]
[ { 'fibery/id': '20f9b920-9752-11e9-81b9-4363f716f666',
'Cricket/Bio':
{ 'Collaboration~Documents/secret': 'b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb' } } ]
Update the document:
curl -X PUT https://YOUR_ACCOUNT.fibery.io/api/documents/b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb?format=md \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'{
"content": "Virat Kohli (born 5 November 1988) is an Indian [cricketer](https://en.wikipedia.org/wiki/Cricket) who currently captains the India national team.\nHe plays for Royal Challengers Bangalore in the Indian Premier League."
}'
const content = 'Virat Kohli (born 5 November 1988) is an Indian [cricketer](https://en.wikipedia.org/wiki/Cricket) who currently captains the India national team.\\nHe plays for Royal Challengers Bangalore in the Indian Premier League.';
await fibery.document.update('b33a25d1-99ba-11e9-8c59-09d0cb6f3aeb', content, 'md');
Status code 200 means that the update has been successful.
Take a look how rich text Fields work in Fibery, if you haven't yet.
To update a rich text Field we should:
- Get
fibery/secret
of the corresponding collaborative document. - Update the document via
api/documents
endpoint using thisfibery/secret
.
Supported document formats:
- Markdown (md) — default
- HTML (html)
- JSON of a particular structure (json)
Cricket/Player
Type used as an example
Field name | Field type |
---|---|
Cricket/Bio |
rich text (Collaboration~Documents/Document ) |
- Add comment
Generate two UUIDs – for the comment ID and the document secret ID:
a88626cb-2f08-4821-9d5f-3edb9b624c26
9f18d395-05da-44dc-9f21-602b2e744b14
Create an Entity of the auxiliary Comment Type and link it to the parent Entity:
curl -X POST https://YO UR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command":"fibery.command/batch",
"args":{
"commands":[
{
"command":"fibery.entity/create",
"args":{
"type":"comments/comment",
"entity":{
"fibery/id":"a88626cb-2f08-4821-9d5f-3edb9b624c26",
"comment/document-secret":"9f18d395-05da-44dc-9f21-602b2e744b14",
"comment/author": { "fibery/id": "fe1db100-3779-11e9-9162-04d77e8d50cb" }
}
}
},
{
"command":"fibery.entity/add-collection-items",
"args":{
"type":"Cricket/Player",
"entity":{
"fibery/id":"20f9b920-9752-11e9-81b9-4363f716f666"
},
"field":"comments/comments",
"items":[
{
"fibery/id": "a88626cb-2f08-4821-9d5f-3edb9b624c26"
}
]
}
}
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const PARENT_ENTITY_ID = '216c2a00-9752-11e9-81b9-4363f716f666';
const COMMENT_AUTHOR_ID = 'fe1db100-3779-11e9-9162-04d77e8d50cb';
const COMMENT_ID = 'a88626cb-2f08-4821-9d5f-3edb9b624c26'; // newly generated
const DOCUMENT_SECRET_ID = '9f18d395-05da-44dc-9f21-602b2e744b14'; // newly generated
const comment = await fibery.entity.create({
'type': 'comments/comment',
'entity': {
'fibery/id': COMMENT_ID,
'comment/document-secret': DOCUMENT_SECRET_ID,
'comment/author': { 'fibery/id': COMMENT_AUTHOR_ID }
}
});
await fibery.entity.addToEntityCollectionField({
'type': 'Cricket/Player',
'field': 'comments/comments',
'entity': { 'fibery/id': PARENT_ENTITY_ID },
'items': [
{ 'fibery/id': COMMENT_ID }
]
});
Make sure the result looks good:
[
{
"success": true,
"result": [
{
"success": true,
"result": {
"comment/document-secret": "9f18d395-05da-44dc-9f21-602b2e744b14",
"fibery/id": "a88626cb-2f08-4821-9d5f-3edb9b624c26",
"fibery/public-id": "139",
"fibery/creation-date": "2021-05-05T17:37:21.933Z",
"comment/content": null,
"comment/author": {
"fibery/id": "fe1db100-3779-11e9-9162-04d77e8d50cb"
}
}
},
{
"success": true,
"result": null
}
]
}
]
Set the comment's content:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/documents/commands?format=md \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'{
"command": "create-or-update-documents",
"args": [
{
"secret": "9f18d395-05da-44dc-9f21-602b2e744b14",
"content": "He is the [G.O.A.T.](https://en.wikipedia.org/wiki/Greatest_of_All_Time) batsman!"
}
]
}'
const content = 'He is the [G.O.A.T.](https://en.wikipedia.org/wiki/Greatest_of_All_Time) batsman!';
await fibery.document.update('9f18d395-05da-44dc-9f21-602b2e744b14', content, 'md');
Once you install the Comments
extension on a Type, you are free to
add comments to the Type's Entities – both via UI and API.
Here at Fibery, we don't throw abstractions around so comments are assembled from the pre-existing basic building blocks:
- Comment (
comments/comment
) is a Type with Fields like Author (comment/author
) and Creation Date (fibery/creation-date
). - The
Comments
extension connects a parent Type with Comment Type via a one-to-many relation. - Each individual comment is an Entity of Comment Type.
- The content of a comment is stored in a collaborative document just like rich-text Fields.
So here is how you add comment:
- Create an Entity of the Comment Type.
- Connect this comment to a proper parent Entity.
- Set the comment's content.
Delete Entity
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/delete",
"args": {
"type": "Cricket/Player",
"entity": { "fibery/id": "93648510-9907-11e9-acf1-fd0d502cdd20" }
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.entity.deleteBatch([
{
'type': 'Cricket/Player',
'entity': { 'fibery/id': 'b4f2e9b0-9907-11e9-acf1-fd0d502cdd20' }
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
[ 'ok' ]
Delete Entity by providing its Type and fibery/id
.
File
Working with Files is different from other scenarios.
To upload or download a File
use api/files
endpoint instead of the usual api/commands
.
When uploading a File, Fibery does two things:
- Saves the File to Storage and gets File's
fibery/secret
. - Creates an Entity of
fibery/file
Type with thefibery/secret
from the previous step and getsfibery/id
.
When working with Storage (ex. downloading a File) use fibery/secret
.
For actions inside Fibery (ex. attaching a File to an Entity) use fibery/id
:
Parent Entity --- (fibery/id
) ---> File Entity --- (fibery/secret
) ---> File in Storage
fibery/file
Type
Field name | Field type | Example |
---|---|---|
fibery/id |
fibery/uuid |
c5bc1ec0-997e-11e9-bcec-8fb5f642f8a5 |
fibery/secret |
fibery/uuid |
c5815fb0-997e-11e9-bcec-8fb5f642f8a5 |
fibery/name |
fibery/text |
"vogon-ship.jpg" |
fibery/content-type |
fibery/text |
"image/jpeg" |
Upload File
Upload an image from a Windows PC:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/files \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'content-type: multipart/form-data' \
-F 'file=@C:\Users\Trillian\Pictures\virat-kohli.jpg'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.file.upload('\\Users\\Trillian\\Pictures\\virat-kohli.jpg');
Result:
{
"fibery/id": "c5bc1ec0-997e-11e9-bcec-8fb5f642f8a5",
"fibery/name": "virat-kohli.jpg",
"fibery/content-type": "image/jpeg",
"fibery/secret": "c5815fb0-997e-11e9-bcec-8fb5f642f8a5"
}
{
"fibery/id": "c5bc1ec0-997e-11e9-bcec-8fb5f642f8a5",
"fibery/name": "virat-kohli.jpg",
"fibery/content-type": "image/jpeg",
"fibery/secret": "c5815fb0-997e-11e9-bcec-8fb5f642f8a5"
}
Upload a locally stored File and get:
Download File
curl -X GET https://YOUR_ACCOUNT.fibery.io/api/files/c5815fb0-997e-11e9-bcec-8fb5f642f8a5 \
-H 'Authorization: Token YOUR_TOKEN'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.file.download('c5815fb0-997e-11e9-bcec-8fb5f642f8a5', './virat.jpg');
Download a File by providing fibery/secret
.
Attach File to Entity
Attach a picture to a Player's profile:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/add-collection-items",
"args": {
"type": "Cricket/Player",
"field": "Files/Files",
"entity": { "fibery/id": "20f9b920-9752-11e9-81b9-4363f716f666" },
"items": [
{ "fibery/id": "c5bc1ec0-997e-11e9-bcec-8fb5f642f8a5" }
]
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.entity.addToEntityCollectionFieldBatch([
{
'type': 'Cricket/Player',
'field': 'Files/Files',
'entity': { 'fibery/id': '20f9b920-9752-11e9-81b9-4363f716f666' },
'items': [
{ 'fibery/id': 'c5bc1ec0-997e-11e9-bcec-8fb5f642f8a5' }
]
}
]);
Result:
[
{
"success": true,
"result": "ok"
}
]
[ 'ok' ]
Before attaching a File, make sure that Files extension is installed for the Entity's Type:
File extension creates an entity collection Field called Files/Files
.
Attach and remove Files the same way you update any other entity collection Field.
Download attachments
Get attached Files
fibery/secret
for a particular Player Entity:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/commands \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'[
{
"command": "fibery.entity/query",
"args": {
"query": {
"q/from": "Cricket/Player",
"q/select": [
"fibery/id",
{ "Files/Files": {
"q/select": ["fibery/secret"],
"q/limit": "q/no-limit"
} }
],
"q/where": ["=", ["fibery/id"], "$entity-id"],
"q/limit": 1
},
"params": {"$entity-id": "20f9b920-9752-11e9-81b9-4363f716f666"}
}
}
]'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
const files = await fibery.entity.query({
'q/from': 'Cricket/Player',
'q/select': [
'fibery/id',
{ 'Files/Files': {
'q/select': ['fibery/secret'],
'q/limit': 'q/no-limit'
} }
],
'q/where': ['=', ['fibery/id'], '$entity-id'],
'q/limit': 1
}, { '$entity-id': '20f9b920-9752-11e9-81b9-4363f716f666' });
Grab the secrets:
[
{
"success": true,
"result": [
{
"fibery/id": "20f9b920-9752-11e9-81b9-4363f716f666",
"Files/Files": [
{ "fibery/secret": "a71a7f30-9991-11e9-b8d4-8aba22381101" },
{ "fibery/secret": "c5815fb0-997e-11e9-bcec-8fb5f642f8a5" }
]
}
]
}
]
[ { 'fibery/id': '20f9b920-9752-11e9-81b9-4363f716f666',
'Files/Files': [
{ 'fibery/secret': 'a71a7f30-9991-11e9-b8d4-8aba22381101' },
{ 'fibery/secret': 'c5815fb0-997e-11e9-bcec-8fb5f642f8a5' } ] } ]
Download Files using these secrets:
curl -X GET https://YOUR_ACCOUNT.fibery.io/api/files/a71a7f30-9991-11e9-b8d4-8aba22381101 \
-H 'Authorization: Token YOUR_TOKEN'
curl -X GET https://YOUR_ACCOUNT.fibery.io/api/files/c5815fb0-997e-11e9-bcec-8fb5f642f8a5 \
-H 'Authorization: Token YOUR_TOKEN'
const Fibery = require('fibery-unofficial');
const fibery = new Fibery({host: "YOUR_ACCOUNT.fibery.io", token: YOUR_TOKEN});
await fibery.file.download('a71a7f30-9991-11e9-b8d4-8aba22381101', './playing.jpg');
await fibery.file.download('c5815fb0-997e-11e9-bcec-8fb5f642f8a5', './resting.jpg');
To download Entity's attached Files:
- Get the Files
fibery/secret
; - Download each File using
fibery/secret
.
Automations
There is a way to stop wasting your priceless time on the same set of actions you do in Fibery periodically. We have created special functionality for configuring these actions one time using a simple and intuitive editor. Please meet Rules and Buttons database editor screen by navigating to Automations.
There is a set of predefined actions, but it is possible to create custom programmable actions via providing JavaScript code in Script action. Additionally, the guide contains information on how to create documents, notifications or comments using Markdown Templates or Text Templates.
Script
Check our help article about Script Action.
Sometimes, you want to do something a bit complicated in an automation rule or action button. Fibery supports automations in the form of rules and action buttons. The former allows actions to be performed automatically when a trigger condition is met. The latter allows users to run a set of pre-determined actions.
There can be times though when you want an automation to do something a bit more complicated, something which might not be possible using the existing actions. In these cases, scripting can help.
Before jumping into Javascript, take a look at our Automations articles.
Arguments
When an action button is run or a rule is triggered, there are pieces of data that are available to be accessed within the script.
This includes the entity (or entities) that was (were) selected/active when the button was pressed/trigger occurred, and the identity of the user that pressed the button/triggered the rule. Every script receives information about the affected Entities and the current user if the rule was triggered by the user:
args.currentUser
args.currentEntities
Both User and Entity objects contain all Fields apart
from entity collection Fields. Field names are stripped
of app/
part and formatted the way they appear on UI.
Here's an example of args.currentUser
:
{ "Public Id": "1", "Id": "fe1db100-3779-11e9-9162-04d77e8d50cb", "Email": "vincent@gattaca.dna", "Creation Date": "2019-02-23T14:47:49.262Z", "Modification Date": "2019-09-27T08:17:46.608Z", "Name": "Vincent Freeman", "Role": { "Id": "57d5dd70-b9df-11e9-828d-51c8014f51c9", "Name": "Navigator" }, "type": "fibery/user" }
To make batch actions possible args.currentEntities
always comes as an array of Entity objects:
[ { "Public Id": "1", "Id": "a129d810-f8a0-11e8-88d2-3d1a5c86c61f", "Creation Date": "2018-12-05T15:15:41.738Z", "Modification Date": "2019-09-27T08:48:08.873Z", "Rank": 500000, "Name": "Swim farthest", "State": { "Name": "Done", "Id": "70df7a70-f8a0-11e8-a406-9abbdf4720ab" }, "type": "Tasks/Task" }, { ... } ]
Note: If a rule has been triggered by something other than a user action, e.g. when the value of a formula field containing the Today() function changes, then args.currentUser will return null.
Fibery Scripting API
You can use script to create, update or delete Fibery Entities or send requests to external services.
Inside Fibery:
const fibery = context.getService("fibery"); // fibery.getEntityById(type: string, id: string, fields: string[]): Promise<object> // fibery.getEntitiesByIds(type: string, ids: string[], fields: string[]): Promise<object[]> // fibery.createEntity(type: string, values: object): Promise<object> // fibery.updateEntity(type: string, id: string, values: object): Promise<object> // fibery.addCollectionItem(type: string, id: string, field: string, itemId: string): Promise<void> // fibery.removeCollectionItem(type: string, id: string, field: string, itemId: string): Promise<void> // fibery.deleteEntity(type: string, id: string): Promise<void> // fibery.setState(type: string, id: string, state: string): Promise<void> // fibery.setStateToFinal(type: string, id: string): Promise<void> // fibery.assignUser(type: string, id: string, userId: string): Promise<void> // fibery.unassignUser(type: string, id: string, userId: string): Promise<void> // fibery.getDocumentContent(secret: string, format: string): Promise<string> // fibery.setDocumentContent(secret: string, content: string, format: string): Promise<void> // fibery.appendDocumentContent(secret: string, content: string, format: string): Promise<void> // fibery.addComment(type: string, id: string, comment: string, authorId: string, format: string): Promise<object> // fibery.executeSingleCommand(command: FiberyCommand): Promise<any> // fibery.addFileFromUrl(url: string, fileName: string, type: string, id: string, headers: object): Promise<object> // fibery.graphql(spaceName: string, query: string, variables: object): Promise<object>
External HTTP requests:
const http = context.getService("http"); // simple GET request const features = await http.getAsync('https://my.targetprocess.com/api/v2/features'); // GET request with extra parameters const users = await http.getAsync('https://my.targetprocess.com/api/v2/users', { headers: { 'Authorization': 'Scheme Token' } }); // POST request const token = await http.postAsync("https://my.targetprocess.com/api/v2/tokens", { body: "client_id=fibery", headers: { 'Content-Type': 'application/x-www-form-urlencoded' } });
There's a chance somebody has already written a script similar to yours — take a look at our community examples before you start.
Debugging
If the reason why the script has failed is not clear, you can learn more by looking at execute
request in your
browser's Network tab when Button is used:
If the root cause of the error is still not clear, feel free to insert console.log(...)
in your code and check the
output in execute
request.
Markdown Template
There are a couple of actions that can create comments and documents, or change rich text fields of an entity. All of these actions have a text area that supports the markdown template.
Markdown Basics
Fibery supports almost all features of the basic markdown
syntax. Please check this guide and apply it for actions
with a markdown template. This is an example of a simple markdown template:
# Hello Hi, **dear friend**. Nice to meet you.
This one will work for adding checklists:
### My checklist - [ ] Conquer markdown - [ ] Procrastinate for the rest of the day
Using entity field shortcuts
You can use entity fields shortcuts in the template when there is a need to use some field values.
The syntax of the shortcut is {{Field Name}}
.
Use "." when you are going to put a relation field into the template:{{Relation Name.Field Name}}
.
Here we will get the entity Name and its State Name:
# My name is {{Name}}! My current status is {{State.Name}}
Using one-to-many or many-to-many field shortcuts
Let's say Story has a collection of Bugs.
Bullet-list output
List can be rendered as bullet list with
{- Bugs:Name -}
Comma-separated output
List can be rendered as comma-separated string by using
{= Bugs:Name =}
Hidden initialization
Sometimes it is needed to init list for future use in script. Can be done by using
{! Bugs:Name,State.Name !}
Table output
There is a way to include entity collections into the output document: {{Collection Name:Field1,Field2,...,FieldN}}. The result of the collection shortcut is a table.
List can be printed into a document like this:
## Quick Overview of {{Name}} Current state is **{{State.Name}}**. ### Bugs {{Bugs:Name, State.Name}}
- We created a button with "Add comment" action
- The result of the button click:
Using javascript code and Fibery API in templates
Javascript code and Fibery API can be used in templates. Javascript code can be executed using <% const sample = 1; %>
syntax. You may place output from your code into the template using <%= sample%>
syntax. An entity can be referenced as
Entity if you would like to make some calls to fibery API and retrieve some additional data. Entity contains Id and Type (database)
properties.
Here is an example of using Javascript and fibery API in a template:
### Overview of assignees <%= Entity.Type %> (#<%= Entity.Id%>) #### Assignees <% const fibery = context.getService('fibery'); const entityWithAssignees = await fibery.getEntityById(Entity.Type, Entity.Id, ['Assignees']); entityWithAssignees.Assignees.forEach((assignee) => { %> - <%= assignee.Name %> <%});%> Date of comment: <%= new Date()%> by <%= CurrentUser.Email || `Unknown User`%>
The output of this template if it is used for "Add Comment" action can be found below:
NOTE: Templates javascript code can have some limitations due to security reasons.
Current User
Every template receives information about the current user if the rule was triggered by the user:
Changes were made by **{{CurrentUser.Email}}**
Note: If a rule has been triggered by something other than a user action, e.g. when the value of a formula field containing the Today() function changes, then {{CurrentUser}} will return empty object.
Insert Comments or Documents into template
Find below an example on how insert last comment into template
{! Comments:Author.Name,Document Secret !} <% const fibery = context.getService('fibery'); const lastComment = Entity.Comments[Entity.Comments.length-1]; %>Comment added for {{Name}} by <%= lastComment['Author.Name'] %> <%= await fibery.getDocumentContent(lastComment['Document Secret'], 'md') %>
Text Template
Text templates have the same capabilities as Markdown Templates excluding support of Markdown Syntax, in other words it is just a text. Good example of Text Template usage is Notify action.
Request limits
To ensure system stability and consistent user experience, our API is rate-limited.
Rate-limited requests will return a "Too Many Requests" error (HTTP response status 429). The rate limit for incoming requests is 3 requests per second per token.
View
Views have to be accessed through a separate interface at https://{YOUR_ACCOUNT}.fibery.io/api/views/json-rpc
.
Get views
To get a list of views use the query-views
method:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/views/json-rpc \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'{
"jsonrpc": "2.0",
"method": "query-views",
"params": {
"filter": {
"ids": ["b190008d-3fef-4df5-b8b9-1b432a0e0f05", "dd62b0df-537e-4c12-89f2-d937da128c7b"],
"publicIds": ["1001", "1002"]
}
}
}'
All filers and params are optional. If omitted, all views will be returned.
Create views
To create one or more views use the create-views
method:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/views/json-rpc \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'{
"jsonrpc": "2.0",
"method": "create-views",
"params": {
"views": [
{
"fibery/id": "3541bdf6-ab15-4d5e-b17b-eb124b8fe2f7",
"fibery/name": "My Board",
"fibery/type": "board",
"fibery/meta": {},
"fibery/container-app": {
"fibery/id": "760ee2e2-e8ca-4f92-aaf2-4cde7f9dad0e"
}
}
]
}
}'
"Container app" in the example will contain a fibery/id reference the the space (a.k.a. app) the new view should be created in.
Update views
To update one or more views use the update-views
method:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/views/json-rpc \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'{
"jsonrpc": "2.0",
"method": "update-views",
"params": {
"updates": [
{
id: "3541bdf6-ab15-4d5e-b17b-eb124b8fe2f7",
values: {
"fibery/name": "My Updated Board",
"fibery/meta": {},
}
}
]
}
}'
Delete views
To delete one or more views use the delete-views
method:
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/views/json-rpc \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'{
"jsonrpc": "2.0",
"method": "delete-views",
"params": {
"ids": ["3541bdf6-ab15-4d5e-b17b-eb124b8fe2f7"]
}
}'
GraphQL API
Find GraphQL API documentation 👉👉👉 here
Integrations API
Find documentation about creating custom integration apps 👉👉👉 here
External Actions API (beta)
Find documentation about creating custom external actions apps 👉👉👉 here
Webhooks
Use webhooks to update other tools based on changes in Fibery.
There is no webhooks UI at the moment, so please use /api/webhooks/v2
endpoint to add or delete a webhook.
Add webhook
curl -X POST https://YOUR_ACCOUNT.fibery.io/api/webhooks/v2 \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
-d \
'{
"url": "http://webhook.site/c2d6d113-aebe-4f68-a337-022ec3c7ab5d",
"type": "Cricket/Player"
}'
Result:
{
"id": 5,
"url": "http://webhook.site/c2d6d113-aebe-4f68-a337-022ec3c7ab5d",
"type": "Cricket/Player",
"state": "active",
"version": "2",
"runs": []
}
Once you update a couple of Fields, the endpoint receives an array of effects:
{
"sequenceId":392,
"authorId":"4044090b-7165-4791-ac15-20fb12ae0b64",
"creationDate":"2021-04-22T12:40:14.325Z",
"effects":
[
{
"effect": "fibery.entity/update",
"id": "d17390c4-98c8-11e9-a2a3-2a2ae2dbcce4",
"type": "Cricket/Player",
"values": {
"fibery/modification-date": "2019-07-30T07:18:48.449Z",
"Cricket/name": "sir Curtly Ambrose"
},
"valuesBefore": {
"fibery/modification-date": "2019-07-04T11:12:13.423Z",
"Cricket/name": "Curtly Ambrose"
}
},
{
"effect": "fibery.entity/add-collection-items",
"id": "d17390c4-98c8-11e9-a2a3-2a2ae2dbcce4",
"type": "Cricket/Player",
"field": "user/Former~Teams",
"items": [
{
"fibery/id": "d328b7b0-97fa-11e9-81b9-4363f716f666"
}
]
}
]
}
Add a webhook to subscribe to Entity changes of a particular Type.
When one or several changes occur, Fibery sends a JSON with new and previous values to the specified URL.
Filter and process the payload in your integration. If you need some extra fields, send a request to the regular API.
Delete webhook
curl -X DELETE https://YOUR_ACCOUNT.fibery.io/api/webhooks/v2/WEBHOOK_ID \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
Status code 200 means that the deletion has been successful.
Delete a webhook when you no longer need it to save the account resources.
Get webhooks
curl -X GET https://YOUR_ACCOUNT.fibery.io/api/webhooks \
-H 'Authorization: Token YOUR_TOKEN' \
-H 'Content-Type: application/json' \
Result:
[
{
"id": 5,
"url": "http://webhook.site/c2d6d113-aebe-4f68-a337-022ec3c7ab5d",
"type": "Cricket/Player",
"state": "active",
"runs": [
{
"http_status": "200",
"elapsed_time": "209",
"request_time": "2019-07-30T07:18:49.883Z"
},
{
"http_status": "200",
"elapsed_time": "181",
"request_time": "2019-07-30T07:23:06.738Z"
}
]
}
]
Get a list of webhooks together with their latest 50 runs.
Permissions
Type and Field permissions
Imagine you've got a Type Task
with a Field called Effort
.
Here's how permissions apply depending on secured?
parameter:
Task secured? |
|||
❌ | ✅ | ||
Effort secured? |
❌ | Everyone has access to all fields | Everyone has access to Effort, but not to other secured? fields |
✅ | Everyone has access to all fields | Everyone has access to Task’s non-secured Fields like Id, but permissions are applied to Effort |