---
title: "Update customers (v4)"
method: POST
path: "/api/v1/business/customers/update-v4"
tags: ["business"]
---

# Update customers (v4)

`POST /api/v1/business/customers/update-v4`

## Request

- Base URL: `https://point11.ai`
- URL: `https://point11.ai/api/v1/business/customers/update-v4`
- Auth: OAuth 2 (authorization code, authorization URL `https://auth.point11.ai/oauth2/authorize`, token URL `https://auth.point11.ai/oauth2/token`)

Save a member's edits to one customer as its next version; expectedVersion is the version you read (STALE_WRITE if it moved). Fields use the customer model's keys, as business_customers_get_v4's editable fields: a category takes an option id from there or null (else INVALID_INPUT); an open category (occupation, audience, channel, market, buyer role, job, trigger type) may be words in newValues (that option, else a new one for the profile). Age, household income and company size take { value, band }; a changed value sets its band unless the edit does. A changed business employer clears company size and annual revenue unless set. The audience after the edit decides the buyer type: a value it lacks (a consumer's company size, an organization buyer's household) is INVALID_INPUT (CUSTOMER_VERSION_ATTRIBUTE_NOT_APPLICABLE, naming field and buyerType), and a buyer-type change clears such values. A place is geocoded with Mapbox (kept as written if not found). A CRM-connected customer's edited fields are pinned against CRM updates. The customer reruns once on the new version in each live campaign, at once or, while a conversation of theirs runs there, once the campaign can take it (an edit before then joins it, rerun.joinedRequestIds; one after reruns again), as the campaign's run for its current period: its scheduled run, not yet admitted, waits and does not run again; work admitted earlier keeps its version. Paused or held campaigns, one-time studies, Bursts, Pulse, Point11's own campaigns and products Billing would not rerun are skipped (rerun.skipped, Billing's sentence in message); the edit saves regardless.

## Headers

- `Point11-Organization` string, uuid
- `Idempotency-Key` string, uuid, required

## Request body

- BusinessCustomersUpdateV4Request
  - `id` string, uuid, required: The customer's id
  - `expectedVersion` integer, required: The customer version you read (currentVersion.version)
  - `values` object, required: Only the fields to change, by the customer model's keys; an empty string or null clears a field. A category takes one id from its options in business_customers_get_v4. Age, household income and company size take { value, band }: a changed value also sets its band unless the same edit sets the band. Household takes { adults, children, pets }.
    - `name` string, nullable
    - `gender` string, nullable
    - `age` object
      - `value` string, nullable
      - `band` string, nullable
    - `language` string, nullable
    - `location` object, nullable
      - `countryCode` string, nullable, required
      - `subdivisionCode` string, nullable, required
      - `locality` string, nullable, required
      - `postalCode` string, nullable, required
      - `country` string, nullable, required
      - `subdivision` string, nullable, required
    - `market` string, nullable
    - `areaType` string, nullable
    - `education` string, nullable
    - `lifeStage` string, nullable
    - `household` object, nullable
      - `adults` integer, nullable, required
      - `children` integer, nullable, required
      - `pets` integer, nullable, required
    - `householdIncome` object
      - `value` string, nullable
      - `band` string, nullable
    - `jobTitle` string, nullable
    - `occupation` string, nullable
    - `seniority` string, nullable
    - `employer` string, nullable
    - `yearsInRole` string, nullable
    - `companySize` object
      - `value` string, nullable
      - `band` string, nullable
    - `annualRevenue` string, nullable
    - `audience` string, nullable
    - `product` string, nullable
    - `channel` string, nullable
    - `buyerRole` string, nullable
    - `stakeholders` string, nullable
    - `intentStage` string, nullable
    - `budget` string, nullable
    - `constraints` string, nullable
    - `job` string, nullable
    - `situation` string, nullable
    - `triggerType` string, nullable
    - `trigger` string, nullable
    - `functionalNeed` string, nullable
    - `emotionalNeed` string, nullable
    - `socialNeed` string, nullable
    - `desiredOutcome` string, nullable
  - `newValues` object: An open category (occupation, audience, channel, market, buyerRole, job, triggerType) stated in words: the option with that label, else a new value added for this customer's business profile. A field named here is not also in values.
    - `market` string
    - `occupation` string
    - `audience` string
    - `product` string
    - `channel` string
    - `buyerRole` string
    - `job` string
    - `triggerType` string

## Response `200`

Success.

- BusinessCustomersUpdateV4Response
  - `id` string, uuid, required
  - `customerVersionId` string, uuid, required
  - `version` integer, required
  - `pinnedFields` string[], required
  - `derivedFields` string[], required: Fields set by rule rather than by the edit: a band computed from its changed value, a business customer's company size and annual revenue cleared with a changed employer (its situation stays), and each attribute the customer's new buyer type does not have cleared with a changed audience
  - `newValues` object[], required: The option each of the edit's newValues set
    - `field` 'market' | 'occupation' | 'audience' | 'product' | 'channel' | 'buyerRole' | 'job' | 'triggerType', required
    - `id` string, uuid, required
    - `label` string, required
    - `created` boolean, required: This edit added the value; false when an option already had that label
  - `place` union, required: The changed place's Mapbox check: placed (its ISO subdivision code and coordinates were set), unresolved (the place is kept as written, without coordinates) or unchecked (nothing finer than a country); null when the place did not change
    - object
      - `outcome` 'placed', required
      - `subdivisionCode` string, nullable, required
    - object
      - `outcome` 'unresolved', required
      - `reason` string, required
    - object
      - `outcome` 'unchecked', required
  - `rerun` object, required: The edit's rerun of the customer in its live campaigns
    - `requestId` string, uuid, required: The edit's rerun request; list its reruns with campaigns_member_reruns_list_v1
    - `joinedRequestIds` string[], required: Earlier edits' rerun requests this edit joined: a customer whose rerun an earlier edit asked for has not started yet reruns once, on its newest version, and that rerun is listed under the earlier request, not requestId
    - `customers` integer, required: Customers that rerun
    - `campaigns` integer, required: Campaigns they rerun in
    - `skipped` object[], required: Campaigns an edited customer is in that take no rerun
      - `campaignId` string, uuid, required
      - `product` 'discovery' | 'research' | 'experience', required
      - `reason` string, required: Why it takes no rerun: campaign_paused, campaign_held, one_time, pulse, point11_campaign or not_started; or Billing's refusal reason (such as no_subscription, billing_suspended or interaction_unavailable) when Billing would not admit the product's reruns
      - `message` string, nullable, required: Billing's own sentence for the member when Billing refused the product's reruns; null for every other reason
      - `paymentDisputeHold` true: Present when Billing refused because the account is on hold while a payment dispute is reviewed: offer support, not a payment method update

## Other responses

- `400`: The input, query, or Idempotency-Key is invalid.
- `401`: The bearer is missing, expired, or not accepted.
- `402`: Billing refused the write: the code names the reason and `details.reason` carries it.
- `403`: The credential lacks the operation's scope or role, or the operation needs a different door.
- `404`: The resource or organization does not exist for this caller.
- `405`: This path takes another HTTP method, named in `Allow`.
- `409`: The request conflicts with current state or with prior use of its Idempotency-Key.
- `413`: The request, or the answer it asks for, is too large; narrow it.
- `429`: The credential's rate budget is spent; retry after `Retry-After` seconds.
- `500`: An unexpected server failure; retry later. Only `request_id` identifies it.
- `503`: A dependency is temporarily unavailable; retry after `Retry-After` seconds.
- `default`: Another status a product answers for its own refusal (for example `415` for an unsupported attachment); branch on `code`.

---

[API](https://skmtc.dev/point11/apis/point11-api.md) · [All operations](https://skmtc.dev/point11/apis/point11-api/llms.txt) · [OpenAPI document](https://skmtc.dev/point11/apis/point11-api/revisions/36a84c7aca11?raw)
