Skip to content

Change several fields’ annotations

PATCH
/orgs/{org}/config/fields/{module}
curl --request PATCH \
--url 'https://api.sloose.com/orgs/org_9f3c/config/fields/accounts?connector=con_8f2a' \
--header 'Authorization: Bearer <token>' \
--header 'Content-Type: application/json' \
--header 'If-Match: "7"' \
--data '{ "fields": [ { "apiName": "example", "set": { "description": "example", "format": "example", "examples": [ "example" ], "aliases": [ "example" ], "excludeFromAi": true, "derived": true, "defaultMapping": { "mode": "column", "source": "example", "staticValue": "example", "transform": "example", "skip": true, "searchField": "example", "searchMethod": "example", "searchExpression": "example", "patch": { "when": [ "pending" ], "overwrite": "always" }, "key": true, "keyMethod": "example", "keyExpression": "example", "onNone": "empty", "onSeveral": "ask" }, "excluded": true, "requiredForImports": "waivable", "writtenAs": "upper", "mustBe": { "rule": "example", "says": "example" } }, "proposedBy": "ai" } ] }'

Changes some properties of several of one module’s fields, in one write under one version: what a module’s page saves when somebody uses the AI’s proposals for it. A field is a connection’s: ?connector= names which. It is required: nothing picks one for a request that does not say (design §14.8).

Each field’s change MERGES. A property it carries is written and null clears it; one it leaves out stays as it is. That is the difference from PATCH …/fields/{module}/{apiName}, whose body is the field’s whole annotation, and from PUT …/fields/{module}/annotations, which replaces the module’s whole set.

Every field lands or none does. A field the module does not have refuses the whole request (422, code: UNKNOWN_FIELDS, naming each in missing: 422 because the body names it, where the one-field route, whose path names the field, answers 404), and so does one the CRM no longer returns (422, code: DEPARTED_FIELDS, naming each in departed): these are the AI’s proposals, and one for a field the CRM dropped is a guess not worth making — the one-field route and a repository’s push accept such a field, which the module page keeps on purpose. Nothing of it is written. That is asked inside the write itself, so a field discovery marks gone while the request is on its way is refused too. Under If-Match the write lands only on the version sent: one the org has moved on from is refused with 409 and nothing of it is written. At most 500 fields, each named once.

The answer carries registryVersion only when you sent If-Match naming a version: one past the version you sent. Without one — no header, or *, which asks for nothing — the write lands on whatever version the org is at and answers none, for the reason the one-field route gives; read again, or send If-Match, to write again.

The change log gets a row for each property that changed, as the one-field route writes; with proposedBy: "ai" each row of that field says the value was the AI’s proposal.

org
required

The org id the session was issued for. A token for one org can never read another.

string
Example
org_9f3c

The org id the session was issued for. A token for one org can never read another.

module
required

The module’s key or CRM API name — either is accepted.

string
Example
accounts

The module’s key or CRM API name — either is accepted.

connector

The connection this is about, by id: one of the org’s, or your own. REQUIRED: absent or empty is 400 CONNECTION_REQUIRED, listing the connections this bearer may name, because nothing picks one for a request that does not say (design §14.8). Any other — another org’s, or another person’s — is 404 CONNECTION_NOT_FOUND.

string
Example
con_8f2a

The connection this is about, by id: one of the org’s, or your own. REQUIRED: absent or empty is 400 CONNECTION_REQUIRED, listing the connections this bearer may name, because nothing picks one for a request that does not say (design §14.8). Any other — another org’s, or another person’s — is 404 CONNECTION_NOT_FOUND.

If-Match

The registryVersion this change was made against, as "7" or 7 — a weak tag (W/"7") is refused, since If-Match uses strong comparison. Sent, the write is refused with 409 (code: REGISTRY_CONFLICT, the current version in the body) when the org has moved since, and otherwise answers the version it made: one past the version sent for a write made in one transaction, or the version sent itself for a request that asks for no change (an empty PATCH /config/writing), since it makes none. A bundle (POST /config/bundle) is several transactions and only its first waits on this version: it answers the version its own bumps took the org to, and none — nor an etag — when another write landed between them; one landing after them, while its templates are saved, withholds the etag alone. Omitted, there is no condition, and * is no condition either — and a write with no condition answers no registryVersion (nor, from a bundle, an etag), since nothing says which version it was made from. A value that is neither is 400 (code: BAD_IF_MATCH) rather than ignored — a precondition silently dropped looks like conflict detection and is not.

string
Example
"7"

The registryVersion this change was made against, as "7" or 7 — a weak tag (W/"7") is refused, since If-Match uses strong comparison. Sent, the write is refused with 409 (code: REGISTRY_CONFLICT, the current version in the body) when the org has moved since, and otherwise answers the version it made: one past the version sent for a write made in one transaction, or the version sent itself for a request that asks for no change (an empty PATCH /config/writing), since it makes none. A bundle (POST /config/bundle) is several transactions and only its first waits on this version: it answers the version its own bumps took the org to, and none — nor an etag — when another write landed between them; one landing after them, while its templates are saved, withholds the etag alone. Omitted, there is no condition, and * is no condition either — and a write with no condition answers no registryVersion (nor, from a bundle, an etag), since nothing says which version it was made from. A value that is neither is 400 (code: BAD_IF_MATCH) rather than ignored — a precondition silently dropped looks like conflict detection and is not.

