MARKETING · EMAIL
Subscribers, tags, sequences, and broadcasts from their own creator account.
Each user connects their own account. Every call carries both identities — the agent and the person it is acting for — so the agent can never reach past what that individual can already do.
Tokens live in the vault and attach server-side at call time. The agent holds a session, not a secret, and revoking access does not mean rotating a key.
Who asked, which agent acted, which action ran, and the verdict that let it through — one audit trail across every integration, not one per vendor.
Each action is granted on its own. An agent allowed to read is not thereby allowed to write, and the scope beside each row is what the acting user must have connected for it to run at all.
kit_delete_v4_broadcasts_by_idWRITEDelete a broadcast. DELETE /v4/broadcasts/{id}. Permanently deletes a draft or scheduled broadcast and returns `204 No Content` on success. This is a hard delete and cannot be undone. Note: a broadcast that is currently sending or has already been sent cannot be deleted — the request returns a `422` with `Broadcast is already sending.` or `Broadcast has already been sent.` respectively. To keep a scheduled broadcast without sending it, unschedule it via Update a broadcast instead.
kit_delete_v4_bulk_tagsWRITEBulk delete tags. DELETE /v4/bulk/tags. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. See "Bulk & async processing" for more information.
kit_delete_v4_bulk_tags_subscribersWRITEBulk remove tags from subscribers. DELETE /v4/bulk/tags/subscribers. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. See "Bulk & async processing" for more information.
kit_delete_v4_custom_fields_by_idWRITEDelete custom field. DELETE /v4/custom_fields/{id}. This will remove all data in this field from your subscribers.
kit_delete_v4_sequences_by_idWRITEDelete a sequence. DELETE /v4/sequences/{id}. Soft-deletes a sequence. The sequence is removed from active delivery immediately, with cleanup of associated state happening in the background. Warning: deleting a sequence with active subscribers stops deliveries to those subscribers — they will not receive remaining emails, and any Visual Automations referencing the sequence will need to be updated. Confirm the sequence is not in active use before deleting. If you want to pause rather than delete, use Update a sequence with `active: false` instead.
kit_delete_v4_sequences_by_sequence_id_emails_by_idWRITEDelete a sequence email. DELETE /v4/sequences/{sequence_id}/emails/{id}. Permanently removes one email from a sequence. Warning: subscribers already queued to receive the deleted email will skip it — they'll continue to the next email in sequence order. This is intentional and not retryable. If subscribers need to receive the email's content, send a broadcast or re-add subscribers to the sequence (with `repeat: true`) before deleting. If you want to pause rather than delete, use Update a sequence email with `published: false` instead.
kit_delete_v4_subscribers_by_subscriber_id_locationWRITEDelete a subscriber's location. DELETE /v4/subscribers/{subscriber_id}/location. Removes the subscriber's pinned location and returns `204 No Content` on success. After deletion, Kit may re-infer the subscriber's location from future open events. To set or replace a pinned location, use Pin a subscriber's location; to replace the values on an existing pin, use Update a subscriber's pinned location. Returns `404` when the subscriber is not found.
kit_delete_v4_tags_by_tag_id_subscribersWRITERemove tag from subscriber by email address. DELETE /v4/tags/{tag_id}/subscribers. Removes the tag from a subscriber identified by the `email_address` query parameter, returning `204 No Content`. The subscriber stays in your account and keeps their other tags — only this tag association is removed. This is the email-address variant of Remove tag from subscriber — use it when you have the subscriber's email but not their `id`. Returns `404` when the tag doesn't exist or no subscriber matches the email address.
kit_delete_v4_tags_by_tag_id_subscribers_by_idWRITERemove tag from subscriber. DELETE /v4/tags/{tag_id}/subscribers/{id}. Removes the tag from the subscriber and returns `204 No Content`. The subscriber stays in your account and keeps their other tags — only this tag association is removed. Returns `404` when the tag or subscriber id doesn't exist. To identify the subscriber by email address instead of id, use Remove tag from subscriber by email address. To remove tags from many subscribers at once, use Bulk remove tags from subscribers.
kit_delete_v4_webhook_endpoints_by_idWRITEDelete a webhook endpoint. DELETE /v4/webhook_endpoints/{id}. Deletes the webhook endpoint and stops all future deliveries of its subscribed events. Returns `204 No Content` on success and `404` when the id doesn't exist or isn't visible to the caller. Endpoints created by an app (via OAuth) can only be deleted by that app; an API key request returns `403`. To stop deliveries temporarily instead, update the endpoint's `status` to `disabled`.
kit_delete_v4_webhooks_by_idWRITEDelete a webhook. DELETE /v4/webhooks/{id}. Legacy: This deletes a previous-generation webhook. If you're replacing it rather than retiring it, consider recreating it as a webhook endpoint — see the webhooks guides. Deletes the webhook and stops all future deliveries of its subscribed events to the target URL. Returns `204 No Content` on success, `404` when the id doesn't exist, and `422` when the webhook cannot be deleted. Find webhook ids with List webhooks; register a replacement with Create a webhook.
kit_get_v4_accountREADGet current account. GET /v4/account. Returns the authenticated account and user: account `id`, `name`, `plan_type`, primary email address, timezone, and the account's sending addresses with their verification and DMARC status. For OAuth apps this is the standard way to identify which account authorized your app after the token exchange. For subscriber-growth metrics, see Get growth stats; for account-level email performance, see Get email stats.
kit_get_v4_account_colorsREADList colors. GET /v4/account/colors. Returns the account's saved brand color palette as an array of hex codes (up to 10). These are the colors available in Kit's editors for emails, forms, and landing pages. To change the palette, use Update colors.
kit_get_v4_account_creator_profileREADGet Creator Profile. GET /v4/account/creator_profile. Returns the account's Creator Profile — the public-facing identity shown on their Kit profile page and in the Creator Network: display `name`, `byline`, `bio`, `image_url`, and the public `profile_url`. Note: returns `404` when the account hasn't set up a Creator Profile, so handle that case rather than treating it as an error in your integration.
kit_get_v4_account_email_statsREADGet email stats. GET /v4/account/email_stats. Returns account-level email performance for the last 90 days: `sent`, `opened`, and `clicked` counts plus open, click, unsubscribe, and bounce rates, with the exact reporting window in `starting`/`ending` (`email_stats_mode` is `last_90`). The `open_tracking_enabled` and `click_tracking_enabled` flags indicate whether tracking is switched on for the account — open and click rates are only meaningful while tracking is enabled. For subscriber-growth metrics over a custom date range, use Get growth stats; for per-broadcast performance, use Get stats for a broadcast.
kit_get_v4_account_growth_statsREADGet growth stats. GET /v4/account/growth_stats. Get growth stats for a specific time period. Defaults to last 90 days. NOTE: We return your stats in your sending time zone. This endpoint does not return timestamps in UTC.
kit_get_v4_broadcastsREADList broadcasts. GET /v4/broadcasts. Returns a cursor-paginated list of broadcasts in the account with their content, targeting (`subscriber_filter`), email template, and web-publishing settings. Filter by lifecycle `status` (`draft`, `scheduled`, `sending`, `completed`, `aborted`) and by the `sent_after`/`sent_before` timestamps. Default 500 results per page, maximum 1000. Tip: set `slim=true` to omit the expensive fields (`content`, `public_url`, `email_address`, `email_template`, `subscriber_filter`) for a faster, smaller response — useful when you only need identifiers and subjects. Delivery and engagement stats are not included in this response; use Get stats for a list of broadcasts for those. Broadcasts that are also published as posts share a `publication_id` with the matching post from List posts.
kit_get_v4_broadcasts_by_broadcast_id_clicksREADGet link clicks for a broadcast. GET /v4/broadcasts/{broadcast_id}/clicks. Returns click performance for each link in a broadcast: the link `url`, its `unique_clicks`, and its click-to-delivery and click-to-open rates. Useful for seeing which calls to action actually drove engagement. Note: Pagination parameters control the list of links returned for the top-level broadcast; results are cursor-paginated. Data retention: Starting October 15, 2026, email stats (opens, clicks, sends, bounces, and unsubscribes) are available via the API for the last 5 years — click data for broadcasts older than that window is no longer available. Older data is archived and can no longer be retrieved via the API; creators can contact Kit support to request an export of their archived data. See Email data retention for the full policy.
kit_get_v4_broadcasts_by_broadcast_id_statsREADGet stats for a broadcast. GET /v4/broadcasts/{broadcast_id}/stats. Returns delivery and engagement stats for a single broadcast: recipients, opens, clicks, unsubscribes, their corresponding rates, plus the sending `status` and `progress`. The `open_tracking_disabled` and `click_tracking_disabled` flags indicate whether tracking was enabled when the broadcast was sent — interpret open and click counts accordingly. To fetch stats for many broadcasts at once, use Get stats for a list of broadcasts; for per-link click detail, use Get link clicks for a broadcast. Data retention: Starting October 15, 2026, email stats (opens, clicks, sends, bounces, and unsubscribes) are available via the API for the last 5 years — requesting stats for a broadcast sent before that window returns a `400` error. Older data is archived and can no longer be retrieved via the API; creators can contact Kit support to request an export of their archived data. See Email data retention for the full policy.
kit_get_v4_broadcasts_by_idREADGet a broadcast. GET /v4/broadcasts/{id}. Returns a single broadcast's full record: subject, `content` (HTML), preview text, targeting (`subscriber_filter`), email template, sending schedule (`send_at`), and web-publishing details (`public`, `public_url`, `published_at`). Delivery and engagement stats are not included; use Get stats for a broadcast for opens, clicks, and unsubscribes, or Get link clicks for a broadcast for per-link detail. A broadcast that is also published as a post shares its `publication_id` with the matching post from List posts.
kit_get_v4_broadcasts_statsREADGet stats for a list of broadcasts. GET /v4/broadcasts/stats. Returns delivery and engagement stats — recipients, opens, clicks, unsubscribes, and their corresponding rates — for a page of broadcasts in a single request, avoiding a call per broadcast. Narrow the results with the `status` filter and the `sent_after`/`sent_before` timestamps; results are cursor-paginated with up to 1000 broadcasts per page (default 500). For a single broadcast, use Get stats for a broadcast. Data retention: Starting October 15, 2026, email stats (opens, clicks, sends, bounces, and unsubscribes) are available via the API for the last 5 years — broadcasts sent before that window are omitted from this list. Older data is archived and can no longer be retrieved via the API; creators can contact Kit support to request an export of their archived data. See Email data retention for the full policy.
kit_get_v4_custom_fieldsREADList custom fields. GET /v4/custom_fields. A custom field allows you to collect subscriber information beyond the standard fields of first name and email address. An example would be a custom field called last name so you can get the full names of your subscribers. You create a custom field, and then you're able to use that in your forms or emails.
kit_get_v4_email_templatesREADList email templates. GET /v4/email_templates. Returns a cursor-paginated list of the account's email templates with each template's `id`, `name`, `is_default` flag, and `category` (for example `HTML` or `Starting point`). Use a template's `id` as the `email_template_id` when creating or updating a broadcast. Note: templates in the `Starting point` category are generally not supported when creating broadcasts via the API — using one returns a `Starting point email template is not supported` error unless your app has been enabled for it. See Create a broadcast.
kit_get_v4_formsREADList forms. GET /v4/forms. Returns a cursor-paginated list of forms and landing pages in the account. Both live on this endpoint — filter with `type=embed` for embedded forms or `type=hosted` for landing pages. By default only `active` forms are returned; use `status` (`active`, `archived`, `trashed`, or `all`) to widen the search. Add `include=subscriber_count` to embed each form's subscriber count. Each form includes its `uid`, `embed_js`, and `embed_url` for embedding on your site. To see who joined via a form, use List subscribers for a form; to add an existing subscriber, use Add subscriber to form.
kit_get_v4_forms_by_form_id_subscribersREADList subscribers for a form. GET /v4/forms/{form_id}/subscribers. Returns a cursor-paginated list of subscribers who joined through (or were added to) the form. By default only `active` subscribers are returned — use `status` (`active`, `inactive`, `bounced`, `complained`, `cancelled`, or `all`) to widen the search. Filter by when they were added to the form with `added_after`/`added_before`, or by when the subscriber record was created with `created_after`/`created_before`. Set `slim=true` to omit expensive optional fields for a faster, smaller response.
kit_get_v4_postsREADList posts. GET /v4/posts. Returns a cursor-paginated list of the account's posts — content published to the creator's Kit site and/or sent by email — with each post's `status` (e.g. `draft`, `scheduled`, `published`), `slug`, `public_url`, `is_paid` flag, and timestamps for publishing and sending. Post bodies are omitted by default; set `include_content=true` to embed the `content` HTML on each post (this significantly increases response size and latency for large collections — prefer Get a post for a single body). A post that was also sent as a broadcast shares its `publication_id` with the matching broadcast from List broadcasts.
kit_get_v4_posts_by_idREADGet a post. GET /v4/posts/{id}. Returns a single post's full record, including its `content` HTML, `status` (e.g. `draft`, `scheduled`, `published`), `slug`, SEO fields (`description`, `meta_description`), thumbnail, `is_paid` flag, and the `public_url` where it's published on the creator's Kit site. A post that was also sent as a broadcast shares its `publication_id` with the matching broadcast — see List broadcasts.
kit_get_v4_purchasesREADList purchases. GET /v4/purchases. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. Returns a cursor-paginated list of purchases recorded in the account, typically imported from e-commerce platforms. Each purchase includes its `transaction_id`, `status`, `source` (e.g. the originating platform), the buyer's `email_address` and `subscriber_id`, monetary breakdown (`subtotal`, `discount`, `tax`, `total`, `currency`), and the purchased `products`. To record a new purchase, use Create a purchase.
kit_get_v4_purchases_by_idREADGet a purchase. GET /v4/purchases/{id}. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. Returns a single purchase's details: `transaction_id`, `status`, `source`, the buyer's `email_address` and `subscriber_id`, monetary breakdown (`subtotal`, `discount`, `tax`, `total`, `currency`), `transaction_time`, and the purchased `products` with quantities and unit prices.
kit_get_v4_segmentsREADList segments. GET /v4/segments. Returns a cursor-paginated list of all segments in the account with their `id`, `name`, and creation date. Segments are created and managed in the Kit app — the API doesn't currently support creating or updating them. Use segment ids for targeting, for example in a broadcast's `subscriber_filter` (see Create a broadcast).
kit_get_v4_sequencesREADList sequences. GET /v4/sequences. Returns every sequence on the account. A sequence is a self-contained set of automated emails — subscribers join, then receive each email in order, governed by per-email `delay_value` / `delay_unit` and the sequence's overall `send_days`, `send_hour`, and `time_zone` schedule. Each entry carries the schedule defaults plus three behavioural toggles: `active` (whether the sequence is delivering), `repeat` (whether subscribers can re-enter), and `hold` (whether subscribers stay active after receiving every published email — an evergreen pattern). See Create a sequence for the full sequence model. Once you have a sequence's `id`, List sequence emails returns the individual emails inside it. For end-user context on how creators build sequences, see the help articles on creating and sending a sequence and evergreen content.
kit_get_v4_sequences_by_idREADGet a sequence. GET /v4/sequences/{id}. Fetches a single sequence by `id`. Use this when you need the current schedule, the `active` / `repeat` / `hold` flags, the configured `email_address` and `email_template_id`, or `exclude_subscriber_sources` for a known sequence — for example, to confirm settings before adding subscribers or to render an editor. For the individual emails inside the sequence, use List sequence emails. For the sequence model and field semantics, see Create a sequence.
kit_get_v4_sequences_by_sequence_id_emailsREADList sequence emails. GET /v4/sequences/{sequence_id}/emails. Returns every email inside a sequence, ordered by `position` (the order subscribers receive them). Each entry carries timing (`delay_value`, `delay_unit`, `send_days`), publish state (`published`), and metadata (`subject`, `preview_text`, `email_template_id`). Tip: the heavier `content` field is omitted by default to keep responses fast on sequences with many emails. Pass `include_content=true` when you need the body — for example, to render a preview, audit Liquid usage, or sync an external draft. For the field semantics — particularly how `delay_unit` and `send_days` interact, and what happens when subscribers hit a `published: false` email — see Create a sequence email.
kit_get_v4_sequences_by_sequence_id_emails_by_idREADGet a sequence email. GET /v4/sequences/{sequence_id}/emails/{id}. Fetches a single sequence email by `id`. Unlike List sequence emails, this endpoint always returns the full `content` — no `include_content` flag needed. Use this when you have an email's `id` and need the current body, timing, or publish state — for example, to render a preview before pushing an update via Update a sequence email. For the field semantics, see Create a sequence email.
kit_get_v4_sequences_by_sequence_id_subscribersREADList subscribers for a sequence. GET /v4/sequences/{sequence_id}/subscribers. Returns a cursor-paginated list of subscribers in the sequence, each with an `added_at` timestamp for when they entered it. By default only `active` subscribers are returned — use `status` (`active`, `inactive`, `bounced`, `complained`, `cancelled`, or `all`) to widen the search. Filter by when subscribers entered the sequence with `added_after`/`added_before`, or by when the subscriber record was created with `created_after`/`created_before`. To add a subscriber to the sequence, use Add subscriber to sequence.
kit_get_v4_snippetsREADList snippets. GET /v4/snippets. Returns every snippet on the account. Each snippet's `key` is the identifier used in Liquid — `{{ snippet.key }}` — when creating a broadcast or sequence email. See Create a snippet for how snippets work end-to-end. Tip: the heavier `content` and `document` fields are omitted by default to keep responses fast. Pass `include_content=true` when you need the body — for example, to render a preview or audit Liquid usage. Filter the result with `snippet_type` (`inline` or `block`) and `archived` (defaults to `false`, set `true` to list only archived snippets).
kit_get_v4_snippets_by_idREADGet a snippet. GET /v4/snippets/{id}. Fetches a single snippet by `id`. Unlike List snippets, this endpoint always returns the full `content` and `document` — no `include_content` flag needed. Use this when you have an `id` (e.g. stored from a prior create call) and need the current `key` and body — for example, to preview the resolved HTML or confirm a snippet still exists before referencing it as `{{ snippet.key }}` in a broadcast or sequence email. See Create a snippet for the snippet model.
kit_get_v4_subscribersREADList subscribers. GET /v4/subscribers. Returns a cursor-paginated list of subscribers in the account. By default only `active` subscribers are returned — use `status` (`active`, `inactive`, `bounced`, `complained`, `cancelled`, or `all`) to widen the search. Look a subscriber up by exact `email_address`, filter by `created_after`/`created_before` and `updated_after`/`updated_before`, and order with `sort_field` (`id`, `created_at`, `updated_at`, `cancelled_at`, or an `engagement__<metric>`) and `sort_order`. Use `include` (comma-separated: `attribution`, `tags`, `location`, `canceled_at`) to embed extra fields on each subscriber — including `canceled_at` without `status=cancelled` returns a `422`. Set `slim=true` to omit the `fields` object (custom field values) for a faster, smaller response. Ordering by an engagement metric (opens, clicks, sends over the trailing 90 days) is supported here via `sort_field=engagement__<metric>`, but cannot be combined with an `email_address` filter. To *filter* subscribers by engagement, use Filter subscribers by engagement instead. Results are eventually consistent and may briefly lag very recent changes — see Eventual consistency.
kit_get_v4_subscribers_by_idREADGet a subscriber. GET /v4/subscribers/{id}. Returns a single subscriber's record: first name, email address, `state` (e.g. `active` or `cancelled`), creation date, and their custom field values under `fields`. To look a subscriber up by email address instead of id, use List subscribers with the `email_address` parameter. For their email engagement history, see List stats for a subscriber; for their tags, see List tags for a subscriber.
kit_get_v4_subscribers_by_subscriber_id_statsREADList stats for a subscriber. GET /v4/subscribers/{subscriber_id}/stats. Retrieve email stats for a specific subscriber: totals for sent, opened, clicked, and bounced emails, open and click rates, and recency signals (`last_sent`, `last_opened`, `last_clicked`, and sends since the last open/click). Filter the stats with the `email_sent_after` and/or `email_sent_before` query parameters to limit them to emails sent within a specific date range. Data retention: Starting October 15, 2026, email stats (opens, clicks, sends, bounces, and unsubscribes) are available via the API for the last 5 years — `email_sent_after`/`email_sent_before` are clamped to that window, and dates outside it return a `400` error indicating the earliest available date. Older data is archived and can no longer be retrieved via the API; creators can contact Kit support to request an export of their archived data. See Email data retention for the full policy.
kit_get_v4_subscribers_by_subscriber_id_tagsREADList tags for a subscriber. GET /v4/subscribers/{subscriber_id}/tags. Returns a cursor-paginated list of the tags currently applied to a subscriber, including when each was applied (`tagged_at`). To see every tag in the account, use List tags. To add or remove a tag for this subscriber, use Tag a subscriber and Remove tag from subscriber.
kit_get_v4_tagsREADList tags. GET /v4/tags. Returns a cursor-paginated list of all tags in the account with their `id`, `name`, and creation date. Add `include=subscriber_count` to embed each tag's subscriber count. Tags are the main building block for segmenting your list: apply one with Tag a subscriber, and see who has one with List subscribers for a tag.
kit_get_v4_tags_by_tag_id_subscribersREADList subscribers for a tag. GET /v4/tags/{tag_id}/subscribers. Returns a cursor-paginated list of subscribers who have this tag. By default only `active` subscribers are returned — use `status` (`active`, `inactive`, `bounced`, `complained`, `cancelled`, or `all`) to widen the search. Filter by when the tag was applied with `tagged_after`/`tagged_before` (format `yyyy-mm-dd`), or by when the subscriber joined with `created_after`/`created_before`. Set `slim=true` to omit expensive optional fields for a faster, smaller response.
kit_get_v4_webhook_endpointsREADList webhook endpoints. GET /v4/webhook_endpoints. Returns a paginated list of the account's webhook endpoints. Filter with `status` to return only `active` or `disabled` endpoints. Webhook endpoints are the current generation of Kit webhooks: one endpoint subscribes to many event types and receives signed, automatically retried deliveries. They supersede the legacy Webhooks resource — which keeps working — and are the right choice for all new integrations. Start with the webhooks guides.
kit_get_v4_webhook_endpoints_by_idREADGet a webhook endpoint. GET /v4/webhook_endpoints/{id}. Returns a single webhook endpoint. The signing `secret` is never included — it's only returned when you create the endpoint or rotate the secret. Returns `404` when the id doesn't exist, belongs to another account, or belongs to an endpoint created by a different app.
kit_get_v4_webhooksREADList webhooks. GET /v4/webhooks. Legacy: This is the previous generation of Kit webhooks. It keeps working and there are no plans to remove it, but it's superseded by webhook endpoints, which support many event types per endpoint, signed deliveries, and automatic retries — use those for new integrations. See the webhooks guides. Webhooks are automations that will receive subscriber data when a subscriber event is triggered, such as when a subscriber completes a sequence. When a webhook is triggered, a `POST` request will be made to your URL with a JSON payload.
kit_patch_v4_subscribers_by_subscriber_id_locationWRITEUpdate a subscriber's pinned location. PATCH /v4/subscribers/{subscriber_id}/location. Updates a subscriber's pinned location. This is a full replacement, not a partial update: `city`, `state_province`, `country_code` (ISO 3166-1 alpha-2), `latitude`, `longitude`, and `timezone` (IANA timezone name, e.g. `America/Denver`) are all required, so resend the current value for any field you are not changing. Omitting one returns `422`. Returns the subscriber's `id` and the updated `location` on success. To create a pin from scratch, use Pin a subscriber's location (POST); to remove the pin entirely, use Delete a subscriber's location. Returns `404` when the subscriber is not found, `422` when a required field is missing or invalid.
kit_patch_v4_webhook_endpoints_by_idWRITEUpdate a webhook endpoint. PATCH /v4/webhook_endpoints/{id}. Updates any of `name`, `url`, `description`, `status`, and `events`. Set `status` to `disabled` to stop deliveries without deleting the endpoint, and back to `active` to resume. Note: `events` replaces the endpoint's entire subscription list — send the complete set you want, not just the additions. Endpoints created by an app (via OAuth) can only be updated by that app; an API key request returns `403`.
kit_post_v4_broadcastsWRITECreate a broadcast. POST /v4/broadcasts. Draft or schedule to send a broadcast to all or a subset of your subscribers. To save a draft, set `send_at` to `null`. To publish to the web, set `public` to `true`. To schedule the broadcast for sending, provide a `send_at` timestamp. Scheduled broadcasts should contain a subject and your content, at a minimum. We currently support targeting your subscribers based on segment or tag ids.<aside class='notice'>Starting point templates are not currently supported.</aside>
kit_post_v4_bulk_custom_fieldsWRITEBulk create custom fields. POST /v4/bulk/custom_fields. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. See "Bulk & async processing" for more information.
kit_post_v4_bulk_custom_fields_subscribersWRITEBulk update subscriber custom field values. POST /v4/bulk/custom_fields/subscribers. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. Creates or updates custom field values for many subscribers in one request. Each entry in `custom_field_values` pairs a `subscriber_id` with a `subscriber_custom_field_id` and the `value` to set. Requires OAuth authentication. Requests with 100 or fewer values are processed synchronously (`200`); larger requests are processed asynchronously (`202`) — provide a `callback_url` to be notified on completion, and see Bulk & async processing for how async requests behave. Returns `413` when the request would exceed the account's data limit for enqueued bulk requests. The custom fields must already exist — entries referencing an unknown `subscriber_custom_field_id` are rejected individually with a `Custom field does not exist` error in the response's failures list, while the rest of the batch is still processed. See List custom fields and Bulk create custom fields.
kit_post_v4_bulk_forms_subscribersWRITEBulk add subscribers to forms. POST /v4/bulk/forms/subscribers. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. Adding subscribers to double opt-in forms will trigger sending an Incentive Email. Subscribers already added to the specified form will not receive the Incentive Email again. For more information about double opt-in see "Double opt-in". The subscribers being added to the form must already exist. Subscribers can be created in bulk using the "Bulk create subscriber" endpoint. See "Bulk & async processing" for more information.
kit_post_v4_bulk_subscribersWRITEBulk create subscribers. POST /v4/bulk/subscribers. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. See "Bulk & async processing" for more information.
kit_post_v4_bulk_tagsWRITEBulk create tags. POST /v4/bulk/tags. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. See "Bulk & async processing" for more information.
kit_post_v4_bulk_tags_subscribersWRITEBulk tag subscribers. POST /v4/bulk/tags/subscribers. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. The subscribers being tagged must already exist. Subscribers can be created in bulk using the "Bulk create subscriber" endpoint. See "Bulk & async processing" for more information.
kit_post_v4_custom_fieldsWRITECreate a custom field. POST /v4/custom_fields. Create a custom field for your account. The label field must be unique to your account. Whitespace will be removed from the beginning and the end of your label. Additionally, a key field and a name field will be generated for you. The key is an ASCII-only, lowercased, underscored representation of your label. This key must be unique to your account. Keys are used in personalization tags in sequences and broadcasts. Names are unique identifiers for use in the HTML of custom forms. They are made up of a combination of ID and the key of the custom field prefixed with "ck_field".
kit_post_v4_forms_by_form_id_subscribersWRITEAdd subscriber to form by email address. POST /v4/forms/{form_id}/subscribers. The subscriber being added to the form must already exist. Subscribers can be created using the "Create a subscriber" endpoint.
kit_post_v4_forms_by_form_id_subscribers_by_idWRITEAdd subscriber to form. POST /v4/forms/{form_id}/subscribers/{id}. The subscriber being added to the form must already exist. Subscribers can be created using the "Create a subscriber" endpoint.
kit_post_v4_purchasesWRITECreate a purchase. POST /v4/purchases. REQUIRES AN OAUTH CONNECTION: Kit refuses an API key here. Records a purchase against a subscriber, identified by `email_address` — use this to sync order data from your e-commerce platform into Kit so it appears on the subscriber's profile and can drive purchase-based automations. If no subscriber with that email address exists, one is created (in the `active` state) as part of the request. Provide the external `transaction_id` (required), monetary breakdown (`subtotal`, `tax`, `shipping`, `discount`, `total`), a 3-letter `currency` code (e.g. `USD`), `transaction_time`, and the purchased `products` — each product needs a `pid` (your platform's product identifier); products that don't exist yet are created automatically. Note: purchases are matched on `transaction_id`, so submitting one that already exists updates the existing purchase instead of creating a duplicate. The `products` in your request are *added* to that purchase as additional line items — they don't replace the ones already recorded — so resending the same products will duplicate the line items. Only include `products` you haven't already synced for that `transaction_id`. Returns `422` when required parameters are missing or invalid.
kit_post_v4_sequencesWRITECreate a sequence. POST /v4/sequences. Creates an empty sequence — the container that holds sequence emails. After creating the shell, use Create a sequence email to populate it. Only `name` is required. Every other field has a sensible default: Kit fills in the account's default sending address, a daily send schedule, and the account time zone — and any of these can be tuned later via Update a sequence. Two behavioural toggles worth flagging up front. `repeat` controls whether a subscriber can re-enter the sequence: by default a subscriber receives the emails once and is marked complete, but with `repeat: true`, re-adding the same subscriber via a Visual Automation, Rule, Bulk Action, or Import resets their position to the start. Filters and exclusions still apply across restarts. `hold` (evergreen) keeps subscribers active in the sequence after they've received every published email — useful when you plan to add more emails later. Without `hold`, subscribers transition to Completed and won't pick up future additions. `exclude_subscriber_sources` lets you exclude subscribers acquired via specific tags, sequences, forms, or segments — they'll skip this sequence entirely. For end-user context, see the help articles on creating and sending a sequence, restarting a sequence, and holding subscribers in evergreen sequences.
kit_post_v4_sequences_by_sequence_id_emailsWRITECreate a sequence email. POST /v4/sequences/{sequence_id}/emails. Adds a single email to a sequence. Each sequence email represents one step subscribers receive on their journey through the sequence — its `position` determines order, and `delay_value` / `delay_unit` / `send_days` determine when it fires relative to either the previous email or the subscriber's entry. `subject`, `delay_value`, and `delay_unit` are required. Day-based emails (`delay_unit: "days"`) follow the parent sequence's `send_days` and `send_hour`; their per-email `send_days` (e.g. `["monday", "wednesday"]`) overrides the sequence schedule for that one email. Hour-based emails (`delay_unit: "hours"`) ignore the sequence schedule and fire once the delay elapses — Kit checks for hour-delayed sends every 15 minutes — and always return `send_days` as `null`. New emails are created in draft (`published: false`) so they don't go out until you flip the flag. `position` is auto-assigned to the end of the sequence if omitted. `content` accepts HTML and can embed snippets with `{{ snippet.<key> }}` — see Create a snippet — which Kit resolves at send time, so editing a snippet later updates every email referencing it without a re-publish. Note: only the first email in a sequence can be an immediate send (`delay_value: 0` with `delay_unit: "days"`). Subsequent emails need a positive delay. Warning: publishing an immediate first email, or inserting a new email at a `position` earlier than where existing subscribers sit, processes those subscribers and triggers a send right away. Plan around active sequences carefully. For end-user context on how creators build sequences in the Kit UI, see the help article on creating and sending a sequence.
kit_post_v4_sequences_by_sequence_id_subscribersWRITEAdd subscriber to sequence by email address. POST /v4/sequences/{sequence_id}/subscribers. The subscriber being added to the sequence must already exist. Subscribers can be created using the "Create a subscriber" endpoint.
kit_post_v4_sequences_by_sequence_id_subscribers_by_idWRITEAdd subscriber to sequence. POST /v4/sequences/{sequence_id}/subscribers/{id}. The subscriber being added to the sequence must already exist. Subscribers can be created using the "Create a subscriber" endpoint.
kit_post_v4_snippetsWRITECreate a snippet. POST /v4/snippets. Snippets are reusable pieces of email content you can drop into a broadcast or sequence email using Liquid: `{{ snippet.key }}`. Update the snippet once and every email that references it picks up the new content on next send. There are two `snippet_type`s. `inline` snippets store plain-text content (with Liquid variable support like `{{ subscriber.first_name }}`) in the `content` field. `block` snippets store rich-text HTML — text, lists, images, buttons — in `document_attributes.value_html`. A snippet's type is fixed at creation: it cannot be changed via Update a snippet. The response includes a `key` field. That's the identifier you use in Liquid — for example, a snippet returned with `"key": "welcome-message"` is referenced inside a broadcast as `{{ snippet.welcome-message }}`. Keys are derived from the snippet name on creation. Note: the API rejects circular references — a snippet cannot reference itself, directly or transitively — with a `422` validation error. For end-user context on how creators build and edit snippets in the Kit UI, see the help articles on content snippets and code snippets for custom templates.
kit_post_v4_subscribersWRITECreate a subscriber. POST /v4/subscribers. Behaves as an upsert. If a subscriber with the provided email address does not exist, it creates one with the specified first name and state. If a subscriber with the provided email address already exists, it updates the first name. If you include a custom field key that does not exist on your account, the request returns an error. Use List custom fields to retrieve existing keys, or Create a custom field to add new fields before setting them for subscribers. <strong>NOTE:</strong> Updating the subscriber state with this endpoint is not supported at this time. <strong>NOTE:</strong> We support creating/updating a maximum of 140 custom fields at a time.
kit_post_v4_subscribers_by_id_unsubscribeWRITEUnsubscribe subscriber. POST /v4/subscribers/{id}/unsubscribe. Unsubscribes the subscriber from all future emails, moving them to the `cancelled` state. Returns `204 No Content` on success. The subscriber record, history, and tags are retained — they are not deleted from the account. Note: this is the API equivalent of the subscriber clicking unsubscribe. Treat it as consent-revoking and effectively permanent — only re-subscribe someone with their explicit permission.
kit_post_v4_subscribers_by_subscriber_id_locationWRITEPin a subscriber's location. POST /v4/subscribers/{subscriber_id}/location. Pins an explicit location to a subscriber, overriding any location Kit has inferred from open events. Provide `city`, `state_province`, `country_code` (ISO 3166-1 alpha-2, required), `latitude`, `longitude`, and `timezone` (IANA timezone name, e.g. `America/Denver`). Returns the subscriber's `id` and the pinned `location` on success. If the subscriber already has a pinned location this replaces it. To replace the values on an existing pin, use Update a subscriber's pinned location (PATCH); to remove the pin, use Delete a subscriber's location. The pinned location is returned on Get a subscriber. Returns `404` when the subscriber is not found, `422` when a required field is missing or invalid.
kit_post_v4_subscribers_filterWRITEFilter subscribers by engagement, sign-up date, state, and tags. POST /v4/subscribers/filter. Searches your subscriber list with compound conditions: email engagement (opens, clicks, sends, deliveries — with count thresholds and date ranges), sign-up date, subscriber state, and tags. Every condition in the `all` array must match (AND logic). Use `counting_mode` to control how engagement thresholds are tallied — `raw` (default) counts every event, `unique_email` counts distinct emails — and the `include` array to embed extra fields (tags, stats, custom fields, location, attribution, canceled_at) on each returned subscriber. Data retention: Starting October 15, 2026, email stats (opens, clicks, sends, bounces, and unsubscribes) are available via the API for the last 5 years — engagement-condition date bounds are clamped to that window, and a `stats` include range outside it returns a `400` error. See Email data retention for the full policy.
kit_post_v4_tagsWRITECreate a tag. POST /v4/tags. Creates a tag with the given `name`. Creation is idempotent on name (matched case-insensitively): if a tag with that name already exists, the endpoint returns `200` with the existing tag instead of creating a duplicate (a newly created tag returns `201`). Returns `422` if `name` is missing. To create many tags in one request, use Bulk create tags.
kit_post_v4_tags_by_tag_id_subscribersWRITETag a subscriber by email address. POST /v4/tags/{tag_id}/subscribers. The subscriber being tagged must already exist. Subscribers can be created using the "Create a subscriber" endpoint.
kit_post_v4_tags_by_tag_id_subscribers_by_idWRITETag a subscriber. POST /v4/tags/{tag_id}/subscribers/{id}. The subscriber being tagged must already exist. Subscribers can be created using the "Create a subscriber" endpoint.
kit_post_v4_webhook_endpointsWRITECreate a webhook endpoint. POST /v4/webhook_endpoints. Registers a URL to receive deliveries for the event types listed in `events`. The `url` must be publicly reachable over HTTP(S) — private, internal, and loopback addresses are rejected. The response is the only time the signing `secret` is returned in plaintext. Store it securely; you need it to verify the signature on every delivery. If you lose it, rotate the secret to get a new one. Note: This resource supersedes the legacy Webhooks resource. Legacy webhooks keep working, but new integrations should be built here — see getting started for a full walkthrough.
kit_post_v4_webhook_endpoints_by_id_revoke_previous_secretWRITERevoke the previous webhook endpoint secret. POST /v4/webhook_endpoints/{id}/revoke_previous_secret. Closes a rotation's overlap window early: the previous secret stops verifying immediately, leaving only the current secret valid. Call this once you've fully switched to the new secret, rather than waiting for `previous_secret_expires_at` to pass. Subsequent deliveries are signed with the current secret only, so the `X-Kit-Signature` header goes back to carrying a single `v1` entry.
kit_post_v4_webhook_endpoints_by_id_rotate_secretWRITERotate a webhook endpoint secret. POST /v4/webhook_endpoints/{id}/rotate_secret. Generates a new signing secret for the endpoint and returns it. The response is the only time the new `secret` appears in plaintext — store it securely. To avoid dropping deliveries mid-rollout, the previous secret keeps verifying until the overlap window closes (the endpoint's `previous_secret_expires_at`). During the window every delivery is signed with both secrets, so the `X-Kit-Signature` header carries two `v1` entries — see secret rotation. Rotating again while a previous rotation's window is still open returns `409`; pass `force: true` to rotate anyway and immediately expire the older secret. Once you've switched over, you can close the window early with Revoke the previous secret.
kit_post_v4_webhooksWRITECreate a webhook. POST /v4/webhooks. Legacy: This creates a previous-generation webhook. Existing webhooks keep working and there are no plans to remove them, but new integrations should use Create a webhook endpoint instead — one endpoint subscribes to many event types and gets signed, automatically retried deliveries. See the webhooks guides. Available event types: - `subscriber.subscriber_activate` - `subscriber.subscriber_unsubscribe` - `subscriber.subscriber_bounce` - `subscriber.subscriber_complain` - `subscriber.form_subscribe`, required parameter `form_id` [Integer] - `subscriber.course_subscribe`, required parameter `sequence_id` [Integer] - `subscriber.course_complete`, required parameter `sequence_id` [Integer] - `subscriber.link_click`, required parameter `initiator_value` [String] as a link URL - `subscriber.product_purchase`, required parameter `product_id` [Integer] - `subscriber.tag_add`, required parameter `tag_id` [Integer] - `subscriber.tag_remove`, required parameter `tag_id` [Integer] - `purchase.purchase_create` - `custom_field.field_created` - `custom_field.field_deleted` - `custom_field.field_value_updated`, required parameter `custom_field_id` [Integer]
kit_put_v4_account_colorsWRITEUpdate colors. PUT /v4/account/colors. Replaces the account's brand color palette with the provided array of up to 10 hex codes and returns the updated list. Note: this overwrites the entire palette rather than appending — include every color you want to keep. Returns `422` when a color code is invalid.
kit_put_v4_broadcasts_by_idWRITEUpdate a broadcast. PUT /v4/broadcasts/{id}. Update an existing broadcast. Continue to draft or schedule to send a broadcast to all or a subset of your subscribers. To save a draft, set `public` to false. To schedule the broadcast for sending, set `public` to true and provide `send_at`. Scheduled broadcasts should contain a subject and your content, at a minimum. We currently support targeting your subscribers based on segment or tag ids.
kit_put_v4_custom_fields_by_idWRITEUpdate a custom field. PUT /v4/custom_fields/{id}. Updates a custom field label (see Create a custom field for more information on labels). Note that the key will change but the name remains the same when the label is updated. <strong>Warning: </strong>An update to a custom field will break all of the liquid personalization tags in emails that reference it - e.g. if you update a `Zip_Code` custom field to `Post_Code`, all liquid tags referencing `{{ subscriber.Zip_Code }}` would no longer work and need to be replaced with `{{ subscriber.Post_Code }}`.
kit_put_v4_sequences_by_idWRITEUpdate a sequence. PUT /v4/sequences/{id}. Updates any sequence settings — `name`, `email_address`, schedule (`send_days`, `send_hour`, `time_zone`), `email_template_id`, `exclude_subscriber_sources`, or the `active` / `repeat` / `hold` flags. Only fields included in the request body change; everything else is preserved. Some changes have user-visible side effects on subscribers already in the sequence: Note: flipping `active` from `false` to `true` resumes delivery for queued subscribers. Flipping it back to `false` pauses the sequence — subscribers stay in their current position but no new emails are sent until it's reactivated. Note: changing the schedule (`send_days`, `send_hour`, or `time_zone`) only affects future sends. It does not retroactively reschedule emails already queued for delivery. Warning: turning off `repeat` while subscribers are mid-sequence does not stop them from finishing — but they won't be re-eligible to start over after completing. See Create a sequence for the full sequence model and what each field controls.
kit_put_v4_sequences_by_sequence_id_emails_by_idWRITEUpdate a sequence email. PUT /v4/sequences/{sequence_id}/emails/{id}. Updates any field on a sequence email — `subject`, `preview_text`, `content`, `delay_value`, `delay_unit`, `send_days`, `position`, `email_template_id`, or `published`. Only fields included in the request body change; everything else is preserved. Note: pass `send_days: null` to revert a per-email schedule override and inherit the parent sequence's `send_days` again. The response will then return all 7 days, indicating no per-email restriction. Warning: sending `send_days` on an email with `delay_unit: "hours"` returns `422` — `send_days` only applies to day-based emails. Warning: changing `position` while subscribers are actively progressing through the sequence can cause emails to be sent out of order or skipped. The same caution applies to flipping `published` on a `position: 0` email — it triggers Kit to process all queued subscribers for that email. For the sequence-email model and how `delay_unit` and `send_days` interact, see Create a sequence email.
kit_put_v4_snippets_by_idWRITEUpdate a snippet. PUT /v4/snippets/{id}. Rename a snippet, replace its body, or archive/restore it. Updates apply on the next send of any email that references the snippet via `{{ snippet.key }}` — there's no per-email versioning, so a content change ripples to every broadcast or sequence email using that key. The request body must match the existing `snippet_type`. For an `inline` snippet, send `content` (and optionally `name`, `archived`). For a `block` snippet, send `document_attributes.value_html` (and optionally `name`, `archived`). Pass `archived: true` to archive, `false` to restore. Warning: `snippet_type` is immutable. Sending a different value, or sending the body shape for the wrong type, returns a `422` with `snippet_type cannot be changed`. See Create a snippet for the full snippet model and how `key` ties into Liquid.
kit_put_v4_subscribers_by_idWRITEUpdate a subscriber. PUT /v4/subscribers/{id}. If you include a custom field key that does not exist on your account, the request returns an error. Use List custom fields to retrieve existing keys, or Create a custom field to add new fields before setting them for subscribers. <strong>NOTE:</strong> We support creating/updating a maximum of 140 custom fields at a time.
kit_put_v4_tags_by_idWRITEUpdate tag name. PUT /v4/tags/{id}. Renames a tag. The tag keeps its `id` and all of its subscribers — only the `name` changes, and the new name is reflected everywhere the tag is used (forms, automations, filters). Returns `422` when the new name is blank or already used by another tag in the account (names are unique, case-insensitive).
Put Kit behind one governed endpoint.
Same permissions, same audit trail, whatever else you connect next.