WebhooksFiltering and options
Filtering and options
Narrow and shape what a webhook delivers with its options, from filter and on-field-change to load-only, chunk_size and skip_keys.
Answer
A webhook's options object narrows and shapes deliveries. Per entity, filter and filter-op choose which records are delivered, on-field-change delivers only when listed fields changed, and load-only and expand shape the record. At the top level, chunk_size (1 to 100), chunk_delay, skip_keys and custom_entity_api_name apply. Option keys use load-only with a hyphen; load_only is refused.
options is optional: without it, a webhook delivers every record of the events it subscribes
to, as the REST API returns it. The API checks every key when you create or update a webhook and
refuses one it does not know with a 400, naming the key (errors). The
options follow the REST API's list parameters, which querying describes,
and are a field of the Webhooks entity.
This update sets a per-entity load-only and two top-level options, chunk_size and
skip_keys:
# The events and options you send replace the webhook's: send the whole list and object.
curl -sS --fail-with-body -X PATCH "$COEVERA_BASE/entities/Webhooks/$WEBHOOK_ID" \
-u "$COEVERA_API_KEY:$COEVERA_API_SECRET" \
-H "Content-Type: application/json" \
-d @- <<JSON
{
"events": ["Opportunity.Won", "Opportunity.Lost", "Opportunity.Move"],
"options": {
"entity": {
"Opportunity": { "load-only": ["id", "name", "owner_id", "step_id", "value", "revision"] }
},
"chunk_size": 50,
"skip_keys": ["northwind-sync"]
}
}
JSON
echo// The events and options you send replace the webhook's: send the whole list and object.
await coevera("PATCH", `/entities/Webhooks/${webhookId}`, {
events: ["Opportunity.Won", "Opportunity.Lost", "Opportunity.Move"],
options: {
entity: { Opportunity: { "load-only": ["id", "name", "owner_id", "step_id", "value", "revision"] } },
chunk_size: 50,
skip_keys: ["northwind-sync"],
},
});# The events and options you send replace the webhook's: send the whole list and object.
coevera(
"PATCH",
f"/entities/Webhooks/{webhook_id}",
json={
"events": ["Opportunity.Won", "Opportunity.Lost", "Opportunity.Move"],
"options": {
"entity": {"Opportunity": {"load-only": ["id", "name", "owner_id", "step_id", "value", "revision"]}},
"chunk_size": 50,
"skip_keys": ["northwind-sync"],
},
},
)# The events and options you send replace the webhook's: send the whole list and object.
jq -n --arg id "$WEBHOOK_ID" '{
query: "mutation UpdateWebhook($input: UpdateWebhookInput!) { updateWebhook(input: $input) { webhook { id events options } } }",
variables: {
input: {
id: $id,
events: ["OpportunityWon", "OpportunityLost", "OpportunityMove"],
options: ({
entity: { Opportunity: { "load-only": ["id", "name", "owner_id", "step_id", "value", "revision"] } },
chunk_size: 50,
skip_keys: ["northwind-sync"]
} | tojson)
}
}
}' | gql// The events and options you send replace the webhook's: send the whole list and object.
await gql(
`mutation UpdateWebhook($input: UpdateWebhookInput!) {
updateWebhook(input: $input) { webhook { id events options } }
}`,
{
input: {
id: webhookId,
events: ["OpportunityWon", "OpportunityLost", "OpportunityMove"],
options: JSON.stringify({
entity: { Opportunity: { "load-only": ["id", "name", "owner_id", "step_id", "value", "revision"] } },
chunk_size: 50,
skip_keys: ["northwind-sync"],
}),
},
},
);# The events and options you send replace the webhook's: send the whole list and object.
gql(
"""
mutation UpdateWebhook($input: UpdateWebhookInput!) {
updateWebhook(input: $input) { webhook { id events options } }
}
""",
{
"input": {
"id": webhook_id,
"events": ["OpportunityWon", "OpportunityLost", "OpportunityMove"],
"options": json.dumps({
"entity": {"Opportunity": {"load-only": ["id", "name", "owner_id", "step_id", "value", "revision"]}},
"chunk_size": 50,
"skip_keys": ["northwind-sync"],
}),
}
},
)Top-level options
| Key | What it does |
|---|---|
entity |
Options for the record in entity, per entity: {"Opportunity": {…}}. The keys are entity names as the events use them; an unknown entity is refused. |
related_ |
expand for the document in related_ of a DocumentLinked event, per event entity: {"Opportunity": {"expand": ["owner"]}}. Only expand is accepted. |
chunk_ |
How many events one delivery carries: 1 to 100, 100 by default. 0 or 101 is refused. |
chunk_ |
Seconds between chunks: chunk N, counted from 0, is sent N × chunk_ seconds later. 0 by default; a negative value is refused. |
skip_ |
Keys that stop this webhook firing: a write sent with the header WebHook-Skip-Key set to one of them does not fire it. |
custom_ |
For CustomEntity events, the custom entities that fire this webhook, such as ["CE_. All of them by default. |
Per-entity options
Under entity.<Entity>, five keys are accepted, in the REST API's names (snake case for fields,
a hyphen in load-only, filter-op and on-field-change):
| Key | What it does |
|---|---|
filter |
Deliver only the records that match, in the REST API's filter form: {"name": "Northwind"}, or a list of values for any of them. A field the entity does not have is refused. |
filter-op |
The operator per filtered field, such as {"name": "contains"}; eq by default. The operators are those of the REST API. |
on-field-change |
Deliver a record only if one of these fields changed in that change: ["step_. An unknown field name is refused. |
load-only |
The fields the record in the delivery carries. Keep id and revision if you deduplicate on them. |
expand |
Related records to include in full, such as ["owner"]. |
Warning
load-only takes a hyphen. load_only, which some REST query parameters tolerate, is refused
here with a 400.
on-field-change narrows every event
on-field-change applies to every event of that entity the webhook subscribes to, not only to
Update: a Create, a Won or a Delete is delivered only if one of the listed fields changed
in that same change. Subscribe to Opportunity.Won with on-field-change: ["value"], and a win
that leaves the value alone is not delivered. Use a second webhook for events that must always
arrive.
It works for these entities: Account, Contact, Lead, Opportunity, Task, Appointment, product line
items (OpptyProductRelation), Project, Quote, Email, and custom entities. OnlineForm is
accepted but has no events. Any other entity, such as Product, Memo or Note, is refused.
Reading and changing options
- An update replaces
optionsas a whole: send every key you want to keep, as the sample above does. - List webhooks without
load-only: with it,optionscomes back as{}. - In GraphQL,
optionsis a JSON string, in the input and in the response. options: nullis refused; send{}to clear them.
Limits
related_entitytakes onlyexpand; there is noload-onlyorfilterfor the document.- The filter applies to the record as it is when the delivery is built, not when it changed.
- Records the webhook's owner cannot read are left out of deliveries. A webhook registered with an API application's credentials has no owner, so it delivers every record.