Media typeapplication/json
object
fields
required
Array<object>
>= 1 items <= 500 items
object
apiName
required

The field’s CRM API name.

string
>= 1 characters
set
required

The properties to change, as FieldAnnotation names them. A property sent is written, null clears it, and one left out stays as it is.

object
description
string | null
format
string | null
examples
Array<string> | null
aliases
Array<string> | null
excludeFromAi
boolean | null
derived
boolean | null
defaultMapping
object
mode
string
Allowed values: column static expression search skip
source
string | null
staticValue
string | null
transform
string | null
skip
boolean
searchField
string | null
searchMethod
string | null
searchExpression
string | null
patch
object
when
Array<string>
Allowed values: pending created updated exists skipped filtered guarded dryrun error blocked
overwrite
string
Allowed values: always if-absent
key
boolean
keyMethod
string | null
keyExpression
string | null
onNone
string | null
Allowed values: empty skip ask
onSeveral
string | null
Allowed values: ask first skip empty
excluded
boolean | null
requiredForImports
Any of:
boolean
writtenAs
string | null
Allowed values: upper lower title
mustBe
object
rule
required
string
>= 1 characters <= 500 characters
says
required
string
>= 1 characters <= 200 characters
proposedBy

ai when these values are the AI’s proposals, used as they were proposed (Ask AI on a module’s page). The change log then says so beside the person who used them; the values themselves are written as any others.

string
Allowed values: ai

Applied, every field of it.

Media typeapplication/json
object
fields
required

Each field as it now stands, in the order the request named them.

Array<object>

A destination field definition, plus present, removedAt and the org’s annotation.

object
key
additional properties
registryVersion

The version the org is at after this write, to send as the next write’s If-Match: one past the version you sent in If-Match for a write made in one transaction (a bundle, several, answers the version its own bumps took the org to, or none when another write landed between them), or that version itself for a request that asks for no change (an empty PATCH /config/writing, which writes nothing and makes no version; sending the value the org already has still writes, and moves it). Only a write sent with a version in If-Match answers one. Without (no header, or *), the write lands on whatever version the org is at, and nothing on the server knows which version your picture of the configuration was built from: another administrator’s change may be inside the number, and sent back as If-Match it would let your next write overwrite that change unseen. So it is left out. To write again, read the configuration first (its GET answers the version), or send If-Match.

number
Examplegenerated
{
"fields": [
{
"additionalProperty": "example"
}
],
"registryVersion": 1
}

The request — its body or its query — did not match the schema (issues carries the Zod issue list), or: The request named no connection (code: CONNECTION_REQUIRED, with connections: the ones this bearer may name). Nothing picks one for a request that does not say (design §14.8).

Media typeapplication/json

The error envelope every non-2xx answer uses.

object
error
required

Human-readable explanation.

string
code

Machine-readable reason. Absent on a few legacy 400s.

string
key
additional properties
Examplegenerated
{
"error": "example",
"code": "example"
}

No bearer, or one that is expired, revoked or no longer resolves to a member.

Media typeapplication/json

The error envelope every non-2xx answer uses.

object
error
required

Human-readable explanation.

string
code

Machine-readable reason. Absent on a few legacy 400s.

string
key
additional properties
Examplegenerated
{
"error": "example",
"code": "example"
}

The bearer’s role is too low, or it was issued for a different org.

Media typeapplication/json

The error envelope every non-2xx answer uses.

object
error
required

Human-readable explanation.

string
code

Machine-readable reason. Absent on a few legacy 400s.

string
key
additional properties
Examplegenerated
{
"error": "example",
"code": "example"
}

No such module or connection, or it is not visible to this session.

Media typeapplication/json

The error envelope every non-2xx answer uses.

object
error
required

Human-readable explanation.

string
code

Machine-readable reason. Absent on a few legacy 400s.

string
key
additional properties
Examplegenerated
{
"error": "example",
"code": "example"
}

The org’s configuration has changed since the version in If-Match; the current one is in the body.

Media typeapplication/json
object
error
required
string
code
required
string
Allowed values: REGISTRY_CONFLICT
registryVersion
required
number
key
additional properties
Example
{
"code": "REGISTRY_CONFLICT"
}

A field the module does not have (code: UNKNOWN_FIELDS, each named in missing), one the CRM no longer returns (code: DEPARTED_FIELDS, each named in departed), a case its kind does not take (code: WRITTEN_AS_NOT_FOR_KIND, each named in fields with its kind and the cases it takes: a website takes none, an email lower case only), or a Must be rule that reads anything but the value, your helpers and plain built-ins (code: INVALID_RULE, each named in fields with the rule and why). Nothing was written.

Media typeapplication/json
object
error
required

Human-readable explanation.

string
code

Machine-readable reason. Absent on a few legacy 400s.

string
fields

WRITTEN_AS_NOT_FOR_KIND: each field given a case its kind does not take. INVALID_RULE: each field given a Must be rule that reaches past the value, and why.

Array
Any of:
object
module
required
string
apiName
required
string
kind
required

The field’s kind, as discovery last read it.

string
writtenAs
required
string
Allowed values: upper lower title
takes
required

The cases this kind takes: none for a website, lower for an email.

Array<string>
Allowed values: upper lower title
key
additional properties
Example
{
"fields": [
{
"writtenAs": "upper",
"takes": [
"upper"
]
}
]
}

Report a problem with this page