# Adjust a customer's account balance

URL: https://docs.sparklayer.io/developers/api/customers/adjust-a-customers-account-balance
Operation: `POST /api/v2/customers/{lookupBy}/{identifier}/credit` (operationId `createCustomerCreditAdjustment`)
OpenAPI spec: https://docs.sparklayer.io/openapi/customers.yaml

Adds an entry to the customer's account credit ledger, which makes up the balance shown in [My Account](https://docs.sparklayer.io/help/storefront/interfaces/my-account.md) when you use [pay on account](https://docs.sparklayer.io/help/ordering/credit-net-terms-and-invoicing.md), and returns `201`. A positive `amount` increases what the customer owes, and a negative one reduces it. What it means depends on `type`:

- **`order`** and **`transaction`**: an amount to add, such as an order total or a payment (negative).
- **`opening_balance`**: the balance on `date`. From then on, the balance is this amount plus the `order` and `transaction` entries dated on or after `date`. Earlier entries, and `default` entries, stop counting.
- **`default`**: the balance you want now. SparkLayer records the difference from the current balance. Once the customer has an opening balance, `default` entries don't change it.

Always send `date`: without it, the entry is dated 1 January 0001.

The Purchasing API already adds an `order` entry for each order you send, and a `transaction` entry for each purchase transaction with `apply_to_balance`. Don't add them again here.

`POST /api/v2/customers/{lookupBy}/{identifier}/credit`

**Base URLs:** `https://app.sparklayer.io` (Live), `https://test.app.sparklayer.io` (Test)

**Authentication:** send `Authorization: Bearer <access_token>` and `Site-Id: <site id>` with every request. Get the token from [Get an access token](https://docs.sparklayer.io/developers/api/core/get-an-access-token.md); see [Authentication](https://docs.sparklayer.io/developers/authentication.md).

### Example request

```bash
curl -X POST "https://app.sparklayer.io/api/v2/customers/platform/7843024560291/credit" \
  -H "Authorization: Bearer $SPARKLAYER_TOKEN" \
  -H "Site-Id: $SPARKLAYER_SITE_ID" \
  -H "Content-Type: application/json" \
  -d '{
  "id": "<id>",
  "amount": 0,
  "type": "opening_balance",
  "purchase_id": "<purchase_id>",
  "section_id": "<section_id>",
  "date": "2024-01-01T00:00:00Z",
  "customer_id": "<customer_id>",
  "info": "<info>"
}'
```

Set `SPARKLAYER_TOKEN` to an access token and `SPARKLAYER_SITE_ID` to your Site ID. For the test environment, use `https://test.app.sparklayer.io`.

### Path parameters

| Name | Type | Required | Description |
| --- | --- | --- | --- |
| `lookupBy` | "sparklayer" \| "platform" \| "email" | Yes | What `identifier` is: `sparklayer` (the customer's SparkLayer ID), `platform` (their ID on your eCommerce platform) or `email` (their email address). Example: `platform` |
| `identifier` | string | Yes | The customer's ID or email address, of the kind set by `lookupBy`. SparkLayer IDs are UUIDs; legacy `cu_` IDs work too, except for shopping lists and favourites. Email lookups are exact and case-sensitive: URL-encode the address, with `+` as `%2B`. Example: `7843024560291` |

### Header parameters

| Name | Type | Required | Description |
| --- | --- | --- | --- |
| `Site-Id` | string | Yes | Your SparkLayer Site ID, from Settings > API in the SparkLayer Dashboard. Length: min 1. Example: `jones-climbing` |

### Request body (`application/json`) (optional)

| Name | Type | Required | Description |
| --- | --- | --- | --- |
| `id` | string \| null | | SparkLayer Account Credit ID |
| `amount` | number | Yes | Positive increases what the customer owes, negative reduces it. For `opening_balance` and `default`, it is the balance itself. Max 1000000000. |
| `type` | "opening_balance" \| "order" \| "transaction" \| "default" | Yes | |
| `purchase_id` | string | | Optionally associate this credit to a specific purchase via it's Spark ID |
| `section_id` | string | | Optionally associate this credit to a specific section via it's Spark ID |
| `date` | string (date-time) | | When the entry takes effect, which can be in the past. Always send it: without it, the entry is dated 1 January 0001. |
| `customer_id` | string | | Leave it out: the customer comes from the URL. |
| `info` | string | | JSON encoded extra info related to the adjustment |

```json
{
  "id": "<id>",
  "amount": 0,
  "type": "opening_balance",
  "purchase_id": "<purchase_id>",
  "section_id": "<section_id>",
  "date": "2024-01-01T00:00:00Z",
  "customer_id": "<customer_id>",
  "info": "<info>"
}
```

### Responses

#### 201: Credit Adjustment created

#### Other statuses: An error. The body describes the problem: see [Errors](https://docs.sparklayer.io/developers/errors.md).

`application/problem+json`: the standard error body (below).

### Error body

Error responses with a body use this RFC 7807 problem details object. See [Errors](https://docs.sparklayer.io/developers/errors.md) for every status code and which errors to retry.

| Name | Type | Required | Description |
| --- | --- | --- | --- |
| `detail` | string | | Human-readable summary of the error |
| `status` | integer | | HTTP Status code returned from API |
| `title` | string | | Machine-readable error code |
| `type` | string | | |
| `errors` | object[] | | |
| `errors[].code` | string | | A machine-readable error message |
| `errors[].property` | string | | The offending property, with the full path |
| `errors[].field` | string | | The offending property, stripped of the path |
| `errors[].message` | string | | A human-readable summary of the error |

```json
{
  "detail": "Data Validation Failed",
  "status": 400,
  "title": "invalid-api-request-contents",
  "type": "https://hub.sparklayer.io/tech-docs",
  "errors": [
    {
      "code": "unique-constraint-violation",
      "property": "purchase_identifiers.sparklayer",
      "field": "sparklayer",
      "message": "Each stock level must have a unique stock location and sku combination"
    }
  ]
}
```
