# Agentic Commerce Protocol Checkout Guide
Source: https://docs.stateset.com/agentic-commerce/agentic-commerce-checkout-guide
Learn how to use the Agentic Commerce Protocol to create, update, and complete checkout flows.
# Build the Agentic Commerce Protocol checkout endpoints
Learn about the Agentic Commerce Protocol specification.
You can use the Agentic Commerce Protocol (ACP) to enable AI agents to manage commerce transactions between buyers and sellers. This specification defines the methods and data structures for creating, updating, and completing checkout flows.
You can find examples for REST integrations below.
ACP is the transaction layer of StateSet’s agentic commerce offering. For the full conversation‑to‑fulfillment architecture, see Stateset iCommerce Architecture.
## Create a Checkout Session
You can create a new Checkout Session with buyer details, line items, and shipping information.
### Request
Specify the parameters required for your request.
| Parameter | Type | Description |
| ------------------------ | ----------------- | ------------------------------------------- |
| **items** | `array` | Array of items you can purchase. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **fulfillment\_address** | `hash` (optional) | Address where the order will ship. |
**Example request:**
```json theme={null}
POST /checkouts
{
"items": [
{
"id": "item_123",
"quantity": 2
}
],
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"fulfillment_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
}
}
```
### Response
The response returns the current state of the checkout from the seller.
| Parameter | Type | Description |
| --------------------- | ----------------- | ------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the Checkout Session. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **payment\_provider** | `hash` (optional) | Payment provider configuration and supported payment methods. |
| **status** | `string` | Current status of the checkout process. (Required) |
Possible values: `not_ready_for_payment` | `ready_for_payment` | `completed` | `canceled` | `in_progress` |
\| **currency** | `string` | Three-letter ISO currency code, in lowercase. (Required) |
\| **line\_items** | `array` | Array of line items in the checkout process. (Required) |
\| **fulfillment\_address** | `hash` (optional) | Address where the order will ship. |
\| **fulfillment\_options** | `array` | Available shipping and fulfillment options. (Required) |
\| **fulfillment\_option\_id** | `string` (optional) | ID of the currently selected fulfillment option. |
\| **totals** | `array` | Overview of charges and discounts. (Required) |
\| **messages** | `array` | Array of messages or notifications related to the checkout process. (Required) |
\| **links** | `array` | Array of links related to the checkout process. (Required) |
**Example response:**
```json theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"payment_provider": {
"provider": "stripe",
"supported_payment_methods": ["card"]
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 2
},
"base_amount": 2000,
"discount": 0,
"total": 2000,
"subtotal": 2000,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 2000
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 2250
}
],
"messages": [],
"links": []
}
```
## Retrieve a Checkout object
To retrieve an existing Checkout Session using its ID, make a request to the appropriate API endpoint with the ID included in the request.
### Request
Specify the parameters required for your request.
| Parameter | Type | Description |
| --------- | -------- | ------------------------------------------------------ |
| **id** | `string` | Unique identifier for the checkout process. (Required) |
**Example request:**
```json theme={null}
GET /checkouts/:id
```
### Response
The response returns the current state of the checkout from the seller.
| Parameter | Type | Description |
| --------------------- | ----------------- | ------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the checkout session. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **payment\_provider** | `hash` (optional) | Payment provider configuration and supported payment methods. |
| **status** | `string` | Current status of the checkout process. (Required) |
Possible values: `not_ready_for_payment` | `ready_for_payment` | `completed` | `canceled` | `in_progress` |
\| **currency** | `string` | Three-letter ISO currency code, in lowercase. (Required) |
\| **line\_items** | `array` | Array of line items in the checkout process. (Required) |
\| **fulfillment\_address** | `hash` (optional) | Address where the order will ship. |
\| **fulfillment\_options** | `array` | Available shipping and fulfillment options. (Required) |
\| **fulfillment\_option\_id** | `string` (optional) | ID of the currently selected fulfillment option. |
\| **totals** | `array` | Overview of charges and discounts. (Required) |
\| **messages** | `array` | Array of messages or notifications related to the checkout process. (Required) |
\| **links** | `array` | Array of links related to the checkout process. (Required) |
**Example response:**
```json theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"payment_provider": {
"provider": "stripe",
"supported_payment_methods": ["card"]
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 2
},
"base_amount": 2000,
"discount": 0,
"total": 2000,
"subtotal": 2000,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 2000
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 2250
}
],
"messages": [],
"links": []
}
```
## Update a Checkout Session
You can update an existing Checkout Session by modifying line items, shipping address, or fulfillment options.
### Request
Specify the parameters required for your request.
| Parameter | Type | Description |
| --------------------------- | ------------------- | ------------------------------------------------------ |
| **id** | `string` | Unique identifier for the checkout process. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **items** | `array` (optional) | Updated array of items to be purchased. |
| **fulfillment\_address** | `hash` (optional) | Updated fulfillment address. |
| **fulfillment\_option\_id** | `string` (optional) | Identifier for the selected fulfillment option. |
**Example request:**
```json theme={null}
PUT /checkouts/:id
{
"items": [
{
"id": "item_123",
"quantity": 3
},
{
"id": "item_456",
"quantity": 1
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_option_id": "shipping_fast"
}
```
### Response
The response returns the current state of the checkout from the seller.
| Parameter | Type | Description |
| --------------------- | ----------------- | ------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the Checkout Session. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **payment\_provider** | `hash` (optional) | Payment provider configuration and supported payment methods. |
| **status** | `string` | Current status of the checkout process. (Required) |
Possible values: `not_ready_for_payment` | `ready_for_payment` | `completed` | `canceled` | `in_progress` |
\| **currency** | `string` | Three-letter ISO currency code, in lowercase. (Required) |
\| **line\_items** | `array` | Array of line items in the checkout process. (Required) |
\| **fulfillment\_address** | `hash` (optional) | Address where the order will ship. |
\| **fulfillment\_options** | `array` | Available shipping and fulfillment options. (Required) |
\| **fulfillment\_option\_id** | `string` (optional) | ID of the currently selected fulfillment option. |
\| **totals** | `array` | Overview of charges and discounts. (Required) |
\| **messages** | `array` | Array of messages or notifications related to the checkout process. (Required) |
\| **links** | `array` | Array of links related to the checkout process. (Required) |
**Example response:**
```json theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"payment_provider": {
"provider": "stripe",
"supported_payment_methods": ["card"]
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 3
},
"base_amount": 3000,
"discount": 0,
"total": 3000,
"subtotal": 3000,
"tax": 0
},
{
"id": "item_456",
"item": {
"id": "item_456",
"quantity": 1
},
"base_amount": 500,
"discount": 0,
"total": 500,
"subtotal": 500,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 3500
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 3750
}
],
"messages": [],
"links": []
}
```
## Complete a Checkout
You can complete the checkout process by processing the payment and creating an order.
### Request
Specify the parameters required for your request.
| Parameter | Type | Description |
| ----------------- | ----------------- | ----------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the checkout process. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **payment\_data** | `hash` | Payment method details for processing the transaction. (Required) |
**Example request:**
```json theme={null}
POST /checkouts/:id/complete
{
"payment_data": {
"token": "spt_123",
"provider": "stripe",
"billing_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
}
}
}
```
### Response
The response returns the current state of the checkout from the seller.
| Parameter | Type | Description |
| --------------------- | ----------------- | ------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the Checkout Session. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **payment\_provider** | `hash` (optional) | Payment provider configuration and supported payment methods. |
| **status** | `string` | Current status of the checkout process. (Required) |
Possible values: `not_ready_for_payment` | `ready_for_payment` | `completed` | `canceled` | `in_progress` |
\| **currency** | `string` | Three-letter ISO currency code, in lowercase. (Required) |
\| **line\_items** | `array` | Array of line items in the checkout process. (Required) |
\| **fulfillment\_address** | `hash` (optional) | Address where the order will ship. |
\| **fulfillment\_options** | `array` | Available shipping and fulfillment options. (Required) |
\| **fulfillment\_option\_id** | `string` (optional) | ID of the currently selected fulfillment option. |
\| **totals** | `array` | Overview of charges and discounts. (Required) |
\| **messages** | `array` | Array of messages or notifications related to the checkout process. (Required) |
\| **links** | `array` | Array of links related to the checkout process. (Required) |
**Example response:**
```json theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"status": "completed",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 3
},
"base_amount": 3000,
"discount": 0,
"total": 3000,
"subtotal": 3000,
"tax": 0
},
{
"id": "item_456",
"item": {
"id": "item_456",
"quantity": 1
},
"base_amount": 500,
"discount": 0,
"total": 500,
"subtotal": 500,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 3500
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 3750
}
],
"messages": [],
"links": []
}
```
## Cancel a Checkout
You can cancel an existing Checkout Session if necessary.
### Request
Specify the parameters required for your request.
| Parameter | Type | Description |
| --------- | -------- | ------------------------------------------------------ |
| **id** | `string` | Unique identifier for the checkout process. (Required) |
**Example request:**
```json theme={null}
POST /checkouts/:id/cancel
{}
```
### Response
The response returns the current state of the checkout from the seller.
| Parameter | Type | Description |
| --------------------- | ----------------- | ------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the Checkout Session. (Required) |
| **buyer** | `hash` (optional) | Information about the buyer. |
| **payment\_provider** | `hash` (optional) | Payment provider configuration and supported payment methods. |
| **status** | `string` | Current status of the checkout process. (Required) |
Possible values: `not_ready_for_payment` | `ready_for_payment` | `completed` | `canceled` | `in_progress` |
\| **currency** | `string` | Three-letter ISO currency code, in lowercase. (Required) |
\| **line\_items** | `array` | Array of line items in the checkout process. (Required) |
\| **fulfillment\_address** | `hash` (optional) | Address where the order will ship. |
\| **fulfillment\_options** | `array` | Available shipping and fulfillment options. (Required) |
\| **fulfillment\_option\_id** | `string` (optional) | ID of the currently selected fulfillment option. |
\| **totals** | `array` | Overview of charges and discounts. (Required) |
\| **messages** | `array` | Array of messages or notifications related to the checkout process. (Required) |
\| **links** | `array` | Array of links related to the checkout process. (Required) |
**Example response:**
```json theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"status": "canceled",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 3
},
"base_amount": 3000,
"discount": 0,
"total": 3000,
"subtotal": 3000,
"tax": 0
},
{
"id": "item_456",
"item": {
"id": "item_456",
"quantity": 1
},
"base_amount": 500,
"discount": 0,
"total": 500,
"subtotal": 500,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 3500
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 3750
}
],
"messages": [
{
"type": "info",
"content_type": "plain",
"content": "Checkout cancelled: Customer changed their mind"
}
],
"links": []
}
```
## Data structures
This section outlines the data structures involved in the checkout process.
### Buyer
The buyer is an individual who initiates the purchase.
| Parameter | Type | Description |
| ----------------- | ------------------- | --------------------------------------- |
| **first\_name** | `string` | The first name of the buyer. (Required) |
| **last\_name** | `string` | The last name of the buyer. (Required) |
| **email** | `string` | The email of the buyer. **Required** |
| **phone\_number** | `string` (optional) | The phone number of the buyer. |
### Item
The Item is a product or service that the buyer requests to purchase, along with its quantity.
| Parameter | Type | Description |
| ------------ | --------- | ---------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the item. (Required) |
| **quantity** | `integer` | The requested quantity of the item for this checkout. (Required) |
### LineItem
The LineItem includes provides about the item added to the checkout, including the amount.
| Parameter | Type | Description |
| ---------------- | --------- | ------------------------------------------------ |
| **id** | `string` | Unique identifier for the line item. (Required) |
| **item** | `hash` | The item details. (Required) |
| **base\_amount** | `integer` | The base amount of the line item. (Required) |
| **discount** | `integer` | The discount amount of the line item. (Required) |
| **total** | `integer` | The total amount of the line item. (Required) |
| **subtotal** | `integer` | The subtotal amount of the line item. (Required) |
| **tax** | `integer` | The tax amount of the line item. (Required) |
### Address
The Address provides the buyer’s shipping or billing address.
| Parameter | Type | Description |
| ---------------- | ------------------- | ------------------------------------------------------------------ |
| **name** | `string` | Name of the person to whom the items are fulfilled. (Required) |
| **line\_one** | `string` | Address line 1 (e.g., street, PO Box, or company name). (Required) |
| **line\_two** | `string` (optional) | Address line 2 (e.g., apartment, suite, unit, or building). |
| **city** | `string` | City, district, suburb, town, or village. (Required) |
| **state** | `string` | State, county, province, or region. (Required) |
| **country** | `string` | Two-letter country code (ISO 3166-1 alpha-2). (Required) |
| **postal\_code** | `string` | ZIP or postal code. (Required) |
### PaymentData
The PaymentData provides the buyer’s payment details, including the tokenized value and the payment provider.
| Parameter | Type | Description |
| -------------------- | ----------------- | ------------------------------------------------------------- |
| **token** | `string` | The secure reference to a payment credential. (Required) |
| **provider** | `string` | The payment provider that the payment data is for. (Required) |
| **billing\_address** | `hash` (optional) | Billing address for the payment method. |
### Total
The Total provides a summary of the overall total.
| Parameter | Type | Description |
| --------- | ------ | ----------------------------- |
| **type** | `enum` | The type of total. (Required) |
Possible values: `items_base_amount` | `items_discount` | `subtotal` | `discount` | `fulfillment` | `tax` | `fee` | `total` |
\| **display\_text** | `string` | The display text for the total. (Required) |
\| **amount** | `integer` | The amount of the total. (Required) |
### FulfillmentOption
Fulfillment options are either shipping or digital. See [ShippingFulfillmentOption](https://docs.stripe.com/agentic-commerce/protocol/specification.md#shipping-fulfillment-option) and [DigitalFulfillmentOption](https://docs.stripe.com/agentic-commerce/protocol/specification.md#digital-fulfillment-option) for specific implementations.
### ShippingFulfillmentOption
The ShippingFulfillmentOption defines the parameters for shipping fulfillment options, including the carrier information and delivery times.
| Parameter | Type | Description |
| --------- | ------ | ------------------------------------------ |
| **type** | `enum` | The type of fulfillment option. (Required) |
Possible values: `shipping` |
\| **id** | `string` | Unique identifier for the shipping fulfillment option. (Required) |
\| **title** | `string` | The title of the shipping fulfillment option. (Required) |
\| **subtitle** | `string` (optional) | The subtitle of the shipping fulfillment option. |
\| **carrier** | `string` (optional) | The carrier of the shipping fulfillment option. |
\| **earliest\_delivery\_time** | `string` (optional) | The earliest delivery time of the shipping fulfillment option (ISO 8601 format). |
\| **latest\_delivery\_time** | `string` (optional) | The latest delivery time of the shipping fulfillment option (ISO 8601 format). |
\| **subtotal** | `integer` | The subtotal of the shipping fulfillment option. (Required) |
\| **tax** | `integer` | The tax of the shipping fulfillment option. (Required) |
\| **total** | `integer` | The total of the shipping fulfillment option. (Required) |
### DigitalFulfillmentOption
The DigitalFulfillmentOption defines the parameters for digital fulfillment options, including the title and pricing information.
| Parameter | Type | Description |
| --------- | ------ | ------------------------------------------ |
| **type** | `enum` | The type of fulfillment option. (Required) |
Possible values: `digital` |
\| **id** | `string` | Unique identifier for the digital fulfillment option. (Required) |
\| **title** | `string` | The title of the digital fulfillment option. (Required) |
\| **subtitle** | `string` (optional) | The subtitle of the digital fulfillment option. |
\| **subtotal** | `integer` | The subtotal of the digital fulfillment option. (Required) |
\| **tax** | `integer` | The tax of the digital fulfillment option. (Required) |
\| **total** | `integer` | The total of the digital fulfillment option. (Required) |
### PaymentProvider
The PaymentProvider defines the seller’s supported payment provider and available methods.
| Parameter | Type | Description |
| ------------ | -------- | ----------------------------------------- |
| **provider** | `string` | The seller’s payment provider. (Required) |
Possible values: `stripe` |
\| **supported\_payment\_methods** | `array` | The payment methods allowed by the seller. (Required)
Possible values: `card` |
### Message
Messages are either informational or error messages.
#### InfoMessage
The InfoMessage represents informational messages, detailing the type and content.
| Parameter | Type | Description |
| --------- | ------ | --------------------------------------- |
| **type** | `enum` | String value representing message type. |
Possible values: `info` |
\| **param** | `string` (optional) | RFC 9535 JSONPath to the component of the Checkout Session that the message references. |
\| **content\_type** | `enum` (optional) | The type of content of the message.
Possible values: `plain` | `markdown` |
\| **content** | `string` | The content of the message. |
#### ErrorMessage
The ErrorMessage represents error messages, detailing the type and code.
| Parameter | Type | Description |
| --------- | ------ | --------------------------------------- |
| **type** | `enum` | String value representing message type. |
Possible values: `error` |
\| **code** | `enum` | The code of the error.
Possible values: `missing` | `invalid` | `out_of_stock` | `payment_declined` | `requires_sign_in` | `requires_3ds` |
\| **param** | `string` (optional) | RFC 9535 JSONPath to the component of the Checkout Session that the message references. |
\| **content\_type** | `enum` (optional) | The type of content of the message.
Possible values: `plain` | `markdown` |
\| **content** | `string` | The content of the message. |
### Error
The Error defines the parameters related to errors occurring during the checkout process.
| Parameter | Type | Description |
| --------- | ------ | ----------------------------- |
| **type** | `enum` | The type of error. (Required) |
Possible values: `invalid_request` | `request_not_idempotent` | `processing_error` | `service_unavailable` |
\| **code** | `string` | The implementation-defined error code. (Required) |
\| **message** | `string` | The message of the error. (Required) |
\| **param** | `string` (optional) | RFC 9535 JSONPath to the component of the Checkout Session that the message references. |
### Link
The Link defines the parameters for links related to policies and agreements.
| Parameter | Type | Description |
| --------- | ------ | ------------------------------------------------------ |
| **type** | `enum` | String value representing the type of link. (Required) |
Possible values: `terms_of_use` | `privacy_policy` | `seller_shop_policies` |
\| **url** | `string` | The URL of the link. (Required) |
### Order
The Order provides the result of the checkout process and offers details to the buyer for order lookup.
| Parameter | Type | Description |
| ------------------------- | -------- | ---------------------------------------------------------------------------- |
| **id** | `string` | Unique identifier for the order. (Required) |
| **checkout\_session\_id** | `string` | Reference to the Checkout Session that the order originated from. (Required) |
| **permalink\_url** | `string` | The permalink URL for the order. (Required) |
### Event
The Event defines the parameters for events related to order creation and updates.
| Parameter | Type | Description |
| --------- | ------ | ----------------------------- |
| **type** | `enum` | The type of event. (Required) |
Possible values: `order_created` | `order_updated` |
\| **data** | `hash` | Event data containing order information. (Required) |
### OrderEventData
The OrderEventData includes data related to order events.
| Parameter | Type | Description |
| ------------------------- | -------- | --------------------------------------------------------------------------------------------------------------------------- |
| **type** | `string` | The string value represents the type of event data. For order data, use the value `order`. (Required) |
| **checkout\_session\_id** | `string` | ID that identifies the Checkout Session that created this order. (Required) |
| **permalink\_url** | `string` | The URL points to the order. Customers can visit this URL and provide their email address to view order details. (Required) |
| **status** | `enum` | String representing the latest status of the order. (Required) |
Possible values: `created` | `manual_review` | `confirmed` | `canceled` | `shipped` | `fulfilled` |
\| **refunds** | `array` | List of refunds that have been issued for the order. (Required) |
### Refund
The Refund defines the parameters for managing refunds associated with completed orders.
| Parameter | Type | Description |
| --------- | ------ | ------------------------------ |
| **type** | `enum` | The type of refund. (Required) |
Possible values: `store_credit` | `original_payment` |
\| **amount** | `integer` | The amount of the refund. (Required) |
# Create Account
Source: https://docs.stateset.com/api-reference/accounts/create
POST https://api.stateset.com/v1/accounts
This endpoint creates a new account
### Body
This is the id of the account.
This is the account name of the account.
This is the account notes of the account.
This is the account subtype of the account.
This is the account type of the account.
This is the account owner of the account.
This is the account source of the account.
This is the annual revenue of the account.
This is the avatar of the account.
This is the billing city of the account.
This is the billing country of the account.
This is the billing latitude of the account.
This is the billing longitude of the account.
This is the billing state of the account.
This is the billing street of the account.
This is the created at of the account.
This is the description of the account.
This is the employees of the account.
This is the fax of the account.
This is the industry of the account.
This is the is active of the account.
This is the is public of the account.
### Response
This is the id of the account.
This is the account name of the account.
This is the account notes of the account.
This is the account subtype of the account.
This is the account type of the account.
This is the account owner of the account.
This is the account source of the account.
This is the annual revenue of the account.
This is the avatar of the account.
This is the billing city of the account.
This is the billing country of the account.
This is the billing latitude of the account.
This is the billing longitude of the account.
This is the billing state of the account.
This is the billing street of the account.
This is the created at of the account.
This is the description of the account.
This is the employees of the account.
This is the fax of the account.
This is the industry of the account.
This is the is active of the account.
This is the is public of the account.
This is the last modified by of the account.
This is the number of employees of the account.
This is the ownership of the account.
This is the phone of the account.
This is the rating of the account.
This is the shipping city of the account.
This is the shipping country of the account.
This is the shipping latitude of the account.
This is the shipping longitude of the account.
This is the shipping state of the account.
This is the shipping street of the account.
This is the sic code of the account.
This is the ticker symbol of the account.
This is the website of the account.
This is the year started of the account.
This is the zip code of the account.
This is the created by of the account.
This is the updated by of the account.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/account' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```graphQL graphQL theme={null}
mutation (
$account: accounts_insert_input!
) {
insert_accounts (
objects: [$account]
) {
returning {
id{
accountName
accountType
rating
industry
contacts {
id
firstName
lastName
email
phone
controller
processor
account_id
}
}
}
}
```
```javascript Node.js theme={null}
const acccount = await stateset.account.create({
accountName: 'Example 1',
accountType: 'Example 1',
rating: 'Example 1',
industry: 'Example 1',
});
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Delete Account
Source: https://docs.stateset.com/api-reference/accounts/delete
DELETE https://api.return.com/v1/accounts
This endpoint deletes an existing account.
### Body
The ID provided in the data tab may be used to identify the account
### Response
The ID provided in the data tab may be used to identify the account
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/accounts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```graphQL GraphQL theme={null}
mutation {
delete_accounts(
where: { id: { _eq: "" } }
) {
affected_rows
}
}
```
```javascript Node.js theme={null}
var deleted = await stateset.accounts.del({
"1"
});
```
```json Response theme={null}
{
{
"data": {
"delete_accounts": {
"affected_rows": 1
}
}
}
}
```
# Get Account
Source: https://docs.stateset.com/api-reference/accounts/get
GET https://api.stateset.com/v1/accounts/:id
This endpoint gets or creates a new account.
### Body
This is the id of the account.
### Response
This is the id of the account.
This is the account name of the account.
This is the account notes of the account.
This is the account subtype of the account.
This is the account type of the account.
This is the account owner of the account.
This is the account source of the account.
This is the annual revenue of the account.
This is the avatar of the account.
This is the billing city of the account.
This is the billing country of the account.
This is the billing latitude of the account.
This is the billing longitude of the account.
This is the billing state of the account.
This is the billing street of the account.
This is the created at of the account.
This is the description of the account.
This is the employees of the account.
This is the fax of the account.
This is the industry of the account.
This is the is active of the account.
This is the is public of the account.
This is the last modified by of the account.
This is the number of employees of the account.
This is the ownership of the account.
This is the phone of the account.
This is the rating of the account.
This is the shipping city of the account.
This is the shipping country of the account.
This is the shipping latitude of the account.
This is the shipping longitude of the account.
This is the shipping state of the account.
This is the shipping street of the account.
This is the sic code of the account.
This is the ticker symbol of the account.
This is the website of the account.
This is the year started of the account.
This is the zip code of the account.
This is the created by of the account.
This is the updated by of the account.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/customer' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"id": "1",
"accountName": "Test Account",
"accountNotes": "Test Account Notes",
"accountSubtype": "Test Account Subtype",
"accountType": "Test Account Type",
"account_owner": "Test Account Owner",
"account_source": "Test Account Source",
"annualRevenue": "Test Annual Revenue",
"avatar": "Test Avatar",
"billingCity": "Test Billing City",
"billingCountry": "Test Billing Country",
"billingLatitude": "Test Billing Latitude",
"billingLongitude": "Test Billing Longitude",
"billingState": "Test Billing State",
"billingStreet": "Test Billing Street",
"created_at": "2021-04-27T15:00:00.000000Z",
"description": "Test Description",
"employees": "Test Employees",
"fax": "Test Fax",
"industry": "Test Industry",
"is_active": true,
"is_public": true,
"last_modified_by": "Test Last Modified By",
"numberOfEmployees": "Test Number Of Employees",
"ownership": "Test Ownership",
"phone": "Test Phone",
"rating": "Test Rating",
"shippingCity": "Test Shipping City",
"shippingCountry": "Test Shipping Country",
"shippingLatitude": "Test Shipping Latitude",
"shippingLongitude": "Test Shipping Longitude",
"shippingState": "Test Shipping State",
"shippingStreet": "Test Shipping Street",
"sicCode": "Test Sic Code",
"tickerSymbol": "Test Ticker Symbol",
"website": "Test Website",
"yearStarted": "Test Year Started",
"zipCode": "Test Zip Code",
"created_by": "Test Created By",
"updated_by": "Test Updated By"
}
]
}
```
# Accounts
Accounts describes the general data about the accounts in Stateset.
## The account object
#### Attributes
| Name | Type | Description |
| ------------------ | --------- | -------------------------------------------------------- |
| id | Text | Unique identifier for the account |
| accountName | Text | Name of the account |
| accountNotes | Text | Notes or additional information about the account |
| accountSubtype | Text | Subtype or specific category of the account |
| accountType | Text | Type or general category of the account |
| account\_owner | Text | Owner or responsible person for the account |
| account\_source | Text | Source or origin of the account |
| annualRevenue | Text | Annual revenue associated with the account |
| avatar | Text | URL or path to the account's avatar image |
| billingCity | Text | City of the billing address |
| billingCountry | Text | Country of the billing address |
| billingLatitude | Text | Latitude coordinate of the billing address |
| billingLongitude | Text | Longitude coordinate of the billing address |
| billingState | Text | State or province of the billing address |
| billingStreet | Text | Street address of the billing address |
| created\_at | Date/Time | Date and time when the account was created |
| description | Text | Description or additional details about the account |
| employees | Text | Number or range of employees associated with the account |
| fax | Text | Fax number of the account |
| industry | Text | Industry or sector of the account |
| is\_active | Boolean | Indicates whether the account is currently active |
| is\_public | Boolean | Indicates whether the account is public or private |
| last\_modified\_by | Text | Last person who modified the account |
| numberOfEmployees | Text | Number of employees associated with the account |
| ownership | Text | Ownership type or structure of the account |
| parentAccount | Text | Parent account associated with the account |
| phone | Text | Phone number of the account |
| rating | Text | Rating or evaluation of the account |
| shippingCity | Text | City of the shipping address |
| shippingCountry | Text | Country of the shipping address |
| shippingLatitude | Text | Latitude coordinate of the shipping address |
| shippingLongitude | Text | Longitude coordinate of the shipping address |
| shippingState | Text | State or province of the shipping address |
| shippingStreet | Text | Street address of the shipping address |
| stockTicker | Text | Stock ticker symbol associated with the account |
| website | Text | Website URL of the account |
| yearStarted | Text | Year the account was started or established |
# List Accounts
Source: https://docs.stateset.com/api-reference/accounts/list
GET https://api.stateset.com/v1/accounts/list
This endpoint gets or creates a new account.
### Body
This is the limit of the accounts.
This is the offset of the accounts.
This is the order direction of the accounts.
### Response
This is the id of the account.
This is the account name of the account.
This is the account notes of the account.
This is the account subtype of the account.
This is the account type of the account.
This is the account owner of the account.
This is the account source of the account.
This is the annual revenue of the account.
This is the avatar of the account.
This is the billing city of the account.
This is the billing country of the account.
This is the billing latitude of the account.
This is the billing longitude of the account.
This is the billing state of the account.
This is the billing street of the account.
This is the created at of the account.
This is the description of the account.
This is the employees of the account.
This is the fax of the account.
This is the industry of the account.
This is the is active of the account.
This is the is public of the account.
This is the last modified by of the account.
This is the number of employees of the account.
This is the ownership of the account.
This is the phone of the account.
This is the rating of the account.
This is the shipping city of the account.
This is the shipping country of the account.
This is the shipping latitude of the account.
This is the shipping longitude of the account.
This is the shipping state of the account.
This is the shipping street of the account.
This is the sic code of the account.
This is the ticker symbol of the account.
This is the website of the account.
This is the year started of the account.
This is the zip code of the account.
This is the created by of the account.
This is the updated by of the account.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/accounts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "desc"
}'
```
```json Response theme={null}
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"id": "1",
"accountName": "Test Account",
"accountNotes": "Test Account Notes",
"accountSubtype": "Test Account Subtype",
"accountType": "Test Account Type",
"account_owner": "Test Account Owner",
"account_source": "Test Account Source",
"annualRevenue": "Test Annual Revenue",
"avatar": "Test Avatar",
"billingCity": "Test Billing City",
"billingCountry": "Test Billing Country",
"billingLatitude": "Test Billing Latitude",
"billingLongitude": "Test Billing Longitude",
"billingState": "Test Billing State",
"billingStreet": "Test Billing Street",
"created_at": "2021-04-27T15:00:00.000000Z",
"description": "Test Description",
"employees": "Test Employees",
"fax": "Test Fax",
"industry": "Test Industry",
"is_active": true,
"is_public": true,
"last_modified_by": "Test Last Modified By",
"numberOfEmployees": "Test Number Of Employees",
"ownership": "Test Ownership",
"phone": "Test Phone",
"rating": "Test Rating",
"shippingCity": "Test Shipping City",
"shippingCountry": "Test Shipping Country",
"shippingLatitude": "Test Shipping Latitude",
"shippingLongitude": "Test Shipping Longitude",
"shippingState": "Test Shipping State",
"shippingStreet": "Test Shipping Street",
"sicCode": "Test Sic Code",
"tickerSymbol": "Test Ticker Symbol",
"website": "Test Website",
"yearStarted": "Test Year Started",
"zipCode": "Test Zip Code",
"created_by": "Test Created By",
"updated_by": "Test Updated By"
}
]
}
```
# Accounts
Accounts describes the general data about the accounts in Stateset.
## The account object
#### Attributes
| Name | Type | Description |
| ------------------ | --------- | -------------------------------------------------------- |
| id | Text | Unique identifier for the account |
| accountName | Text | Name of the account |
| accountNotes | Text | Notes or additional information about the account |
| accountSubtype | Text | Subtype or specific category of the account |
| accountType | Text | Type or general category of the account |
| account\_owner | Text | Owner or responsible person for the account |
| account\_source | Text | Source or origin of the account |
| annualRevenue | Text | Annual revenue associated with the account |
| avatar | Text | URL or path to the account's avatar image |
| billingCity | Text | City of the billing address |
| billingCountry | Text | Country of the billing address |
| billingLatitude | Text | Latitude coordinate of the billing address |
| billingLongitude | Text | Longitude coordinate of the billing address |
| billingState | Text | State or province of the billing address |
| billingStreet | Text | Street address of the billing address |
| created\_at | Date/Time | Date and time when the account was created |
| description | Text | Description or additional details about the account |
| employees | Text | Number or range of employees associated with the account |
| fax | Text | Fax number of the account |
| industry | Text | Industry or sector of the account |
| is\_active | Boolean | Indicates whether the account is currently active |
| is\_public | Boolean | Indicates whether the account is public or private |
| last\_modified\_by | Text | Last person who modified the account |
| numberOfEmployees | Text | Number of employees associated with the account |
| ownership | Text | Ownership type or structure of the account |
| parentAccount | Text | Parent account associated with the account |
| phone | Text | Phone number of the account |
| rating | Text | Rating or evaluation of the account |
| shippingCity | Text | City of the shipping address |
| shippingCountry | Text | Country of the shipping address |
| shippingLatitude | Text | Latitude coordinate of the shipping address |
| shippingLongitude | Text | Longitude coordinate of the shipping address |
| shippingState | Text | State or province of the shipping address |
| shippingStreet | Text | Street address of the shipping address |
| stockTicker | Text | Stock ticker symbol associated with the account |
| website | Text | Website URL of the account |
| yearStarted | Text | Year the account was started or established |
# Update Account
Source: https://docs.stateset.com/api-reference/accounts/update
PUT https://api.stateset.com/v1/accounts
This endpoint updates an existing account.
### Body
This is the id of the account.
This is the account name of the account.
This is the account notes of the account.
This is the account subtype of the account.
This is the account type of the account.
This is the account owner of the account.
This is the account source of the account.
This is the annual revenue of the account.
This is the avatar of the account.
This is the billing city of the account.
This is the billing country of the account.
This is the billing latitude of the account.
This is the billing longitude of the account.
This is the billing state of the account.
This is the billing street of the account.
This is the created at of the account.
This is the description of the account.
This is the employees of the account.
This is the fax of the account.
This is the industry of the account.
This is the is active of the account.
This is the is public of the account.
### Response
This is the id of the account.
This is the account name of the account.
This is the account notes of the account.
This is the account subtype of the account.
This is the account type of the account.
This is the account owner of the account.
This is the account source of the account.
This is the annual revenue of the account.
This is the avatar of the account.
This is the billing city of the account.
This is the billing country of the account.
This is the billing latitude of the account.
This is the billing longitude of the account.
This is the billing state of the account.
This is the billing street of the account.
This is the created at of the account.
This is the description of the account.
This is the employees of the account.
This is the fax of the account.
This is the industry of the account.
This is the is active of the account.
This is the is public of the account.
This is the last modified by of the account.
This is the number of employees of the account.
This is the ownership of the account.
This is the phone of the account.
This is the rating of the account.
This is the shipping city of the account.
This is the shipping country of the account.
This is the shipping latitude of the account.
This is the shipping longitude of the account.
This is the shipping state of the account.
This is the shipping street of the account.
This is the sic code of the account.
This is the ticker symbol of the account.
This is the website of the account.
This is the year started of the account.
This is the zip code of the account.
This is the created by of the account.
This is the updated by of the account.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/account' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 113,
"token": "",
"name": "ok",
"provided_id": "6"
}
}
```
# API Design Guidelines
Source: https://docs.stateset.com/api-reference/api-design-guidelines
Best practices and standards for StateSet API development
# StateSet API Design Guidelines
This document outlines the design principles, patterns, and best practices for the StateSet API. Following these guidelines ensures consistency, usability, and maintainability across all API endpoints.
## Core Principles
### 1. RESTful Design
* Use standard HTTP methods appropriately:
* `GET` for retrieving resources
* `POST` for creating resources
* `PUT/PATCH` for updating resources
* `DELETE` for removing resources
### 2. Resource-Oriented URLs
```
Good:
GET /v1/orders
GET /v1/orders/{id}
POST /v1/orders
PUT /v1/orders/{id}
DELETE /v1/orders/{id}
Avoid:
GET /v1/getOrders
POST /v1/createOrder
POST /v1/orders/update
```
### 3. Consistent Naming Conventions
* Use lowercase with hyphens for URLs: `/v1/work-orders`
* Use camelCase for JSON properties: `firstName`, `createdAt`
* Use snake\_case for query parameters: `created_after`, `sort_by`
* Pluralize collection endpoints: `/orders` not `/order`
## Request Standards
### Headers
Required headers for all requests:
```http theme={null}
Authorization: Bearer YOUR_API_KEY
Content-Type: application/json
Accept: application/json
```
Optional headers:
```http theme={null}
X-API-Version: 2024-01-01
X-Idempotency-Key: unique-request-id
X-Request-ID: client-generated-id
Accept-Language: en-US
```
### Query Parameters
#### Pagination
All list endpoints must support:
```
GET /v1/orders?limit=20&offset=0
GET /v1/orders?limit=20&cursor=eyJpZCI6MTAwfQ==
```
Default pagination:
* `limit`: 20 (max: 100)
* `offset`: 0
#### Filtering
Use consistent filter patterns:
```
# Exact match
GET /v1/orders?status=shipped
# Multiple values
GET /v1/orders?status_in=shipped,delivered
# Range queries
GET /v1/orders?created_after=2024-01-01T00:00:00Z
GET /v1/orders?created_before=2024-12-31T23:59:59Z
GET /v1/orders?amount_gte=10000
GET /v1/orders?amount_lte=50000
# Search
GET /v1/orders?search=john+doe
GET /v1/orders?customer_email=john@example.com
```
#### Sorting
```
GET /v1/orders?sort=created_at&order=desc
GET /v1/orders?sort=-created_at # Alternative: prefix with - for desc
```
### Request Body
#### Required Fields
Clearly mark required fields in documentation:
```json theme={null}
{
"customer": { // required
"email": "...", // required
"name": "..." // optional
}
}
```
#### Nested Objects
Use nested objects for logical grouping:
```json theme={null}
{
"customer": {
"email": "john@example.com",
"first_name": "John",
"last_name": "Doe"
},
"shipping_address": {
"line1": "123 Main St",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
}
}
```
## Response Standards
### Success Responses
#### Single Resource
```json theme={null}
{
"id": "ord_1a2b3c4d",
"object": "order",
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T10:30:00Z",
// ... resource fields
}
```
#### Collection
```json theme={null}
{
"object": "list",
"data": [
{
"id": "ord_1a2b3c4d",
"object": "order",
// ... resource fields
}
],
"has_more": true,
"total_count": 150,
"url": "/v1/orders"
}
```
#### With Metadata
```json theme={null}
{
"data": {
"id": "ord_1a2b3c4d",
"object": "order",
// ... resource fields
},
"meta": {
"request_id": "req_xyz789",
"version": "v1",
"timestamp": "2024-01-15T10:30:00Z"
}
}
```
### Error Responses
#### Standard Error Format
```json theme={null}
{
"error": {
"type": "validation_error",
"code": "VALIDATION_ERROR",
"message": "Invalid request parameters",
"details": {
"field_errors": {
"email": "Invalid email format",
"quantity": "Must be a positive integer"
}
},
"documentation_url": "https://docs.stateset.com/errors/VALIDATION_ERROR",
"request_id": "req_xyz789"
}
}
```
#### HTTP Status Codes
| Status | Usage |
| ------------------------- | --------------------------------------- |
| 200 OK | Successful GET, PUT, PATCH |
| 201 Created | Successful POST creating resource |
| 202 Accepted | Request accepted for async processing |
| 204 No Content | Successful DELETE |
| 400 Bad Request | Invalid request parameters |
| 401 Unauthorized | Missing or invalid authentication |
| 403 Forbidden | Valid auth but insufficient permissions |
| 404 Not Found | Resource doesn't exist |
| 409 Conflict | Resource conflict (e.g., duplicate) |
| 422 Unprocessable Entity | Validation errors |
| 429 Too Many Requests | Rate limit exceeded |
| 500 Internal Server Error | Server error |
| 503 Service Unavailable | Temporary unavailability |
## Data Types and Formats
### Timestamps
Always use ISO 8601 format with timezone:
```json theme={null}
{
"created_at": "2024-01-15T10:30:00Z",
"scheduled_for": "2024-01-20T14:00:00-08:00"
}
```
### Money/Currency
Store monetary values in smallest currency unit (cents):
```json theme={null}
{
"amount": 1999, // $19.99
"currency": "USD"
}
```
### Phone Numbers
Use E.164 format:
```json theme={null}
{
"phone": "+14155551234"
}
```
### Countries and States
Use ISO standards:
* Countries: ISO 3166-1 alpha-2 (US, CA, GB)
* States/Provinces: ISO 3166-2 (CA-ON, US-NY)
```json theme={null}
{
"country": "US",
"state": "CA"
}
```
## Versioning
### URL Versioning
Primary versioning method:
```
https://api.stateset.com/v1/orders
https://api.stateset.com/v2/orders
```
### Header Versioning
For minor versions:
```http theme={null}
X-API-Version: 2024-01-01
```
### Deprecation Process
1. Announce deprecation with 90-day notice
2. Add deprecation headers:
```http theme={null}
Sunset: Sat, 31 Dec 2024 23:59:59 GMT
Deprecation: true
Link: ; rel="successor-version"
```
3. Maintain deprecated version for minimum 12 months
## Idempotency
### Implementation
Support idempotency for all POST, PUT, PATCH requests:
```http theme={null}
POST /v1/orders
X-Idempotency-Key: unique-request-id-123
```
Response includes:
```http theme={null}
X-Idempotency-Key: unique-request-id-123
X-Idempotent-Replayed: true
```
## Webhooks
### Event Naming
Use dot notation for event types:
```
order.created
order.updated
order.shipped
order.delivered
return.requested
return.approved
payment.succeeded
payment.failed
```
### Webhook Payload
```json theme={null}
{
"id": "evt_1a2b3c4d",
"type": "order.created",
"created_at": "2024-01-15T10:30:00Z",
"data": {
"object": {
"id": "ord_xyz789",
"object": "order",
// ... full object
},
"previous_attributes": {
// ... for update events
}
},
"request": {
"id": "req_abc123",
"idempotency_key": "unique-key-123"
}
}
```
### Security
Always include signature header:
```http theme={null}
X-StateSet-Signature: sha256=3f3b3c4d...
```
## Performance Guidelines
### Response Times
Target response times:
* Simple reads: \< 200ms
* Complex queries: \< 500ms
* Writes: \< 1000ms
### Payload Size
* Limit response size to 1MB
* Use pagination for large collections
* Support field filtering:
```
GET /v1/orders?fields=id,status,customer
```
### Caching
Include cache headers:
```http theme={null}
Cache-Control: private, max-age=300
ETag: "33a64df551"
Last-Modified: Wed, 15 Jan 2024 10:30:00 GMT
```
## GraphQL Guidelines
### Query Naming
```graphql theme={null}
# Good
query GetOrder($id: ID!) {
order(id: $id) {
id
status
}
}
# Avoid
query fetchOrderData($id: ID!) {
getOrderById(id: $id) {
id
status
}
}
```
### Mutations
```graphql theme={null}
mutation CreateOrder($input: OrderCreateInput!) {
orderCreate(input: $input) {
order {
id
status
}
userErrors {
field
message
}
}
}
```
### Error Handling
Return errors in userErrors field:
```json theme={null}
{
"data": {
"orderCreate": {
"order": null,
"userErrors": [
{
"field": "customer.email",
"message": "Email is required"
}
]
}
}
}
```
## Testing
### Test Coverage
All endpoints must include:
* Success path tests
* Error handling tests
* Edge case tests
* Performance tests
### Example Test Cases
```javascript theme={null}
describe('POST /v1/orders', () => {
test('creates order successfully', async () => {
const response = await api.post('/v1/orders', validOrderData);
expect(response.status).toBe(201);
expect(response.body.object).toBe('order');
});
test('returns 400 for invalid data', async () => {
const response = await api.post('/v1/orders', invalidOrderData);
expect(response.status).toBe(400);
expect(response.body.error.code).toBe('VALIDATION_ERROR');
});
test('handles idempotency', async () => {
const key = 'test-idempotency-key';
const response1 = await api.post('/v1/orders', data, {
headers: { 'X-Idempotency-Key': key }
});
const response2 = await api.post('/v1/orders', data, {
headers: { 'X-Idempotency-Key': key }
});
expect(response1.body.id).toBe(response2.body.id);
});
});
```
## Documentation Requirements
Every endpoint must document:
1. **Description**: Clear explanation of what the endpoint does
2. **Authentication**: Required permissions
3. **Parameters**: All query params, headers, and body fields
4. **Response**: Success and error response formats
5. **Examples**: Working code examples in multiple languages
6. **Rate Limits**: Specific limits if different from defaults
7. **Webhooks**: Related webhook events
8. **See Also**: Links to related endpoints
## Security Best Practices
1. **Always use HTTPS**
2. **Validate all inputs** - Never trust client data
3. **Rate limit all endpoints**
4. **Log security events** - Failed auth, permission denials
5. **Sanitize outputs** - Prevent XSS in responses
6. **Use secure headers**:
```http theme={null}
X-Content-Type-Options: nosniff
X-Frame-Options: DENY
X-XSS-Protection: 1; mode=block
```
## Monitoring and Observability
Include correlation IDs in all requests:
```http theme={null}
X-Request-ID: client-generated-uuid
X-Correlation-ID: server-generated-uuid
```
Log format:
```json theme={null}
{
"timestamp": "2024-01-15T10:30:00Z",
"request_id": "req_abc123",
"method": "POST",
"path": "/v1/orders",
"status": 201,
"duration_ms": 145,
"user_id": "usr_xyz789"
}
```
## Change Management
1. **Backwards Compatibility**: Never break existing integrations
2. **Additive Changes**: New fields are safe to add
3. **Deprecation Notices**: Minimum 90 days
4. **Migration Guides**: Provide clear upgrade paths
5. **Changelog**: Maintain detailed changelog
## Contact
For API design questions or to propose changes to these guidelines:
* Email: [api-team@stateset.com](mailto:api-team@stateset.com)
* Slack: #api-design
* GitHub: stateset/api-guidelines
# Cancel ASN
Source: https://docs.stateset.com/api-reference/asns/cancel
POST https://api.stateset.com/v1/asns/:id/cancel
Cancel an ASN that hasn't been received yet
ASNs can only be cancelled if they haven't been received. Once receiving has started, the ASN cannot be cancelled.
### Path Parameters
The unique identifier of the ASN to cancel
### Request Body
Reason for cancellation
User ID or email of the person cancelling the ASN
Whether to notify the supplier of the cancellation (default: true)
Additional notes about the cancellation
### Response
ASN ID
ASN number
Updated status (will be "cancelled")
Timestamp of cancellation
User who cancelled the ASN
Reason for cancellation
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/asns/asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"reason": "Supplier notified of production delay",
"cancelled_by": "purchasing@company.com",
"notify_supplier": true,
"notes": "Shipment delayed by 2 weeks due to material shortage. Will create new ASN when shipment is ready."
}'
```
```graphQL GraphQL theme={null}
mutation CancelASN($id: ID!, $input: CancelASNInput!) {
cancelASN(id: $id, input: $input) {
id
asn_number
status
cancelled_at
cancelled_by
cancellation_reason
purchase_order_id
}
}
```
```javascript Node.js theme={null}
const result = await stateset.asns.cancel(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
reason: 'Supplier notified of production delay',
cancelled_by: 'purchasing@company.com',
notify_supplier: true,
notes: 'Shipment delayed by 2 weeks due to material shortage'
}
);
```
```python Python theme={null}
result = stateset.asns.cancel(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
reason='Supplier notified of production delay',
cancelled_by='purchasing@company.com',
notify_supplier=True,
notes='Shipment delayed by 2 weeks due to material shortage'
)
```
```json Response theme={null}
{
"id": "asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "asn",
"asn_number": "ASN-2024-00001",
"status": "cancelled",
"cancelled_at": "2024-01-16T10:30:00Z",
"cancelled_by": "purchasing@company.com",
"cancellation_reason": "Supplier notified of production delay",
"purchase_order_id": "po_123456789",
"supplier_id": "sup_abc123",
"items_affected": [
{
"sku": "WBH-001",
"quantity": 500
},
{
"sku": "USB-C-001",
"quantity": 1000
}
],
"notifications_sent": [
{
"type": "email",
"recipient": "supplier@audiotech.com",
"sent_at": "2024-01-16T10:31:00Z"
},
{
"type": "webhook",
"endpoint": "warehouse_system",
"sent_at": "2024-01-16T10:31:00Z"
}
],
"notes": "Shipment delayed by 2 weeks due to material shortage. Will create new ASN when shipment is ready."
}
```
### Error Responses
Error object when cancellation fails
Type of error (e.g., "invalid\_status", "already\_received")
Human-readable error message
Error code for programmatic handling
```json Error Response theme={null}
{
"error": {
"type": "invalid_status",
"message": "Cannot cancel ASN that has already been received",
"code": "ASN_ALREADY_RECEIVED"
}
}
```
# Create ASN
Source: https://docs.stateset.com/api-reference/asns/create
POST https://api.stateset.com/v1/asns
Create an Advanced Shipping Notice for inbound shipments
This endpoint creates a new ASN (Advanced Shipping Notice) to notify about incoming shipments from suppliers. ASNs help warehouses prepare for receiving inventory and automate the receiving process.
## Authentication
This endpoint requires a valid API key with `asns:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
The purchase order ID this ASN is associated with
The supplier ID sending the shipment
Date when the shipment was sent (ISO 8601)
Expected delivery date at warehouse (ISO 8601)
Destination warehouse ID
Shipping and tracking information
Carrier name (e.g., "UPS", "FedEx", "DHL")
Primary tracking number
Service level (e.g., "Ground", "Express", "2-Day")
Additional tracking numbers for multi-package shipments
Array of items being shipped
Product SKU
Quantity being shipped
Original quantity ordered (for reference)
Cost per unit
Cost in cents
ISO 4217 currency code
Lot or batch number for tracking
Expiration date for perishable items (ISO 8601)
Array of serial numbers for serialized items
Packaging and palletization information
Total number of packages/boxes
Total number of pallets
Total shipment weight
Weight value
Weight unit (e.g., "lb", "kg")
Detailed package information
Unique package identifier
Package type (e.g., "box", "pallet", "crate")
Package dimensions
Package weight
Items contained in this package
Related shipping documents
Document type (e.g., "packing\_list", "bill\_of\_lading", "commercial\_invoice")
Document reference number
URL to access the document
Additional notes or special instructions for receiving
Additional custom fields as key-value pairs
### Response
Unique ASN identifier
Always "asn"
System-generated ASN number
ASN status: "pending", "in\_transit", "delivered", "received", "cancelled"
ISO 8601 timestamp of creation
ISO 8601 timestamp of last update
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/asns' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"purchase_order_id": "po_123456789",
"supplier_id": "sup_abc123",
"shipment_date": "2024-01-15T14:00:00Z",
"expected_arrival_date": "2024-01-18T10:00:00Z",
"warehouse_id": "wh_001",
"tracking_info": {
"carrier": "UPS",
"tracking_number": "1Z999AA10123456784",
"service_type": "Ground"
},
"items": [
{
"sku": "WBH-001",
"quantity_shipped": 500,
"quantity_ordered": 500,
"unit_cost": {
"amount": 7500,
"currency": "USD"
},
"lot_number": "LOT-2024-001"
},
{
"sku": "USB-C-001",
"quantity_shipped": 1000,
"quantity_ordered": 1000,
"unit_cost": {
"amount": 450,
"currency": "USD"
},
"lot_number": "LOT-2024-002"
}
],
"packaging_details": {
"total_packages": 10,
"total_pallets": 2,
"total_weight": {
"value": 250,
"unit": "lb"
}
},
"notes": "Please schedule receiving appointment. Fragile electronics."
}'
```
```graphQL GraphQL theme={null}
mutation CreateASN {
createASN(input: {
purchase_order_id: "po_123456789"
supplier_id: "sup_abc123"
shipment_date: "2024-01-15T14:00:00Z"
expected_arrival_date: "2024-01-18T10:00:00Z"
warehouse_id: "wh_001"
tracking_info: {
carrier: "UPS"
tracking_number: "1Z999AA10123456784"
service_type: "Ground"
}
items: [
{
sku: "WBH-001"
quantity_shipped: 500
unit_cost: {
amount: 7500
currency: "USD"
}
}
]
}) {
id
asn_number
status
expected_arrival_date
items {
sku
quantity_shipped
}
}
}
```
```javascript Node.js theme={null}
const asn = await stateset.asns.create({
purchase_order_id: "po_123456789",
supplier_id: "sup_abc123",
shipment_date: "2024-01-15T14:00:00Z",
expected_arrival_date: "2024-01-18T10:00:00Z",
warehouse_id: "wh_001",
tracking_info: {
carrier: "UPS",
tracking_number: "1Z999AA10123456784",
service_type: "Ground"
},
items: [
{
sku: "WBH-001",
quantity_shipped: 500,
quantity_ordered: 500,
unit_cost: {
amount: 7500,
currency: "USD"
},
lot_number: "LOT-2024-001"
}
],
packaging_details: {
total_packages: 10,
total_pallets: 2,
total_weight: {
value: 250,
unit: "lb"
}
}
});
```
```python Python theme={null}
asn = stateset.asns.create({
"purchase_order_id": "po_123456789",
"supplier_id": "sup_abc123",
"shipment_date": "2024-01-15T14:00:00Z",
"expected_arrival_date": "2024-01-18T10:00:00Z",
"warehouse_id": "wh_001",
"tracking_info": {
"carrier": "UPS",
"tracking_number": "1Z999AA10123456784",
"service_type": "Ground"
},
"items": [
{
"sku": "WBH-001",
"quantity_shipped": 500,
"quantity_ordered": 500,
"unit_cost": {
"amount": 7500,
"currency": "USD"
},
"lot_number": "LOT-2024-001"
}
]
})
```
```json Response theme={null}
{
"id": "asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "asn",
"asn_number": "ASN-2024-00001",
"status": "pending",
"created_at": "2024-01-15T14:30:00Z",
"updated_at": "2024-01-15T14:30:00Z",
"purchase_order_id": "po_123456789",
"supplier_id": "sup_abc123",
"warehouse_id": "wh_001",
"shipment_date": "2024-01-15T14:00:00Z",
"expected_arrival_date": "2024-01-18T10:00:00Z",
"actual_arrival_date": null,
"tracking_info": {
"carrier": "UPS",
"tracking_number": "1Z999AA10123456784",
"service_type": "Ground",
"tracking_url": "https://www.ups.com/track?tracknum=1Z999AA10123456784"
},
"items": [
{
"id": "asn_item_123",
"sku": "WBH-001",
"product_name": "Wireless Bluetooth Headphones",
"quantity_shipped": 500,
"quantity_ordered": 500,
"quantity_received": 0,
"unit_cost": {
"amount": 7500,
"currency": "USD"
},
"lot_number": "LOT-2024-001",
"status": "pending"
},
{
"id": "asn_item_124",
"sku": "USB-C-001",
"product_name": "USB-C Charging Cable",
"quantity_shipped": 1000,
"quantity_ordered": 1000,
"quantity_received": 0,
"unit_cost": {
"amount": 450,
"currency": "USD"
},
"lot_number": "LOT-2024-002",
"status": "pending"
}
],
"packaging_details": {
"total_packages": 10,
"total_pallets": 2,
"total_weight": {
"value": 250,
"unit": "lb"
}
},
"notes": "Please schedule receiving appointment. Fragile electronics.",
"metadata": {}
}
```
# Delete ASN
Source: https://docs.stateset.com/api-reference/asns/delete
DELETE https://api.stateset.com/v1/asns/:id
Delete an ASN from the system
ASNs can only be deleted if they are in "cancelled" status or created in error. Received ASNs cannot be deleted for audit trail purposes.
### Path Parameters
The unique identifier of the ASN to delete
### Response
The ID of the deleted ASN
Always "asn"
Always true for successful deletion
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/asns/asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```graphQL GraphQL theme={null}
mutation DeleteASN($id: ID!) {
deleteASN(id: $id) {
id
deleted
}
}
```
```javascript Node.js theme={null}
const result = await stateset.asns.delete(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
result = stateset.asns.delete(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "asn",
"deleted": true
}
```
### Error Responses
Error object when deletion fails
Type of error (e.g., "invalid\_request", "asn\_received")
Human-readable error message
Error code for programmatic handling
```json Error Response theme={null}
{
"error": {
"type": "asn_received",
"message": "Cannot delete ASN that has been received. ASNs with received status must be maintained for audit purposes.",
"code": "ASN_ALREADY_RECEIVED"
}
}
```
# Get ASN
Source: https://docs.stateset.com/api-reference/asns/get
GET https://api.stateset.com/v1/asns/:id
Retrieve a single ASN by ID with full shipment details
### Path Parameters
The unique identifier of the ASN to retrieve
### Query Parameters
Include detailed receiving data if available (default: true)
Include tracking status history (default: false)
### Response
Unique ASN identifier
Always "asn"
System-generated ASN number
Current status: "pending", "in\_transit", "delivered", "received", "partially\_received", "cancelled"
ISO 8601 timestamp of creation
ISO 8601 timestamp of last update
Associated purchase order ID
Supplier information
Destination warehouse details
Date when shipment was sent
Expected delivery date
Actual delivery date (when delivered)
Shipping and tracking details
Array of items with shipping and receiving details
Packaging and palletization information
Receiving information if ASN has been processed
Date when items were received
User who processed the receiving
Any discrepancies found during receiving
Receiving notes
Related shipping documents
Additional notes or instructions
Custom metadata fields
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/asns/asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```graphQL GraphQL theme={null}
query GetASN($id: ID!) {
asn(id: $id) {
id
asn_number
status
supplier {
id
name
}
warehouse {
id
name
}
shipment_date
expected_arrival_date
actual_arrival_date
tracking_info {
carrier
tracking_number
tracking_url
current_status
}
items {
id
sku
product_name
quantity_shipped
quantity_received
status
discrepancies {
type
expected
actual
notes
}
}
receiving_data {
received_date
received_by
total_items_received
discrepancy_count
}
}
}
```
```javascript Node.js theme={null}
const asn = await stateset.asns.retrieve(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
include_receiving_data: true,
include_tracking_history: true
}
);
```
```python Python theme={null}
asn = stateset.asns.retrieve(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
include_receiving_data=True,
include_tracking_history=True
)
```
```json Response theme={null}
{
"id": "asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "asn",
"asn_number": "ASN-2024-00001",
"status": "delivered",
"created_at": "2024-01-15T14:30:00Z",
"updated_at": "2024-01-18T11:15:00Z",
"purchase_order_id": "po_123456789",
"purchase_order_number": "PO-2024-00123",
"supplier": {
"id": "sup_abc123",
"name": "AudioTech Suppliers Inc.",
"contact_email": "shipping@audiotech.com"
},
"warehouse": {
"id": "wh_001",
"name": "Main Distribution Center",
"address": {
"line1": "123 Warehouse Way",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
}
},
"shipment_date": "2024-01-15T14:00:00Z",
"expected_arrival_date": "2024-01-18T10:00:00Z",
"actual_arrival_date": "2024-01-18T09:30:00Z",
"tracking_info": {
"carrier": "UPS",
"tracking_number": "1Z999AA10123456784",
"service_type": "Ground",
"tracking_url": "https://www.ups.com/track?tracknum=1Z999AA10123456784",
"current_status": "Delivered",
"last_update": "2024-01-18T09:30:00Z",
"tracking_history": [
{
"timestamp": "2024-01-15T14:15:00Z",
"status": "Picked up",
"location": "San Francisco, CA"
},
{
"timestamp": "2024-01-16T22:00:00Z",
"status": "In transit",
"location": "Fresno, CA"
},
{
"timestamp": "2024-01-18T06:00:00Z",
"status": "Out for delivery",
"location": "Los Angeles, CA"
},
{
"timestamp": "2024-01-18T09:30:00Z",
"status": "Delivered",
"location": "Los Angeles, CA"
}
]
},
"items": [
{
"id": "asn_item_123",
"sku": "WBH-001",
"product_name": "Wireless Bluetooth Headphones",
"quantity_shipped": 500,
"quantity_ordered": 500,
"quantity_received": 0,
"unit_cost": {
"amount": 7500,
"currency": "USD"
},
"lot_number": "LOT-2024-001",
"status": "pending_receipt"
},
{
"id": "asn_item_124",
"sku": "USB-C-001",
"product_name": "USB-C Charging Cable",
"quantity_shipped": 1000,
"quantity_ordered": 1000,
"quantity_received": 0,
"unit_cost": {
"amount": 450,
"currency": "USD"
},
"lot_number": "LOT-2024-002",
"status": "pending_receipt"
}
],
"packaging_details": {
"total_packages": 10,
"total_pallets": 2,
"total_weight": {
"value": 250,
"unit": "lb"
},
"packages": [
{
"package_id": "PKG001",
"type": "pallet",
"tracking_number": "1Z999AA10123456784"
}
]
},
"shipping_documents": [
{
"type": "packing_list",
"document_number": "PL-2024-00001",
"url": "https://documents.stateset.com/packing-lists/PL-2024-00001.pdf"
}
],
"receiving_data": null,
"notes": "Please schedule receiving appointment. Fragile electronics.",
"metadata": {}
}
```
# List ASNs
Source: https://docs.stateset.com/api-reference/asns/list
GET https://api.stateset.com/v1/asns
Retrieve a paginated list of ASNs with filtering options
### Query Parameters
Number of ASNs to return (default: 20, max: 100)
Number of ASNs to skip (for pagination)
Cursor for pagination (alternative to offset)
Filter by status: "pending", "in\_transit", "delivered", "received", "partially\_received", "cancelled"
Filter by purchase order ID
Filter by supplier ID
Filter by destination warehouse ID
Filter by shipping carrier
Filter ASNs with expected arrival after this date (ISO 8601)
Filter ASNs with expected arrival before this date (ISO 8601)
Filter ASNs created after this date (ISO 8601)
Filter ASNs created before this date (ISO 8601)
Filter ASNs with receiving discrepancies
Search by ASN number, tracking number, or supplier name
Sort field: "created\_at", "expected\_arrival\_date", "asn\_number", "status" (default: "created\_at")
Sort order: "asc" or "desc" (default: "desc")
### Response
Always "list"
Array of ASN objects
Whether there are more ASNs to retrieve
Total number of ASNs matching the filters
Cursor for retrieving the next page
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/asns?status=in_transit&warehouse_id=wh_001&limit=10' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```graphQL GraphQL theme={null}
query ListASNs(
$limit: Int
$offset: Int
$status: ASNStatus
$warehouse_id: String
$expected_arrival_after: DateTime
) {
asns(
limit: $limit
offset: $offset
status: $status
warehouse_id: $warehouse_id
expected_arrival_after: $expected_arrival_after
) {
data {
id
asn_number
status
supplier {
id
name
}
warehouse {
id
name
}
expected_arrival_date
tracking_info {
carrier
tracking_number
current_status
}
item_summary {
total_items
total_quantity
}
}
has_more
total_count
}
}
```
```javascript Node.js theme={null}
const asns = await stateset.asns.list({
status: 'in_transit',
warehouse_id: 'wh_001',
expected_arrival_after: '2024-01-15T00:00:00Z',
limit: 10,
sort_by: 'expected_arrival_date',
sort_order: 'asc'
});
// Iterate through all ASNs
for await (const asn of stateset.asns.list()) {
console.log(asn.asn_number, asn.status);
}
```
```python Python theme={null}
asns = stateset.asns.list(
status='in_transit',
warehouse_id='wh_001',
expected_arrival_after='2024-01-15T00:00:00Z',
limit=10,
sort_by='expected_arrival_date',
sort_order='asc'
)
# Iterate through all ASNs
for asn in stateset.asns.list():
print(asn.asn_number, asn.status)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "asn",
"asn_number": "ASN-2024-00001",
"status": "in_transit",
"created_at": "2024-01-15T14:30:00Z",
"updated_at": "2024-01-16T08:00:00Z",
"purchase_order_id": "po_123456789",
"purchase_order_number": "PO-2024-00123",
"supplier": {
"id": "sup_abc123",
"name": "AudioTech Suppliers Inc."
},
"warehouse": {
"id": "wh_001",
"name": "Main Distribution Center"
},
"shipment_date": "2024-01-15T14:00:00Z",
"expected_arrival_date": "2024-01-18T10:00:00Z",
"tracking_info": {
"carrier": "UPS",
"tracking_number": "1Z999AA10123456784",
"current_status": "In Transit",
"last_update": "2024-01-16T08:00:00Z"
},
"item_summary": {
"total_items": 2,
"total_quantity": 1500,
"total_value": {
"amount": 4200000,
"currency": "USD"
}
}
},
{
"id": "asn_xyz789def456",
"object": "asn",
"asn_number": "ASN-2024-00002",
"status": "in_transit",
"created_at": "2024-01-16T09:00:00Z",
"updated_at": "2024-01-16T15:00:00Z",
"purchase_order_id": "po_987654321",
"purchase_order_number": "PO-2024-00124",
"supplier": {
"id": "sup_def456",
"name": "TechConnect Wholesale"
},
"warehouse": {
"id": "wh_001",
"name": "Main Distribution Center"
},
"shipment_date": "2024-01-16T08:00:00Z",
"expected_arrival_date": "2024-01-19T14:00:00Z",
"tracking_info": {
"carrier": "FedEx",
"tracking_number": "123456789012",
"current_status": "In Transit",
"last_update": "2024-01-16T15:00:00Z"
},
"item_summary": {
"total_items": 5,
"total_quantity": 2500,
"total_value": {
"amount": 1875000,
"currency": "USD"
}
}
}
],
"has_more": true,
"total_count": 15,
"next_cursor": "eyJpZCI6ImFzbl94eXo3ODlkZWY0NTYifQ=="
}
```
# Receive ASN
Source: https://docs.stateset.com/api-reference/asns/receive
POST https://api.stateset.com/v1/asns/:id/receive
Process the receiving of items from an ASN and update inventory
This endpoint processes the receiving of items from an ASN. It updates inventory levels, records any discrepancies, and can trigger automated workflows for putaway and quality control.
### Path Parameters
The unique identifier of the ASN to receive
### Request Body
Date and time when items were received (ISO 8601)
User ID or name of the person processing the receipt
Array of received items with quantities and conditions
ASN item ID being received
Actual quantity received
Condition of received items: "new", "damaged", "defective"
Lot number for tracking (can override ASN lot number)
Expiration date for perishable items
Array of serial numbers for serialized items
Warehouse location where items are placed
Notes about any discrepancies found
Quality control information
Whether quality check was performed
Whether items passed quality check
Quality check notes
List of items that failed quality check
Overall discrepancies found during receiving
Type: "quantity", "damage", "wrong\_item", "missing\_item"
Description of the discrepancy
How the discrepancy was resolved
General receiving notes
Whether this completes the ASN receipt (default: true)
### Response
ASN ID
Updated ASN status
Summary of the receiving process
Details of inventory updates made
Summary of any discrepancies found
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/asns/asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/receive' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"received_date": "2024-01-18T11:00:00Z",
"received_by": "john.doe@warehouse.com",
"items": [
{
"item_id": "asn_item_123",
"quantity_received": 498,
"condition": "new",
"lot_number": "LOT-2024-001",
"location": "A-12-3",
"discrepancy_notes": "2 units damaged in transit"
},
{
"item_id": "asn_item_124",
"quantity_received": 1000,
"condition": "new",
"lot_number": "LOT-2024-002",
"location": "B-5-1"
}
],
"quality_check": {
"performed": true,
"passed": true,
"notes": "All items meet quality standards"
},
"discrepancies": [
{
"type": "damage",
"description": "2 units of WBH-001 damaged in transit",
"resolution": "Filed claim with carrier"
}
],
"notes": "Shipment received in good condition except for noted damages",
"complete_receipt": true
}'
```
```graphQL GraphQL theme={null}
mutation ReceiveASN($id: ID!, $input: ReceiveASNInput!) {
receiveASN(id: $id, input: $input) {
id
status
receiving_summary {
total_items_expected
total_items_received
discrepancy_count
receipt_completed
}
inventory_updates {
sku
quantity_added
new_total
location
}
discrepancy_report {
has_discrepancies
total_discrepancies
discrepancies {
type
description
impact
}
}
}
}
```
```javascript Node.js theme={null}
const receipt = await stateset.asns.receive(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
received_date: '2024-01-18T11:00:00Z',
received_by: 'john.doe@warehouse.com',
items: [
{
item_id: 'asn_item_123',
quantity_received: 498,
condition: 'new',
lot_number: 'LOT-2024-001',
location: 'A-12-3',
discrepancy_notes: '2 units damaged in transit'
},
{
item_id: 'asn_item_124',
quantity_received: 1000,
condition: 'new',
lot_number: 'LOT-2024-002',
location: 'B-5-1'
}
],
quality_check: {
performed: true,
passed: true,
notes: 'All items meet quality standards'
},
complete_receipt: true
}
);
```
```python Python theme={null}
receipt = stateset.asns.receive(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
received_date='2024-01-18T11:00:00Z',
received_by='john.doe@warehouse.com',
items=[
{
'item_id': 'asn_item_123',
'quantity_received': 498,
'condition': 'new',
'lot_number': 'LOT-2024-001',
'location': 'A-12-3',
'discrepancy_notes': '2 units damaged in transit'
},
{
'item_id': 'asn_item_124',
'quantity_received': 1000,
'condition': 'new',
'lot_number': 'LOT-2024-002',
'location': 'B-5-1'
}
],
quality_check={
'performed': True,
'passed': True,
'notes': 'All items meet quality standards'
},
complete_receipt=True
)
```
```json Response theme={null}
{
"id": "asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"asn_number": "ASN-2024-00001",
"status": "received",
"receiving_summary": {
"total_items_expected": 1500,
"total_items_received": 1498,
"discrepancy_count": 1,
"receipt_completed": true,
"received_date": "2024-01-18T11:00:00Z",
"received_by": "john.doe@warehouse.com"
},
"inventory_updates": [
{
"sku": "WBH-001",
"product_name": "Wireless Bluetooth Headphones",
"quantity_added": 498,
"previous_quantity": 145,
"new_total": 643,
"location": "A-12-3",
"lot_number": "LOT-2024-001"
},
{
"sku": "USB-C-001",
"product_name": "USB-C Charging Cable",
"quantity_added": 1000,
"previous_quantity": 487,
"new_total": 1487,
"location": "B-5-1",
"lot_number": "LOT-2024-002"
}
],
"discrepancy_report": {
"has_discrepancies": true,
"total_discrepancies": 1,
"discrepancies": [
{
"type": "damage",
"description": "2 units of WBH-001 damaged in transit",
"expected_quantity": 500,
"received_quantity": 498,
"impact": "inventory_shortage",
"resolution": "Filed claim with carrier"
}
]
},
"purchase_order_update": {
"po_id": "po_123456789",
"items_received": 1498,
"items_outstanding": 2,
"po_status": "partially_received"
},
"workflows_triggered": [
{
"type": "putaway",
"status": "initiated",
"assigned_to": "warehouse_team"
},
{
"type": "carrier_claim",
"status": "initiated",
"reference": "CLAIM-2024-00123"
}
]
}
```
# Update ASN
Source: https://docs.stateset.com/api-reference/asns/update
PUT https://api.stateset.com/v1/asns/:id
Update an existing ASN with new tracking information or status
This endpoint supports partial updates. Only include the fields you want to change. Once an ASN is received, only certain fields can be updated.
### Path Parameters
The unique identifier of the ASN to update
### Request Body
Updated expected delivery date (ISO 8601)
Actual delivery date when shipment arrives (ISO 8601)
Updated status: "pending", "in\_transit", "delivered", "received", "partially\_received", "cancelled"
Updated tracking information
Carrier name
Primary tracking number
Service level
Current tracking status
Additional tracking numbers
Updated packaging information
Total number of packages
Total number of pallets
Total shipment weight
Updated or additional shipping documents
Document type
Document reference number
URL to access the document
Updated notes or instructions
Updated custom metadata
### Response
Returns the updated ASN object with all fields.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/asns/asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"status": "delivered",
"actual_arrival_date": "2024-01-18T09:30:00Z",
"tracking_info": {
"current_status": "Delivered"
},
"shipping_documents": [
{
"type": "proof_of_delivery",
"document_number": "POD-2024-00001",
"url": "https://documents.stateset.com/pod/POD-2024-00001.pdf"
}
]
}'
```
```graphQL GraphQL theme={null}
mutation UpdateASN($id: ID!, $input: UpdateASNInput!) {
updateASN(id: $id, input: $input) {
id
asn_number
status
actual_arrival_date
tracking_info {
current_status
last_update
}
shipping_documents {
type
document_number
url
}
}
}
```
```javascript Node.js theme={null}
const asn = await stateset.asns.update(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
status: 'delivered',
actual_arrival_date: '2024-01-18T09:30:00Z',
tracking_info: {
current_status: 'Delivered'
},
shipping_documents: [
{
type: 'proof_of_delivery',
document_number: 'POD-2024-00001',
url: 'https://documents.stateset.com/pod/POD-2024-00001.pdf'
}
]
}
);
```
```python Python theme={null}
asn = stateset.asns.update(
'asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
status='delivered',
actual_arrival_date='2024-01-18T09:30:00Z',
tracking_info={
'current_status': 'Delivered'
},
shipping_documents=[
{
'type': 'proof_of_delivery',
'document_number': 'POD-2024-00001',
'url': 'https://documents.stateset.com/pod/POD-2024-00001.pdf'
}
]
)
```
```json Response theme={null}
{
"id": "asn_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "asn",
"asn_number": "ASN-2024-00001",
"status": "delivered",
"created_at": "2024-01-15T14:30:00Z",
"updated_at": "2024-01-18T09:35:00Z",
"purchase_order_id": "po_123456789",
"supplier_id": "sup_abc123",
"warehouse_id": "wh_001",
"shipment_date": "2024-01-15T14:00:00Z",
"expected_arrival_date": "2024-01-18T10:00:00Z",
"actual_arrival_date": "2024-01-18T09:30:00Z",
"tracking_info": {
"carrier": "UPS",
"tracking_number": "1Z999AA10123456784",
"service_type": "Ground",
"tracking_url": "https://www.ups.com/track?tracknum=1Z999AA10123456784",
"current_status": "Delivered",
"last_update": "2024-01-18T09:30:00Z"
},
"items": [
{
"id": "asn_item_123",
"sku": "WBH-001",
"product_name": "Wireless Bluetooth Headphones",
"quantity_shipped": 500,
"quantity_ordered": 500,
"quantity_received": 0,
"unit_cost": {
"amount": 7500,
"currency": "USD"
},
"lot_number": "LOT-2024-001",
"status": "pending_receipt"
},
{
"id": "asn_item_124",
"sku": "USB-C-001",
"product_name": "USB-C Charging Cable",
"quantity_shipped": 1000,
"quantity_ordered": 1000,
"quantity_received": 0,
"unit_cost": {
"amount": 450,
"currency": "USD"
},
"lot_number": "LOT-2024-002",
"status": "pending_receipt"
}
],
"packaging_details": {
"total_packages": 10,
"total_pallets": 2,
"total_weight": {
"value": 250,
"unit": "lb"
}
},
"shipping_documents": [
{
"type": "packing_list",
"document_number": "PL-2024-00001",
"url": "https://documents.stateset.com/packing-lists/PL-2024-00001.pdf"
},
{
"type": "proof_of_delivery",
"document_number": "POD-2024-00001",
"url": "https://documents.stateset.com/pod/POD-2024-00001.pdf"
}
],
"notes": "Please schedule receiving appointment. Fragile electronics.",
"metadata": {}
}
```
# Authentication
Source: https://docs.stateset.com/api-reference/authentication
Complete guide to authenticating with the Stateset API
**Quick Start:** All API requests require authentication via API key in the `Authorization` header:
```bash theme={null}
Authorization: Bearer sk_live_your_api_key_here
```
Stateset provides multiple authentication methods to secure your API access, including API keys, JWT tokens, and OAuth 2.0 for different use cases.
## Authentication Overview
All data in Stateset is private by default, requiring authentication for every API request. We support multiple authentication methods:
### Supported Authentication Methods
Best for server-to-server communication and backend integrations
Ideal for user-specific access and session management
Perfect for third-party integrations and partner access
Secure webhook delivery with HMAC signatures
## API Key Authentication
### Key Types and Permissions
| Key Type | Prefix | Use Case | Permissions |
| ------------------- | ---------- | ---------------------- | --------------------- |
| **Secret Key** | `sk_live_` | Server-side operations | Full API access |
| **Restricted Key** | `rk_live_` | Limited scope access | Custom permissions |
| **Publishable Key** | `pk_live_` | Client-side operations | Read-only public data |
| **Test Key** | `sk_test_` | Development & testing | Sandbox environment |
### Creating API Keys
1. Navigate to **Settings → API Keys** in your dashboard
2. Click **Create New Key**
3. Select key type and permissions
4. Copy and securely store your key
API keys are shown only once. Store them securely and never expose secret keys in client-side code.
### Using API Keys
```bash cURL theme={null}
curl https://api.stateset.com/v1/orders \
-H "Authorization: Bearer sk_live_your_api_key_here" \
-H "Content-Type: application/json"
```
```javascript Node.js theme={null}
// Using environment variables (recommended)
const headers = {
'Authorization': `Bearer ${process.env.STATESET_API_KEY}`,
'Content-Type': 'application/json'
};
const response = await fetch('https://api.stateset.com/v1/orders', {
headers
});
```
```python Python theme={null}
import os
import requests
headers = {
'Authorization': f'Bearer {os.getenv("STATESET_API_KEY")}',
'Content-Type': 'application/json'
}
response = requests.get(
'https://api.stateset.com/v1/orders',
headers=headers
)
```
### Restricted API Keys
Create keys with specific permissions for enhanced security:
```javascript theme={null}
// Creating a restricted key via API
const restrictedKey = await stateset.apiKeys.create({
name: 'Read-only Orders Key',
permissions: [
'orders:read',
'customers:read'
],
expires_at: '2024-12-31T23:59:59Z'
});
```
## JWT Token Authentication
JWT tokens provide secure, stateless authentication for user sessions.
### JWT Token Structure
```json theme={null}
{
"header": {
"alg": "RS256",
"typ": "JWT",
"kid": "key_id_123"
},
"payload": {
"sub": "user_123",
"org_id": "org_456",
"role": "admin",
"permissions": ["orders:*", "customers:*"],
"iat": 1704067200,
"exp": 1704070800,
"iss": "https://api.stateset.com"
},
"signature": "..."
}
```
## GraphQL API Authentication
### GraphQL Endpoint Access
Stateset GraphQL API requires authentication via HTTP headers:
```graphql theme={null}
# GraphQL endpoint
https://api.stateset.com/graphql
# Required headers
Authorization: Bearer sk_live_your_api_key
Content-Type: application/json
```
### GraphQL Request Example
```javascript Apollo Client theme={null}
import { ApolloClient, InMemoryCache, createHttpLink } from '@apollo/client';
import { setContext } from '@apollo/client/link/context';
const httpLink = createHttpLink({
uri: 'https://api.stateset.com/graphql',
});
const authLink = setContext((_, { headers }) => {
const token = process.env.STATESET_API_KEY;
return {
headers: {
...headers,
authorization: token ? `Bearer ${token}` : "",
}
}
});
const client = new ApolloClient({
link: authLink.concat(httpLink),
cache: new InMemoryCache()
});
```
```python Python GraphQL theme={null}
import requests
query = """
query GetOrders {
orders(limit: 10) {
id
status
total
}
}
"""
response = requests.post(
'https://api.stateset.com/graphql',
json={'query': query},
headers={
'Authorization': f'Bearer {api_key}',
'Content-Type': 'application/json'
}
)
```
## OAuth 2.0 Authentication
For third-party integrations and partner access, we support OAuth 2.0:
### OAuth Flow
```bash theme={null}
GET https://api.stateset.com/oauth/authorize?
client_id=YOUR_CLIENT_ID&
redirect_uri=YOUR_REDIRECT_URI&
response_type=code&
scope=orders:read customers:read&
state=RANDOM_STATE
```
```bash theme={null}
POST https://api.stateset.com/oauth/token
Content-Type: application/x-www-form-urlencoded
grant_type=authorization_code&
code=AUTH_CODE&
client_id=YOUR_CLIENT_ID&
client_secret=YOUR_CLIENT_SECRET&
redirect_uri=YOUR_REDIRECT_URI
```
```bash theme={null}
GET https://api.stateset.com/v1/orders
Authorization: Bearer ACCESS_TOKEN
```
### Available Scopes
| Scope | Description |
| ----------------- | ------------------------ |
| `orders:read` | Read order data |
| `orders:write` | Create and update orders |
| `customers:read` | Read customer data |
| `customers:write` | Manage customers |
| `inventory:read` | View inventory levels |
| `inventory:write` | Update inventory |
| `returns:*` | Full returns access |
| `admin` | Full API access |
## Role-Based Access Control (RBAC)
### User Roles and Permissions
Stateset implements fine-grained permissions using role-based access control:
| Role | Description | Default Permissions | API Key Prefix |
| ---------------- | -------------------- | -------------------------- | -------------- |
| **anonymous** | Unauthenticated user | Public read-only endpoints | N/A |
| **viewer** | Read-only access | All read operations | `rk_view_` |
| **operator** | Standard user | CRUD on assigned resources | `sk_live_` |
| **manager** | Team manager | CRUD on team resources | `sk_mgr_` |
| **admin** | Full access | All operations | `sk_admin_` |
| **super\_admin** | System admin | System configuration | `sk_super_` |
### Permission Matrix
| Resource | Anonymous | Viewer | Operator | Manager | Admin |
| --------- | --------- | ------ | ---------- | ------------- | ---------- |
| Orders | ❌ | Read | CRUD (own) | CRUD (team) | CRUD (all) |
| Customers | ❌ | Read | Read (own) | CRUD (team) | CRUD (all) |
| Inventory | Read | Read | Read | CRUD | CRUD |
| Returns | ❌ | Read | CRUD (own) | CRUD (team) | CRUD (all) |
| Reports | ❌ | Read | Read (own) | Read (team) | CRUD |
| Settings | ❌ | ❌ | Read (own) | Update (team) | CRUD |
### Custom Permissions with Session Variables
Implement fine-grained access control using session variables:
#### JWT Claims Structure
```json theme={null}
{
"https://hasura.io/jwt/claims": {
"x-hasura-org-id": "org_123",
"x-hasura-user-id": "user_456",
"x-hasura-default-role": "operator",
"x-hasura-allowed-roles": ["viewer", "operator", "manager"],
"x-hasura-team-id": "team_789",
"x-hasura-permissions": [
"orders:read",
"orders:write",
"customers:read"
]
},
"iat": 1704067200,
"exp": 1704070800
}
```
#### Permission Checks
```javascript theme={null}
// Middleware for permission checking
function requirePermission(permission) {
return (req, res, next) => {
const token = req.headers.authorization?.split(' ')[1];
const decoded = jwt.verify(token, process.env.JWT_SECRET);
const claims = decoded['https://hasura.io/jwt/claims'];
const permissions = claims['x-hasura-permissions'] || [];
if (!permissions.includes(permission)) {
return res.status(403).json({
error: 'INSUFFICIENT_PERMISSIONS',
message: `Missing required permission: ${permission}`
});
}
req.user = {
id: claims['x-hasura-user-id'],
org_id: claims['x-hasura-org-id'],
role: claims['x-hasura-default-role'],
permissions
};
next();
};
}
// Usage
app.post('/api/orders',
requirePermission('orders:write'),
createOrderHandler
);
```
## Webhook Authentication
### Webhook Signature Verification
All webhooks from Stateset are signed for security:
```javascript theme={null}
const crypto = require('crypto');
class WebhookVerifier {
constructor(secret) {
this.secret = secret;
}
verify(payload, signature) {
// Parse signature header
const elements = signature.split(' ');
const timestamp = elements.find(e => e.startsWith('t=')).slice(2);
const signatures = elements
.filter(e => e.startsWith('v1='))
.map(e => e.slice(3));
// Check timestamp (5 minute tolerance)
const currentTime = Math.floor(Date.now() / 1000);
if (currentTime - parseInt(timestamp) > 300) {
throw new Error('Webhook timestamp expired');
}
// Compute expected signature
const signedPayload = `${timestamp}.${payload}`;
const expectedSig = crypto
.createHmac('sha256', this.secret)
.update(signedPayload)
.digest('hex');
// Timing-safe comparison
const valid = signatures.some(sig =>
crypto.timingSafeEqual(
Buffer.from(sig),
Buffer.from(expectedSig)
)
);
if (!valid) {
throw new Error('Invalid webhook signature');
}
return JSON.parse(payload);
}
}
// Express middleware
const webhookAuth = (req, res, next) => {
const verifier = new WebhookVerifier(process.env.WEBHOOK_SECRET);
try {
req.body = verifier.verify(
req.rawBody,
req.headers['stateset-signature']
);
next();
} catch (error) {
res.status(401).json({ error: 'Webhook verification failed' });
}
};
```
## Security Best Practices
* Store keys in environment variables, never in code
* Use different keys for different environments
* Rotate keys regularly (every 90 days recommended)
* Use restricted keys with minimal permissions
* Monitor key usage for anomalies
* Implement short token lifetimes (15-30 minutes)
* Use refresh tokens for long-lived sessions
* Store tokens securely (httpOnly cookies)
* Implement token revocation
* Log all authentication events
* Always use HTTPS for API calls
* Implement IP allowlisting for production
* Use VPN or private networks when possible
* Enable CORS with specific origins
* Implement rate limiting per API key
## Authentication Examples
### React Hook with Authentication
```jsx theme={null}
import { useState, useEffect } from 'react';
import { useAuth } from '@clerk/nextjs';
/**
* Custom hook for authenticated Stateset API calls
*/
export const useStatesetAPI = () => {
const { getToken, isSignedIn } = useAuth();
const [loading, setLoading] = useState(false);
const [error, setError] = useState(null);
const apiCall = async (endpoint, options = {}) => {
if (!isSignedIn) {
throw new Error('User not authenticated');
}
setLoading(true);
setError(null);
try {
const token = await getToken({ template: 'stateset' });
const response = await fetch(`https://api.stateset.com/v1${endpoint}`, {
...options,
headers: {
'Authorization': `Bearer ${token}`,
'Content-Type': 'application/json',
...options.headers
}
});
if (!response.ok) {
const error = await response.json();
throw new Error(error.message || 'API request failed');
}
const data = await response.json();
return data;
} catch (err) {
setError(err);
throw err;
} finally {
setLoading(false);
}
};
return { apiCall, loading, error };
};
// Usage
function OrderList() {
const { apiCall } = useStatesetAPI();
const [orders, setOrders] = useState([]);
useEffect(() => {
apiCall('/orders')
.then(data => setOrders(data.orders))
.catch(console.error);
}, []);
return (
{orders.map(order => (
))}
);
}
```
### Python Authentication Manager
```python theme={null}
import os
import time
import requests
from typing import Optional, Dict, Any
from functools import wraps
class StatesetAuth:
def __init__(self, api_key: Optional[str] = None):
self.api_key = api_key or os.getenv('STATESET_API_KEY')
self.base_url = 'https://api.stateset.com/v1'
self.session = requests.Session()
self.session.headers.update({
'Authorization': f'Bearer {self.api_key}',
'Content-Type': 'application/json'
})
def validate_key(self) -> bool:
"""Validate API key is active"""
try:
response = self.session.get(f'{self.base_url}/auth/validate')
return response.status_code == 200
except:
return False
def with_retry(self, max_retries: int = 3):
"""Decorator for automatic retry with exponential backoff"""
def decorator(func):
@wraps(func)
def wrapper(*args, **kwargs):
for attempt in range(max_retries):
try:
return func(*args, **kwargs)
except requests.exceptions.RequestException as e:
if attempt == max_retries - 1:
raise
wait_time = 2 ** attempt
time.sleep(wait_time)
return None
return wrapper
return decorator
@with_retry(max_retries=3)
def api_request(
self,
method: str,
endpoint: str,
data: Optional[Dict[Any, Any]] = None
) -> Dict[Any, Any]:
"""Make authenticated API request"""
url = f'{self.base_url}{endpoint}'
response = self.session.request(method, url, json=data)
response.raise_for_status()
return response.json()
# Usage
auth = StatesetAuth()
if auth.validate_key():
orders = auth.api_request('GET', '/orders')
print(f"Found {len(orders['data'])} orders")
```
## Troubleshooting Authentication
### Common Issues and Solutions
| Issue | Cause | Solution |
| ----------------------- | ---------------------------- | ------------------------------- |
| `401 Unauthorized` | Invalid or expired API key | Check key validity in dashboard |
| `403 Forbidden` | Insufficient permissions | Verify key has required scopes |
| `429 Too Many Requests` | Rate limit exceeded | Implement exponential backoff |
| `CORS Error` | Cross-origin request blocked | Use server-side proxy or SDK |
| `Signature Mismatch` | Invalid webhook secret | Verify webhook secret matches |
### Debug Authentication
```bash theme={null}
# Test API key validity
curl -I https://api.stateset.com/v1/auth/validate \
-H "Authorization: Bearer YOUR_API_KEY"
# Check key permissions
curl https://api.stateset.com/v1/auth/permissions \
-H "Authorization: Bearer YOUR_API_KEY"
```
***
**Next Steps:** [Create your first API request →](/api-reference/quickstart)
# StateSet API
Source: https://docs.stateset.com/api-reference/backend-framework
A high-performance, scalable backend framework built with Rust, Axum, and SeaORM for enterprise-grade applications.
# StateSet API: A Robust Backend Framework
StateSet API is a modern, scalable, and reliable backend system designed for enterprise-grade web services. Built with Rust, it leverages cutting-edge web technologies and best practices to deliver a high-performance infrastructure solution. It is particularly well-suited for e-commerce and manufacturing businesses, adept at handling order management, inventory control, returns processing, warranty management, shipment tracking, and work order handling.
## Core Features
StateSet API is built to handle complex business operations. Here's a breakdown of its key features:
* **Order Management:** Full CRUD operations for orders, support for complex workflows and statuses.
* **Inventory Control:** Real-time tracking across multiple locations, automated reorder point notifications.
* **Returns Processing:** Streamlined return authorization, processing, and integration with refund and exchange systems.
* **Warranty Management:** Track and manage product warranties, handle automated claim processing.
* **Shipment Tracking:** Real-time integration with major carriers, custom shipment status notifications.
* **Manufacturing & Production:** Supplier management, BOM tracking, and version control.
* **Work Order Handling:** Create and manage work orders, track progress, and manage resource allocation.
## Tech Stack: The Foundation of Performance
Our carefully selected tech stack ensures high performance, scalability, and maintainability.
### Core Technologies
* **Language:** [Rust](https://www.rust-lang.org/) (for performance, safety, and concurrency)
* **Web Framework:** [Axum](https://github.com/tokio-rs/axum/) (a lightweight, async, and fast web framework)
* **Database:** [PostgreSQL](https://www.postgresql.org/) (for robust, reliable data storage) with [SQLx](https://github.com/launchbadge/sqlx) (for async operations).
### ORM and Query Building
* [SeaORM](https://www.sea-ql.org/SeaORM) (a powerful async ORM for Rust).
### API Protocols and Services
* **REST:** Implemented natively with Axum.
* **GraphQL:** Implemented using [Async-GraphQL](https://async-graphql.github.io/) for a high-performance GraphQL API.
* **gRPC:** Built with [Tonic](https://github.com/hyperium/tonic) for efficient, type-safe gRPC support.
### Caching and Messaging
* **Caching:** [Redis](https://redis.io/) for high-speed data caching.
* **Message Queue:** [RabbitMQ](https://www.rabbitmq.com/) for reliable asynchronous processing.
### Observability
* **Metrics:** [Prometheus](https://prometheus.io/) for detailed system monitoring.
* **Tracing:** [OpenTelemetry](https://opentelemetry.io/) with [Jaeger](https://www.jaegertracing.io/) for distributed tracing.
* **Logging:** [slog](https://docs.rs/slog/latest/slog/) for structured, efficient logging.
### Technological Advantages:
* **Rust's Performance & Safety:** Guarantees memory safety and prevents common programming errors, leading to a highly reliable and performant API.
* **Asynchronous Operations:** Utilizing Rust's async capabilities for high-throughput and non-blocking processing.
* **Comprehensive Observability:** Enables proactive maintenance and rapid issue resolution.
* **Flexible API Protocols:** Supports various API protocols, ensuring integration with different client applications and services.
### Use Cases:
* **E-commerce Platforms:** Efficiently manage orders, inventory, shipments, and customer interactions.
* **Manufacturing Systems:** Streamline production workflows, inventory control, supplier management, and quality assurance.
* **Enterprise Solutions:** Provides a scalable backend infrastructure for a wide variety of business operations and services.
## Architecture: Modular and Event-Driven
StateSet API adopts a modular, asynchronous, event-driven architecture designed for scalability and maintainability.
```mermaid theme={null}
flowchart TB
Client[Client]
subgraph API["StateSet API"]
direction TB
Handlers[Handlers]
Commands[Commands]
Queries[Queries]
Services[Services]
Models[Models]
Middleware[Middleware]
end
subgraph Core["Core Technologies"]
direction LR
Rust[Rust]
Axum[Axum]
PostgreSQL[PostgreSQL]
end
subgraph Data["Data Layer"]
direction LR
SeaORM[SeaORM]
SQLx[SQLx]
end
subgraph Protocols["API Protocols"]
direction TB
REST[REST]
GraphQL[Async-GraphQL]
gRPC[Tonic gRPC]
end
subgraph Cache["Caching & Messaging"]
direction LR
Redis[Redis]
RabbitMQ[RabbitMQ]
end
subgraph Observability["Observability"]
direction TB
Prometheus[Prometheus]
OpenTelemetry[OpenTelemetry]
Jaeger[Jaeger]
Slog[Slog]
end
Client --> Protocols
Protocols --> API
API --> Core
API --> Data
API --> Cache
API --> Observability
Core --> PostgreSQL
Data --> PostgreSQL
```
### Key Components
* **Services:** Implement the core business logic for specific functionalities.
* **Handlers:** Process incoming HTTP requests, routing them to the appropriate logic.
* **Commands:** Handle operations that modify data or state in the system (writes).
* **Queries:** Handle read operations, retrieving data without modifying it.
* **Events:** Enable asynchronous communication and processing through event triggers.
* **Models:** Represent domain entities, providing a structured data layer.
* **Middleware:** Handle cross-cutting concerns like authentication, rate limiting, and logging.
## Performance and Reliability
StateSet API is engineered for high performance and reliability:
* Handles 10,000+ requests per second on a single node (This is a claim. If you have concrete benchmarks include them here or state in which conditions you measured this).
* Scales horizontally to accommodate increased load.
* Designed for 99.99% uptime SLA (Include specifics if this is part of an actual SLA).
## Code Examples
Here are some representative code snippets to demonstrate the implementation.
### Axum Web Service Entrypoint
This code sets up the Axum web service, including routes, middleware, and integration with other services.
```rust theme={null}
#[tokio::main]
async fn main() -> Result<(), AppError> {
dotenv().ok();
let config = Arc::new(config::load()?);
let log = setup_logger(&config);
info!(log, "Starting StateSet API";
"environment" => &config.environment,
"version" => env!("CARGO_PKG_VERSION")
);
let app_state = build_app_state(&config, &log).await?;
let schema = Arc::new(graphql::create_schema(
app_state.services.order_service.clone(),
// ... other service clones
));
setup_telemetry(&config)?;
// Spawn event processing
tokio::spawn(events::process_events(
app_state.event_sender.subscribe(),
app_state.services.clone(),
log.clone(),
));
// Start gRPC server (conditionally included)
#[cfg(feature = "grpc")]
let grpc_server = grpc_server::start(config.clone(), app_state.services.clone()).await?;
let app = Router::new()
.route("/health", get(health::health_check))
.nest("/orders", handlers::orders::routes())
// ... other route nests
.route("/proto_endpoint", post(handle_proto_request))
.layer(Extension(app_state))
.layer(Extension(schema))
.layer(TraceLayer::new_for_http())
.layer(CompressionLayer::new())
.layer(axum::middleware::from_fn(auth::auth_middleware))
.layer(axum::middleware::from_fn(rate_limiter::rate_limit_middleware));
let addr = format!("{}:{}", config.host, config.port);
info!(log, "StateSet API server running"; "address" => &addr);
axum::Server::bind(&addr.parse().unwrap())
.serve(app.into_make_service())
.await
.unwrap();
info!(log, "Shutting down");
Ok(())
}
```
> This shows the main entry point of the server including the config loading, setup of global services, the route definition, telemetry and the server startup
### Handlers: API Request Routing
Here are some examples of how API requests are routed to the correct command.
#### Create Order Handler
```rust theme={null}
async fn create_order(
State(order_service): State>,
Json(command): Json,
) -> Result {
let result = command.execute(order_service).await?;
Ok(Json(result))
}
```
> This handler pulls the OrderService from the application state and calls the execute method on the CreateOrderCommand
#### Close Return Handler
```rust theme={null}
async fn close_return(
State(return_service): State>,
Path(return_id): Path,
) -> Result {
let command = CloseReturnCommand { return_id };
let closed_return = command.execute(return_service).await?;
Ok(Json(closed_return))
}
```
> This handler pulls the ReturnService from the application state and calls the execute method on the CloseReturnCommand
### Commands: Business Logic Execution
The following shows the Create Order and Close Return commands which handle the business logic.
#### Create Order Command
```rust theme={null}
#[derive(Debug, Serialize, Deserialize, Validate)]
pub struct CreateOrderCommand {
pub customer_id: Uuid,
#[validate(length(min = 1, message = "At least one item is required"))]
pub items: Vec,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct OrderItem {
pub product_id: Uuid,
#[validate(range(min = 1))]
pub quantity: i32,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct CreateOrderResult {
pub id: Uuid,
pub customer_id: Uuid,
pub status: String,
pub created_at: DateTime,
pub items: Vec,
}
#[async_trait::async_trait]
impl Command for CreateOrderCommand {
type Result = CreateOrderResult;
#[instrument(skip(self, db_pool, event_sender))]
async fn execute(
&self,
db_pool: Arc,
event_sender: Arc,
) -> Result {
// Validates the incoming command. Returns a validation error if invalid
self.validate().map_err(|e| {
ORDER_CREATION_FAILURES.inc();
let msg = format!("Invalid input: {}", e);
error!("{}", msg);
ServiceError::ValidationError(msg)
})?;
let db = db_pool.as_ref();
let saved_order = self.create_order(db).await?;
self.log_and_trigger_event(&event_sender, &saved_order).await?;
ORDER_CREATIONS.inc();
Ok(CreateOrderResult {
id: saved_order.id,
customer_id: saved_order.customer_id,
status: saved_order.status,
created_at: saved_order.created_at.and_utc(),
items: self.items.clone(),
})
}
}
// ... create order implementation
```
> This shows the command definition, validation, and execution of the create order command.
#### Close Return Command
```rust theme={null}
#[derive(Debug, Serialize, Deserialize)]
pub struct CloseReturnCommand {
pub return_id: Uuid,
}
#[derive(Debug, Serialize, Deserialize)]
pub struct CloseReturnResult {
pub id: Uuid,
pub object: String,
pub completed: bool,
}
#[async_trait::async_trait]
impl Command for CloseReturnCommand {
type Result = CloseReturnResult;
#[instrument(skip(self, db_pool, event_sender))]
async fn execute(
&self,
db_pool: Arc,
event_sender: Arc,
) -> Result {
let db = db_pool.as_ref();
let completed_return = self.close_return(db).await?;
self.log_and_trigger_event(&event_sender, &completed_return)
.await?;
Ok(CloseReturnResult {
id: completed_return.id,
object: "return".to_string(),
completed: true,
})
}
}
// ... close return implementation
```
> This shows the command definition, and execution of the close return command.
### Queries: Data Retrieval
These show the two return queries used by the application.
#### Get Returns By Order Query
```rust theme={null}
#[derive(Debug, Serialize, Deserialize)]
pub struct GetReturnsByOrderQuery {
pub order_id: i32,
}
#[async_trait]
impl Query for GetReturnsByOrderQuery {
type Result = Vec;
async fn execute(&self, db_pool: Arc) -> Result {
let db = db_pool.get().map_err(|_| ServiceError::DatabaseError)?;
Return::find()
.filter(Return::Column::OrderId.eq(self.order_id))
.all(&db)
.await
.map_err(|_| ServiceError::DatabaseError)
}
}
```
> This shows how we can find the returns based on the order ID using SeaORM
#### Get Returns By Date Range Query
```rust theme={null}
#[derive(Debug, Serialize, Deserialize)]
pub struct GetReturnsByDateRangeQuery {
pub start_date: DateTime,
pub end_date: DateTime,
pub limit: u64,
pub offset: u64,
}
#[async_trait]
impl Query for GetReturnsByDateRangeQuery {
type Result = Vec;
async fn execute(&self, db_pool: Arc) -> Result {
let db = db_pool.get().map_err(|_| ServiceError::DatabaseError)?;
Return::find()
.filter(Return::Column::CreatedAt.between(self.start_date, self.end_date))
.order_by_desc(Return::Column::CreatedAt)
.limit(self.limit)
.offset(self.offset)
.all(&db)
.await
.map_err(|_| ServiceError::DatabaseError)
}
}
```
> This shows how we can find the returns based on a date range using SeaORM.
To learn more about SeaORM, check out [this article](https://www.sea-ql.org/blog/2024-08-04-sea-orm-1.0/).
## Acknowledgments
We express our gratitude to the open-source community and the creators of the following libraries:
* [Axum](https://github.com/tokio-rs/axum/) for the powerful web framework.
* [SeaORM](https://www.sea-ql.org/SeaORM) for providing a robust ORM.
* [Tonic](https://github.com/hyperium/tonic) for enabling gRPC support.
* [Async-GraphQL](https://async-graphql.github.io/) for efficient GraphQL handling.
# Build to Stock
Source: https://docs.stateset.com/api-reference/billofmaterials/buildtostock
POST https://api.stateset.com/v1/bill_of_materials/:id/buildtostock
This endpoint updates the status of a bill of materials to build to stock.
### Body
The ID provided in the data tab may be used to identify the bill\_of\_materials
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/bill_of_materials/:id/buildtostock' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```js Node.js theme={null}
const buildToStock = await stateset.billofmaterials.buildToStock({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "bill_of_materials",
"built_to_stock": true
}
```
# Create Bill of Materials
Source: https://docs.stateset.com/api-reference/billofmaterials/create
POST https://api.stateset.com/v1/bill_of_materials
This endpoint creates a new bill of materials
### Body
This is the id of the bill of materials
This is the number of the bill of materials
This is the name of the bill of materials
This is the description of the bill of materials
This is the groups of the bill of materials
This is the date and time when the bill of materials was created
This is the date and time when the bill of materials was last updated
This indicates whether the bill of materials is valid or not
### Response
This is the id of the bill of materials.
This is the number of the bill of materials.
This is the name of the bill of materials.
This is the description of the bill of materials.
This is the groups of the bill of materials.
This is the date and time when the bill of materials was created.
This is the date and time when the bill of materials was last updated.
This indicates whether the bill of materials is valid or not.
This is an array of line items associated with the bill of materials.
This is the id of the line item.
This is the number of the bill of materials to which the line item belongs.
This is the type or category of the line item.
This is the number or code associated with the part or item.
This is the name of the part or item.
This is the type or category of the purchase/supply associated with the line item.
This is the quantity of the part or item required in the bill of materials.
This is the status or state of the line item.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/bill_of_materials' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b"
}'
```
```graphQL GraphQL theme={null}
mutation addBillOfMaterial($bill_of_material: bill_of_materials_insert_input!) {
insert_bill_of_materials(objects: [$bill_of_material]) {
returning {
id
}
}
}
```
```javascript Node.js theme={null}
const created = await stateset.billofmaterials.create(
'bom_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
created = stateset.billofmaterials.create(
'bom_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
created = Stateset::BillOfMaterials.create(
'bom_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$created = $stateset->billofmaterials->create(
'bom_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
created, err := stateset.BillOfMaterials.Create(
'bom_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
BillOfMaterials created = stateset.billOfMaterials.create(
'bom_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"name": "Bill of Materials",
"description": "Bill of Materials",
"groups": "Bill of Materials",
"created_at": "2021-01-01T00:00:00.000Z",
"updated_at": "2021-01-01T00:00:00.000Z",
"valid": true,
"line_items": [
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"bill_of_materials_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"line_type": "Bill of Materials",
"part_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"part_name": "Bill of Materials",
"purchase_supply_type": "Bill of Materials",
"quantity": 1,
"status": "Bill of Materials"
}
]
}
}
```
# Delete Bill Of Materials
Source: https://docs.stateset.com/api-reference/billofmaterials/delete
DELETE https://api.return.com/v1/bill_of_materials
This endpoint deletes an existing bill of materials.
### Body
The id of the bill of materials to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/bill_of_materials' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "bom_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteBillOfMaterials ($id: String!) {
delete_bill_of_materials(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```javascript Node.js theme={null}
const billOfMaterials = await stateset.billofmaterials.del({
'bom_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```python Python theme={null}
billOfMaterials = stateset.billofmaterials.del({
'bom_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```ruby Ruby theme={null}
billOfMaterials = Stateset::BillOfMaterials.delete({
'bom_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$billOfMaterials = $stateset->billOfMaterials->delete([
'bom_1NXWPnCo6bFb1KQto6C8OWvE'
]);
```
```go Go theme={null}
billOfMaterials, err := stateset.BillOfMaterials.Delete(
"bom_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
BillOfMaterials billOfMaterials = stateset.billOfMaterials.delete(
"bom_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```json Response theme={null}
{
"id": "bom_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "billofmaterials",
"deleted": true
}
```
# Get Bill Of Materials
Source: https://docs.stateset.com/api-reference/billofmaterials/get
GET https://api.stateset.com/v1/bill_of_materials/:id
This endpoint gets or creates a new bill of materials.
### Body
This is the id of the bill of materials to get. If the id is not provided, a new bill of materials will be created.
### Response
This is the id of the bill of materials.
This is the number of the bill of materials.
This is the name of the bill of materials.
This is the description of the bill of materials.
This is the groups of the bill of materials.
This is the date and time when the bill of materials was created.
This is the date and time when the bill of materials was last updated.
This indicates whether the bill of materials is valid or not.
This is an array of line items associated with the bill of materials.
This is the id of the line item.
This is the number of the bill of materials to which the line item belongs.
This is the type or category of the line item.
This is the number or code associated with the part or item.
This is the name of the part or item.
This is the type or category of the purchase/supply associated with the line item.
This is the quantity of the part or item required in the bill of materials.
This is the status or state of the line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/bill_of_materials' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b"
}'
```
```graphQL GraphQL theme={null}
query MyBillOfMaterials {
bill_of_materials {
created_at
description
groups
id
number
name
updated_at
valid
bill_of_material_line_items {
bill_of_materials_number
id
line_type
part_name
part_number
purchase_supply_type
quantity
status
}
}
}
```
```js Node.js theme={null}
var billOfMaterials = stateset.billofmaterials.retrieve({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
});
```
```python Python theme={null}
bill_of_materials = stateset.billofmaterials.retrieve({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
})
```
```ruby Ruby theme={null}
bill_of_materials = Stateset::BillOfMaterials.retreive({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
})
```
```php PHP theme={null}
$bill_of_materials = $stateset->billofmaterials->retrieve({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
});
```
```go Go theme={null}
bill_of_materials, err := stateset.BillOfMaterials.Retrieve({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
})
```
```java Java theme={null}
BillOfMaterials billOfMaterials = stateset.billOfMaterials.retrieve({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
});
```
```json Response theme={null}
{
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"name": "Bill of Materials",
"description": "Bill of Materials",
"groups": "Bill of Materials",
"created_at": "2021-01-01T00:00:00.000Z",
"updated_at": "2021-01-01T00:00:00.000Z",
"valid": true,
"line_items": [
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"bill_of_materials_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"line_type": "Bill of Materials",
"part_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"part_name": "Bill of Materials",
"purchase_supply_type": "Bill of Materials",
"quantity": 1,
"status": "Bill of Materials"
}
]
}
}
```
### Bill Of Materials
| Name | Type | Description |
| ----------- | --------- | ------------------------------------------------------------- |
| created\_at | Date/Time | Date and time when the bill of materials was created |
| description | Text | Description or additional details about the bill of materials |
| groups | Text | Groups or categories associated with the bill of materials |
| id | Text | Unique identifier for the bill of materials |
| number | Text | Number associated with the bill of materials |
| name | Text | Name of the bill of materials |
| updated\_at | Date/Time | Date and time when the bill of materials was last updated |
| valid | Boolean | Indicates whether the bill of materials is valid or not |
### Bill Of Materials Line Item
| Name | Type | Description |
| --------------------------- | ------- | --------------------------------------------------------------------------- |
| bill\_of\_materials\_number | Text | Number associated with the bill of materials to which the line item belongs |
| id | Text | Unique identifier for the line item |
| line\_type | Text | Type or category of the line item |
| part\_name | Text | Name of the part or item included in the bill of materials |
| part\_number | Text | Number or code associated with the part or item |
| purchase\_supply\_type | Text | Type or category of the purchase/supply associated with the line item |
| quantity | Numeric | Quantity of the part or item required in the bill of materials |
| status | Text | Status or state of the line item |
# List Bill Of Materials
Source: https://docs.stateset.com/api-reference/billofmaterials/list
GET https://api.stateset.com/v1/bill_of_materials/list
This endpoint lists the bill of materials.
### Body
This is the limit of the bill of materials.
This is the offset of the bill of materials.
This is the order direction of the bill of materials.
### Response
This is the id of the bill of materials.
This is the number of the bill of materials.
This is the name of the bill of materials.
This is the description of the bill of materials.
This is the groups of the bill of materials.
This is the date and time when the bill of materials was created.
This is the date and time when the bill of materials was last updated.
This indicates whether the bill of materials is valid or not.
This is an array of line items associated with the bill of materials.
This is the id of the line item.
This is the number of the bill of materials to which the line item belongs.
This is the type or category of the line item.
This is the number or code associated with the part or item.
This is the name of the part or item.
This is the type or category of the purchase/supply associated with the line item.
This is the quantity of the part or item required in the bill of materials.
This is the status or state of the line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/bill_of_materials' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "asc"
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
bill_of_materials(limit: $limit, offset: $offset, order_by: {created_at: $order_direction}) {
created_at
description
groups
id
number
name
updated_at
valid
bill_of_material_line_items {
bill_of_materials_number
id
line_type
part_name
part_number
purchase_supply_type
quantity
status
}
}
}
```
```js Node.js theme={null}
var billOfMaterials = stateset.billofmaterials.list({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
});
```
```python Python theme={null}
bill_of_materials = stateset.billofmaterials.list({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
})
```
```ruby Ruby theme={null}
bill_of_materials = Stateset::BillOfMaterials.retreive({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
})
```
```php PHP theme={null}
$bill_of_materials = $stateset->billofmaterials->list({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
});
```
```go Go theme={null}
bill_of_materials, err := stateset.BillOfMaterials.list({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
})
```
```java Java theme={null}
BillOfMaterials billOfMaterials = stateset.billOfMaterials.list({
'5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b'
});
```
```json Response theme={null}
{
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"name": "Bill of Materials",
"description": "Bill of Materials",
"groups": "Bill of Materials",
"created_at": "2021-01-01T00:00:00.000Z",
"updated_at": "2021-01-01T00:00:00.000Z",
"valid": true,
"line_items": [
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"bill_of_materials_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"line_type": "Bill of Materials",
"part_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"part_name": "Bill of Materials",
"purchase_supply_type": "Bill of Materials",
"quantity": 1,
"status": "Bill of Materials"
}
]
}
}
```
### Bill Of Materials
| Name | Type | Description |
| ----------- | --------- | ------------------------------------------------------------- |
| created\_at | Date/Time | Date and time when the bill of materials was created |
| description | Text | Description or additional details about the bill of materials |
| groups | Text | Groups or categories associated with the bill of materials |
| id | Text | Unique identifier for the bill of materials |
| number | Text | Number associated with the bill of materials |
| name | Text | Name of the bill of materials |
| updated\_at | Date/Time | Date and time when the bill of materials was last updated |
| valid | Boolean | Indicates whether the bill of materials is valid or not |
### Bill Of Materials Line Item
| Name | Type | Description |
| --------------------------- | ------- | --------------------------------------------------------------------------- |
| bill\_of\_materials\_number | Text | Number associated with the bill of materials to which the line item belongs |
| id | Text | Unique identifier for the line item |
| line\_type | Text | Type or category of the line item |
| part\_name | Text | Name of the part or item included in the bill of materials |
| part\_number | Text | Number or code associated with the part or item |
| purchase\_supply\_type | Text | Type or category of the purchase/supply associated with the line item |
| quantity | Numeric | Quantity of the part or item required in the bill of materials |
| status | Text | Status or state of the line item |
# Update Bill of Materials
Source: https://docs.stateset.com/api-reference/billofmaterials/update
PUT https://api.stateset.com/v1/bill_of_materials/:id
This endpoint updates an existing bill of materials.
### Body
This is the id of the bill of materials
This is the number of the bill of materials
This is the name of the bill of materials
This is the description of the bill of materials
This is the groups of the bill of materials
This is the date and time when the bill of materials was created
This is the date and time when the bill of materials was last updated
This indicates whether the bill of materials is valid or not
### Response
This is the id of the bill of materials.
This is the number of the bill of materials.
This is the name of the bill of materials.
This is the description of the bill of materials.
This is the groups of the bill of materials.
This is the date and time when the bill of materials was created.
This is the date and time when the bill of materials was last updated.
This indicates whether the bill of materials is valid or not.
This is an array of line items associated with the bill of materials.
This is the id of the line item.
This is the number of the bill of materials to which the line item belongs.
This is the type or category of the line item.
This is the number or code associated with the part or item.
This is the name of the part or item.
This is the type or category of the purchase/supply associated with the line item.
This is the quantity of the part or item required in the bill of materials.
This is the status or state of the line item.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/bill_of_materials' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```javascript Node.js theme={null}
const updated = await stateset.billofmaterials.update(
'bom_ODkRWQtx9NVsRX'
);
```
```graphQL GraphQL theme={null}
mutation (
$id: String
$bill_of_materials: bill_of_materials_set_input!
) {
update_bill_of_materials (
where: { id : { _eq: $id}}
_set: $bill_of_materials
) {
returning {
created_at
description
groups
id
number
name
updated_at
valid
}
}
}`;
```
```python Python theme={null}
updated = stateset.billofmaterials.update(
'bom_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
updated = Stateset::BillOfMaterials.update(
'bom_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$updated = $stateset->billofmaterials->update(
'bom_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
updated, err := stateset.BillOfMaterials.Update(
'bom_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
BillOfMaterials updated = stateset.billOfMaterials.update(
'bom_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"name": "Bill of Materials",
"description": "Bill of Materials",
"groups": "Bill of Materials",
"created_at": "2021-01-01T00:00:00.000Z",
"updated_at": "2021-01-01T00:00:00.000Z",
"valid": true,
"line_items": [
{
"id": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"bill_of_materials_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"line_type": "Bill of Materials",
"part_number": "5f7b1b4a-5b0b-4b0a-8b0b-4b0a5b0b4a5b",
"part_name": "Bill of Materials",
"purchase_supply_type": "Bill of Materials",
"quantity": 1,
"status": "Bill of Materials"
}
]
}
}
```
# Create Bill of Materials Line Item
Source: https://docs.stateset.com/api-reference/billofmaterialslineitem/create
POST https://api.stateset.com/api/bill_of_materials_line_items
This endpoint creates a new bill of materials line item.
### Body
This is the id of the bill of materials line item.
This is the part number of the bill of materials line item.
This is the part name of the bill of materials line item.
This is the quantity of the bill of materials line item.
This is the purchase supply type of the bill of materials line item.
This is the bill of materials number of the bill of materials line item.
### Response
This is the id of the bill of materials line item.
This is the number of the bill of materials to which the line item belongs.
This is the type or category of the line item.
This is the name of the part or item included in the bill of materials.
This is the number or code associated with the part or item.
This is the type or category of the purchase/supply associated with the line item.
This is the quantity of the part or item required in the bill of materials.
This is the status or state of the line item.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/api/bill_of_materials_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```graphQL GraphQL theme={null}
mutation AddBillOfMaterialLineItem($bill_of_material_line_item: bill_of_material_line_items_insert_input!) {
insert_bill_of_material_line_items(objects: [$bill_of_material_line_item]) {
returning {
...BillOfMaterialLineItemFields
}
}
}
fragment BillOfMaterialLineItemFields on bill_of_material_line_items {
id
part_number
part_name
quantity
purchase_supply_type
bill_of_materials_number
}
```
```js Node.js theme={null}
const created = await stateset.billofmaterialItems.create(
'bomi_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
created = stateset.billofmaterialItems.create(
'bomi_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
created = Stateset::BillOfMaterialItems.create(
'bomi_ODkRWQtx9NVsRX'
)
```
```go Golang theme={null}
created, err := stateset.BillOfMaterialItems.Create(
'bomi_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
BillOfMaterialItems created = stateset.billOfMaterialItems.create(
'bomi_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
{
"data": {
"insert_bill_of_material_line_items": {
"returning": [
{
"id": "bomli_1",
"bill_of_materials_number": "bom_1",
"line_type": "part",
"part_name": "Part 1",
"part_number": "P1",
"purchase_supply_type": "purchase",
"quantity": 1,
"status": "active"
}
]
}
}
}
}
```
# Delete Bill of Materials Line Item
Source: https://docs.stateset.com/api-reference/billofmaterialslineitem/delete
DELETE https://api.return.com/v1/bill_of_materials_line_items/:id
This endpoint deletes an existing bill of materials line item.
### Body
The id of the bill of materials line item you want to delete
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/bill_of_materials_line_item/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1"
"current_token": "abcdef"
}'
```
```graphQL GraphQL theme={null}
mutation deleteBillOfMaterialLineItem($bill_of_material_line_item_id: uuid!) {
delete_bill_of_material_line_items(where: { id: { _eq: $bill_of_material_line_item_id } }) {
affected_rows
}
}
```
```javascript Node.js theme={null}
const created = await stateset.billofmaterialItems.del(
'bomi_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
created = stateset.billofmaterialItems.del(
'bomi_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
created = Stateset::BillofmaterialItems.del(
'bomi_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$created = $stateset->billofmaterialItems->del(
'bomi_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
created, err := stateset.BillofmaterialItems.Del(
'bomi_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
BillofmaterialItemsResponse created = stateset.billofmaterialItems.del(
'bomi_ODkRWQtx9NVsRX'
);
```
```csharp C# theme={null}
var created = stateset.BillofmaterialItems.Del(
'bomi_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"id": "bomi_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "bill_of_materials_line_item",
"deleted": true
}
```
# Get Bill of Materials Line Item
Source: https://docs.stateset.com/api-reference/billofmaterialslineitem/get
GET https://api.stateset.com/v1/bill_of_materials_line_items/:id
This endpoint gets or creates a new bill of materials line item.
### Body
This is the id of the bill of materials line item. If this is not provided, a new bill of materials line item will be created.
### Response
This is the id of the bill of materials line item.
This is the number of the bill of materials to which the line item belongs.
This is the type or category of the line item.
This is the name of the part or item included in the bill of materials.
This is the number or code associated with the part or item.
This is the type or category of the purchase/supply associated with the line item.
This is the quantity of the part or item required in the bill of materials.
This is the status or state of the line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/bill_of_materials_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
'id': '1'
}'
```
```json Response theme={null}
{
{
"id": "1",
"bill_of_materials_number": "1",
"line_type": "1",
"part_name": "1",
"part_number": "1",
"purchase_supply_type": "1",
"quantity": "1",
"status": "1"
}
}
```
### Bill Of Materials Line Item
| Name | Type | Description |
| --------------------------- | ------- | --------------------------------------------------------------------------- |
| bill\_of\_materials\_number | Text | Number associated with the bill of materials to which the line item belongs |
| id | Text | Unique identifier for the line item |
| line\_type | Text | Type or category of the line item |
| part\_name | Text | Name of the part or item included in the bill of materials |
| part\_number | Text | Number or code associated with the part or item |
| purchase\_supply\_type | Text | Type or category of the purchase/supply associated with the line item |
| quantity | Numeric | Quantity of the part or item required in the bill of materials |
| status | Text | Status or state of the line item |
# Update Bill of Materials Line Item
Source: https://docs.stateset.com/api-reference/billofmaterialslineitem/update
PUT https://api.stateset.com/v1/bill_of_materials_line_items/:id
This endpoint updates an existing bill of materials line item.
### Body
This is the id of the bill of materials line item.
This is the part number of the bill of materials line item.
This is the part name of the bill of materials line item.
This is the quantity of the bill of materials line item.
This is the purchase supply type of the bill of materials line item.
This is the bill of materials number of the bill of materials line item.
### Response
This is the id of the bill of materials line item.
This is the number of the bill of materials to which the line item belongs.
This is the type or category of the line item.
This is the name of the part or item included in the bill of materials.
This is the number or code associated with the part or item.
This is the type or category of the purchase/supply associated with the line item.
This is the quantity of the part or item required in the bill of materials.
This is the status or state of the line item.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/bill_of_materials_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```graphQL GraphQL theme={null}
mutation (
$id: uuid
$bill_of_material_line_item: bill_of_material_line_items_set_input!
) {
update_bill_of_material_line_items(
where: { id: { _eq: $id } }
_set: $bill_of_material_line_item
) {
returning {
id
}
}
}
```
```javascript Node.js theme={null}
const update = await stateset.billofmaterialItems.update(
'bomi_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
update = stateset.billofmaterialItems.update(
'bomi_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
update = Stateset::BillofmaterialItems.update(
'bomi_ODkRWQtx9NVsRX'
)
```
```json Response theme={null}
{
"data": {
"update_bill_of_material_line_items": {
"returning": [
{
"id": "bomi_ODkRWQtx9NVsRX"
}
]
}
}
}
```
# Add Item to Cart
Source: https://docs.stateset.com/api-reference/cart/add-item
POST https://api.stateset.com/v1/carts/:id/items
Add a product to an existing cart
This endpoint adds one or more items to a cart. If the item already exists, it updates the quantity. Inventory availability is checked in real-time.
## Authentication
This endpoint requires a valid API key with `carts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the cart
## Request Body
Product ID to add
Product variant ID (required if product has variants)
Quantity to add (must be positive)
Custom price in cents (requires special permissions)
Special instructions for this item
Custom fields for the item
Check inventory availability before adding
Replace existing quantity instead of adding to it
### Response
Returns the updated cart object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/carts/cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/items' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"product_id": "prod_789",
"variant_id": "var_red_medium",
"quantity": 1,
"notes": "Gift wrap please"
}'
```
```javascript Node.js theme={null}
const cart = await stateset.carts.addItem(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
product_id: "prod_789",
variant_id: "var_red_medium",
quantity: 1,
notes: "Gift wrap please"
}
);
```
```python Python theme={null}
cart = stateset.carts.add_item(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
product_id="prod_789",
variant_id="var_red_medium",
quantity=1,
notes="Gift wrap please"
)
```
```json Response theme={null}
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"status": "active",
"items": [
{
"id": "ci_abc123",
"product_id": "prod_123",
"variant_id": "var_blue_large",
"product_name": "Wireless Headphones",
"variant_name": "Blue - Large",
"quantity": 2,
"unit_price": 9999,
"subtotal": 19998
},
{
"id": "ci_def456",
"product_id": "prod_456",
"product_name": "USB-C Cable",
"quantity": 1,
"unit_price": 1999,
"subtotal": 1999
},
{
"id": "ci_ghi789",
"product_id": "prod_789",
"variant_id": "var_red_medium",
"product_name": "T-Shirt",
"variant_name": "Red - Medium",
"quantity": 1,
"unit_price": 2499,
"subtotal": 2499,
"notes": "Gift wrap please",
"inventory_status": "in_stock",
"available_quantity": 15
}
],
"item_count": 4,
"unique_item_count": 3,
"subtotal": 24496,
"tax_amount": 0,
"shipping_amount": 0,
"discount_amount": 2000,
"total": 22496,
"updated_at": "2024-06-20T15:00:00Z",
"last_activity": "2024-06-20T15:00:00Z",
"messages": [
{
"type": "info",
"message": "Item added successfully"
}
]
}
```
# Apply Coupon
Source: https://docs.stateset.com/api-reference/cart/apply-coupon
POST https://api.stateset.com/v1/carts/:id/coupons
Apply a coupon or promotion code to the cart
This endpoint applies a coupon code to the cart. The system validates the coupon and calculates applicable discounts based on cart contents and customer eligibility.
## Authentication
This endpoint requires a valid API key with `carts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the cart
## Request Body
Coupon or promotion code to apply
Only validate without applying (preview discount)
### Response
Returns the updated cart with applied discount.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/carts/cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/coupons' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"code": "WELCOME10"
}'
```
```javascript Node.js theme={null}
const cart = await stateset.carts.applyCoupon(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
code: "WELCOME10"
}
);
```
```python Python theme={null}
cart = stateset.carts.apply_coupon(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
code="WELCOME10"
)
```
```json Response theme={null}
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"status": "active",
"items": [
{
"id": "ci_abc123",
"product_id": "prod_123",
"quantity": 3,
"unit_price": 9999,
"subtotal": 29997,
"discounts": [
{
"promotion_id": "promo_welcome10",
"code": "WELCOME10",
"amount": 2999,
"type": "percentage"
}
],
"final_price": 26997
},
{
"id": "ci_ghi789",
"product_id": "prod_789",
"quantity": 1,
"unit_price": 2499,
"subtotal": 2499,
"discounts": [
{
"promotion_id": "promo_welcome10",
"code": "WELCOME10",
"amount": 250,
"type": "percentage"
}
],
"final_price": 2249
}
],
"subtotal": 32496,
"discount_amount": 3249,
"tax_amount": 2268,
"shipping_amount": 599,
"total": 32114,
"applied_coupons": [
{
"code": "WELCOME10",
"promotion_id": "promo_welcome10",
"promotion_name": "Welcome 10% Off",
"discount_amount": 3249,
"applied_at": "2024-06-20T16:30:00Z"
}
],
"messages": [
{
"type": "success",
"message": "Coupon applied successfully. You saved $32.49!"
}
]
}
```
# Checkout Cart
Source: https://docs.stateset.com/api-reference/cart/checkout
POST https://api.stateset.com/v1/carts/:id/checkout
Convert a cart into an order and process payment
This endpoint initiates the checkout process, converting a cart into an order. It validates inventory, calculates final totals, and processes payment.
## Authentication
This endpoint requires a valid API key with `carts:write` and `orders:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the cart to checkout
## Request Body
Payment method details
Payment type: "card", "ach", "wire", "purchase\_order"
Saved payment method ID
Card details (if not using saved method)
Card number
Expiration month
Expiration year
CVC code
Billing address
Street address
Apartment, suite, etc.
City
State/Province code
Postal/ZIP code
ISO 3166-1 alpha-2 country code
Shipping address (uses billing if not provided)
Same structure as billing address
Selected shipping method ID
Special instructions for the order
Purchase order number (for B2B)
Additional order metadata
### Response
Returns the created order object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/carts/cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/checkout' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"payment_method": {
"type": "card",
"payment_method_id": "pm_saved_123"
},
"billing_address": {
"line1": "123 Main St",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"shipping_method_id": "ship_standard",
"customer_note": "Please leave at front door"
}'
```
```javascript Node.js theme={null}
const order = await stateset.carts.checkout(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
payment_method: {
type: "card",
payment_method_id: "pm_saved_123"
},
billing_address: {
line1: "123 Main St",
city: "San Francisco",
state: "CA",
postal_code: "94105",
country: "US"
},
shipping_method_id: "ship_standard",
customer_note: "Please leave at front door"
}
);
```
```python Python theme={null}
order = stateset.carts.checkout(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
payment_method={
"type": "card",
"payment_method_id": "pm_saved_123"
},
billing_address={
"line1": "123 Main St",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
shipping_method_id="ship_standard",
customer_note="Please leave at front door"
)
```
```json Response theme={null}
{
"id": "order_123456",
"object": "order",
"cart_id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"order_number": "ORD-2024-123456",
"customer_id": "cust_abc123",
"status": "processing",
"payment_status": "paid",
"fulfillment_status": "unfulfilled",
"items": [
{
"id": "oi_abc123",
"product_id": "prod_123",
"variant_id": "var_blue_large",
"product_name": "Wireless Headphones",
"variant_name": "Blue - Large",
"sku": "WH-BL-L",
"quantity": 3,
"unit_price": 9999,
"discount_amount": 2999,
"subtotal": 26997
},
{
"id": "oi_def456",
"product_id": "prod_789",
"variant_id": "var_red_medium",
"product_name": "T-Shirt",
"variant_name": "Red - Medium",
"sku": "TS-RD-M",
"quantity": 1,
"unit_price": 2499,
"discount_amount": 250,
"subtotal": 2249
}
],
"subtotal": 32496,
"discount_amount": 3249,
"tax_amount": 2268,
"shipping_amount": 599,
"total": 32114,
"currency": "USD",
"payment": {
"id": "pay_xyz789",
"method": "card",
"last4": "4242",
"brand": "visa",
"status": "succeeded",
"amount": 32114
},
"shipping_address": {
"line1": "123 Main St",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"shipping_method": {
"id": "ship_standard",
"name": "Standard Shipping",
"amount": 599,
"estimated_delivery": "2024-06-25"
},
"customer_note": "Please leave at front door",
"created_at": "2024-06-20T17:00:00Z",
"updated_at": "2024-06-20T17:00:00Z",
"metadata": {
"source": "web_checkout"
}
}
```
# Clear Cart
Source: https://docs.stateset.com/api-reference/cart/clear
POST https://api.stateset.com/v1/carts/:id/clear
Remove all items from a cart
This endpoint removes all items from a cart while preserving the cart itself, customer information, and applied settings. Useful for "Clear Cart" functionality.
## Authentication
This endpoint requires a valid API key with `carts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the cart to clear
## Request Body
Keep applied coupon codes
Reason for clearing the cart (for analytics)
### Response
Returns the cleared cart object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/carts/cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/clear' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"preserve_coupons": false,
"reason": "customer_requested"
}'
```
```javascript Node.js theme={null}
const cart = await stateset.carts.clear(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
preserve_coupons: false,
reason: "customer_requested"
}
);
```
```python Python theme={null}
cart = stateset.carts.clear(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
preserve_coupons=False,
reason="customer_requested"
)
```
```json Response theme={null}
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"session_id": "sess_xyz789",
"channel": "web",
"currency": "USD",
"locale": "en-US",
"status": "active",
"items": [],
"item_count": 0,
"unique_item_count": 0,
"subtotal": 0,
"tax_amount": 0,
"shipping_amount": 0,
"discount_amount": 0,
"total": 0,
"shipping_address": {
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"applied_coupons": [],
"applied_promotions": [],
"expires_at": "2024-07-20T10:00:00Z",
"created_at": "2024-06-20T10:00:00Z",
"updated_at": "2024-06-20T17:30:00Z",
"last_activity": "2024-06-20T17:30:00Z",
"cleared_at": "2024-06-20T17:30:00Z",
"metadata": {
"clear_reason": "customer_requested",
"items_cleared": 3
},
"messages": [
{
"type": "info",
"message": "Cart has been cleared"
}
]
}
```
# Create Cart
Source: https://docs.stateset.com/api-reference/cart/create
POST https://api.stateset.com/v1/carts
Create a new shopping cart for a customer or guest session
This endpoint creates a new shopping cart that persists across sessions. Carts can be associated with authenticated customers or anonymous sessions.
## Authentication
This endpoint requires a valid API key with `carts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Customer ID to associate with the cart (for authenticated users)
Session ID for guest carts (auto-generated if not provided)
Sales channel: "web", "mobile", "pos", "api"
ISO 4217 currency code
Locale for the cart (e.g., "en-US")
Initial items to add to the cart
Product ID
Product variant ID
Quantity to add
Override price in cents (for custom pricing)
Custom fields for the item
Shipping address for tax/shipping calculations
Street address
Apartment, suite, etc.
City
State/Province code
Postal/ZIP code
ISO 3166-1 alpha-2 country code
Email for guest checkout and abandoned cart recovery
Custom expiration date (ISO 8601, default: 30 days)
Additional custom fields
### Response
Returns the created cart object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/carts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"customer_id": "cust_abc123",
"channel": "web",
"currency": "USD",
"locale": "en-US",
"items": [
{
"product_id": "prod_123",
"variant_id": "var_blue_large",
"quantity": 2
}
],
"shipping_address": {
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
}
}'
```
```javascript Node.js theme={null}
const cart = await stateset.carts.create({
customer_id: "cust_abc123",
channel: "web",
currency: "USD",
locale: "en-US",
items: [
{
product_id: "prod_123",
variant_id: "var_blue_large",
quantity: 2
}
],
shipping_address: {
city: "San Francisco",
state: "CA",
postal_code: "94105",
country: "US"
}
});
```
```python Python theme={null}
cart = stateset.carts.create(
customer_id="cust_abc123",
channel="web",
currency="USD",
locale="en-US",
items=[
{
"product_id": "prod_123",
"variant_id": "var_blue_large",
"quantity": 2
}
],
shipping_address={
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
}
)
```
```json Response theme={null}
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"session_id": "sess_xyz789",
"channel": "web",
"currency": "USD",
"locale": "en-US",
"status": "active",
"items": [
{
"id": "ci_abc123",
"product_id": "prod_123",
"variant_id": "var_blue_large",
"product_name": "Wireless Headphones",
"variant_name": "Blue - Large",
"sku": "WH-BL-L",
"quantity": 2,
"unit_price": 9999,
"list_price": 9999,
"subtotal": 19998,
"discounts": [],
"image_url": "https://images.stateset.com/products/wh-blue-large.jpg",
"metadata": {}
}
],
"item_count": 2,
"unique_item_count": 1,
"subtotal": 19998,
"tax_amount": 0,
"shipping_amount": 0,
"discount_amount": 0,
"total": 19998,
"shipping_address": {
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"available_shipping_methods": [],
"applied_coupons": [],
"applied_promotions": [],
"expires_at": "2024-07-20T10:00:00Z",
"created_at": "2024-06-20T10:00:00Z",
"updated_at": "2024-06-20T10:00:00Z",
"metadata": {}
}
```
# Get Cart
Source: https://docs.stateset.com/api-reference/cart/get
GET https://api.stateset.com/v1/carts/:id
Retrieve details of a specific shopping cart
This endpoint retrieves the current state of a shopping cart, including all items, calculated totals, and applied discounts.
## Authentication
This endpoint requires a valid API key with `carts:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the cart
## Query Parameters
Expand related objects: "items.product", "customer", "shipping\_methods"
Calculate available shipping methods (requires shipping address)
Calculate tax amount (requires shipping address)
### Response
Returns the cart object if found.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/carts/cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30?calculate_shipping=true&calculate_tax=true' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const cart = await stateset.carts.retrieve(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
calculate_shipping: true,
calculate_tax: true
}
);
```
```python Python theme={null}
cart = stateset.carts.retrieve(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
calculate_shipping=True,
calculate_tax=True
)
```
```json Response theme={null}
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"customer": {
"id": "cust_abc123",
"email": "john@example.com",
"name": "John Doe"
},
"session_id": "sess_xyz789",
"channel": "web",
"currency": "USD",
"locale": "en-US",
"status": "active",
"items": [
{
"id": "ci_abc123",
"product_id": "prod_123",
"variant_id": "var_blue_large",
"product_name": "Wireless Headphones",
"variant_name": "Blue - Large",
"sku": "WH-BL-L",
"quantity": 2,
"unit_price": 9999,
"list_price": 9999,
"subtotal": 19998,
"discounts": [
{
"promotion_id": "promo_summer20",
"code": "SUMMER20",
"amount": 2000,
"type": "percentage"
}
],
"final_price": 17998,
"image_url": "https://images.stateset.com/products/wh-blue-large.jpg",
"inventory_status": "in_stock",
"available_quantity": 50,
"metadata": {}
},
{
"id": "ci_def456",
"product_id": "prod_456",
"variant_id": null,
"product_name": "USB-C Cable",
"variant_name": null,
"sku": "USBC-6FT",
"quantity": 1,
"unit_price": 1999,
"list_price": 1999,
"subtotal": 1999,
"discounts": [],
"final_price": 1999,
"image_url": "https://images.stateset.com/products/usbc-cable.jpg",
"inventory_status": "in_stock",
"available_quantity": 200,
"metadata": {}
}
],
"item_count": 3,
"unique_item_count": 2,
"subtotal": 21997,
"discount_amount": 2000,
"tax_amount": 1755,
"tax_breakdown": [
{
"name": "CA State Tax",
"rate": 0.0725,
"amount": 1450
},
{
"name": "SF County Tax",
"rate": 0.0175,
"amount": 305
}
],
"shipping_amount": 599,
"total": 20351,
"shipping_address": {
"line1": "123 Main St",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"selected_shipping_method": {
"id": "ship_standard",
"name": "Standard Shipping",
"amount": 599,
"estimated_days": 5
},
"available_shipping_methods": [
{
"id": "ship_standard",
"name": "Standard Shipping",
"amount": 599,
"estimated_days": 5
},
{
"id": "ship_express",
"name": "Express Shipping",
"amount": 1299,
"estimated_days": 2
}
],
"applied_coupons": [
{
"code": "SUMMER20",
"promotion_id": "promo_summer20",
"discount_amount": 2000
}
],
"applied_promotions": [
{
"id": "promo_summer20",
"name": "Summer Sale",
"type": "percentage",
"amount": 10
}
],
"abandoned_at": null,
"expires_at": "2024-07-20T10:00:00Z",
"created_at": "2024-06-20T10:00:00Z",
"updated_at": "2024-06-20T14:30:00Z",
"last_activity": "2024-06-20T14:30:00Z",
"metadata": {
"source": "product_page",
"utm_campaign": "summer_sale"
}
}
```
# List Carts
Source: https://docs.stateset.com/api-reference/cart/list
GET https://api.stateset.com/v1/carts
List all carts with filtering and pagination options
This endpoint returns a paginated list of carts. You can filter by customer, status, date range, and more. Useful for abandoned cart recovery and analytics.
## Authentication
This endpoint requires a valid API key with `carts:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of carts to return (1-100)
Number of carts to skip
Filter by customer ID
Filter by session ID
Filter by status: "active", "abandoned", "converted", "expired"
Filter by channel: "web", "mobile", "pos", "api"
Filter carts created after date (ISO 8601)
Filter carts created before date (ISO 8601)
Filter carts updated after date (ISO 8601)
Filter carts with email addresses (for recovery)
Minimum cart value in cents
Sort by field: "created\_at", "updated\_at", "total", "abandoned\_at"
Sort order: "asc" or "desc"
### Response
Returns a paginated list of cart objects.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/carts?status=abandoned&has_email=true&limit=20' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const carts = await stateset.carts.list({
status: 'abandoned',
has_email: true,
limit: 20
});
```
```python Python theme={null}
carts = stateset.carts.list(
status='abandoned',
has_email=True,
limit=20
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"email": "john@example.com",
"status": "abandoned",
"channel": "web",
"currency": "USD",
"item_count": 3,
"subtotal": 34495,
"total": 37762,
"abandoned_at": "2024-06-19T20:00:00Z",
"last_activity": "2024-06-19T19:30:00Z",
"created_at": "2024-06-19T18:00:00Z",
"recovery_status": "not_attempted"
},
{
"id": "cart_1234f083-bb2d-54d6-bg6d-1b0e3gd75f41",
"object": "cart",
"customer_id": null,
"email": "jane@example.com",
"status": "abandoned",
"channel": "mobile",
"currency": "USD",
"item_count": 1,
"subtotal": 4999,
"total": 5648,
"abandoned_at": "2024-06-18T15:00:00Z",
"last_activity": "2024-06-18T14:45:00Z",
"created_at": "2024-06-18T14:00:00Z",
"recovery_status": "email_sent"
}
],
"has_more": true,
"total_count": 156,
"url": "/v1/carts",
"summary": {
"total_abandoned_value": 2847532,
"average_cart_value": 18252,
"recovery_rate": 0.23,
"status_breakdown": {
"active": 45,
"abandoned": 156,
"converted": 1234,
"expired": 89
}
}
}
```
# Merge Carts
Source: https://docs.stateset.com/api-reference/cart/merge
POST https://api.stateset.com/v1/carts/:id/merge
Merge a guest cart with a customer cart after login
This endpoint merges items from one cart (typically a guest cart) into another cart (typically the logged-in customer's cart). Useful when customers add items before logging in.
## Authentication
This endpoint requires a valid API key with `carts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The target cart ID (cart to merge INTO)
## Request Body
The source cart ID (cart to merge FROM)
How to handle duplicate items: "combine" (add quantities), "keep\_source", "keep\_target"
Whether to preserve metadata from source cart items
Whether to delete the source cart after merge
### Response
Returns the merged cart object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/carts/cart_customer_123/merge' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"source_cart_id": "cart_guest_456",
"merge_strategy": "combine",
"delete_source_cart": true
}'
```
```javascript Node.js theme={null}
const mergedCart = await stateset.carts.merge(
'cart_customer_123',
{
source_cart_id: "cart_guest_456",
merge_strategy: "combine",
delete_source_cart: true
}
);
```
```python Python theme={null}
merged_cart = stateset.carts.merge(
'cart_customer_123',
source_cart_id="cart_guest_456",
merge_strategy="combine",
delete_source_cart=True
)
```
```json Response theme={null}
{
"id": "cart_customer_123",
"object": "cart",
"customer_id": "cust_abc123",
"status": "active",
"items": [
{
"id": "ci_abc123",
"product_id": "prod_123",
"variant_id": "var_blue_large",
"product_name": "Wireless Headphones",
"variant_name": "Blue - Large",
"quantity": 5,
"unit_price": 9999,
"subtotal": 49995,
"source": "merged",
"metadata": {
"original_cart": "cart_customer_123",
"merged_quantity": 2,
"merge_timestamp": "2024-06-20T18:00:00Z"
}
},
{
"id": "ci_new789",
"product_id": "prod_456",
"product_name": "USB-C Cable",
"quantity": 2,
"unit_price": 1999,
"subtotal": 3998,
"source": "merged",
"metadata": {
"original_cart": "cart_guest_456",
"merge_timestamp": "2024-06-20T18:00:00Z"
}
}
],
"item_count": 7,
"unique_item_count": 2,
"subtotal": 53993,
"total": 58792,
"merge_details": {
"source_cart_id": "cart_guest_456",
"items_merged": 2,
"items_combined": 1,
"merge_timestamp": "2024-06-20T18:00:00Z",
"source_cart_deleted": true
},
"updated_at": "2024-06-20T18:00:00Z",
"messages": [
{
"type": "success",
"message": "Successfully merged 2 items from guest cart"
}
]
}
```
# Remove Cart Item
Source: https://docs.stateset.com/api-reference/cart/remove-item
DELETE https://api.stateset.com/v1/carts/:id/items/:item_id
Remove an item from the cart
This endpoint removes a specific item from the cart completely. To update quantity instead, use the update item endpoint.
## Authentication
This endpoint requires a valid API key with `carts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the cart
The unique identifier of the cart item to remove
### Response
Returns the updated cart object without the removed item.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/carts/cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/items/ci_def456' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const cart = await stateset.carts.removeItem(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'ci_def456'
);
```
```python Python theme={null}
cart = stateset.carts.remove_item(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'ci_def456'
)
```
```json Response theme={null}
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"status": "active",
"items": [
{
"id": "ci_abc123",
"product_id": "prod_123",
"variant_id": "var_blue_large",
"product_name": "Wireless Headphones",
"variant_name": "Blue - Large",
"quantity": 3,
"unit_price": 9999,
"subtotal": 29997
},
{
"id": "ci_ghi789",
"product_id": "prod_789",
"variant_id": "var_red_medium",
"product_name": "T-Shirt",
"variant_name": "Red - Medium",
"quantity": 1,
"unit_price": 2499,
"subtotal": 2499
}
],
"item_count": 4,
"unique_item_count": 2,
"subtotal": 32496,
"discount_amount": 3000,
"total": 29496,
"updated_at": "2024-06-20T16:00:00Z",
"last_activity": "2024-06-20T16:00:00Z",
"messages": [
{
"type": "info",
"message": "Item removed from cart"
}
]
}
```
# Update Cart Item
Source: https://docs.stateset.com/api-reference/cart/update-item
PUT https://api.stateset.com/v1/carts/:id/items/:item_id
Update quantity or properties of an item in the cart
This endpoint updates an existing item in the cart. You can change quantity, add notes, or update metadata. Setting quantity to 0 removes the item.
## Authentication
This endpoint requires a valid API key with `carts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the cart
The unique identifier of the cart item
## Request Body
New quantity (set to 0 to remove item)
Update special instructions
Update custom fields
Validate inventory for quantity increase
### Response
Returns the updated cart object.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/carts/cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/items/ci_abc123' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"quantity": 3,
"notes": "Updated quantity"
}'
```
```javascript Node.js theme={null}
const cart = await stateset.carts.updateItem(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'ci_abc123',
{
quantity: 3,
notes: "Updated quantity"
}
);
```
```python Python theme={null}
cart = stateset.carts.update_item(
'cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'ci_abc123',
quantity=3,
notes="Updated quantity"
)
```
```json Response theme={null}
{
"id": "cart_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "cart",
"customer_id": "cust_abc123",
"status": "active",
"items": [
{
"id": "ci_abc123",
"product_id": "prod_123",
"variant_id": "var_blue_large",
"product_name": "Wireless Headphones",
"variant_name": "Blue - Large",
"quantity": 3,
"unit_price": 9999,
"subtotal": 29997,
"notes": "Updated quantity",
"inventory_status": "in_stock",
"available_quantity": 50
},
{
"id": "ci_def456",
"product_id": "prod_456",
"product_name": "USB-C Cable",
"quantity": 1,
"unit_price": 1999,
"subtotal": 1999
},
{
"id": "ci_ghi789",
"product_id": "prod_789",
"variant_id": "var_red_medium",
"product_name": "T-Shirt",
"variant_name": "Red - Medium",
"quantity": 1,
"unit_price": 2499,
"subtotal": 2499,
"notes": "Gift wrap please"
}
],
"item_count": 5,
"unique_item_count": 3,
"subtotal": 34495,
"updated_at": "2024-06-20T15:30:00Z",
"last_activity": "2024-06-20T15:30:00Z",
"messages": [
{
"type": "info",
"message": "Item quantity updated"
}
]
}
```
# Close Case
Source: https://docs.stateset.com/api-reference/cases/close
POST https://api.stateset.com/v1/cases/:id/close
This endpoint updates an existing case.
### Body
The ID provided in the data tab may be used to identify the case
### Response
The ID provided in the data tab may be used to identify the case
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/cases/:id/close' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation caseCloseMutation {
caseClose (id: "${caseId}") {
case {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const cases = await stateset.cases.close({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
cases = stateset.cases.close({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
cases = Stateset::Return.close({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
cases, err := stateset.cases.close({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Return cases = stateset.cases.close({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$cases = $stateset->cases->close({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var cases = await stateset.cases.close({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "case",
"closed": true
}
```
# Create Case
Source: https://docs.stateset.com/api-reference/cases/create
POST https://api.stateset.com/v1/cases
Create a new case record for tracking issues or requests
This endpoint requires authentication with `cases:write` permission.
### Request Parameters
The name or title of the case
Detailed description of the case or issue
Optional custom case number (auto-generated if not provided)
Initial status of the case. Options: `new`, `in_progress`, `resolved`, `closed`
Priority level. Options: `low`, `medium`, `high`, `urgent`
ID or name of the person submitting the case
ID or name of the assigned resolver (can be assigned later)
### Response
Unique identifier for the newly created case
The name or title of the case
Detailed description of the case
Assigned case number
Current status of the case
Priority level of the case
Submitter of the case
Assigned resolver (if any)
Timestamp when the case was created
Timestamp when the case was last updated
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/cases' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer ' \
--data-raw '{
"caseName": "Network Connectivity Issue",
"description": "Customer unable to connect to WiFi",
"priority": "high",
"submitter": "user_123"
}'
```
```javascript JavaScript theme={null}
const response = await fetch('https://api.stateset.com/v1/cases', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': 'Bearer YOUR_API_KEY'
},
body: JSON.stringify({
caseName: 'Network Connectivity Issue',
description: 'Customer unable to connect to WiFi',
priority: 'high',
submitter: 'user_123'
})
});
```
```python Python theme={null}
import requests
response = requests.post(
'https://api.stateset.com/v1/cases',
headers={
'Content-Type': 'application/json',
'Authorization': 'Bearer YOUR_API_KEY'
},
json={
'caseName': 'Network Connectivity Issue',
'description': 'Customer unable to connect to WiFi',
'priority': 'high',
'submitter': 'user_123'
}
)
```
```json Success Response theme={null}
{
"id": "case_001",
"caseName": "Network Connectivity Issue",
"description": "Customer unable to connect to WiFi",
"caseNumber": "CASE-20240101-001",
"caseStatus": "new",
"priority": "high",
"submitter": "user_123",
"resolver": null,
"createdDate": "2024-01-01T12:00:00Z",
"updatedDate": "2024-01-01T12:00:00Z"
}
```
```json Error Response theme={null}
{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "Missing required field: caseName"
}
}
```
# Delete Case
Source: https://docs.stateset.com/api-reference/cases/delete
DELETE https://api.stateset.com/v1/cases:/id
This endpoint deletes an existing case.
### Body
The ID provided in the data tab may be used to identify the case
### Response
The ID provided in the data tab may be used to identify the case
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/case' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteCase ($id: String!) {
delete_cases(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const cases = await stateset.cases.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
cases = stateset.cases.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
cases, err := stateset.Cases.Del(
"rt_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Case cases = stateset.cases.del(
"rt_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const cases = await stateset.cases.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
cases = Stateset::Return.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$cases = $stateset->cases->del(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
DELETE /v1/case HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "ca_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "case",
"deleted": true
}
```
# Escalate Case
Source: https://docs.stateset.com/api-reference/cases/escalate
POST https://api.stateset.com/v1/cases/:id/escalate
This endpoint escalates an existing case.
### Body
The ID provided in the data tab may be used to identify the case
### Response
The ID provided in the data tab may be used to identify the case
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/cases/:id/escalate' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation caseEscalateMutation {
caseEscalate (id: "${caseId}") {
case {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const cases = await stateset.cases.escalate({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
cases = stateset.cases.escalate({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
cases = Stateset::Return.escalate({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
cases, err := stateset.cases.escalate({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Return cases = stateset.cases.escalate({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$cases = $stateset->cases->escalate({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var cases = await stateset.cases.escalate({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "case",
"escalated": true
}
```
# Get Cases
Source: https://docs.stateset.com/api-reference/cases/get
GET https://api.stateset.com/v1/cases/:id
This endpoint gets a case.
### Body
This is the id of the case
### Response
This is the id of the case
This is the name of the case
This is the description of the case
This is the number of the case
This is the status of the case
This is the priority of the case
This is the submitter of the case
This is the resolver of the case
This is the date the case was created
This is the date the case was updated
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/case' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query getMyCases {
cases(order_by: {createdDate: desc}) {
id
caseName
description
caseNumber
caseStatus
priority
submitter
resolver
createdDate
}
}
```
```js Node.js theme={null}
const cases= await stateset.channel_threads.retrieve({
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
cases= stateset.channel_threads.retrieve({
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
channel_threads, err := stateset.Messages.Retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
cases= Stateset::Messages.retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
Cases cases= Stateset.Cases.retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
Cases cases= Stateset.Cases.Retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$cases= Stateset\Cases::retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/cases HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"data": {
"case": {
"id": "ca_1NXWPnCo6bFb1KQto6C8OWvE",
"caseName": "Case Name",
"description": "Case Description",
"caseNumber": "Case Number",
"caseStatus": "Case Status",
"priority": "Priority",
"submitter": "Submitter",
"resolver": "Resolver",
"createdDate": "2021-01-01T00:00:00.000Z"
}
}
}
```
# List Cases
Source: https://docs.stateset.com/api-reference/cases/list
GET https://api.stateset.com/v1/cases/list
This endpoint list cases.
### Body
This is the limit of the cases.
This is the offset of the cases.
This is the order direction of the cases.
### Response
This is the id of the case
This is the name of the case
This is the description of the case
This is the number of the case
This is the status of the case
This is the priority of the case
This is the submitter of the case
This is the resolver of the case
This is the date the case was created
This is the date the case was updated
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/cases' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "asc"
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
cases(limit: $limit, offset: $offset, order_by: {createdDate: $order_direction}) {
id
caseName
description
caseNumber
caseStatus
priority
submitter
resolver
createdDate
}
}
```
```js Node.js theme={null}
const cases= await stateset.channel_threads.retrieve({
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
cases= stateset.channel_threads.retrieve({
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
channel_threads, err := stateset.Messages.Retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
cases= Stateset::Messages.retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
Cases cases= Stateset.Cases.retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
Cases cases= Stateset.Cases.Retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$cases= Stateset\Cases::retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/cases HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"data": {
"case": {
"id": "ca_1NXWPnCo6bFb1KQto6C8OWvE",
"caseName": "Case Name",
"description": "Case Description",
"caseNumber": "Case Number",
"caseStatus": "Case Status",
"priority": "Priority",
"submitter": "Submitter",
"resolver": "Resolver",
"createdDate": "2021-01-01T00:00:00.000Z"
}
}
}
```
# Resolve Case
Source: https://docs.stateset.com/api-reference/cases/resolve
POST https://api.stateset.com/v1/cases/:id/resolve
This endpoint resolves an existing case.
### Body
The ID provided in the data tab may be used to identify the case
### Response
The ID provided in the data tab may be used to identify the case
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/cases/:id/resolve' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation caseResolveMutation {
caseResolve (id: "${caseId}") {
case {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const cases = await stateset.cases.resolve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
cases = stateset.cases.resolve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
cases = Stateset::Return.resolve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
cases, err := stateset.cases.resolve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Return cases = stateset.cases.resolve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$cases = $stateset->cases->resolve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var cases = await stateset.cases.resolve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "case",
"resolved": true
}
```
# Update Case
Source: https://docs.stateset.com/api-reference/cases/update
POST https://api.stateset.com/v1/cases
This endpoint updates a cases
### Body
This is the ID of the case to update.
### Response
This is the id of the case
This is the name of the case
This is the description of the case
This is the number of the case
This is the status of the case
This is the priority of the case
This is the submitter of the case
This is the resolver of the case
This is the date the case was created
This is the date the case was updated
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/case' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```graphQL GraphQL theme={null}
mutation (
$id: String
$casex: cases_set_input!
) {
update_cases (
where: { id : { _eq: $id }}
_set: $casex
) {
returning {
id
caseName
caseNumber
caseStatus
description
priority
resolver
submitter
}
}
}
```
```javascript Node.js theme={null}
const created = await stateset.case.update({
id: "",
});
```
```json Response theme={null}
{
"data": {
"update_cases": {
"returning": [
{
"id": "0x0",
"caseName": "Case Name",
"caseNumber": "Case Number",
"description": "Case Description",
"caseStatus": "Case Status",
"priority": "Case Priority",
"submitter": "Submitter",
"resolver": "Resolver"
}
]
}
}
}
```
# API Changelog
Source: https://docs.stateset.com/api-reference/changelog
Recent changes and updates to the StateSet API
# API Changelog
This page documents changes to the StateSet API, including new features, improvements, and breaking changes. We follow semantic versioning and announce changes in advance when possible.
## Version 1.0.0 (Current)
### 2024-01-15: Initial Release
* Launched core endpoints for agents, conversations, knowledge bases, and workflows
* Added support for REST and GraphQL interfaces
* Implemented authentication and rate limiting
* Released SDKs for Node.js, Python, Go, and Ruby
### 2024-02-01: Feature Update
* Added webhook support for real-time events
* Introduced cursor-based pagination for list endpoints
* Enhanced filtering and sorting capabilities
* Improved error responses with detailed codes and messages
## Previous Versions
### Version 0.9.0 (Beta)
* Internal beta release with basic CRUD operations
* Initial GraphQL schema implementation
* Basic authentication support
Subscribe to our [developer newsletter](https://stateset.com/newsletter) for advance notice of upcoming changes.
# Create Channel Thread
Source: https://docs.stateset.com/api-reference/channels/create
POST https://api.stateset.com/v1/channel_thread
This endpoint creates a new channel thread
### Body
This is the ID of the channel thread to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/channel_thread' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```graphQL GraphQL theme={null}
mutation addChannelThread(
$channel_thread: channel_thread_insert_input!
) {
insert_channel_thread(objects: [$channel_thread]) {
returning {
id
name
uuid
user_id
}
}
}
```
```javascript Node.js theme={null}
const created = await stateset.channel.create({
id: "",
});
```
```json Response theme={null}
{
"data": {
"insert_channel_thread": {
"returning": [
{
"id": "",
"name": "",
"uuid": "",
"user_id": ""
}
]
}
}
}
```
# Delete Channel Thread
Source: https://docs.stateset.com/api-reference/channels/delete
DELETE https://api.stateset.com/v1/channel_thread
This endpoint deletes an existing thread.
### Body
The ID provided in the data tab may be used to identify the case
### Response
The ID provided in the data tab may be used to identify the case
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/channel_thread' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteChannelThread ($id: String!) {
delete_channel_thread(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const channelthead = await stateset.channelthread.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
channelthead = stateset.channelthead.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
channelthead, err := stateset.Cases.Del(
"rt_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Case channelthead = stateset.channelthead.del(
"rt_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const channelthead = await stateset.channelthead.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
channelthead = Stateset::Return.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$channelthead = $stateset->channelthead->del(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
DELETE /v1/channelthread HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "ct_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "channel_thread",
"deleted": true
}
```
# Get Channel Threads
Source: https://docs.stateset.com/api-reference/channels/get
GET https://api.stateset.com/v1/channel_threads
This endpoint gets a channel threads.
### Body
This is the id of the channel thread.
### Response
This is the id of the channel\_thread
This is the name of the channel\_thread
This is the uuid of the channel\_thread
This is the user\_id of the channel\_thread
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/channelthread' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query MyChannelThread {
channel_thread {
id
created_at
name
system_prompt
user_id
messages {
id
body
channel_id
chat_id
created_at
date
deliveredReceipt
from
fromMe
likes
messageNumber
points
sentReceipt
timestamp
to
}
}
}
```
```js Node.js theme={null}
const channel_threads = await stateset.channel_threads.retrieve({
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
channel_threads = stateset.channel_threads.retrieve({
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
channel_threads, err := stateset.Messages.Retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
channel_threads = Stateset::Messages.retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
ChannelThread channel_threads = Stateset.ChannelThreads.retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
ChannelThread channel_threads = Stateset.ChannelThreads.Retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$channel_threads = Stateset\ChannelThreads::retrieve(
'ct_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/channel_threads HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"data": {
"message": {
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"body": "Hello World",
"created_at": "2021-01-01T00:00:00.000000Z",
"date": "2021-01-01",
"deliveredReceipt": true,
"from": "user1",
"fromMe": true,
"is_public": true,
"messageNumber": 1,
"sentReceipt": true,
"time": "00:00:00",
"timestamp": "2021-01-01T00:00:00.000000Z",
"to": "user2",
"user_id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"username": "user1"
}
}
}
```
# Update Channel Thread
Source: https://docs.stateset.com/api-reference/channels/update
PUT https://api.stateset.com/v1/channel_thread
This endpoint creates a new channel thread
### Body
This is the ID of the channel thread to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/channel_thread' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```javascript Node.js theme={null}
const created = await stateset.channel.update({
id: "",
});
```
```json Response theme={null}
{
"data": {
"insert_channel_thread": {
"returning": [
{
"id": "",
"name": "",
"uuid": "",
"user_id": ""
}
]
}
}
}
```
# Cancel Checkout
Source: https://docs.stateset.com/api-reference/checkouts/cancel
POST https://api.stateset.com/v1/checkouts/:id/cancel
Cancel an existing checkout session
This endpoint cancels an active checkout session. Once canceled, the checkout cannot be completed or updated. This is useful when a customer abandons their cart or decides not to proceed with the purchase.
## Authentication
This endpoint requires a valid API key with `checkouts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
Unique identifier for the checkout session
## Request Body
Optional reason for canceling the checkout (e.g., "customer\_requested", "timeout", "inventory\_unavailable")
Optional custom message about the cancellation
### Response
Unique identifier for the Checkout Session
Status will be `canceled` after successful cancellation
Information about the buyer
Line items from the canceled checkout
Final totals before cancellation
Array including cancellation message
ISO 8601 timestamp of when the checkout was canceled
```bash cURL theme={null}
curl -X POST https://api.stateset.com/v1/checkouts/checkout_abc123/cancel \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"reason": "customer_requested",
"message": "Customer changed their mind"
}'
```
```javascript Node.js theme={null}
const checkout = await stateset.checkouts.cancel('checkout_abc123', {
reason: "customer_requested",
message: "Customer changed their mind"
});
```
```python Python theme={null}
checkout = stateset.checkouts.cancel(
'checkout_abc123',
reason="customer_requested",
message="Customer changed their mind"
)
```
```json Success Response theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"status": "canceled",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 3
},
"base_amount": 3000,
"discount": 0,
"total": 3000,
"subtotal": 3000,
"tax": 0
},
{
"id": "item_456",
"item": {
"id": "item_456",
"quantity": 1
},
"base_amount": 500,
"discount": 0,
"total": 500,
"subtotal": 500,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 3500
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 3750
}
],
"messages": [
{
"type": "info",
"content_type": "plain",
"content": "Checkout cancelled: Customer changed their mind"
}
],
"links": [],
"canceled_at": "2024-09-30T14:30:00Z"
}
```
```json Error Response - Already Completed theme={null}
{
"success": false,
"error": {
"type": "invalid_request",
"code": "INVALID_STATUS",
"message": "Cannot cancel a checkout that has already been completed",
"param": "status"
}
}
```
```json Error Response - Not Found theme={null}
{
"success": false,
"error": {
"type": "invalid_request",
"code": "RESOURCE_NOT_FOUND",
"message": "Checkout session not found",
"param": "id"
}
}
```
# Complete Checkout
Source: https://docs.stateset.com/api-reference/checkouts/complete
POST https://api.stateset.com/v1/checkouts/:id/complete
Complete the checkout process by processing payment and creating an order
This endpoint finalizes the checkout session by processing the payment and converting it into an order. The checkout status will be updated to `completed` upon successful payment.
## Authentication
This endpoint requires a valid API key with `checkouts:write` and `payments:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
Unique identifier for the checkout session
## Request Body
Payment method details for processing the transaction
Secure reference to a payment credential (tokenized payment method)
Payment provider: `stripe`, `paypal`, `square`
Billing address for the payment method
Billing name
Street address line 1
Street address line 2
City name
State or province code
ISO 3166-1 alpha-2 country code
Postal or ZIP code
Additional buyer information if needed
First name of the buyer
Last name of the buyer
Email address of the buyer
Phone number of the buyer
### Response
Unique identifier for the Checkout Session
Status will be `completed` after successful payment
ID of the created order
Payment processing details and status
Final line items with calculated amounts
Final breakdown of all charges
```bash cURL theme={null}
curl -X POST https://api.stateset.com/v1/checkouts/checkout_abc123/complete \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"payment_data": {
"token": "spt_123",
"provider": "stripe",
"billing_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
}
}
}'
```
```javascript Node.js theme={null}
const checkout = await stateset.checkouts.complete('checkout_abc123', {
payment_data: {
token: "spt_123",
provider: "stripe",
billing_address: {
name: "John Doe",
line_one: "123 Main St",
line_two: "Apt 4B",
city: "San Francisco",
state: "CA",
country: "US",
postal_code: "94105"
}
}
});
```
```python Python theme={null}
checkout = stateset.checkouts.complete(
'checkout_abc123',
payment_data={
"token": "spt_123",
"provider": "stripe",
"billing_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
}
}
)
```
```json Success Response theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"status": "completed",
"currency": "usd",
"order_id": "order_xyz789",
"payment": {
"id": "pay_456",
"status": "succeeded",
"amount": 3750,
"provider": "stripe"
},
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 3
},
"base_amount": 3000,
"discount": 0,
"total": 3000,
"subtotal": 3000,
"tax": 0
},
{
"id": "item_456",
"item": {
"id": "item_456",
"quantity": 1
},
"base_amount": 500,
"discount": 0,
"total": 500,
"subtotal": 500,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 3500
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 3750
}
],
"messages": [],
"links": []
}
```
```json Error Response - Payment Declined theme={null}
{
"success": false,
"error": {
"type": "processing_error",
"code": "PAYMENT_DECLINED",
"message": "Payment was declined by the payment processor",
"details": {
"decline_code": "insufficient_funds",
"provider_message": "Card has insufficient funds"
}
}
}
```
```json Error Response - Invalid Status theme={null}
{
"success": false,
"error": {
"type": "invalid_request",
"code": "INVALID_STATUS",
"message": "Checkout must be in ready_for_payment status to complete",
"param": "status"
}
}
```
# Create Checkout Session
Source: https://docs.stateset.com/api-reference/checkouts/create
POST https://api.stateset.com/v1/checkouts
Create a new checkout session with buyer details, line items, and shipping information
This endpoint creates a new Checkout Session for the Agentic Commerce Protocol, enabling AI agents to manage commerce transactions. The session tracks buyer information, cart items, and fulfillment options.
## Authentication
This endpoint requires a valid API key with `checkouts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Array of items to purchase
Unique identifier for the item
Requested quantity of the item
Information about the buyer
First name of the buyer
Last name of the buyer
Email address of the buyer
Phone number of the buyer (E.164 format recommended)
Address where the order will ship
Name of the person receiving the items
Street address line 1
Street address line 2 (apartment, suite, etc.)
City name
State or province code
ISO 3166-1 alpha-2 country code (e.g., "US", "CA")
Postal or ZIP code
### Response
Unique identifier for the Checkout Session
Information about the buyer
Payment provider configuration and supported payment methods
Current status: `not_ready_for_payment`, `ready_for_payment`, `completed`, `canceled`, `in_progress`
Three-letter ISO currency code in lowercase
Array of line items in the checkout with calculated amounts
Address where the order will ship
Available shipping and fulfillment options
ID of the currently selected fulfillment option
Breakdown of charges including subtotal, tax, shipping, and total
Array of messages or notifications related to the checkout
Array of links related to policies and agreements
```bash cURL theme={null}
curl -X POST https://api.stateset.com/v1/checkouts \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"items": [
{
"id": "item_123",
"quantity": 2
}
],
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"fulfillment_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
}
}'
```
```javascript Node.js theme={null}
const checkout = await stateset.checkouts.create({
items: [
{
id: "item_123",
quantity: 2
}
],
buyer: {
first_name: "John",
last_name: "Doe",
email: "john.doe@example.com",
phone_number: "+1234567890"
},
fulfillment_address: {
name: "John Doe",
line_one: "123 Main St",
line_two: "Apt 4B",
city: "San Francisco",
state: "CA",
country: "US",
postal_code: "94105"
}
});
```
```python Python theme={null}
checkout = stateset.checkouts.create(
items=[
{
"id": "item_123",
"quantity": 2
}
],
buyer={
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
fulfillment_address={
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
}
)
```
```json Success Response theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"payment_provider": {
"provider": "stripe",
"supported_payment_methods": ["card"]
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 2
},
"base_amount": 2000,
"discount": 0,
"total": 2000,
"subtotal": 2000,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 2000
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 2250
}
],
"messages": [],
"links": []
}
```
```json Error Response - Validation Error theme={null}
{
"success": false,
"error": {
"type": "invalid_request",
"code": "VALIDATION_ERROR",
"message": "Invalid request parameters",
"details": {
"items": "At least one item is required",
"buyer.email": "Invalid email format"
}
}
}
```
# Delete Checkout
Source: https://docs.stateset.com/api-reference/checkouts/delete
Delete an existing checkout.
# Delete Checkout
Use this endpoint to delete a checkout by ID.
# Retrieve Checkout Session
Source: https://docs.stateset.com/api-reference/checkouts/get
GET https://api.stateset.com/v1/checkouts/:id
Retrieve an existing checkout session by its unique identifier
This endpoint retrieves the current state of a checkout session, including all items, totals, fulfillment options, and status information.
## Authentication
This endpoint requires a valid API key with `checkouts:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
Unique identifier for the checkout session
### Response
Unique identifier for the Checkout Session
Information about the buyer
Payment provider configuration and supported payment methods
Current status: `not_ready_for_payment`, `ready_for_payment`, `completed`, `canceled`, `in_progress`
Three-letter ISO currency code in lowercase
Array of line items in the checkout with calculated amounts
Address where the order will ship
Available shipping and fulfillment options
ID of the currently selected fulfillment option
Breakdown of charges including subtotal, tax, shipping, and total
Array of messages or notifications related to the checkout
Array of links related to policies and agreements
```bash cURL theme={null}
curl -X GET https://api.stateset.com/v1/checkouts/checkout_abc123 \
-H "Authorization: Bearer YOUR_API_KEY"
```
```javascript Node.js theme={null}
const checkout = await stateset.checkouts.retrieve('checkout_abc123');
```
```python Python theme={null}
checkout = stateset.checkouts.retrieve('checkout_abc123')
```
```json Success Response theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"payment_provider": {
"provider": "stripe",
"supported_payment_methods": ["card"]
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 2
},
"base_amount": 2000,
"discount": 0,
"total": 2000,
"subtotal": 2000,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "123 Main St",
"line_two": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"country": "US",
"postal_code": "94105"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 2000
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 2250
}
],
"messages": [],
"links": []
}
```
```json Error Response - Not Found theme={null}
{
"success": false,
"error": {
"type": "invalid_request",
"code": "RESOURCE_NOT_FOUND",
"message": "Checkout session not found",
"param": "id"
}
}
```
# List Checkout Sessions
Source: https://docs.stateset.com/api-reference/checkouts/list
GET https://api.stateset.com/v1/checkouts
Retrieve a list of checkout sessions with optional filters
This endpoint returns a paginated list of checkout sessions. You can filter by status, buyer email, or date range.
## Authentication
This endpoint requires a valid API key with `checkouts:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Filter by checkout status: `not_ready_for_payment`, `ready_for_payment`, `completed`, `canceled`, `in_progress`
Filter by buyer's email address
Filter checkouts created after this ISO 8601 timestamp
Filter checkouts created before this ISO 8601 timestamp
Number of results per page (default: 20, max: 100)
Cursor for pagination - ID of the last item from the previous page
### Response
Array of checkout session objects
Whether there are more results available
Total number of checkouts matching the filters
```bash cURL theme={null}
curl -X GET 'https://api.stateset.com/v1/checkouts?status=ready_for_payment&limit=10' \
-H "Authorization: Bearer YOUR_API_KEY"
```
```javascript Node.js theme={null}
const checkouts = await stateset.checkouts.list({
status: 'ready_for_payment',
limit: 10
});
```
```python Python theme={null}
checkouts = stateset.checkouts.list(
status='ready_for_payment',
limit=10
)
```
```json Success Response theme={null}
{
"data": [
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 2
},
"base_amount": 2000,
"discount": 0,
"total": 2000,
"subtotal": 2000,
"tax": 0
}
],
"totals": [
{
"type": "total",
"display_text": "Total",
"amount": 2250
}
],
"created_at": "2024-09-30T10:00:00Z",
"updated_at": "2024-09-30T10:05:00Z"
},
{
"id": "checkout_def456",
"buyer": {
"first_name": "Jane",
"last_name": "Smith",
"email": "jane.smith@example.com"
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_789",
"item": {
"id": "item_789",
"quantity": 1
},
"base_amount": 5000,
"discount": 500,
"total": 4500,
"subtotal": 4500,
"tax": 0
}
],
"totals": [
{
"type": "total",
"display_text": "Total",
"amount": 4800
}
],
"created_at": "2024-09-30T09:30:00Z",
"updated_at": "2024-09-30T09:35:00Z"
}
],
"has_more": false,
"total_count": 2
}
```
```json Error Response - Invalid Parameter theme={null}
{
"success": false,
"error": {
"type": "invalid_request",
"code": "INVALID_PARAMETER",
"message": "Invalid status value provided",
"param": "status"
}
}
```
# Update Checkout Session
Source: https://docs.stateset.com/api-reference/checkouts/update
PUT https://api.stateset.com/v1/checkouts/:id
Update an existing checkout session by modifying items, shipping address, or fulfillment options
This endpoint updates an existing Checkout Session. You can modify line items, buyer information, shipping address, or select different fulfillment options. The response will include recalculated totals.
## Authentication
This endpoint requires a valid API key with `checkouts:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
Unique identifier for the checkout session
## Request Body
Updated array of items to purchase
Unique identifier for the item
Updated quantity of the item
Updated buyer information
First name of the buyer
Last name of the buyer
Email address of the buyer
Phone number of the buyer
Updated fulfillment address
Name of the person receiving the items
Street address line 1
Street address line 2
City name
State or province code
ISO 3166-1 alpha-2 country code
Postal or ZIP code
Identifier for the selected fulfillment option
### Response
Returns the updated checkout session with recalculated totals.
```bash cURL theme={null}
curl -X PUT https://api.stateset.com/v1/checkouts/checkout_abc123 \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"items": [
{
"id": "item_123",
"quantity": 3
},
{
"id": "item_456",
"quantity": 1
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_option_id": "shipping_fast"
}'
```
```javascript Node.js theme={null}
const checkout = await stateset.checkouts.update('checkout_abc123', {
items: [
{
id: "item_123",
quantity: 3
},
{
id: "item_456",
quantity: 1
}
],
fulfillment_address: {
name: "John Doe",
line_one: "456 Oak Ave",
city: "Los Angeles",
state: "CA",
country: "US",
postal_code: "90210"
},
fulfillment_option_id: "shipping_fast"
});
```
```python Python theme={null}
checkout = stateset.checkouts.update(
'checkout_abc123',
items=[
{
"id": "item_123",
"quantity": 3
},
{
"id": "item_456",
"quantity": 1
}
],
fulfillment_address={
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
fulfillment_option_id="shipping_fast"
)
```
```json Success Response theme={null}
{
"id": "checkout_abc123",
"buyer": {
"first_name": "John",
"last_name": "Doe",
"email": "john.doe@example.com",
"phone_number": "+1234567890"
},
"payment_provider": {
"provider": "stripe",
"supported_payment_methods": ["card"]
},
"status": "ready_for_payment",
"currency": "usd",
"line_items": [
{
"id": "item_123",
"item": {
"id": "item_123",
"quantity": 3
},
"base_amount": 3000,
"discount": 0,
"total": 3000,
"subtotal": 3000,
"tax": 0
},
{
"id": "item_456",
"item": {
"id": "item_456",
"quantity": 1
},
"base_amount": 500,
"discount": 0,
"total": 500,
"subtotal": 500,
"tax": 0
}
],
"fulfillment_address": {
"name": "John Doe",
"line_one": "456 Oak Ave",
"city": "Los Angeles",
"state": "CA",
"country": "US",
"postal_code": "90210"
},
"fulfillment_options": [
{
"type": "shipping",
"id": "shipping_fast",
"title": "Express Shipping",
"subtitle": "2-3 business days",
"carrier": "Shipping Co",
"subtotal": 150,
"tax": 0,
"total": 150
}
],
"fulfillment_option_id": "shipping_fast",
"totals": [
{
"type": "subtotal",
"display_text": "Subtotal",
"amount": 3500
},
{
"type": "fulfillment",
"display_text": "Shipping",
"amount": 150
},
{
"type": "tax",
"display_text": "Tax",
"amount": 100
},
{
"type": "total",
"display_text": "Total",
"amount": 3750
}
],
"messages": [],
"links": []
}
```
```json Error Response - Invalid Item theme={null}
{
"success": false,
"error": {
"type": "invalid_request",
"code": "ITEM_UNAVAILABLE",
"message": "One or more items are no longer available",
"details": {
"unavailable_items": ["item_456"]
}
}
}
```
# Create COGS Entry
Source: https://docs.stateset.com/api-reference/cogs/create
POST https://api.stateset.com/v1/cogs_entries
This endpoint creates a new COGS (Cost of Goods Sold) entry.
### Body
The accounting period for the COGS entry
The product associated with the COGS entry
The quantity of the product sold
The Cost of Goods Sold amount
The average cost per unit
The quantity of inventory remaining at the end of the period
The value of the ending inventory
The currency used for the financial calculations
Identifier for the related exchange rate
Identifier for the related sale transaction
The selling price per unit
The total gross sales amount
The method used to calculate COGS
The category of the product
The channel through which the sale was made
The segment of the customer who made the purchase
The date of the sale
Indicates whether this entry is for a return
The reason for the return, if applicable
The cost center associated with the COGS entry
Identifier for the related supplier
### Response
Unique identifier for the newly created COGS entry
A success message confirming the creation of the COGS entry
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/cogs_entries' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"period": "2024-Q1",
"product": "Widget A",
"quantity_sold": 100,
"cogs": 5000,
"average_cost": 50,
"ending_inventory_quantity": 500,
"ending_inventory_value": 25000,
"currency": "USD",
"unit_selling_price": 75,
"gross_sales": 7500,
"cogs_method": "FIFO",
"sale_date": "2024-03-15"
}'
```
```python theme={null}
import requests
import json
url = "https://api.stateset.com/v1/cogs_entries"
headers = {
"Content-Type": "application/json",
"Authorization": "Token "
}
data = {
"period": "2024-Q1",
"product": "Widget A",
"quantity_sold": 100,
"cogs": 5000,
"average_cost": 50,
"ending_inventory_quantity": 500,
"ending_inventory_value": 25000,
"currency": "USD",
"unit_selling_price": 75,
"gross_sales": 7500,
"cogs_method": "FIFO",
"sale_date": "2024-03-15"
}
response = requests.post(url, headers=headers, data=json.dumps(data))
print(response.json())
```
```
```
# Get COGS Entry
Source: https://docs.stateset.com/api-reference/cogs/get
GET https://api.stateset.com/v1/cogs_entries/{id}
This endpoint gets a COGS (Cost of Goods Sold) entry.
### Response
Unique identifier for the COGS entry (primary key)
### Response
Unique identifier for the COGS entry (primary key)
The accounting period for the COGS entry
The product associated with the COGS entry
The quantity of the product sold
The Cost of Goods Sold amount
The average cost per unit
The quantity of inventory remaining at the end of the period
The value of the ending inventory
The currency used for the financial calculations
Identifier for the related exchange rate
Identifier for the related sale transaction
The selling price per unit
The total gross sales amount
The gross profit amount
The gross margin percentage
The COGS as a percentage of sales
The method used to calculate COGS
The category of the product
The channel through which the sale was made
The segment of the customer who made the purchase
The date of the sale
Indicates whether this entry is for a return
The reason for the return, if applicable
The cost center associated with the COGS entry
Identifier for the related supplier
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/cogs_entries' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "asc"
}'
```
```graphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
cogs_entries(limit: $limit, offset: $offset, order_by: {id: $order_direction}) {
id
period
product
quantity_sold
cogs
average_cost
ending_inventory_quantity
ending_inventory_value
currency
exchange_rate_id
sale_transaction_id
unit_selling_price
gross_sales
gross_profit
gross_margin_percentage
cogs_percentage
cogs_method
product_category
sales_channel
customer_segment
sale_date
is_return
return_reason
cost_center
supplier_id
}
}
```
# List COGS Entries
Source: https://docs.stateset.com/api-reference/cogs/list
GET https://api.stateset.com/v1/cogs_entries/list
This endpoint lists COGS (Cost of Goods Sold) entries.
### Body
This is the limit of the COGS entries to return.
This is the offset of the COGS entries.
This is the order direction of the COGS entries.
### Response
Unique identifier for the COGS entry (primary key)
The accounting period for the COGS entry
The product associated with the COGS entry
The quantity of the product sold
The Cost of Goods Sold amount
The average cost per unit
The quantity of inventory remaining at the end of the period
The value of the ending inventory
The currency used for the financial calculations
Identifier for the related exchange rate
Identifier for the related sale transaction
The selling price per unit
The total gross sales amount
The gross profit amount
The gross margin percentage
The COGS as a percentage of sales
The method used to calculate COGS
The category of the product
The channel through which the sale was made
The segment of the customer who made the purchase
The date of the sale
Indicates whether this entry is for a return
The reason for the return, if applicable
The cost center associated with the COGS entry
Identifier for the related supplier
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/cogs_entries' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "asc"
}'
```
```graphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
cogs_entries(limit: $limit, offset: $offset, order_by: {id: $order_direction}) {
id
period
product
quantity_sold
cogs
average_cost
ending_inventory_quantity
ending_inventory_value
currency
exchange_rate_id
sale_transaction_id
unit_selling_price
gross_sales
gross_profit
gross_margin_percentage
cogs_percentage
cogs_method
product_category
sales_channel
customer_segment
sale_date
is_return
return_reason
cost_center
supplier_id
}
}
```
# Update COGS Entry
Source: https://docs.stateset.com/api-reference/cogs/update
PUT https://api.stateset.com/v1/cogs_entries/{id}
This endpoint updates an existing COGS (Cost of Goods Sold) entry.
### Path Parameters
The unique identifier of the COGS entry to update
### Body
The accounting period for the COGS entry
The product associated with the COGS entry
The quantity of the product sold
The Cost of Goods Sold amount
The average cost per unit
The quantity of inventory remaining at the end of the period
The value of the ending inventory
The currency used for the financial calculations
Identifier for the related exchange rate
Identifier for the related sale transaction
The selling price per unit
The total gross sales amount
The method used to calculate COGS
The category of the product
The channel through which the sale was made
The segment of the customer who made the purchase
The date of the sale
Indicates whether this entry is for a return
The reason for the return, if applicable
The cost center associated with the COGS entry
Identifier for the related supplier
### Response
The unique identifier of the updated COGS entry
A success message confirming the update of the COGS entry
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/cogs_entries/123' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"quantity_sold": 150,
"cogs": 7500,
"average_cost": 50,
"ending_inventory_quantity": 450,
"ending_inventory_value": 22500,
"gross_sales": 11250
}'
```
# Create Contact
Source: https://docs.stateset.com/api-reference/contacts/create
POST https://api.stateset.com/v1/contacts
This endpoint creates a new contacts
### Body
This is the current user group token you have for the user group that you want
to rotate.
### Response
### Response
The ID of the contact.
Name or details of the assistant associated with the contact.
Phone number of the assistant.
URL or path to the contact's avatar image.
Date of birth of the contact.
Name or details of the controller associated with the contact.
Date and time when the contact was created.
Name or details of the person who created the contact.
Department or division associated with the contact.
Description or additional details about the contact.
Indicates whether the contact should not be called.
Email address of the contact.
Indicates whether the contact has opted out of email communication.
Fax number of the contact.
Indicates whether the contact has opted out of fax communication.
First name of the contact.
Handle or username associated with the contact.
Indicates whether the contact is marked as invalid.
Languages known or spoken by the contact.
Last name of the contact.
Last person who modified the contact.
Source or origin of the lead/contact.
City of the mailing address.
Country of the mailing address.
Geocoding accuracy of the mailing address.
State or province of the mailing address.
Street of the mailing address.
Name or details of the owner of the contact.
Phone number of the contact.
URL or path to the contact's photo.
Name or details of the processor associated with the contact.
Title or position of the contact.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/contact' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Delete Contact
Source: https://docs.stateset.com/api-reference/contacts/delete
DELETE https://api.return.com/v1/contacts/:id
This endpoint deletes an existing contact.
### Body
The ID of the contact to delete.
### Response
The ID provided in the data tab may be used to identify the case
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/contact/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "co_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```json Response theme={null}
{
"id": "co_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "contact",
"deleted": true
}
```
# Get Contact
Source: https://docs.stateset.com/api-reference/contacts/get
GET https://api.stateset.com/v1/contacts/:id
This endpoint gets or creates a new contact.
### Body
The ID of the user group to which the contact belongs.
### Response
The ID of the contact.
Name or details of the assistant associated with the contact.
Phone number of the assistant.
URL or path to the contact's avatar image.
Date of birth of the contact.
Name or details of the controller associated with the contact.
Date and time when the contact was created.
Name or details of the person who created the contact.
Department or division associated with the contact.
Description or additional details about the contact.
Indicates whether the contact should not be called.
Email address of the contact.
Indicates whether the contact has opted out of email communication.
Fax number of the contact.
Indicates whether the contact has opted out of fax communication.
First name of the contact.
Handle or username associated with the contact.
Indicates whether the contact is marked as invalid.
Languages known or spoken by the contact.
Last name of the contact.
Last person who modified the contact.
Source or origin of the lead/contact.
City of the mailing address.
Country of the mailing address.
Geocoding accuracy of the mailing address.
State or province of the mailing address.
Street of the mailing address.
Name or details of the owner of the contact.
Phone number of the contact.
URL or path to the contact's photo.
Name or details of the processor associated with the contact.
Title or position of the contact.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/contacts/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "example_1",
}'
```
```json Response theme={null}
{
"success": 1,
"new_user_group": true,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
| Name | Type | Description |
| ---------------------- | --------- | ------------------------------------------------------------------ |
| id | Text | Unique identifier for the contact |
| assistant | Text | Name or details of the assistant associated with the contact |
| assistant\_phone | Text | Phone number of the assistant |
| avatar | Text | URL or path to the contact's avatar image |
| birthdate | Text | Date of birth of the contact |
| controller | Text | Name or details of the controller associated with the contact |
| created\_at | Date/Time | Date and time when the contact was created |
| created\_by | Text | Name or details of the person who created the contact |
| department | Text | Department or division associated with the contact |
| description | Text | Description or additional details about the contact |
| do\_not\_call | Boolean | Indicates whether the contact should not be called |
| email | Text | Email address of the contact |
| email\_opt\_out | Boolean | Indicates whether the contact has opted out of email communication |
| fax | Text | Fax number of the contact |
| fax\_opt\_out | Boolean | Indicates whether the contact has opted out of fax communication |
| firstName | Text | First name of the contact |
| handle | Text | Handle or username associated with the contact |
| invalid\_contact | Boolean | Indicates whether the contact is marked as invalid |
| languages | Text | Languages known or spoken by the contact |
| lastName | Text | Last name of the contact |
| last\_modified\_by | Text | Last person who modified the contact |
| leadSource | Text | Source or origin of the lead/contact |
| mailingCity | Text | City of the mailing address |
| mailingCountry | Text | Country of the mailing address |
| mailingGeocodeAccuracy | Text | Geocoding accuracy of the mailing address |
| mailingState | Text | State or province of the mailing address |
| mailingStreet | Text | Street address of the mailing address |
| nextMeeting | Text | Details or date/time of the next scheduled meeting |
| owner | Text | Owner or responsible person for the contact |
| phone | Text | Phone number of the contact |
| photoUrl | Text | URL or path to the contact's photo/image |
| processor | Text | Name or details of the processor associated with the contact |
| supplier\_id | Text | Supplier ID associated with the contact |
| title | Text | Title or job position of the contact |
# List Contact
Source: https://docs.stateset.com/api-reference/contacts/list
GET https://api.stateset.com/v1/contacts/list
This endpoint list contacts.
### Body
This is the limit of the contacts.
This is the offset of the contacts.
This is the order direction of the contacts.
### Response
The ID of the contact.
Name or details of the assistant associated with the contact.
Phone number of the assistant.
URL or path to the contact's avatar image.
Date of birth of the contact.
Name or details of the controller associated with the contact.
Date and time when the contact was created.
Name or details of the person who created the contact.
Department or division associated with the contact.
Description or additional details about the contact.
Indicates whether the contact should not be called.
Email address of the contact.
Indicates whether the contact has opted out of email communication.
Fax number of the contact.
Indicates whether the contact has opted out of fax communication.
First name of the contact.
Handle or username associated with the contact.
Indicates whether the contact is marked as invalid.
Languages known or spoken by the contact.
Last name of the contact.
Last person who modified the contact.
Source or origin of the lead/contact.
City of the mailing address.
Country of the mailing address.
Geocoding accuracy of the mailing address.
State or province of the mailing address.
Street of the mailing address.
Name or details of the owner of the contact.
Phone number of the contact.
URL or path to the contact's photo.
Name or details of the processor associated with the contact.
Title or position of the contact.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/contacts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "ASC"
}'
```
```json Response theme={null}
{
"contacts": [
{
"id": "1",
"assistant": "Assistant",
"assistant_phone": "1234567890",
"avatar": "https://www.stateset.com/avatar.png",
"birthdate": "2020-01-01",
"controller": "Controller",
"created_at": "2020-01-01T00:00:00.000000Z",
"created_by": "Created By",
"department": "Department",
"description": "Description",
"do_not_call": false,
}
```
# Update Contact
Source: https://docs.stateset.com/api-reference/contacts/update
PUT https://api.stateset.com/v1/contacts
This endpoint updates an existing contact.
### Body
This is the name of the user group.
### Response
### Response
The ID of the contact.
Name or details of the assistant associated with the contact.
Phone number of the assistant.
URL or path to the contact's avatar image.
Date of birth of the contact.
Name or details of the controller associated with the contact.
Date and time when the contact was created.
Name or details of the person who created the contact.
Department or division associated with the contact.
Description or additional details about the contact.
Indicates whether the contact should not be called.
Email address of the contact.
Indicates whether the contact has opted out of email communication.
Fax number of the contact.
Indicates whether the contact has opted out of fax communication.
First name of the contact.
Handle or username associated with the contact.
Indicates whether the contact is marked as invalid.
Languages known or spoken by the contact.
Last name of the contact.
Last person who modified the contact.
Source or origin of the lead/contact.
City of the mailing address.
Country of the mailing address.
Geocoding accuracy of the mailing address.
State or province of the mailing address.
Street of the mailing address.
Name or details of the owner of the contact.
Phone number of the contact.
URL or path to the contact's photo.
Name or details of the processor associated with the contact.
Title or position of the contact.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/contacts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
""
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 113,
"token": "",
"name": "ok",
"provided_id": "6"
}
}
```
# Create Customer
Source: https://docs.stateset.com/api-reference/customer/create
POST https://api.stateset.com/v1/customers
Create a new customer record with comprehensive validation and optional integrations
This endpoint creates a new customer and can optionally create associated accounts in integrated systems like Stripe.
## Request Body
Customer's email address. Must be unique and valid format.
**Example:** `customer@example.com`
Customer's first name. Must be 1-50 characters.
**Example:** `John`
Customer's last name. Must be 1-50 characters.
**Example:** `Doe`
Customer's phone number in E.164 format (recommended) or local format.
**Examples:** `+1-555-123-4567`, `(555) 123-4567`
Customer's date of birth in ISO 8601 format (YYYY-MM-DD).
**Example:** `1990-05-15`
Customer's primary address information.
Primary street address
Secondary address line (apartment, suite, etc.)
City name
State or province code (e.g., "CA", "NY", "ON")
ZIP or postal code
ISO 3166-1 alpha-2 country code (e.g., "US", "CA", "GB")
Whether the customer has consented to marketing communications.
Customer tier for loyalty programs. Options: `bronze`, `silver`, `gold`, `platinum`
How the customer found your business.
**Options:** `organic`, `paid_search`, `social_media`, `referral`, `email`, `direct`, `other`
Existing Stripe customer ID if you're syncing with an external Stripe account.
**Note:** If not provided and Stripe integration is enabled, a new Stripe customer will be created automatically.
Internal notes about the customer (not visible to customer).
**Max length:** 1000 characters
Array of tags for customer segmentation and organization.
**Example:** `["vip", "wholesale", "early-adopter"]`
Additional custom fields as key-value pairs. Keys must be alphanumeric with underscores.
**Example:**
```json theme={null}
{
"company_name": "Acme Corp",
"industry": "Technology",
"employee_count": "50-100"
}
```
Customer communication preferences.
Allow email notifications
Allow SMS notifications
Preferred language (ISO 639-1 code)
Customer's timezone (IANA timezone identifier)
## Response
Unique identifier for the created customer
**Example:** `cust_1NXWPnCo6bFb1KQto6C8OWvE`
Customer's email address
Customer's first name
Customer's last name
Customer's full name (computed field)
Customer's phone number
Customer's date of birth
Customer's address information
Customer's loyalty tier
Marketing consent status
Associated Stripe customer ID (if Stripe integration is enabled)
ISO 8601 timestamp when the customer was created
ISO 8601 timestamp when the customer was last updated
Customer status: `active`, `inactive`, `suspended`
Customer's lifetime value (computed from order history)
Total number of orders placed by this customer
Array of customer tags
Custom field key-value pairs
Customer communication preferences
```bash Basic Customer theme={null}
curl -X POST https://api.stateset.com/v1/customers \
-H "Authorization: Bearer ${STATESET_API_KEY}" \
-H "Content-Type: application/json" \
-d '{
"email": "john.doe@example.com",
"first_name": "John",
"last_name": "Doe",
"phone": "+1-555-123-4567"
}'
```
```bash Complete Customer Profile theme={null}
curl -X POST https://api.stateset.com/v1/customers \
-H "Authorization: Bearer ${STATESET_API_KEY}" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: customer-creation-12345" \
-d '{
"email": "sarah.wilson@techcorp.com",
"first_name": "Sarah",
"last_name": "Wilson",
"phone": "+1-555-987-6543",
"date_of_birth": "1985-12-03",
"address": {
"street1": "123 Innovation Drive",
"street2": "Suite 200",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"marketing_consent": true,
"customer_tier": "gold",
"referral_source": "paid_search",
"notes": "High-value enterprise customer",
"tags": ["enterprise", "tech", "high-value"],
"custom_fields": {
"company_name": "Tech Corp",
"job_title": "CTO",
"industry": "Technology"
},
"preferences": {
"email_notifications": true,
"sms_notifications": false,
"language": "en",
"timezone": "America/Los_Angeles"
}
}'
```
```javascript Node.js SDK theme={null}
import { StateSetClient } from 'stateset-node';
const client = new StateSetClient({
apiKey: process.env.STATESET_API_KEY
});
try {
const customer = await client.customers.create({
email: 'john.doe@example.com',
first_name: 'John',
last_name: 'Doe',
phone: '+1-555-123-4567',
address: {
street1: '123 Main Street',
city: 'New York',
state: 'NY',
postal_code: '10001',
country: 'US'
},
marketing_consent: true,
customer_tier: 'silver',
tags: ['newsletter-subscriber']
});
console.log('Customer created:', customer.id);
// Optionally, create a welcome email workflow
await client.workflows.trigger({
workflow_id: 'welcome_series',
customer_id: customer.id
});
} catch (error) {
if (error.code === 'DUPLICATE_EMAIL') {
console.log('Customer already exists with this email');
} else {
console.error('Error creating customer:', error.message);
}
}
```
```python Python SDK theme={null}
from stateset import StateSet
import os
client = StateSet(api_key=os.getenv('STATESET_API_KEY'))
try:
customer = client.customers.create({
'email': 'jane.smith@example.com',
'first_name': 'Jane',
'last_name': 'Smith',
'phone': '+1-555-234-5678',
'address': {
'street1': '456 Oak Avenue',
'city': 'Los Angeles',
'state': 'CA',
'postal_code': '90210',
'country': 'US'
},
'marketing_consent': False,
'customer_tier': 'bronze',
'referral_source': 'social_media',
'custom_fields': {
'how_did_you_hear': 'Instagram ad',
'interests': 'sustainability'
}
})
print(f'Customer created: {customer.id}')
# Send welcome email
client.emails.send({
'template': 'welcome',
'to': customer.email,
'variables': {
'first_name': customer.first_name
}
})
except Exception as error:
if hasattr(error, 'code') and error.code == 'DUPLICATE_EMAIL':
print('Customer already exists')
else:
print(f'Error: {str(error)}')
```
```ruby Ruby SDK theme={null}
require 'stateset'
client = StateSet::Client.new(
api_key: ENV['STATESET_API_KEY']
)
begin
customer = client.customers.create({
email: 'mike.johnson@example.com',
first_name: 'Mike',
last_name: 'Johnson',
phone: '+1-555-345-6789',
address: {
street1: '789 Pine Street',
city: 'Seattle',
state: 'WA',
postal_code: '98101',
country: 'US'
},
customer_tier: 'platinum',
tags: ['vip', 'longtime-customer']
})
puts "Customer created: #{customer.id}"
rescue StateSet::DuplicateEmailError
puts "Customer already exists with this email"
rescue StateSet::Error => e
puts "Error creating customer: #{e.message}"
end
```
```go Go SDK theme={null}
package main
import (
"context"
"fmt"
"log"
"os"
"github.com/stateset/stateset-go"
"github.com/stateset/stateset-go/option"
)
func main() {
client := stateset.NewClient(
option.WithAPIKey(os.Getenv("STATESET_API_KEY")),
)
customer, err := client.Customers.Create(context.Background(), &stateset.CustomerCreateParams{
Email: "alex.brown@example.com",
FirstName: "Alex",
LastName: "Brown",
Phone: "+1-555-456-7890",
Address: &stateset.AddressParams{
Street1: "321 Elm Street",
City: "Austin",
State: "TX",
PostalCode: "73301",
Country: "US",
},
MarketingConsent: stateset.Bool(true),
CustomerTier: stateset.String("gold"),
Tags: []string{"referral", "premium"},
})
if err != nil {
var apiErr *stateset.Error
if errors.As(err, &apiErr) && apiErr.Code == "DUPLICATE_EMAIL" {
fmt.Println("Customer already exists")
return
}
log.Fatal(err)
}
fmt.Printf("Customer created: %s\n", customer.ID)
}
```
```php PHP SDK theme={null}
$_ENV['STATESET_API_KEY']
]);
try {
$customer = $client->customers->create([
'email' => 'lisa.davis@example.com',
'first_name' => 'Lisa',
'last_name' => 'Davis',
'phone' => '+1-555-567-8901',
'address' => [
'street1' => '654 Maple Drive',
'city' => 'Denver',
'state' => 'CO',
'postal_code' => '80202',
'country' => 'US'
],
'customer_tier' => 'silver',
'marketing_consent' => true,
'referral_source' => 'email'
]);
echo "Customer created: " . $customer->id . "\n";
// Send welcome SMS if phone provided
if ($customer->phone) {
$client->sms->send([
'to' => $customer->phone,
'message' => "Welcome to our store, {$customer->first_name}!"
]);
}
} catch (StateSetException $e) {
if ($e->getCode() === 'DUPLICATE_EMAIL') {
echo "Customer already exists\n";
} else {
echo "Error: " . $e->getMessage() . "\n";
}
}
?>
```
```java Java SDK theme={null}
import com.stateset.StateSetClient;
import com.stateset.models.Customer;
import com.stateset.models.CustomerCreateParams;
import com.stateset.models.Address;
import com.stateset.exception.StateSetException;
public class CreateCustomerExample {
public static void main(String[] args) {
StateSetClient client = StateSetClient.builder()
.apiKey(System.getenv("STATESET_API_KEY"))
.build();
try {
CustomerCreateParams params = CustomerCreateParams.builder()
.email("tom.wilson@example.com")
.firstName("Tom")
.lastName("Wilson")
.phone("+1-555-678-9012")
.address(Address.builder()
.street1("987 Oak Boulevard")
.city("Miami")
.state("FL")
.postalCode("33101")
.country("US")
.build())
.customerTier("gold")
.marketingConsent(true)
.addTag("newsletter")
.addTag("loyalty-program")
.build();
Customer customer = client.customers().create(params);
System.out.println("Customer created: " + customer.getId());
} catch (StateSetException e) {
if ("DUPLICATE_EMAIL".equals(e.getCode())) {
System.out.println("Customer already exists");
} else {
System.err.println("Error: " + e.getMessage());
}
}
}
}
```
```graphql GraphQL Mutation theme={null}
mutation CreateCustomer($input: CustomerCreateInput!) {
createCustomer(input: $input) {
id
email
firstName
lastName
fullName
phone
address {
street1
street2
city
state
postalCode
country
}
customerTier
marketingConsent
status
createdAt
stripeCustomerId
tags
customFields
preferences {
emailNotifications
smsNotifications
language
timezone
}
}
}
# Variables:
{
"input": {
"email": "emily.chen@example.com",
"firstName": "Emily",
"lastName": "Chen",
"phone": "+1-555-789-0123",
"address": {
"street1": "159 Innovation Way",
"city": "Boston",
"state": "MA",
"postalCode": "02101",
"country": "US"
},
"customerTier": "platinum",
"marketingConsent": true,
"tags": ["enterprise", "tech-executive"],
"customFields": {
"company": "Innovation Labs",
"role": "VP Engineering"
}
}
}
```
```json Success Response (201 Created) theme={null}
{
"id": "cust_1NXWPnCo6bFb1KQto6C8OWvE",
"email": "sarah.wilson@techcorp.com",
"first_name": "Sarah",
"last_name": "Wilson",
"full_name": "Sarah Wilson",
"phone": "+1-555-987-6543",
"date_of_birth": "1985-12-03",
"address": {
"street1": "123 Innovation Drive",
"street2": "Suite 200",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"customer_tier": "gold",
"marketing_consent": true,
"referral_source": "paid_search",
"stripe_customer_id": "cus_ABC123DEF456",
"status": "active",
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T10:30:00Z",
"lifetime_value": 0.00,
"total_orders": 0,
"tags": ["enterprise", "tech", "high-value"],
"custom_fields": {
"company_name": "Tech Corp",
"job_title": "CTO",
"industry": "Technology"
},
"preferences": {
"email_notifications": true,
"sms_notifications": false,
"language": "en",
"timezone": "America/Los_Angeles"
}
}
```
```json Error Response (400 Bad Request) theme={null}
{
"error": {
"code": "VALIDATION_ERROR",
"message": "Request validation failed",
"errors": [
{
"field": "email",
"message": "Invalid email format",
"value": "invalid-email"
},
{
"field": "first_name",
"message": "First name is required",
"value": null
}
],
"request_id": "req_1NXWPnCo6bFb1KQto6C8OWvE"
}
}
```
```json Error Response (409 Conflict) theme={null}
{
"error": {
"code": "DUPLICATE_EMAIL",
"message": "A customer with this email already exists",
"details": {
"email": "sarah.wilson@techcorp.com",
"existing_customer_id": "cust_2OYZRpEq8dHd3MSvq8E0QYwG"
},
"request_id": "req_1NXWPnCo6bFb1KQto6C8OWvE"
}
}
```
```json Error Response (422 Unprocessable Entity) theme={null}
{
"error": {
"code": "BUSINESS_RULE_VIOLATION",
"message": "Customer creation violates business rules",
"errors": [
{
"rule": "age_restriction",
"message": "Customer must be at least 13 years old",
"field": "date_of_birth"
}
],
"request_id": "req_1NXWPnCo6bFb1KQto6C8OWvE"
}
}
```
## Additional Features
### Idempotency
Use the `Idempotency-Key` header to safely retry customer creation requests:
```bash theme={null}
curl -X POST https://api.stateset.com/v1/customers \
-H "Idempotency-Key: customer-signup-form-abc123" \
-H "Authorization: Bearer sk_live_..." \
-d '{"email": "customer@example.com", ...}'
```
### Stripe Integration
When Stripe integration is enabled:
* A Stripe customer is automatically created if `stripe_customer_id` is not provided
* Customer data is synced between StateSet and Stripe
* Payment methods can be attached to the Stripe customer
### Webhook Events
Creating a customer triggers these webhook events:
* `customer.created` - Fired when customer is successfully created
* `customer.stripe_synced` - Fired when Stripe customer is created (if integration enabled)
### Validation Rules
| Field | Validation |
| --------------- | -------------------------------------------------- |
| `email` | Must be valid email format, unique across account |
| `first_name` | 1-50 characters, letters and spaces only |
| `last_name` | 1-50 characters, letters and spaces only |
| `phone` | Valid phone number format |
| `date_of_birth` | Valid date, customer must be at least 13 years old |
| `postal_code` | Valid format for specified country |
| `country` | Valid ISO 3166-1 alpha-2 country code |
### Rate Limiting
Customer creation is subject to rate limits:
* **Standard:** 100 customers/minute
* **Enterprise:** 1000 customers/minute
Consider using batch import for large datasets.
# Delete Customer
Source: https://docs.stateset.com/api-reference/customer/delete
DELETE https://api.return.com/v1/customers/:id
This endpoint deletes an existing customer.
### Body
The ID of the customer to delete.
### Response
The ID provided in the data tab may be used to identify the manufacture order
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/customers/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1"
"current_token": "abcdef"
}'
```
```graphQL GraphQL theme={null}
mutation {
deleteCustomer(
input: {
id: "example_1"
}
) {
id
object
deleted
}
}
```
```js Node.js theme={null}
var deleted = await stateset.customers.del({
id: "example_1"
});
```
```python Python theme={null}
deleted = stateset.customers.del({
"id": "example_1"
})
```
```ruby Ruby theme={null}
deleted = stateset.customers.del({
"id": "example_1"
})
```
```go Go theme={null}
deleted, err := stateset.Customers.Delete(
"example_1"
)
```
```java Java theme={null}
Customer deleted = stateset.customers.delete(
"example_1"
);
```
```php PHP theme={null}
$deleted = $stateset->customers->delete([
"id" => "example_1"
]);
```
```json Response theme={null}
{
"id": "cu_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "customer",
"deleted": true
}
```
# Get Customer
Source: https://docs.stateset.com/api-reference/customer/get
GET https://api.stateset.com/v1/customers/:id
Retrieve a single customer by their unique identifier
Returns the full customer object including profile, address, and integration details.
## Path Parameters
The unique identifier (SSO ID) of the customer to retrieve.
**Example:** `1234-5678-9012-3456`
### Response
Unique identifier for the customer.
Customer's email address.
Customer's first name.
Customer's last name.
Customer's phone number.
Associated Stripe customer ID for payment processing.
ISO 8601 date when the customer account was activated.
ISO 8601 timestamp of the last update to the customer record.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/customers/1234-5678-9012-3456' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer '
```
```graphql GraphQL theme={null}
query getCustomer($sso_id: uuid!) {
customers: customers_by_pk(sso_id: $sso_id) {
sso_id
activationDate
email
firstName
lastName
phone
stripe_customer_id
timestamp
}
}
```
```javascript Node.js theme={null}
const customer = await stateset.customers.retrieve(
'1234-5678-9012-3456'
);
```
```python Python theme={null}
customer = stateset.customers.retrieve(
'1234-5678-9012-3456'
)
```
```ruby Ruby theme={null}
customer = Stateset::Customers.retrieve(
'1234-5678-9012-3456'
)
```
```go Go theme={null}
customer, err := stateset.Customers.Retrieve(
"1234-5678-9012-3456",
)
```
```php PHP theme={null}
$customer = $stateset->customers->retrieve(
'1234-5678-9012-3456'
);
```
```java Java theme={null}
Customer customer = stateset.customers().retrieve(
"1234-5678-9012-3456"
);
```
```json Response theme={null}
{
"customer": {
"sso_id": "1234-5678-9012-3456",
"email": "jane.doe@example.com",
"firstName": "Jane",
"lastName": "Doe",
"phone": "+1-555-123-4567",
"stripe_customer_id": "cus_1234567890",
"activationDate": "2024-01-15T00:00:00.000Z",
"timestamp": "2024-06-01T12:30:00.000Z"
}
}
```
```json Error Response (404 Not Found) theme={null}
{
"error": {
"code": "RESOURCE_NOT_FOUND",
"message": "Customer not found",
"details": {
"resource": "customer",
"id": "1234-5678-9012-3456"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (401 Unauthorized) theme={null}
{
"error": {
"code": "INVALID_API_KEY",
"message": "The API key provided is invalid or has been revoked",
"request_id": "req_abc123def456"
}
}
```
# List Customers
Source: https://docs.stateset.com/api-reference/customer/list
GET https://api.stateset.com/v1/customers
Retrieve a paginated list of customers with optional filtering and sorting
Returns a paginated array of customer objects. Use query parameters to filter, sort, and paginate results.
## Query Parameters
Maximum number of customers to return per page. Range: 1-100.
**Example:** `50`
Number of records to skip for pagination.
**Example:** `20`
Sort direction for results. Options: `asc`, `desc`.
Filter customers by email address (exact match).
**Example:** `jane.doe@example.com`
Filter customers created after this ISO 8601 date.
**Example:** `2024-01-01T00:00:00.000Z`
### Response
Array of customer objects.
Unique identifier for the customer.
Customer's email address.
Customer's first name.
Customer's last name.
Customer's phone number.
Associated Stripe customer ID.
ISO 8601 date when the customer account was activated.
ISO 8601 timestamp of the last update.
Total number of customers matching the query.
Whether there are more results beyond the current page.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/customers?limit=20&offset=0&order_direction=desc' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer '
```
```graphql GraphQL theme={null}
query listCustomers($limit: Int!, $offset: Int!) {
customers(limit: $limit, offset: $offset, order_by: { timestamp: desc }) {
sso_id
activationDate
email
firstName
lastName
phone
stripe_customer_id
timestamp
}
customers_aggregate {
aggregate {
count
}
}
}
```
```javascript Node.js theme={null}
const customers = await stateset.customers.list({
limit: 20,
offset: 0,
order_direction: 'desc',
});
```
```python Python theme={null}
customers = stateset.customers.list(
limit=20,
offset=0,
order_direction='desc',
)
```
```ruby Ruby theme={null}
customers = Stateset::Customers.list(
limit: 20,
offset: 0,
order_direction: 'desc',
)
```
```go Go theme={null}
customers, err := stateset.Customers.List(&CustomerListParams{
Limit: 20,
Offset: 0,
OrderDirection: "desc",
})
```
```php PHP theme={null}
$customers = $stateset->customers->list([
'limit' => 20,
'offset' => 0,
'order_direction' => 'desc',
]);
```
```java Java theme={null}
CustomerCollection customers = stateset.customers().list(
CustomerListParams.builder()
.setLimit(20)
.setOffset(0)
.setOrderDirection("desc")
.build()
);
```
```json Response theme={null}
{
"customers": [
{
"sso_id": "1234-5678-9012-3456",
"email": "jane.doe@example.com",
"firstName": "Jane",
"lastName": "Doe",
"phone": "+1-555-123-4567",
"stripe_customer_id": "cus_1234567890",
"activationDate": "2024-01-15T00:00:00.000Z",
"timestamp": "2024-06-01T12:30:00.000Z"
},
{
"sso_id": "9876-5432-1098-7654",
"email": "john.smith@example.com",
"firstName": "John",
"lastName": "Smith",
"phone": "+1-555-987-6543",
"stripe_customer_id": "cus_0987654321",
"activationDate": "2024-02-20T00:00:00.000Z",
"timestamp": "2024-05-28T09:15:00.000Z"
}
],
"total_count": 142,
"has_more": true
}
```
```json Error Response (400 Bad Request) theme={null}
{
"error": {
"code": "INVALID_PARAMETER",
"message": "limit must be between 1 and 100",
"details": {
"parameter": "limit",
"value": 500
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (401 Unauthorized) theme={null}
{
"error": {
"code": "INVALID_API_KEY",
"message": "The API key provided is invalid or has been revoked",
"request_id": "req_abc123def456"
}
}
```
# Merge Customers
Source: https://docs.stateset.com/api-reference/customer/merge
POST https://api.stateset.com/v1/customers/merge
This endpoint merges duplicate customer records into a single primary record.
### Body
The customer ID that will be kept as the primary record
Array of customer IDs to be merged into the primary record
Strategy for handling conflicting data during merge
How to merge contact info: "primary\_only", "merge\_all", "most\_recent"
How to handle orders: "transfer\_all", "keep\_separate"
How to merge addresses: "primary\_only", "merge\_unique", "keep\_all"
How to merge preferences: "primary\_only", "merge\_all", "most\_recent"
The reason for merging these customer records
### Response
The ID of the primary customer record after merge
Array of customer IDs that were merged
Summary of what was merged
Number of orders transferred
Number of addresses merged
Number of contacts merged
Combined lifetime value of all merged customers
List of conflicts that were resolved during merge
Timestamp when the merge was completed
User who performed the merge
Indicates whether the merge was successful
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/customers/merge' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"primary_customer_id": "cust_primary_123",
"duplicate_customer_ids": ["cust_dup_456", "cust_dup_789"],
"merge_strategy": {
"contacts": "merge_all",
"orders": "transfer_all",
"addresses": "merge_unique",
"preferences": "most_recent"
},
"reason": "Duplicate accounts identified during data cleanup"
}'
```
```graphQL GraphQL theme={null}
mutation customerMergeMutation {
customerMerge(
primaryCustomerId: "${primaryCustomerId}",
duplicateCustomerIds: ${duplicateCustomerIds},
mergeStrategy: ${mergeStrategy},
reason: "${reason}"
) {
customer {
id
email
merge_summary {
orders_transferred
addresses_merged
total_lifetime_value
}
}
userErrors {
field
message
}
}
}
```
```js Node.js theme={null}
const mergedCustomer = await stateset.customers.merge({
primary_customer_id: 'cust_primary_123',
duplicate_customer_ids: ['cust_dup_456', 'cust_dup_789'],
merge_strategy: {
contacts: 'merge_all',
orders: 'transfer_all',
addresses: 'merge_unique',
preferences: 'most_recent'
},
reason: 'Duplicate accounts identified during data cleanup'
});
```
```python Python theme={null}
merged_customer = stateset.customers.merge({
'primary_customer_id': 'cust_primary_123',
'duplicate_customer_ids': ['cust_dup_456', 'cust_dup_789'],
'merge_strategy': {
'contacts': 'merge_all',
'orders': 'transfer_all',
'addresses': 'merge_unique',
'preferences': 'most_recent'
},
'reason': 'Duplicate accounts identified during data cleanup'
})
```
```ruby Ruby theme={null}
merged_customer = Stateset::Customer.merge({
primary_customer_id: 'cust_primary_123',
duplicate_customer_ids: ['cust_dup_456', 'cust_dup_789'],
merge_strategy: {
contacts: 'merge_all',
orders: 'transfer_all',
addresses: 'merge_unique',
preferences: 'most_recent'
},
reason: 'Duplicate accounts identified during data cleanup'
})
```
```go Go theme={null}
mergedCustomer, err := stateset.Customers.merge({
PrimaryCustomerID: 'cust_primary_123',
DuplicateCustomerIDs: []string{'cust_dup_456', 'cust_dup_789'},
MergeStrategy: MergeStrategy{
Contacts: 'merge_all',
Orders: 'transfer_all',
Addresses: 'merge_unique',
Preferences: 'most_recent'
},
Reason: 'Duplicate accounts identified during data cleanup'
})
```
```java Java theme={null}
Customer mergedCustomer = stateset.customers.merge({
primaryCustomerId: 'cust_primary_123',
duplicateCustomerIds: ['cust_dup_456', 'cust_dup_789'],
mergeStrategy: {
contacts: 'merge_all',
orders: 'transfer_all',
addresses: 'merge_unique',
preferences: 'most_recent'
},
reason: 'Duplicate accounts identified during data cleanup'
});
```
```php PHP theme={null}
$merged_customer = $stateset->customers->merge([
'primary_customer_id' => 'cust_primary_123',
'duplicate_customer_ids' => ['cust_dup_456', 'cust_dup_789'],
'merge_strategy' => [
'contacts' => 'merge_all',
'orders' => 'transfer_all',
'addresses' => 'merge_unique',
'preferences' => 'most_recent'
],
'reason' => 'Duplicate accounts identified during data cleanup'
]);
```
```csharp C# theme={null}
var mergedCustomer = await stateset.Customers.Merge(new {
PrimaryCustomerId = 'cust_primary_123',
DuplicateCustomerIds = new[] { 'cust_dup_456', 'cust_dup_789' },
MergeStrategy = new {
Contacts = 'merge_all',
Orders = 'transfer_all',
Addresses = 'merge_unique',
Preferences = 'most_recent'
},
Reason = 'Duplicate accounts identified during data cleanup'
});
```
```json Response theme={null}
{
"id": "cust_primary_123",
"merged_customer_ids": ["cust_dup_456", "cust_dup_789"],
"merge_summary": {
"orders_transferred": 15,
"addresses_merged": 3,
"contacts_merged": 2,
"total_lifetime_value": 4567.89,
"loyalty_points_combined": 2500
},
"conflicts_resolved": [
{
"field": "email",
"primary_value": "john@example.com",
"duplicate_values": ["j.doe@example.com", "johndoe@example.com"],
"resolution": "kept_primary"
},
{
"field": "phone",
"primary_value": "+1-555-0123",
"duplicate_values": ["+1-555-0124"],
"resolution": "kept_all_as_secondary"
}
],
"merged_at": "2024-01-15T14:30:00Z",
"merged_by": "user_admin_123",
"success": true
}
```
```json Error Response theme={null}
{
"error": {
"code": "merge_conflict",
"message": "Cannot merge customers with active subscriptions. Please resolve subscriptions first.",
"details": {
"primary_customer_subscriptions": 1,
"duplicate_customer_subscriptions": ["cust_dup_456"],
"resolution_required": "cancel_or_transfer_subscriptions"
}
}
}
```
# Tag Customer
Source: https://docs.stateset.com/api-reference/customer/tag
POST https://api.stateset.com/v1/customers/:id/tag
This endpoint adds or removes tags from a customer for segmentation and categorization.
### Body
The unique identifier of the customer
Array of tags to add to the customer
Array of tags to remove from the customer
Optional metadata for tags
Tag category (e.g., "loyalty", "segment", "preference", "behavior")
Source of the tag (e.g., "manual", "automatic", "import", "rule\_based")
Optional expiry date for time-limited tags
### Response
The customer ID
Array of all current tags on the customer
Tags that were successfully added
Tags that were successfully removed
Total number of tags on the customer
Customer segments based on current tags
Timestamp when tags were last updated
Indicates whether the operation was successful
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/customers/:id/tag' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"customer_id": "cust_123abc",
"tags_to_add": ["vip", "high_value", "early_adopter"],
"tags_to_remove": ["prospect"],
"tag_metadata": {
"category": "loyalty",
"source": "manual",
"expiry_date": "2024-12-31"
}
}'
```
```graphQL GraphQL theme={null}
mutation customerTagMutation {
customerTag(
customerId: "${customerId}",
tagsToAdd: ${tagsToAdd},
tagsToRemove: ${tagsToRemove},
tagMetadata: ${tagMetadata}
) {
customer {
id
current_tags
segments
tag_count
}
userErrors {
field
message
}
}
}
```
```js Node.js theme={null}
const taggedCustomer = await stateset.customers.tag({
customer_id: 'cust_123abc',
tags_to_add: ['vip', 'high_value', 'early_adopter'],
tags_to_remove: ['prospect'],
tag_metadata: {
category: 'loyalty',
source: 'manual',
expiry_date: '2024-12-31'
}
});
```
```python Python theme={null}
tagged_customer = stateset.customers.tag({
'customer_id': 'cust_123abc',
'tags_to_add': ['vip', 'high_value', 'early_adopter'],
'tags_to_remove': ['prospect'],
'tag_metadata': {
'category': 'loyalty',
'source': 'manual',
'expiry_date': '2024-12-31'
}
})
```
```ruby Ruby theme={null}
tagged_customer = Stateset::Customer.tag({
customer_id: 'cust_123abc',
tags_to_add: ['vip', 'high_value', 'early_adopter'],
tags_to_remove: ['prospect'],
tag_metadata: {
category: 'loyalty',
source: 'manual',
expiry_date: '2024-12-31'
}
})
```
```go Go theme={null}
taggedCustomer, err := stateset.Customers.tag({
CustomerID: 'cust_123abc',
TagsToAdd: []string{'vip', 'high_value', 'early_adopter'},
TagsToRemove: []string{'prospect'},
TagMetadata: TagMetadata{
Category: 'loyalty',
Source: 'manual',
ExpiryDate: '2024-12-31'
}
})
```
```java Java theme={null}
Customer taggedCustomer = stateset.customers.tag({
customerId: 'cust_123abc',
tagsToAdd: ['vip', 'high_value', 'early_adopter'],
tagsToRemove: ['prospect'],
tagMetadata: {
category: 'loyalty',
source: 'manual',
expiryDate: '2024-12-31'
}
});
```
```php PHP theme={null}
$tagged_customer = $stateset->customers->tag([
'customer_id' => 'cust_123abc',
'tags_to_add' => ['vip', 'high_value', 'early_adopter'],
'tags_to_remove' => ['prospect'],
'tag_metadata' => [
'category' => 'loyalty',
'source' => 'manual',
'expiry_date' => '2024-12-31'
]
]);
```
```csharp C# theme={null}
var taggedCustomer = await stateset.Customers.Tag(new {
CustomerId = 'cust_123abc',
TagsToAdd = new[] { 'vip', 'high_value', 'early_adopter' },
TagsToRemove = new[] { 'prospect' },
TagMetadata = new {
Category = 'loyalty',
Source = 'manual',
ExpiryDate = '2024-12-31'
}
});
```
```json Response theme={null}
{
"id": "cust_123abc",
"current_tags": [
"vip",
"high_value",
"early_adopter",
"repeat_buyer",
"email_subscriber"
],
"tags_added": ["vip", "high_value", "early_adopter"],
"tags_removed": ["prospect"],
"tag_count": 5,
"segments": [
{
"id": "seg_premium",
"name": "Premium Customers",
"matched_by_tags": ["vip", "high_value"]
},
{
"id": "seg_engaged",
"name": "Highly Engaged",
"matched_by_tags": ["repeat_buyer", "email_subscriber"]
}
],
"updated_at": "2024-01-15T10:30:00Z",
"updated_by": "user_123",
"success": true
}
```
```json Error Response theme={null}
{
"error": {
"code": "invalid_tag",
"message": "Tag 'invalid-tag!' contains invalid characters. Tags must be alphanumeric with underscores only.",
"details": {
"invalid_tags": ["invalid-tag!"],
"valid_pattern": "^[a-zA-Z0-9_]+$"
}
}
}
```
# Update Customer
Source: https://docs.stateset.com/api-reference/customer/update
PUT https://api.stateset.com/v1/customers/:id
This endpoint updates an existing customer.
### Body
This is the sso\_id of the customer
This is the customer object.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
The contents of the user group
Indicates whether a new user group was created.
This is the user group token (userGroupToken or USER\_GROUP\_TOKEN) that will be
used to identify which user group is viewing the dashboard. You should save
this on your end to use when rendering an embedded dashboard.
This is the name of the user group provided in the request body.
This is the user\_group\_id provided in the request body.
This is the properties object if it was provided in the request body
This is the environment tag of the user group. Possible values are 'Customer'
and 'Testing'
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/customers/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "string",
"email": "string",
"firstName": "string",
"lastName": "string",
"phone": "string",
"stripe_customer_id": "string",
"timestamp": "string",
"activationDate": "string"
}'
```
```json Response theme={null}
{
"id": "string",
"email": "string",
"firstName": "string",
"lastName": "string",
"phone": "string",
"stripe_customer_id": "string",
"timestamp": "string",
"activationDate": "string"
}
```
# Create Cycle Count
Source: https://docs.stateset.com/api-reference/cyclecounts/create
POST https://api.stateset.com/v1/cycle_counts
This endpoint creates a new cycle count
### Body
The id of the cycle count to be created. If not provided, a new id will be generated.
The number of the cycle count to be created. If not provided, a new number will be generated.
The status of the cycle count to be created. If not provided, the status will be set to "open".
The part associated with the cycle count to be created.
The standard tracking information associated with the cycle count to be created.
The serialized tracking information associated with the cycle count to be created.
The expected quantity of the part associated with the cycle count to be created.
The actual quantity of the part counted during the cycle count to be created.
The difference between the expected and actual quantity of the part.
The difference in cost between the expected and actual quantity of the part.
An explanation for any variances in the cycle count to be created.
The site associated with the cycle count to be created.
The location associated with the cycle count to be created.
The bin associated with the cycle count to be created.
The lot associated with the cycle count to be created.
The start date associated with the cycle count to be created.
The end date associated with the cycle count to be created.
The completion date associated with the cycle count to be created.
The user assigned to the cycle count to be created.
The method used to count the part associated with the cycle count to be created.
The status of the cycle count to be created.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/cycle_counts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```javascript Node.js theme={null}
var created = await stateset.cyclecounts.create({
id: ''
});
```
```python Python theme={null}
created = stateset.cyclecounts.create({
'id': ''
})
```
```ruby Ruby theme={null}
created = Stateset::CycleCount.create({
id: ''
})
```
```php PHP theme={null}
$created = $stateset->cyclecounts->create([
'id' => ''
]);
```
```go Go theme={null}
created := cyclecounts.Create(&stateset.CycleCount{
ID: ''
})
```
```java Java theme={null}
CycleCount created = cyclecounts.create(new CycleCount(){
id: ''
});
```
```json Response theme={null}
```
# Delete Cycle Count
Source: https://docs.stateset.com/api-reference/cyclecounts/delete
DELETE https://api.stateset.com/v1/cycle_counts/:id
This endpoint deletes an existing cycle count.
### Body
The id of the cycle count to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/cycle_counts/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "pl_ODkRWQtx9NVsRX"
}'
```
```javascript Node.js theme={null}
const deleted = await stateset.cyclecounts.del(
'cc_ODkRWQtx9NVsRX'
);
```
```graphQL GraphQL theme={null}
mutation deleteCycleCounts ($pick_id: String!) {
delete_cycle_counts(where: {id: {_eq: $cycle_count_id}}) {
affected_rows
}
}
```
```python Python theme={null}
deleted = stateset.cyclecounts.del(
'pl_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
deleted = Stateset::cyclecounts.del(
'pl_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$deleted = $stateset->cyclecounts->del(
'pl_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
deleted, err := stateset.cyclecounts.Del(
'pl_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
cyclecounts deleted = stateset.cyclecounts.del(
'pl_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"id": "pi_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "cyclecounts",
"deleted": true
}
```
# Get Cycle Count
Source: https://docs.stateset.com/api-reference/cyclecounts/get
GET https://api.stateset.com/v1/cycle_counts
This endpoint creates a new cycle count
### Body
The id of the cycle count to be created. If not provided, a new id will be generated.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/cycle_counts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```javascript Node.js theme={null}
var created = await stateset.cyclecounts.get({
id: ''
});
```
```json Response theme={null}
```
# Get Cycle Count
Source: https://docs.stateset.com/api-reference/cyclecounts/list
GET https://api.stateset.com/v1/cycle_counts
This endpoint creates a new cycle count
### Body
This is the limit of the picks.
This is the offset of the picks.
This is the order direction of the picks.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/cycle_counts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```javascript Node.js theme={null}
var created = await stateset.cyclecounts.list({
id: ''
});
```
```json Response theme={null}
```
# Update Cycle Count
Source: https://docs.stateset.com/api-reference/cyclecounts/update
POST https://api.stateset.com/v1/cycle_counts
This endpoint creates a new cycle count
### Body
The id of the cycle count to be created. If not provided, a new id will be generated.
The number of the cycle count to be created. If not provided, a new number will be generated.
The status of the cycle count to be created. If not provided, the status will be set to "open".
The part associated with the cycle count to be created.
The standard tracking information associated with the cycle count to be created.
The serialized tracking information associated with the cycle count to be created.
The expected quantity of the part associated with the cycle count to be created.
The actual quantity of the part counted during the cycle count to be created.
The difference between the expected and actual quantity of the part.
The difference in cost between the expected and actual quantity of the part.
An explanation for any variances in the cycle count to be created.
The site associated with the cycle count to be created.
The location associated with the cycle count to be created.
The bin associated with the cycle count to be created.
The lot associated with the cycle count to be created.
The start date associated with the cycle count to be created.
The end date associated with the cycle count to be created.
The completion date associated with the cycle count to be created.
The user assigned to the cycle count to be created.
The method used to count the part associated with the cycle count to be created.
The status of the cycle count to be created.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/cycle_counts' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```javascript Node.js theme={null}
var created = await stateset.cyclecounts.create({
id: ''
});
```
```json Response theme={null}
```
# Error Handling
Source: https://docs.stateset.com/api-reference/errors
Comprehensive guide to API error responses and handling strategies
StateSet API uses standard HTTP response codes and provides detailed error information to help you handle issues gracefully.
## Error Response Format
All errors follow a consistent JSON structure to make error handling predictable:
```json theme={null}
{
"error": {
"code": "ERROR_CODE",
"message": "Human-readable error message",
"type": "error_type",
"details": {
// Additional context-specific information
},
"request_id": "req_1NXWPnCo6bFb1KQto6C8OWvE",
"timestamp": "2024-01-15T10:30:00Z",
"documentation_url": "https://docs.stateset.com/errors/ERROR_CODE"
}
}
```
## HTTP Status Codes
| Status Code | Meaning | Common Causes |
| ----------- | --------------------- | ---------------------------------------------- |
| **200** | OK | Request succeeded |
| **201** | Created | Resource successfully created |
| **202** | Accepted | Request accepted for async processing |
| **204** | No Content | Request succeeded with no response body |
| **400** | Bad Request | Invalid request parameters or malformed syntax |
| **401** | Unauthorized | Missing or invalid authentication |
| **403** | Forbidden | Valid auth but insufficient permissions |
| **404** | Not Found | Resource doesn't exist |
| **409** | Conflict | Resource conflict or duplicate |
| **422** | Unprocessable Entity | Valid syntax but semantic errors |
| **429** | Too Many Requests | Rate limit exceeded |
| **500** | Internal Server Error | Server error - retry with backoff |
| **502** | Bad Gateway | Upstream service error |
| **503** | Service Unavailable | Temporary service outage |
## Error Types and Codes
### Authentication Errors (401)
| Error Code | Description | Resolution |
| ---------------------- | -------------------------------- | -------------------------- |
| `INVALID_API_KEY` | API key is invalid or revoked | Check key in dashboard |
| `EXPIRED_API_KEY` | API key has expired | Generate new API key |
| `MISSING_AUTH_HEADER` | No Authorization header provided | Include Bearer token |
| `INVALID_TOKEN_FORMAT` | Token format is incorrect | Use `Bearer sk_...` format |
| `INACTIVE_ACCOUNT` | Account is suspended or inactive | Contact support |
### Authorization Errors (403)
| Error Code | Description | Resolution |
| -------------------------- | ------------------------------------- | -------------------------- |
| `INSUFFICIENT_PERMISSIONS` | API key lacks required permissions | Use key with proper scopes |
| `RESOURCE_ACCESS_DENIED` | Cannot access this specific resource | Check resource ownership |
| `PLAN_LIMIT_EXCEEDED` | Feature not available on current plan | Upgrade plan |
| `IP_NOT_ALLOWED` | Request from unauthorized IP | Add IP to allowlist |
### Validation Errors (400/422)
| Error Code | Description | Resolution |
| ------------------------ | ------------------------------------- | --------------------------- |
| `VALIDATION_ERROR` | Request validation failed | Check field requirements |
| `MISSING_REQUIRED_FIELD` | Required field not provided | Include all required fields |
| `INVALID_FIELD_VALUE` | Field value doesn't meet requirements | Validate field format |
| `INVALID_ENUM_VALUE` | Value not in allowed enum list | Use accepted values |
| `FIELD_TOO_LONG` | Field exceeds maximum length | Truncate field value |
| `INVALID_DATE_FORMAT` | Date format incorrect | Use ISO 8601 format |
### Resource Errors (404/409)
| Error Code | Description | Resolution |
| ------------------------- | ----------------------------------- | ----------------------------------- |
| `RESOURCE_NOT_FOUND` | Requested resource doesn't exist | Verify resource ID |
| `RESOURCE_ALREADY_EXISTS` | Duplicate resource creation attempt | Use existing resource |
| `RESOURCE_LOCKED` | Resource is locked for editing | Wait and retry |
| `RESOURCE_ARCHIVED` | Resource has been archived | Unarchive or use different resource |
| `PARENT_NOT_FOUND` | Parent resource doesn't exist | Create parent first |
### Business Logic Errors (422)
| Error Code | Description | Resolution |
| -------------------------- | ------------------------------ | ------------------------------ |
| `INSUFFICIENT_INVENTORY` | Not enough inventory available | Reduce quantity or check stock |
| `PAYMENT_FAILED` | Payment processing failed | Verify payment details |
| `INVALID_STATE_TRANSITION` | Invalid status change | Check allowed transitions |
| `OUTSIDE_RETURN_WINDOW` | Return period expired | Check return policy |
| `DUPLICATE_REQUEST` | Duplicate request detected | Use idempotency key |
### Rate Limiting Errors (429)
```json theme={null}
{
"error": {
"code": "RATE_LIMITED",
"message": "Rate limit exceeded",
"type": "rate_limit_error",
"details": {
"limit": 100,
"remaining": 0,
"reset_at": "2024-01-15T10:35:00Z",
"retry_after": 300
}
}
}
```
## Error Handling Best Practices
### 1. Implement Exponential Backoff
```javascript Node.js theme={null}
class APIClient {
async requestWithRetry(url, options, maxRetries = 3) {
let lastError;
for (let attempt = 0; attempt <= maxRetries; attempt++) {
try {
const response = await fetch(url, options);
if (response.status === 429) {
const retryAfter = response.headers.get('X-RateLimit-Retry-After');
const delay = retryAfter
? parseInt(retryAfter) * 1000
: Math.min(1000 * Math.pow(2, attempt), 32000);
if (attempt < maxRetries) {
await new Promise(resolve => setTimeout(resolve, delay));
continue;
}
}
if (!response.ok) {
const error = await response.json();
throw new APIError(error);
}
return response.json();
} catch (error) {
lastError = error;
if (attempt < maxRetries && this.isRetryable(error)) {
const delay = Math.min(1000 * Math.pow(2, attempt), 32000);
await new Promise(resolve => setTimeout(resolve, delay));
continue;
}
throw error;
}
}
throw lastError;
}
isRetryable(error) {
const retryableCodes = [429, 500, 502, 503, 504];
return error.status && retryableCodes.includes(error.status);
}
}
```
```python Python theme={null}
import time
import requests
from typing import Optional, Dict, Any
class APIClient:
def __init__(self, api_key: str):
self.api_key = api_key
self.base_url = "https://api.stateset.com/v1"
def request_with_retry(
self,
method: str,
endpoint: str,
data: Optional[Dict] = None,
max_retries: int = 3
) -> Dict[str, Any]:
url = f"{self.base_url}{endpoint}"
headers = {
"Authorization": f"Bearer {self.api_key}",
"Content-Type": "application/json"
}
last_exception = None
for attempt in range(max_retries + 1):
try:
response = requests.request(
method,
url,
json=data,
headers=headers
)
if response.status_code == 429:
retry_after = response.headers.get('X-RateLimit-Retry-After', 1)
delay = min(
int(retry_after),
2 ** attempt
)
if attempt < max_retries:
time.sleep(delay)
continue
response.raise_for_status()
return response.json()
except requests.exceptions.RequestException as e:
last_exception = e
if attempt < max_retries and self._is_retryable(e):
delay = min(2 ** attempt, 32)
time.sleep(delay)
continue
raise
raise last_exception
def _is_retryable(self, error: Exception) -> bool:
if hasattr(error, 'response'):
retryable_codes = {429, 500, 502, 503, 504}
return error.response.status_code in retryable_codes
return False
```
### 2. Handle Specific Error Types
```javascript theme={null}
class ErrorHandler {
handle(error) {
switch (error.code) {
case 'INVALID_API_KEY':
// Refresh API key or prompt for new one
return this.refreshApiKey();
case 'INSUFFICIENT_PERMISSIONS':
// Inform user about permission requirements
return this.showPermissionError(error.details);
case 'VALIDATION_ERROR':
// Show field-specific errors
return this.showValidationErrors(error.details);
case 'RATE_LIMITED':
// Implement backoff and queue
return this.queueRequest(error.details.retry_after);
case 'INSUFFICIENT_INVENTORY':
// Update UI with available quantity
return this.updateInventory(error.details);
default:
// Generic error handling
return this.showGenericError(error.message);
}
}
}
```
### 3. Implement Circuit Breaker Pattern
```javascript theme={null}
class CircuitBreaker {
constructor(threshold = 5, timeout = 60000) {
this.failureCount = 0;
this.failureThreshold = threshold;
this.timeout = timeout;
this.state = 'CLOSED';
this.nextAttempt = Date.now();
}
async call(fn) {
if (this.state === 'OPEN') {
if (Date.now() < this.nextAttempt) {
throw new Error('Circuit breaker is OPEN');
}
this.state = 'HALF_OPEN';
}
try {
const result = await fn();
this.onSuccess();
return result;
} catch (error) {
this.onFailure();
throw error;
}
}
onSuccess() {
this.failureCount = 0;
this.state = 'CLOSED';
}
onFailure() {
this.failureCount++;
if (this.failureCount >= this.failureThreshold) {
this.state = 'OPEN';
this.nextAttempt = Date.now() + this.timeout;
}
}
}
```
### 4. Log and Monitor Errors
```javascript theme={null}
class ErrorLogger {
log(error, context) {
const errorData = {
timestamp: new Date().toISOString(),
request_id: error.request_id,
error_code: error.code,
message: error.message,
context: {
user_id: context.userId,
endpoint: context.endpoint,
method: context.method,
...context
},
stack_trace: error.stack
};
// Send to logging service
logger.error(errorData);
// Track in analytics
analytics.track('API_ERROR', errorData);
// Alert on critical errors
if (this.isCritical(error)) {
alerting.notify(errorData);
}
}
isCritical(error) {
const criticalCodes = [
'PAYMENT_FAILED',
'SERVICE_UNAVAILABLE',
'DATABASE_ERROR'
];
return criticalCodes.includes(error.code);
}
}
```
## Error Recovery Strategies
### Idempotency for Safe Retries
```javascript theme={null}
// Use idempotency keys to safely retry requests
const createOrder = async (orderData) => {
const idempotencyKey = `order-${uuidv4()}`;
try {
return await api.post('/orders', orderData, {
headers: {
'Idempotency-Key': idempotencyKey
}
});
} catch (error) {
if (error.code === 'DUPLICATE_REQUEST') {
// Return existing order from previous request
return error.details.existing_resource;
}
throw error;
}
};
```
### Graceful Degradation
```javascript theme={null}
class ResilientClient {
async getProductWithFallback(productId) {
try {
// Try primary API
return await this.api.get(`/products/${productId}`);
} catch (error) {
if (error.code === 'SERVICE_UNAVAILABLE') {
// Fall back to cache
const cached = await this.cache.get(`product:${productId}`);
if (cached) {
return { ...cached, from_cache: true };
}
// Fall back to secondary service
return await this.secondaryApi.get(`/products/${productId}`);
}
throw error;
}
}
}
```
## Common Error Scenarios
### Handling Validation Errors
```json theme={null}
// Request
POST /v1/orders
{
"customer_email": "invalid-email",
"items": []
}
// Response (422)
{
"error": {
"code": "VALIDATION_ERROR",
"message": "Request validation failed",
"type": "validation_error",
"details": {
"errors": [
{
"field": "customer_email",
"message": "Invalid email format",
"expected": "valid email address"
},
{
"field": "items",
"message": "At least one item is required",
"expected": "non-empty array"
}
]
},
"request_id": "req_abc123"
}
}
```
### Handling Resource Conflicts
```json theme={null}
// Request
POST /v1/customers
{
"email": "existing@example.com"
}
// Response (409)
{
"error": {
"code": "RESOURCE_ALREADY_EXISTS",
"message": "Customer with this email already exists",
"type": "conflict_error",
"details": {
"existing_id": "cus_123abc",
"field": "email",
"value": "existing@example.com"
},
"request_id": "req_def456"
}
}
```
## Error Webhooks
Configure error webhooks to receive notifications for critical failures:
```json theme={null}
{
"event": "api.error",
"created": "2024-01-15T10:30:00Z",
"data": {
"error_code": "PAYMENT_FAILED",
"request_id": "req_xyz789",
"customer_id": "cus_123",
"order_id": "ord_456",
"amount": 9999,
"currency": "usd"
}
}
```
## SDK Error Handling
Our SDKs provide built-in error handling:
```javascript Node.js SDK theme={null}
try {
const order = await stateset.orders.create({
customer_email: 'customer@example.com',
items: [...]
});
} catch (error) {
if (error.code === 'INSUFFICIENT_INVENTORY') {
// Handle inventory shortage
const available = error.details.available_items;
console.log(`Only ${available} items available`);
} else if (error.code === 'VALIDATION_ERROR') {
// Handle validation errors
error.details.errors.forEach(err => {
console.log(`${err.field}: ${err.message}`);
});
} else {
// Generic error handling
console.error('Unexpected error:', error.message);
}
}
```
```python Python SDK theme={null}
from stateset import StatesetError, ValidationError, RateLimitError
try:
order = stateset.orders.create(
customer_email='customer@example.com',
items=[...]
)
except ValidationError as e:
# Handle validation errors
for error in e.errors:
print(f"{error['field']}: {error['message']}")
except RateLimitError as e:
# Handle rate limiting
print(f"Rate limited. Retry after {e.retry_after} seconds")
except StatesetError as e:
# Handle other API errors
print(f"API error: {e.code} - {e.message}")
```
## Testing Error Scenarios
Use test mode to simulate error conditions:
```bash theme={null}
# Trigger specific error in test mode
curl -X POST https://api.sandbox.stateset.com/v1/orders \
-H "Authorization: Bearer sk_test_..." \
-H "X-Test-Error-Code: INSUFFICIENT_INVENTORY" \
-d '{...}'
```
## Support
If you encounter persistent errors or need help with error handling:
* **API Status**: Check [status.stateset.com](https://status.stateset.com)
* **Support**: Contact [api-support@stateset.com](mailto:api-support@stateset.com)
* **Discord**: Join our [developer community](https://discord.gg/VfcaqgZywq)
***
**Related:** [Rate Limiting](/api-reference/rate-limiting) | [Authentication](/api-reference/authentication) | [Webhooks](/api-reference/webhooks)
# Event-Driven APIs with StateSet One
Source: https://docs.stateset.com/api-reference/events
Build autonomous commerce applications with StateSet's event-driven API.
# Event-Driven APIs with StateSet One
StateSet One provides a powerful event-driven API, designed to empower developers to build autonomous and responsive commerce applications. This approach allows systems to react in real-time to changes, creating more dynamic and efficient processes.
## Core Architecture Principles
StateSet's architecture follows a Three-Factor App model integrated with a Durable Execution OS. This design prioritizes scalability, reliability, and maintainability.
### Three-Factor App Architecture with Durable Execution OS
* **Single-Point GraphQL API:** A unified interface for data interactions, providing remote data joins.
* **Event Triggers and Webhooks:** Enable seamless integrations and automation through event-driven logic.
* **Realtime Search:** Provides customer service and warehouse operations with efficient data access.
* **Data Validation and Synchronization:** Maintains data integrity and consistency.
* **Workflow Orchestration:** Manages complex business processes using Temporal.
* **Automated Processes:** Automates routine tasks such as label printing and refund processing.
* **Comprehensive Testing:** Ensures quality through rigorous QA testing for all serverless functions.
### Three Factors of StateSet Architecture
#### Factor #1: Realtime GraphQL API
StateSet uses GraphQL as a flexible and efficient way for clients to interact with its data.
* **Low-Latency Responses:** GraphQL ensures that state changes provide immediate feedback to the user.
* **GraphQL Subscriptions:** Enables real-time data streaming, eliminating the need for polling and improving scalability.
```mermaid theme={null}
graph LR
A[Client App] <--> B(GraphQL API)
B --> C[Data Source]
```
> A client application sends a GraphQL query to the API which then fetches the data from its underlying data sources.
#### Factor #2: Reliable Eventing System
StateSet is built on an event-driven architecture where state changes trigger events.
* **Atomic Operations:** State changes and event generation are atomic, ensuring consistency.
* **At-Least-Once Delivery:** Guarantees that events are delivered to consumers, allowing a complete state history for observability.
```mermaid theme={null}
graph LR
A[State Change] --> B(Event Bus);
B --> C[Event Handlers];
```
> When a state change happens, it is sent to the event bus and then picked up by the configured event handlers.
#### Factor #3: Asynchronous Serverless Functions
StateSet uses serverless functions to handle events, providing scalability and cost-efficiency.
* **Idempotent Functions:** Functions can handle duplicate events without creating inconsistencies.
* **Out-of-Order Event Handling:** Functions handle events reliably, regardless of the order of arrival.
```mermaid theme={null}
graph LR
A[Event] --> B(Serverless Function);
B --> C[Action];
```
> An event is received by a serverless function which then executes an action.
### Detailed Architecture Components
Here's a deeper look at the core components:
#### Three-Factor App with Durable Execution OS
StateSet's architecture promotes:
* **Modular Design:** Business domains are separated into distinct services, allowing independent development and deployment.
* **Durable Execution OS:** Ensures workflows and state transitions are reliable, preventing data loss, and enabling recovery from failures.
#### Single-Point GraphQL API
The GraphQL API offers:
* **Remote Data Joins:** Combines data from multiple sources into a single API request, reducing network calls.
* **Flexible Queries:** Clients can request specific data, optimizing performance.
```mermaid theme={null}
graph LR
A[Client App] <--> B(GraphQL API)
B --> C[Data Source 1]
B --> D[Data Source 2]
```
> The GraphQL API combines data from multiple sources into a single response.
#### Event Triggers and Webhooks
StateSet leverages:
* **Seamless Integrations:** Connects with external systems and services.
* **Automated Workflows:** Enables event-driven automated processes.
#### Realtime Search Capabilities
StateSet provides powerful search functionalities for:
* **Customer Service:** Enables quick access to customer information for support teams.
* **Warehouse Operations:** Facilitates efficient inventory and order management.
#### Data Validation and Synchronization
StateSet maintains data integrity with:
* **Comprehensive Validation:** Validates incoming data to prevent errors.
* **Synchronization Mechanisms:** Keeps data consistent across all systems.
#### Workflow Orchestration with Temporal
StateSet uses Temporal for:
* **Complex Workflow Management:** Orchestrates intricate business processes with ease.
* **Automated Execution:** Ensures workflows are reliably executed and can recover from failures.
```mermaid theme={null}
graph LR
A[Event Trigger] --> B(Temporal Workflow);
B --> C[Activity 1];
B --> D[Activity 2];
```
> An event triggers a temporal workflow. The workflow then coordinates multiple activities
#### Automated Processes
StateSet automates critical operations:
* **Label Printing:** Automatically generates and prints shipping labels for various regions.
* **Refund Processing:** Streamlines refund handling for quick and accurate transactions.
#### Comprehensive Testing and QA
StateSet ensures reliability through:
* **Test QA Paths:** Rigorous testing for all serverless functions.
## Event Handling
Here's a simple example of how event handling might be implemented in a serverless function:
```javascript theme={null}
exports.handler = async (event) => {
console.log('Received event:', JSON.stringify(event, null, 2));
try {
// Extract event data
const { type, payload } = event;
if (type === 'order.created') {
// Process Order Created Event
console.log('Processing order creation:', payload);
// Add business logic to perform when order is created
// ...
}
else if (type === 'return.created') {
// Process Return Created Event
console.log('Processing return creation:', payload);
// Add business logic to perform when return is created
// ...
}
else if (type === 'inventory.updated') {
// Process Inventory Updated Event
console.log('Processing inventory update:', payload);
// Add business logic to perform when inventory is updated
// ...
}
else {
console.log('Unknown Event Type')
}
return {
statusCode: 200,
body: JSON.stringify({ message: 'Event processed successfully' }),
};
} catch (error) {
console.error('Error processing event:', error);
return {
statusCode: 500,
body: JSON.stringify({ message: 'Error processing event' }),
};
}
};
```
> This is an example of a serverless function that can handle multiple different events. The function will check for the event type, extract the payload, perform the business logic, and then return a response.
```mermaid theme={null}
graph TD
A[StateSet One Web App] <--> B[Realtime GraphQL API]
B --> C[(State)]
C --> D[Event system]
D --> B
D --> T[StateSet Cloud Platform]
subgraph StateSet_Cloud_Platform[StateSet Cloud Platform]
T --> H[Workflows]
H --> I[Generate Label]
H --> J[Create Order]
H --> K[Process Refund]
end
```
> The diagram shows the high level interactions between the different parts of the system.
## Conclusion
StateSet's event-driven API provides a powerful foundation for building modern commerce applications that are responsive, scalable, and reliable. This framework enables developers to build autonomous systems that react in real-time to changes in their environment.
# Features
Source: https://docs.stateset.com/api-reference/features
Explore the powerful features of the StateSet Platform for agentic commerce operations.
# StateSet: Features for Agentic Commerce
StateSet is an AI-powered platform designed for direct-to-consumer businesses, warehouses, suppliers, and their developer partners. It's built to automate your commerce operations, providing the scalability and efficiency of major brands.
## Core Benefits
StateSet empowers you to:
* **Revolutionize Business Operations:** Move beyond manual tasks and embrace automated processes.
* **Scale Operations Seamlessly:** Handle increased demand without sacrificing efficiency.
* **Improve Efficiency and Productivity:** Streamline workflows to achieve more with less.
* **Access Cutting-Edge Technology:** Leverage the latest advancements in web development, AI, and workflow automation.
* **Enhance Customer Experience:** Provide superior service and build stronger relationships.
## Key Features
### 1. Streamlined Operations for Enhanced Efficiency
StateSet is a comprehensive platform that streamlines your entire operation, from order fulfillment to reverse logistics.
* **Simplified Workflows:** Automate routine tasks, allowing your team to focus on strategic initiatives.
* **Reverse Logistics:** Efficiently manage returns, exchanges, and warranty processes.
* **Automated Label Printing:** Generate shipping labels for regions such as US and Canada with ease.
> Spend less time on manual operations and more time on growing your business.
### 2. Enhanced Customer Experience with Intelligent Notifications
Keep your customers informed with real-time notifications.
* **Real-Time Updates:** Automated event-driven system ensures customers receive updates at every step of their order journey.
* **Personalized Notifications:** Tailor notifications to individual customer preferences and needs.
* **Reduced Support Overhead:** Proactive communication reduces customer inquiries and support tickets.
```mermaid theme={null}
graph LR
A[Order Event] --> B(Notification Service);
B --> C[Customer];
```
> The customer gets notified whenever there is an event on their order.
> Build trust and loyalty through seamless and transparent communication.
### 3. AI-Powered Customer Support
Stateset's AI-powered chat utilizes GPT-5.2 to deliver exceptional support:
* **Instant Responses:** Provide immediate answers to customer inquiries, significantly improving response times.
* **Automated Support:** Handle FAQs and common issues, freeing up your support team.
* **Leverage Existing Data:** Use your FAQ and customer data to personalize responses.
> Provide fast, reliable, and intelligent support to boost customer satisfaction.
### 4. Automated Refunds
Automate your refund process to provide a frictionless experience.
* **Automated Calculations:** Calculate refunds based on order history and return policies without manual intervention.
* **Faster Refund Processing:** Process refunds quickly, enhancing customer satisfaction and loyalty.
> Process refunds quickly and accurately every time.
### 5. Event-Driven Workflows
Orchestrate workflows using Stateset's integrated platform.
* **Seamless Workflows:** Build and execute custom workflows tailored to your specific needs.
* **Autonomous Operations:** Automate complex business processes from order processing to fulfillment.
* **Unified Platform:** Bring together your e-commerce, warehouse, and development teams.
```mermaid theme={null}
graph LR
A[Event] --> B(Stateset Workflows);
B --> C[Action 1]
B --> D[Action 2]
```
> StateSet Workflows make it easy to build and orchestrate business operations.
> Streamline your operations with a platform that brings together your teams and processes.
### 6. Modern and Agile Technology
Stateset uses cutting-edge technologies for a modern platform:
* **Web Development Frameworks:** Leverages modern web development frameworks for high performance.
* **Distributed Consensus Protocols:** Ensures reliability and consistency in the platform.
* **Eliminate Legacy Systems:** Say goodbye to legacy ERP and CRM systems, reducing technical debt.
> Harness modern technology to propel your business forward.
### 7. Seamless Developer Collaboration
Our platform facilitates seamless integration:
* **Interconnected Systems:** Promote collaboration and data flow between different systems and teams.
* **Custom Integrations:** Integrate and customize the platform to fit your unique needs.
* **Developer-Friendly Environment:** Empower your developer teams to deliver exceptional results.
> Collaborate with your developer partners easily with our intuitive platform.
### 8. Robust API
Build custom integrations and extend functionality:
* **Custom Integrations:** Build custom integrations using our powerful API.
* **Streamlined Processes:** Automate your business processes, increasing efficiency.
* **Unlock Limitless Possibilities:** Extend the platform to meet your specific requirements.
> Unlock the full potential of your data and streamline your operations.
### 9. Reliable Infrastructure
Built on proven technology for reliable performance:
* **Cloud Services:** Built on proven cloud technologies ensuring high availability and performance.
* **Secure Platform:** Prioritizes security and data protection for all users.
* **Flexible Solution:** Designed to scale and adapt to your changing business needs.
> You can focus on your business and leave the technical details to us.
### 10. Composable Commerce in Minutes
Grow faster and scale easier:
* **Fast Implementation:** Get started in minutes with easy to use setup tools.
* **Scalable Platform:** Grow your business without worrying about infrastructure limitations.
* **Collaboration:** Connect with developers through the powerful API and developer friendly documentation.
> Embrace the future of commerce automation with StateSet.
## Conclusion
StateSet offers a powerful set of features designed to help your business thrive in today's fast-paced market. Our platform enables you to automate, scale, and enhance your operations, leading to increased efficiency, improved customer experience, and business growth.
# Web Framework
Source: https://docs.stateset.com/api-reference/framework
Building modern web applications with React Server Components (RSC)
# Framework
## Introduction
React Server Components (RSC) is an experimental approach to building server-rendered React applications. By running components directly on the server, developers can simplify data fetching, reduce client-side JavaScript, and maintain a more seamless, modular architecture. This guide explores how RSC can integrate with GraphQL queries and mutations to create modern, scalable web apps—without the complexity of legacy approaches like wrapping entire layouts in providers or managing extensive client-side state.
## Getting Started
With React Server Components, you can call server actions directly from the UI while leveraging your existing GraphQL operations. This approach sidesteps the need for client-side wrappers like Apollo providers or libraries such as Axios within React components. Instead, RSC enables a more intuitive pattern: server components make direct GraphQL calls, and server actions expose these calls to the client for efficient data fetching and updates.
Consider the following example, where server actions trigger GraphQL mutations without requiring additional layers or complex setups:
```typescript theme={null}
export const closeReturnAction = async (returnId: string): Promise => {
try {
await closeReturn(returnId);
} catch (e) {
return 'Error closing return';
}
};
export const reopenReturnAction = async (returnId: string): Promise => {
try {
await reopenReturn(returnId);
} catch (e) {
return 'Error reopening return';
}
};
export const cancelReturnAction = async (returnId: string): Promise => {
try {
await cancelReturn(returnId);
} catch (e) {
return 'Error closing return';
}
};
```
By integrating these actions directly, we retain a clean, modular, and type-safe architecture. The result is a more maintainable codebase that can easily evolve as the application grows.
## Data Fetching with `statesetFetch`
RSC excels at server-side data fetching. Below is an example of fetching a return object directly from the server, allowing your page component to receive fully-hydrated data without additional round trips:
```typescript theme={null}
export async function getReturn(returnId: string): Promise {
const res = await statesetFetch({
cache: 'no-store',
query: getReturnQuery,
variables: { returnId },
});
return res.body.data.returns_by_pk;
}
```
In this example, we use a typed operation (`StatesetReturnOperation`) to ensure end-to-end type safety. The server component (e.g. `page.tsx`) can directly call `getReturn`, removing the complexity of managing GraphQL queries in individual React components.
## GraphQL Operations and Fragments
Keep your codebase organized and consistent by centralizing GraphQL queries, mutations, and fragments. This approach ensures you can quickly adapt your data schema without hunting through multiple files.
**Query Example:**
```graphql theme={null}
export const getReturnQuery = /* GraphQL */ `
query getReturn($returnId: String!) {
returns_by_pk(id: $returnId) {
...returnFields
}
}
${returnFragment}
`;
```
**Fragment Example:**
```graphql theme={null}
export const returnFragment = /* GraphQL */ `
fragment returnFields on returns {
id
created_date
amount
action_needed
condition
customerEmail
customer_id
description
enteredBy
flat_rate_shipping
order_date
order_id
reason_category
reported_condition
requested_date
rma
serial_number
scanned_serial_number
shipped_date
status
tax_refunded
total_refunded
tracking_number
warehouse_received_date
warehouse_condition_date
refunded_date
}
`;
```
Because all operations and fragments are stored in a centralized `lib/stateset` directory, you maintain a single source of truth, minimizing duplication and improving consistency.
## Integrating Server Actions
Server actions call these GraphQL operations and return typed data. This approach provides a clearly defined interface for the UI to request data, enabling a smooth integration with server components and client-side interactivity:
```typescript theme={null}
export async function getReturns({
limit,
offset,
order_direction
}: {
limit?: number;
offset?: number;
order_direction?: string;
}): Promise {
const res = await statesetFetch({
query: getReturnsQuery,
variables: { limit, offset, order_direction },
cache: 'no-store'
});
return res.body.data.returns;
}
```
## From Server Component to Client
In your server-rendered pages, you can now retrieve data before sending it to the client. The component below demonstrates how data can be fetched with RSC and then hydrated in the browser for client-side interaction where necessary:
```typescript theme={null}
export default function ReturnPage({ returnId }: { returnId: string }) {
const [returnData, setReturnData] = useState(undefined);
useEffect(() => {
const fetchData = async () => {
const res = await getReturnAction(returnId);
setReturnData(res);
};
fetchData();
}, [returnId]);
return (
<>
>
);
}
```
By combining server components with server actions and a well-structured GraphQL strategy, you gain the best of both worlds—server-rendered efficiency and client-side responsiveness—without overly complicated data management layers.
For a deeper understanding of React Server Components, explore [this article](https://vercel.com/blog/understanding-react-server-components).
# Getting Started
Source: https://docs.stateset.com/api-reference/getting-started
Building intelligent commerce operations with the StateSet API
# Getting Started with StateSet API
Welcome to StateSet API! This guide will help you get up and running with our comprehensive backend system for order management, inventory control, returns processing, and more.
## Table of Contents
* [Prerequisites](#prerequisites)
* [Installation](#installation)
* [Configuration](#configuration)
* [Database Setup](#database-setup)
* [Building the Project](#building-the-project)
* [Running the API](#running-the-api)
* [Development Workflow](#development-workflow)
* [Testing](#testing)
* [API Documentation](#api-documentation)
* [Troubleshooting](#troubleshooting)
## Prerequisites
Before you begin, ensure you have the following installed on your development machine:
### Required Software
* **Rust** (latest stable version)
```bash theme={null}
# Install Rust via rustup
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh
# Verify installation
rustc --version
cargo --version
```
* **Database** (Choose one):
* **SQLite** (default for development)
* Automatically created when running the API
* **PostgreSQL 14+** (recommended for production)
```bash theme={null}
# macOS
brew install postgresql@14
# Ubuntu/Debian
sudo apt-get install postgresql-14
# Verify installation
psql --version
```
### Optional Tools
* **Redis** (for caching, optional)
```bash theme={null}
# macOS
brew install redis
# Ubuntu/Debian
sudo apt-get install redis-server
```
* **Protocol Buffer Compiler** (for gRPC development)
```bash theme={null}
# macOS
brew install protobuf
# Ubuntu/Debian
sudo apt-get install protobuf-compiler
```
## Installation
1. **Clone the Repository**
```bash theme={null}
git clone https://github.com/stateset/stateset-api.git
cd stateset-api
```
2. **Install Rust Dependencies**
```bash theme={null}
# This will download and compile all dependencies
cargo fetch
```
## Configuration
StateSet API uses environment variables and configuration files for setup.
### 1. Environment Variables (.env)
Create a `.env` file in the project root:
```bash theme={null}
cp .env.example .env
```
Edit `.env` with your configuration:
```env theme={null}
# Database Configuration
DATABASE_URL=sqlite:stateset.db?mode=rwc # For SQLite (development)
# DATABASE_URL=postgres://username:password@localhost/stateset_db # For PostgreSQL
# JWT Configuration
JWT_SECRET=your_secure_jwt_secret_key_change_in_production
JWT_EXPIRATION=3600 # 1 hour in seconds
JWT_REFRESH_EXPIRATION=604800 # 7 days in seconds
# Server Configuration
PORT=8080
HOST=0.0.0.0
APP_ENV=development
# Logging
RUST_LOG=stateset_api=debug,tower_http=debug,sea_orm=debug,info
# Optional: Redis (if using caching)
# REDIS_URL=redis://localhost:6379
```
### 2. Configuration File (config/default.toml)
The TOML configuration file provides additional settings:
```toml theme={null}
# Database
database_url = "sqlite:stateset.db?mode=rwc"
auto_migrate = true # Automatically run migrations on startup
# Server
host = "0.0.0.0"
port = 8080
# Cache (optional)
[cache]
cache_type = "memory" # or "redis" if Redis is configured
capacity = 1000
default_ttl_secs = 300
```
## Database Setup
### SQLite (Default for Development)
SQLite requires no additional setup. The database file will be created automatically when you first run the application.
### PostgreSQL (Production)
1. **Create Database**
```bash theme={null}
# Connect to PostgreSQL
psql -U postgres
# Create database and user
CREATE DATABASE stateset_db;
CREATE USER stateset_user WITH ENCRYPTED PASSWORD 'your_password';
GRANT ALL PRIVILEGES ON DATABASE stateset_db TO stateset_user;
\q
```
2. **Update DATABASE\_URL in .env**
```env theme={null}
DATABASE_URL=postgres://stateset_user:your_password@localhost/stateset_db
```
### Running Migrations
Migrations are handled automatically on startup if `auto_migrate = true` in your config. To run them manually:
```bash theme={null}
# Using the migration binary
cargo run --bin migration
# Or using SQLx CLI (if installed)
sqlx migrate run
```
## Building the Project
StateSet API provides several build options:
### Development Build
```bash theme={null}
# Quick build for development
cargo build
# Or using the Makefile
make build
```
### Release Build (Optimized)
```bash theme={null}
# Optimized build for production
cargo build --release
# Or using the Makefile
make build-release
```
### Build Specific Components
```bash theme={null}
# Build only the main API server
cargo build --bin stateset-api
# Build the minimal server (lightweight version)
cargo build --bin minimal-server
# Build the gRPC server
cargo build --bin grpc-server
# Build performance testing tools
cargo build --bin orders-bench
cargo build --bin orders-mock-server
```
## Running the API
### Main API Server
```bash theme={null}
# Run in development mode
cargo run
# Or using the Makefile
make run
# Run with specific binary
cargo run --bin stateset-api
# Run release build
./target/release/stateset-api
```
### Alternative Servers
```bash theme={null}
# Run minimal server (lightweight, fewer features)
cargo run --bin minimal-server
# Run gRPC server
cargo run --bin grpc-server
# Run mock server for testing
cargo run --bin orders-mock-server
```
### Verify the Server is Running
```bash theme={null}
# Health check
curl http://localhost:8080/health
# Should return:
# {"status":"healthy"}
```
## Development Workflow
### 1. Code Organization
```
src/
├── commands/ # Write operations (Command pattern)
├── queries/ # Read operations (Query pattern)
├── handlers/ # HTTP request handlers
├── services/ # Business logic
├── entities/ # Database entities (SeaORM)
├── models/ # Domain models
├── repositories/ # Data access layer
└── main.rs # Application entry point
```
### 2. Adding New Features
1. **Create Command/Query**
```rust theme={null}
// src/commands/orders/create_order_command.rs
pub struct CreateOrderCommand {
pub customer_id: Uuid,
pub items: Vec,
}
```
2. **Implement Service**
```rust theme={null}
// src/services/orders.rs
impl OrderService {
pub async fn create_order(&self, cmd: CreateOrderCommand) -> Result {
// Business logic here
}
}
```
3. **Add Handler**
```rust theme={null}
// src/handlers/orders.rs
pub async fn create_order(
State(state): State,
Json(payload): Json,
) -> Result> {
// Handle HTTP request
}
```
### 3. Hot Reloading (Development)
Use `cargo-watch` for automatic recompilation:
```bash theme={null}
# Install cargo-watch
cargo install cargo-watch
# Run with auto-reload
cargo watch -x run
```
### 4. Code Quality Tools
```bash theme={null}
# Format code
cargo fmt
# Run linter
cargo clippy
# Check for security issues
cargo audit
# Generate documentation
cargo doc --open
```
## Testing
### Running Tests
```bash theme={null}
# Run all tests
cargo test
# Run specific test
cargo test test_create_order
# Run tests with output
cargo test -- --nocapture
# Run tests with backtrace
RUST_BACKTRACE=1 cargo test
# Run integration tests only
cargo test --test '*'
# Using Makefile
make test
```
### Writing Tests
```rust theme={null}
#[cfg(test)]
mod tests {
use super::*;
#[tokio::test]
async fn test_create_order() {
// Test implementation
let service = OrderService::new(db_pool);
let order = service.create_order(cmd).await.unwrap();
assert_eq!(order.status, "pending");
}
}
```
### Performance Testing
```bash theme={null}
# Run order throughput benchmark
cargo run --bin orders-bench
# Start mock server for load testing
cargo run --bin orders-mock-server
# In another terminal, run benchmarks
ab -n 1000 -c 10 http://localhost:8080/orders
```
## API Documentation
### REST API Endpoints
The API provides comprehensive endpoints for all operations:
#### Authentication
* `POST /auth/register` - Register new user
* `POST /auth/login` - Login and receive JWT token
* `POST /auth/refresh` - Refresh JWT token
#### Orders
* `GET /orders` - List all orders
* `GET /orders/:id` - Get order by ID
* `POST /orders` - Create new order
* `PUT /orders/:id` - Update order
* `DELETE /orders/:id` - Delete order
* `POST /orders/:id/cancel` - Cancel order
* `POST /orders/:id/hold` - Put order on hold
#### Inventory
* `GET /inventory` - Get inventory levels
* `POST /inventory/adjust` - Adjust inventory
* `POST /inventory/allocate` - Allocate inventory
* `POST /inventory/reserve` - Reserve inventory
#### Returns
* `POST /returns` - Create return
* `GET /returns/:id` - Get return details
* `POST /returns/:id/approve` - Approve return
* `POST /returns/:id/reject` - Reject return
### OpenAPI/Swagger Documentation
When running in development mode, interactive API documentation is available at:
```
http://localhost:8080/swagger-ui
```
### gRPC API
For gRPC clients, proto files are located in `proto/` directory. Generate client code:
```bash theme={null}
# Generate Rust code from proto files
cargo build # Automatically generates during build
# For other languages, use protoc directly
protoc --go_out=. --go-grpc_out=. proto/*.proto
```
## Troubleshooting
### Common Issues and Solutions
#### 1. Build Errors
```bash theme={null}
# Clear build cache
cargo clean
# Update dependencies
cargo update
# Check for specific errors
cargo build 2>&1 | tee build_errors.log
```
#### 2. Database Connection Issues
```bash theme={null}
# Test database connection
psql $DATABASE_URL -c "SELECT 1"
# For SQLite, check file permissions
ls -la stateset.db
# Reset database
rm stateset.db # For SQLite
# OR
DROP DATABASE stateset_db; CREATE DATABASE stateset_db; # For PostgreSQL
```
#### 3. Port Already in Use
```bash theme={null}
# Find process using port 8080
lsof -i :8080
# Kill the process
kill -9
# Or use a different port
PORT=3000 cargo run
```
#### 4. Migration Failures
```bash theme={null}
# Reset migrations
cargo run --bin migration -- reset
# Run migrations step by step
cargo run --bin migration -- up
```
### Debugging
```bash theme={null}
# Enable debug logging
RUST_LOG=debug cargo run
# Enable backtrace for errors
RUST_BACKTRACE=1 cargo run
# Use debugger (VS Code or IntelliJ Rust)
# Add breakpoints and run in debug mode
```
### Performance Issues
```bash theme={null}
# Profile the application
cargo build --release
valgrind --tool=callgrind ./target/release/stateset-api
# Check database queries
RUST_LOG=sea_orm=debug cargo run
# Monitor resource usage
htop # While application is running
```
## Next Steps
1. **Explore the Codebase**
* Review `src/handlers/` for API endpoints
* Check `src/services/` for business logic
* Look at `tests/` for usage examples
2. **Customize Configuration**
* Modify `config/default.toml` for your needs
* Set up proper JWT secrets for security
* Configure database connections
3. **Set Up Development Environment**
* Install VS Code with rust-analyzer extension
* Configure your IDE for Rust development
* Set up pre-commit hooks for code quality
4. **Learn the Architecture**
* Read about CQRS pattern used in commands/queries
* Understand the event-driven architecture
* Review the domain models and entities
5. **Contribute**
* Check out open issues on GitHub
* Read CONTRIBUTING.md for guidelines
* Join our community discussions
## Getting Help
* **Documentation**: Full docs at [docs.stateset.com](https://docs.stateset.com)
* **GitHub Issues**: [github.com/stateset/stateset-api/issues](https://github.com/stateset/stateset-api/issues)
* **Discord Community**: Join our Discord for real-time help
* **API Reference**: Check `/swagger-ui` when running locally
## License
StateSet API is licensed under the MIT License. See [LICENSE](LICENSE) for details.
***
Happy coding! Welcome to the StateSet community! 🚀
# Check Gift Card Balance
Source: https://docs.stateset.com/api-reference/gift-cards/check-balance
POST https://api.stateset.com/v1/gift-cards/balance
Check the balance and validity of a gift card
This endpoint checks the current balance and status of a gift card. It's commonly used at checkout or in customer portals.
## Authentication
This endpoint requires a valid API key with `gift_cards:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Gift card code to check
Gift card PIN (required for some gift cards)
### Response
Returns gift card balance and status information.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/gift-cards/balance' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"code": "GIFT-XMAS-A3B7C9D2"
}'
```
```javascript Node.js theme={null}
const balance = await stateset.giftCards.checkBalance({
code: "GIFT-XMAS-A3B7C9D2"
});
```
```python Python theme={null}
balance = stateset.gift_cards.check_balance(
code="GIFT-XMAS-A3B7C9D2"
)
```
```json Response theme={null}
{
"valid": true,
"gift_card": {
"id": "gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"code": "GIFT-XMAS-A3B7C9D2",
"status": "active",
"current_balance": 3750,
"initial_balance": 5000,
"currency": "USD",
"expires_at": "2025-02-14T23:59:59Z",
"is_expired": false,
"days_until_expiry": 390
},
"transactions": {
"total_redeemed": 1250,
"redemption_count": 2,
"last_redemption": {
"date": "2024-01-15T14:30:00Z",
"amount": 750,
"order_id": "order_456789"
}
},
"restrictions": {
"minimum_purchase": null,
"product_restrictions": false,
"category_restrictions": false
},
"can_be_used": true,
"messages": []
}
```
# Create Gift Card
Source: https://docs.stateset.com/api-reference/gift-cards/create
POST https://api.stateset.com/v1/gift-cards
Create a new gift card with a specified balance
This endpoint creates a new gift card that can be purchased or issued to customers. Gift cards support both physical and digital delivery, custom designs, and flexible redemption rules.
## Authentication
This endpoint requires a valid API key with `gift_cards:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Gift card type: "physical", "digital", "both"
Initial balance in cents (e.g., 5000 for \$50.00)
ISO 4217 currency code
Gift card recipient information
Recipient email for digital delivery
Recipient name
Personal message to recipient
Scheduled delivery date (ISO 8601)
Gift card purchaser information
Existing customer ID
Purchaser email
Purchaser name
Gift card design customization
Design template ID
Custom image URL
Theme: "birthday", "holiday", "thank\_you", "congratulations", "custom"
Gift card validity settings
Expiration date (ISO 8601)
Activation date for future use (ISO 8601)
Usage restrictions
Restricted to specific products
Restricted to specific categories
Cannot be used on sale items
Minimum purchase amount in cents
Custom gift card code (auto-generated if not provided)
Associated order ID if purchased
Additional custom fields
### Response
Returns the created gift card object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/gift-cards' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"type": "digital",
"initial_balance": 5000,
"currency": "USD",
"recipient": {
"email": "recipient@example.com",
"name": "Jane Smith",
"message": "Happy Birthday! Enjoy your shopping.",
"delivery_date": "2024-02-14T09:00:00Z"
},
"purchaser": {
"customer_id": "cust_abc123",
"email": "purchaser@example.com",
"name": "John Doe"
},
"design": {
"template_id": "tmpl_birthday_001",
"theme": "birthday"
},
"validity": {
"expires_at": "2025-02-14T23:59:59Z"
},
"order_id": "order_789012"
}'
```
```javascript Node.js theme={null}
const giftCard = await stateset.giftCards.create({
type: "digital",
initial_balance: 5000,
currency: "USD",
recipient: {
email: "recipient@example.com",
name: "Jane Smith",
message: "Happy Birthday! Enjoy your shopping.",
delivery_date: "2024-02-14T09:00:00Z"
},
purchaser: {
customer_id: "cust_abc123",
email: "purchaser@example.com",
name: "John Doe"
},
design: {
template_id: "tmpl_birthday_001",
theme: "birthday"
},
validity: {
expires_at: "2025-02-14T23:59:59Z"
},
order_id: "order_789012"
});
```
```python Python theme={null}
gift_card = stateset.gift_cards.create(
type="digital",
initial_balance=5000,
currency="USD",
recipient={
"email": "recipient@example.com",
"name": "Jane Smith",
"message": "Happy Birthday! Enjoy your shopping.",
"delivery_date": "2024-02-14T09:00:00Z"
},
purchaser={
"customer_id": "cust_abc123",
"email": "purchaser@example.com",
"name": "John Doe"
},
design={
"template_id": "tmpl_birthday_001",
"theme": "birthday"
},
validity={
"expires_at": "2025-02-14T23:59:59Z"
},
order_id="order_789012"
)
```
```json Response theme={null}
{
"id": "gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "gift_card",
"code": "GIFT-XMAS-A3B7C9D2",
"type": "digital",
"status": "active",
"initial_balance": 5000,
"current_balance": 5000,
"currency": "USD",
"recipient": {
"email": "recipient@example.com",
"name": "Jane Smith",
"message": "Happy Birthday! Enjoy your shopping.",
"delivery_date": "2024-02-14T09:00:00Z",
"delivery_status": "scheduled"
},
"purchaser": {
"customer_id": "cust_abc123",
"email": "purchaser@example.com",
"name": "John Doe"
},
"design": {
"template_id": "tmpl_birthday_001",
"theme": "birthday",
"preview_url": "https://gift-cards.stateset.com/preview/gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
},
"validity": {
"activated_at": "2024-01-20T12:00:00Z",
"expires_at": "2025-02-14T23:59:59Z",
"is_expired": false,
"days_until_expiry": 390
},
"restrictions": {
"product_ids": [],
"category_ids": [],
"exclude_sale_items": false,
"minimum_purchase": null
},
"redemption_url": "https://shop.example.com/gift-card/GIFT-XMAS-A3B7C9D2",
"order_id": "order_789012",
"created_at": "2024-01-20T12:00:00Z",
"updated_at": "2024-01-20T12:00:00Z",
"transactions": [],
"metadata": {
"campaign": "birthday_promo_2024"
}
}
```
# Get Gift Card
Source: https://docs.stateset.com/api-reference/gift-cards/get
GET https://api.stateset.com/v1/gift-cards/:id
Retrieve details of a specific gift card
This endpoint retrieves detailed information about a specific gift card, including balance, transaction history, and redemption details.
## Authentication
This endpoint requires a valid API key with `gift_cards:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the gift card
### Response
Returns the gift card object if found.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/gift-cards/gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const giftCard = await stateset.giftCards.retrieve(
'gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
gift_card = stateset.gift_cards.retrieve(
'gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "gift_card",
"code": "GIFT-XMAS-A3B7C9D2",
"type": "digital",
"status": "active",
"initial_balance": 5000,
"current_balance": 3750,
"currency": "USD",
"recipient": {
"email": "recipient@example.com",
"name": "Jane Smith",
"message": "Happy Birthday! Enjoy your shopping.",
"delivery_date": "2024-02-14T09:00:00Z",
"delivery_status": "delivered",
"delivered_at": "2024-02-14T09:00:05Z"
},
"purchaser": {
"customer_id": "cust_abc123",
"email": "purchaser@example.com",
"name": "John Doe"
},
"design": {
"template_id": "tmpl_birthday_001",
"theme": "birthday",
"preview_url": "https://gift-cards.stateset.com/preview/gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
},
"validity": {
"activated_at": "2024-02-14T09:00:05Z",
"expires_at": "2025-02-14T23:59:59Z",
"is_expired": false,
"days_until_expiry": 328
},
"restrictions": {
"product_ids": [],
"category_ids": [],
"exclude_sale_items": false,
"minimum_purchase": null
},
"redemption_url": "https://shop.example.com/gift-card/GIFT-XMAS-A3B7C9D2",
"order_id": "order_789012",
"created_at": "2024-01-20T12:00:00Z",
"updated_at": "2024-03-15T10:30:00Z",
"transactions": [
{
"id": "txn_123",
"type": "redemption",
"amount": 750,
"balance_after": 4250,
"order_id": "order_456789",
"created_at": "2024-03-01T14:20:00Z"
},
{
"id": "txn_124",
"type": "redemption",
"amount": 500,
"balance_after": 3750,
"order_id": "order_567890",
"created_at": "2024-03-15T10:30:00Z"
}
],
"metadata": {
"campaign": "birthday_promo_2024"
}
}
```
# Redeem Gift Card
Source: https://docs.stateset.com/api-reference/gift-cards/redeem
POST https://api.stateset.com/v1/gift-cards/redeem
Redeem a gift card for an order
This endpoint redeems a gift card, deducting the specified amount from the card's balance. It validates the card and checks all restrictions before processing.
## Authentication
This endpoint requires a valid API key with `gift_cards:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Gift card code to redeem
Gift card PIN (if required)
Amount to redeem in cents
Order ID to apply the gift card to
Customer ID making the redemption
### Response
Returns the redemption transaction details.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/gift-cards/redeem' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"code": "GIFT-XMAS-A3B7C9D2",
"amount": 2500,
"order_id": "order_987654",
"customer_id": "cust_def456"
}'
```
```javascript Node.js theme={null}
const redemption = await stateset.giftCards.redeem({
code: "GIFT-XMAS-A3B7C9D2",
amount: 2500,
order_id: "order_987654",
customer_id: "cust_def456"
});
```
```python Python theme={null}
redemption = stateset.gift_cards.redeem(
code="GIFT-XMAS-A3B7C9D2",
amount=2500,
order_id="order_987654",
customer_id="cust_def456"
)
```
```json Response theme={null}
{
"id": "txn_125",
"object": "gift_card_transaction",
"type": "redemption",
"gift_card_id": "gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"code": "GIFT-XMAS-A3B7C9D2",
"amount": 2500,
"currency": "USD",
"balance_before": 3750,
"balance_after": 1250,
"order_id": "order_987654",
"customer_id": "cust_def456",
"status": "completed",
"created_at": "2024-06-20T16:00:00Z",
"gift_card": {
"id": "gc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"current_balance": 1250,
"expires_at": "2025-02-14T23:59:59Z",
"is_expired": false,
"status": "active"
},
"metadata": {
"pos_terminal_id": null,
"cashier_id": null
}
}
```
# gRPC Framework
Source: https://docs.stateset.com/api-reference/grpc-framework
Building modern web apps with the gRPC framework
# Framework
## Introduction
gRPC is a high-performance, open-source universal RPC framework that puts data first. It provides a simple, efficient, and scalable way to build distributed systems.
## Getting Started
```protobuf theme={null}
syntax = "proto3";
package stateset.return_order;
import "google/protobuf/timestamp.proto";
import "common.proto";
message Return {
string id = 1;
string order_id = 2;
string customer_id = 3;
repeated ReturnItem items = 4;
string status = 5;
string reason = 6;
google.protobuf.Timestamp created_at = 7;
google.protobuf.Timestamp updated_at = 8;
}
message ReturnItem {
string product_id = 1;
int32 quantity = 2;
string reason = 3;
}
message CreateReturnRequest {
Return return = 1;
}
message CreateReturnResponse {
string return_id = 1;
string status = 2;
}
message GetReturnRequest {
string return_id = 1;
}
message GetReturnResponse {
Return return = 1;
}
message UpdateReturnStatusRequest {
string return_id = 1;
string new_status = 2;
}
message UpdateReturnStatusResponse {
string return_id = 1;
string status = 2;
}
message ListReturnsRequest {
string customer_id = 1;
string order_id = 2;
string status = 3;
google.protobuf.Timestamp start_date = 4;
google.protobuf.Timestamp end_date = 5;
common.PaginationRequest pagination = 6;
}
message ListReturnsResponse {
repeated Return returns = 1;
common.PaginationResponse pagination = 2;
}
service ReturnService {
rpc CreateReturn (CreateReturnRequest) returns (CreateReturnResponse);
rpc GetReturn (GetReturnRequest) returns (GetReturnResponse);
rpc UpdateReturnStatus (UpdateReturnStatusRequest) returns (UpdateReturnStatusResponse);
rpc ListReturns (ListReturnsRequest) returns (ListReturnsResponse);
}
```
We can now build our handlers and services to handle the requests and responses.
To learn more about Protocol Buffers, check out [this article](https://protobuf.dev/).
# Integrations
Source: https://docs.stateset.com/api-reference/integrations
Overview of the Stateset One Platform Integrations
# Integrations
## Overview
The StateSet One Platform integrates with a wide range of third-party services and systems to provide a comprehensive and seamless experience for users. These integrations enable users to leverage existing tools and services while extending the capabilities of the StateSet One Platform.
# API Reference
Source: https://docs.stateset.com/api-reference/introduction
Complete reference for the StateSet API - Build powerful autonomous business applications
# StateSet API Reference
Welcome to the StateSet API. Our comprehensive REST and GraphQL APIs enable you to build powerful autonomous business applications that scale with your needs.
**API Version:** v1 (Current)
**SDK Versions:** Node.js v3.2.0 | Python v2.1.0 | Go v1.4.0 | Ruby v2.0.0
**Last Updated:** January 2026
RESTful endpoints for all StateSet resources
Flexible queries with real-time subscriptions
Official SDKs for popular languages
Real-time event notifications
**Production Environment:**
* Base URL: `https://api.stateset.com/v1`
* GraphQL: `https://api.stateset.com/graphql`
* WebSocket: `wss://api.stateset.com/v1/ws`
**Sandbox Environment:**
* Base URL: `https://api.sandbox.stateset.com/v1`
* GraphQL: `https://api.sandbox.stateset.com/graphql`
* WebSocket: `wss://api.sandbox.stateset.com/v1/ws`
## Quick Start
1. Sign up at [stateset.com](https://stateset.com)
2. Navigate to **Settings** → **API Keys**
3. Generate a new API key with appropriate scopes
Store your API key securely and never expose it in client-side code.
Test the connection with a simple API call:
```bash theme={null}
curl https://api.stateset.com/v1/orders \
-H "Authorization: Bearer sk_live_..." \
-H "Content-Type: application/json"
```
Browse our comprehensive API reference to discover all available endpoints and capabilities.
## Authentication
StateSet API uses API key authentication with support for multiple authentication methods to suit different use cases.
### API Key Types
| Key Type | Prefix | Environment | Usage |
| ------------------- | ---------- | ----------- | -------------------------- |
| **Live Key** | `sk_live_` | Production | Real transactions and data |
| **Test Key** | `sk_test_` | Sandbox | Development and testing |
| **Restricted Key** | `rk_live_` | Production | Limited scope access |
| **Publishable Key** | `pk_live_` | Client-side | Public operations only |
### API Key Authentication
```bash cURL theme={null}
curl https://api.stateset.com/v1/orders \
-H "Authorization: Bearer ${STATESET_API_KEY}"
```
```javascript JavaScript/Node.js theme={null}
// Using fetch
const response = await fetch('https://api.stateset.com/v1/orders', {
headers: {
'Authorization': `Bearer ${process.env.STATESET_API_KEY}`,
'Content-Type': 'application/json'
}
});
// Using our SDK
import { StateSetClient } from 'stateset-node';
const client = new StateSetClient({
apiKey: process.env.STATESET_API_KEY
});
```
```python Python theme={null}
import requests
import os
# Using requests
response = requests.get(
'https://api.stateset.com/v1/orders',
headers={
'Authorization': f'Bearer {os.getenv("STATESET_API_KEY")}',
'Content-Type': 'application/json'
}
)
# Using our SDK
from stateset import StateSet
client = StateSet(api_key=os.getenv("STATESET_API_KEY"))
```
```go Go theme={null}
package main
import (
"net/http"
"os"
)
func main() {
client := &http.Client{}
req, _ := http.NewRequest("GET", "https://api.stateset.com/v1/orders", nil)
req.Header.Add("Authorization", "Bearer " + os.Getenv("STATESET_API_KEY"))
req.Header.Add("Content-Type", "application/json")
resp, _ := client.Do(req)
}
```
### Environment Variables
We recommend storing your API keys as environment variables:
```bash theme={null}
# .env.development
STATESET_API_KEY=sk_test_your_actual_key_here
STATESET_WEBHOOK_SECRET=whsec_test_...
STATESET_ENVIRONMENT=sandbox
# .env.production
STATESET_API_KEY=sk_live_your_actual_key_here
STATESET_WEBHOOK_SECRET=whsec_live_...
STATESET_ENVIRONMENT=production
```
Never commit API keys to version control. Use environment variables or secure key management services.
## Rate Limits
**Rate Limits by Plan:**
* **Starter:** 100 requests/minute, 10,000 requests/day
* **Growth:** 1,000 requests/minute, 100,000 requests/day
* **Scale:** 5,000 requests/minute, 500,000 requests/day
* **Enterprise:** Custom limits up to 10,000 requests/minute
**Rate limit headers included in responses:**
* `X-RateLimit-Limit`: Maximum requests allowed in current window
* `X-RateLimit-Remaining`: Requests remaining in current window
* `X-RateLimit-Reset`: Unix timestamp when limit resets
* `X-RateLimit-Retry-After`: Seconds to wait before retrying (when limited)
### Handling Rate Limits
When you exceed rate limits, you'll receive a `429 Too Many Requests` response:
```json theme={null}
{
"error": {
"code": "RATE_LIMITED",
"message": "Rate limit exceeded. Please retry after 60 seconds.",
"retry_after": 60,
"limit": 1000,
"remaining": 0,
"reset_at": "2024-01-15T12:00:00Z"
}
}
```
**Best practices for handling rate limits:**
```javascript Exponential Backoff theme={null}
async function apiRequestWithRetry(url, options, maxRetries = 3) {
for (let attempt = 0; attempt <= maxRetries; attempt++) {
try {
const response = await fetch(url, options);
if (response.status === 429) {
const retryAfter = response.headers.get('X-RateLimit-Retry-After');
const delay = retryAfter ? parseInt(retryAfter) * 1000 : Math.pow(2, attempt) * 1000;
if (attempt < maxRetries) {
await new Promise(resolve => setTimeout(resolve, delay));
continue;
}
}
return response;
} catch (error) {
if (attempt === maxRetries) throw error;
await new Promise(resolve => setTimeout(resolve, Math.pow(2, attempt) * 1000));
}
}
}
```
```python Python Retry Logic theme={null}
import time
import requests
from requests.adapters import HTTPAdapter
from urllib3.util.retry import Retry
def create_session_with_retries():
session = requests.Session()
retry_strategy = Retry(
total=3,
status_forcelist=[429, 500, 502, 503, 504],
backoff_factor=1,
respect_retry_after_header=True
)
adapter = HTTPAdapter(max_retries=retry_strategy)
session.mount("https://", adapter)
return session
# Usage
session = create_session_with_retries()
response = session.get('https://api.stateset.com/v1/orders',
headers={'Authorization': 'Bearer your_key'})
```
## Error Handling
StateSet API uses conventional HTTP response codes and returns detailed error information in JSON format with consistent error structures.
### HTTP Status Codes
| Code | Meaning |
| ----- | -------------------------------------------------------------- |
| `200` | **OK** - Request succeeded |
| `201` | **Created** - Resource created successfully |
| `400` | **Bad Request** - Invalid request parameters |
| `401` | **Unauthorized** - Invalid or missing API key |
| `403` | **Forbidden** - Insufficient permissions |
| `404` | **Not Found** - Resource doesn't exist |
| `409` | **Conflict** - Resource already exists or constraint violation |
| `422` | **Unprocessable Entity** - Validation errors |
| `429` | **Too Many Requests** - Rate limit exceeded |
| `500` | **Internal Server Error** - Something went wrong on our end |
### Error Response Format
```json theme={null}
{
"error": {
"code": "VALIDATION_ERROR",
"message": "Request validation failed",
"details": {
"field": "email",
"issue": "Invalid email format",
"expected": "valid email address",
"received": "invalid-email"
},
"request_id": "req_1NXWPnCo6bFb1KQto6C8OWvE",
"timestamp": "2024-01-15T10:30:00Z",
"documentation_url": "https://docs.stateset.com/errors/VALIDATION_ERROR"
}
}
```
### Common Error Codes
* `INVALID_API_KEY`: API key is invalid or expired
* `MISSING_API_KEY`: No API key provided
* `INSUFFICIENT_PERMISSIONS`: API key doesn't have required permissions
* `VALIDATION_ERROR`: Request data failed validation
* `MISSING_REQUIRED_FIELD`: Required field not provided
* `INVALID_FIELD_FORMAT`: Field format is incorrect
* `RESOURCE_NOT_FOUND`: Requested resource doesn't exist
* `RESOURCE_ALREADY_EXISTS`: Resource with same identifier exists
* `RESOURCE_CONFLICT`: Operation conflicts with current resource state
## Pagination
List endpoints support both offset-based and cursor-based pagination. We recommend cursor-based pagination for better performance and consistency.
### Pagination Parameters
| Parameter | Type | Default | Max | Description |
| --------- | ------- | ------- | ----- | ---------------------------------- |
| `limit` | integer | 10 | 100 | Number of items per page |
| `cursor` | string | null | - | Cursor for next page (recommended) |
| `offset` | integer | 0 | 10000 | Number of items to skip |
| `page` | integer | 1 | - | Page number (deprecated) |
### Offset-Based Pagination
```bash theme={null}
GET /v1/orders?limit=20&offset=40
```
### Cursor-Based Pagination (Recommended)
More efficient for large datasets and handles real-time data changes:
```bash theme={null}
GET /v1/orders?limit=20&cursor=eyJpZCI6Im9yZF8xMjM0NSJ9
```
**Response format:**
```json theme={null}
{
"data": [...],
"pagination": {
"has_more": true,
"next_cursor": "eyJpZCI6Im9yZF82Nzg5MCJ9",
"previous_cursor": "eyJpZCI6Im9yZF8wMTIzNCJ9",
"total_count": 1250,
"page_count": 63,
"current_page": 3
},
"meta": {
"request_id": "req_1NXWPnCo6bFb1KQto6C8OWvE",
"response_time_ms": 142
}
}
```
## Filtering and Sorting
Most list endpoints support powerful filtering and sorting capabilities using a consistent query syntax.
### Filter Operators
| Operator | Description | Example |
| ---------- | --------------------- | ---------------------------------------- |
| `_eq` | Equals | `?status_eq=shipped` |
| `_ne` | Not equals | `?status_ne=cancelled` |
| `_gt` | Greater than | `?amount_gt=100` |
| `_gte` | Greater than or equal | `?amount_gte=100` |
| `_lt` | Less than | `?amount_lt=500` |
| `_lte` | Less than or equal | `?amount_lte=500` |
| `_in` | In array | `?status_in=pending,processing` |
| `_like` | Pattern match | `?email_like=%@example.com` |
| `_between` | Range | `?created_between=2024-01-01,2024-01-31` |
### Common Filter Patterns
```bash theme={null}
# Exact match
GET /v1/orders?status=shipped
# Multiple values
GET /v1/orders?status_in=pending,processing,shipped
# Range queries
GET /v1/orders?created_after=2024-01-01T00:00:00Z
GET /v1/orders?total_amount_gte=100.00&total_amount_lte=500.00
# Search
GET /v1/orders?search=john@example.com
# Complex filtering
GET /v1/orders?status=shipped&created_after=2024-01-01&customer_tier=gold
```
### Sorting
```bash theme={null}
# Sort by field (default: ascending)
GET /v1/orders?sort=created_at
# Specify direction
GET /v1/orders?sort=total_amount&order=desc
# Multiple sort fields
GET /v1/orders?sort=status,created_at&order=asc,desc
```
## Official SDKs
```bash theme={null}
npm install stateset-node
```
```bash theme={null}
pip install stateset-python
```
```bash theme={null}
gem install stateset-ruby
```
```bash theme={null}
go get github.com/stateset/stateset-go
```
### SDK Quick Example
```javascript Node.js theme={null}
import { StateSetClient } from 'stateset-node';
// Replace with a structured logger (Winston, Pino, etc) in production
const logger = console;
const client = new StateSetClient({
apiKey: process.env.STATESET_API_KEY,
environment: 'production' // or 'sandbox'
});
// Create an order
const order = await client.orders.create({
customer_email: 'customer@example.com',
items: [
{ sku: 'WIDGET-001', quantity: 2, price: 29.99 }
]
});
logger.info('Order created', { orderId: order.id });
```
```python Python theme={null}
from stateset import StateSet
client = StateSet(
api_key=os.getenv('STATESET_API_KEY'),
environment='production'
)
# Create an order
order = client.orders.create({
'customer_email': 'customer@example.com',
'items': [
{'sku': 'WIDGET-001', 'quantity': 2, 'price': 29.99}
]
})
print(f'Order created: {order.id}')
```
## GraphQL API
StateSet offers a powerful GraphQL API for flexible data querying and real-time subscriptions.
### GraphQL Endpoint
```
POST https://api.stateset.com/graphql
```
### Basic Query Example
```graphql theme={null}
query GetOrdersWithItems {
orders(limit: 10, where: {status: {_eq: "shipped"}}) {
id
order_number
status
total_amount
customer {
id
email
first_name
last_name
}
line_items {
id
sku
quantity
price
product {
name
category
}
}
}
}
```
### Real-time Subscriptions
```graphql theme={null}
subscription OrderUpdates {
orders(where: {status: {_in: ["processing", "shipped"]}}) {
id
status
updated_at
}
}
```
## Webhooks
StateSet can send webhook notifications for important events in your account. Webhooks enable real-time integrations and automated workflows.
### Webhook Configuration
1. Configure endpoints in Dashboard → Settings → Webhooks
2. Select events to subscribe to
3. Add webhook signing secret to verify authenticity
4. Test with webhook simulator
### Webhook Events
* `order.created` - New order placed
* `order.updated` - Order details modified
* `order.paid` - Payment confirmed
* `order.processing` - Order processing started
* `order.shipped` - Shipment created
* `order.delivered` - Delivery confirmed
* `order.cancelled` - Order cancelled
* `order.refunded` - Refund processed
* `return.created` - Return initiated
* `return.approved` - Return approved
* `return.received` - Items received
* `return.processed` - Return completed
* `return.rejected` - Return rejected
* `inventory.low_stock` - Stock below threshold
* `inventory.out_of_stock` - Item out of stock
* `inventory.updated` - Stock levels changed
* `inventory.transfer` - Stock transferred
* `customer.created` - New customer registered
* `customer.updated` - Customer profile updated
* `customer.deleted` - Customer deleted
* `customer.subscription.created` - Subscription started
* `customer.subscription.cancelled` - Subscription cancelled
### Webhook Payload Structure
```json theme={null}
{
"id": "evt_1NXWPnCo6bFb1KQto6C8OWvE",
"type": "order.created",
"created": "2024-01-15T10:30:00Z",
"data": {
"object": { /* Full object data */ }
},
"previous_attributes": { /* For update events */ },
"metadata": {
"workspace_id": "ws_123",
"user_id": "usr_456",
"api_version": "2024-01-01"
}
}
```
### Webhook Security & Verification
```javascript theme={null}
// Production-ready webhook verification
const crypto = require('crypto');
// Replace with a structured logger (Winston, Pino, etc) in production
const logger = console;
function verifyWebhook(payload, signature, secret) {
// Extract timestamp and signatures
const elements = signature.split(' ');
const timestamp = elements.find(e => e.startsWith('t=')).slice(2);
const signatures = elements.filter(e => e.startsWith('v1=')).map(e => e.slice(3));
// Verify timestamp is within 5 minutes
const currentTime = Math.floor(Date.now() / 1000);
if (currentTime - parseInt(timestamp) > 300) {
throw new Error('Webhook timestamp too old');
}
// Compute expected signature
const signedPayload = `${timestamp}.${payload}`;
const expectedSignature = crypto
.createHmac('sha256', secret)
.update(signedPayload)
.digest('hex');
// Verify signature matches
const valid = signatures.some(sig =>
crypto.timingSafeEqual(Buffer.from(sig), Buffer.from(expectedSignature))
);
if (!valid) {
throw new Error('Invalid webhook signature');
}
return true;
}
// Express.js webhook handler
app.post('/webhooks/stateset', express.raw({type: 'application/json'}), (req, res) => {
const signature = req.headers['stateset-signature'];
const secret = process.env.STATESET_WEBHOOK_SECRET;
try {
verifyWebhook(req.body, signature, secret);
const event = JSON.parse(req.body);
// Process webhook event
switch(event.type) {
case 'order.created':
handleOrderCreated(event.data.object);
break;
case 'return.approved':
handleReturnApproved(event.data.object);
break;
// ... handle other events
}
res.json({received: true});
} catch (error) {
logger.error('Webhook error', { message: error.message });
res.status(400).json({error: 'Webhook verification failed'});
}
});
```
## Testing
### Sandbox Environment
The sandbox environment provides a complete testing environment that mirrors production:
```bash theme={null}
# Sandbox endpoints
REST API: https://api.sandbox.stateset.com/v1
GraphQL: https://api.sandbox.stateset.com/graphql
Webhooks: https://webhooks.sandbox.stateset.com
# Test API keys
Authorization: Bearer ${STATESET_API_KEY}
```
### Test Data
| Card Number | Scenario | Result |
| --------------------- | ------------------ | ------------------------------ |
| `4242 4242 4242 4242` | Successful payment | Always succeeds |
| `4000 0000 0000 0002` | Card declined | Always fails |
| `4000 0000 0000 9995` | Insufficient funds | Fails with insufficient\_funds |
| `4000 0000 0000 0127` | Incorrect CVC | Fails CVC check |
```javascript theme={null}
// Test order scenarios
const testScenarios = {
// Successful order
success: {
customer_email: 'test-success@example.com',
items: [{sku: 'TEST-SUCCESS', quantity: 1}]
},
// Inventory shortage
out_of_stock: {
customer_email: 'test-oos@example.com',
items: [{sku: 'TEST-OOS', quantity: 1}]
},
// Payment failure
payment_fail: {
customer_email: 'test-fail@example.com',
payment: {test_mode: 'fail'}
}
};
```
Use the webhook simulator to test your endpoint:
```bash theme={null}
# Trigger test webhook
curl -X POST https://api.sandbox.stateset.com/v1/webhooks/simulate \
-H "Authorization: Bearer sk_test_..." \
-d event_type="order.created" \
-d endpoint_url="https://your-app.com/webhooks"
```
### Idempotency
StateSet API supports idempotency for safely retrying requests without side effects:
**Idempotency Keys:**
* Valid for 24 hours after first request
* Must be unique per API key
* Recommended format: `{resource}-{uuid}` (e.g., `order-550e8400-e29b-41d4-a716`)
```bash theme={null}
# Using idempotency for safe retries
curl -X POST https://api.stateset.com/v1/orders \
-H "Idempotency-Key: order-550e8400-e29b-41d4-a716" \
-H "Authorization: Bearer sk_test_..." \
-d @order.json
```
```javascript theme={null}
// Node.js with automatic retry and idempotency
const { v4: uuidv4 } = require('uuid');
async function createOrderSafely(orderData) {
const idempotencyKey = `order-${uuidv4()}`;
return await stateset.orders.create(orderData, {
idempotencyKey,
maxRetries: 3,
retryDelay: 1000
});
}
```
## API Limits & Quotas
### Request Limits by Plan
| Plan | Requests/Min | Requests/Day | Burst Limit | Concurrent Connections |
| -------------- | ------------ | ------------ | ----------- | ---------------------- |
| **Free** | 60 | 1,000 | 100/sec | 10 |
| **Starter** | 100 | 10,000 | 200/sec | 25 |
| **Growth** | 1,000 | 100,000 | 1,000/sec | 100 |
| **Scale** | 5,000 | 500,000 | 5,000/sec | 500 |
| **Enterprise** | Custom | Unlimited | Custom | Unlimited |
### Resource Limits
| Resource | Limit | Notes |
| ----------------- | ----------- | ------------------------------------ |
| Max request size | 10 MB | Increase available for Enterprise |
| Max response size | 50 MB | Paginate for larger datasets |
| Webhook timeout | 30 seconds | Retry up to 3 times |
| File upload size | 100 MB | Direct upload to S3 for larger files |
| Batch operations | 1,000 items | Use async jobs for larger batches |
## Support and Community
Get help with integration issues
Join our developer community
Check API status and uptime
### Additional Resources
* [API Changelog](/api-reference/changelog) - Latest updates and changes
* [Postman Collection](https://www.postman.com/stateset/workspace/stateset-api) - Ready-to-use API collection
* [OpenAPI Specification](/spec/openapi.yaml) - Machine-readable API spec
* [Code Examples](https://github.com/stateset/examples) - Sample implementations
***
Ready to get started? Check out our [5-minute quickstart guide](/quickstart) or explore the API reference sections below.
# Adjust Inventory
Source: https://docs.stateset.com/api-reference/inventory/adjust
POST https://api.stateset.com/v1/inventory_items/:id/adjust
This endpoint adjusts inventory levels for stock reconciliation, damage, or other reasons.
### Body
The unique identifier of the inventory item to adjust
The type of adjustment (e.g., "reconciliation", "damage", "theft", "expiration", "return", "manual")
The quantity to adjust (positive for increase, negative for decrease)
Detailed reason for the adjustment
The warehouse where the adjustment is being made
The specific location within the warehouse
Reference number for tracking (e.g., count sheet number, incident report)
The cost impact of this adjustment for accounting purposes
### Response
The unique identifier of the adjustment record
The inventory item that was adjusted
The type of adjustment performed
The quantity before adjustment
The quantity after adjustment
The actual quantity change applied
The financial impact of this adjustment
The user who performed the adjustment
Timestamp when the adjustment was made
Indicates whether the adjustment was successful
### Error Responses
Error object containing details about what went wrong
Error code (e.g., "insufficient\_stock", "invalid\_quantity", "warehouse\_not\_found")
Human-readable error message
Additional error details
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/inventory_items/:id/adjust' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"inventory_item_id": "inv_abc123",
"adjustment_type": "reconciliation",
"quantity_change": -5,
"reason": "Physical count showed 5 less than system",
"warehouse_id": "wh_east_01",
"location_id": "loc_a1_shelf_3",
"reference_number": "COUNT_2024_001",
"cost_adjustment": -125.00
}'
```
```graphQL GraphQL theme={null}
mutation inventoryAdjustMutation {
inventoryAdjust(
inventoryItemId: "${inventoryItemId}",
adjustmentType: "${adjustmentType}",
quantityChange: ${quantityChange},
reason: "${reason}",
warehouseId: "${warehouseId}",
locationId: "${locationId}",
referenceNumber: "${referenceNumber}",
costAdjustment: ${costAdjustment}
) {
adjustment {
id
quantity_before
quantity_after
quantity_change
cost_impact
}
userErrors {
field
message
}
}
}
```
```js Node.js theme={null}
const adjustment = await stateset.inventory.adjust({
inventory_item_id: 'inv_abc123',
adjustment_type: 'reconciliation',
quantity_change: -5,
reason: 'Physical count showed 5 less than system',
warehouse_id: 'wh_east_01',
location_id: 'loc_a1_shelf_3',
reference_number: 'COUNT_2024_001',
cost_adjustment: -125.00
});
```
```python Python theme={null}
adjustment = stateset.inventory.adjust({
'inventory_item_id': 'inv_abc123',
'adjustment_type': 'reconciliation',
'quantity_change': -5,
'reason': 'Physical count showed 5 less than system',
'warehouse_id': 'wh_east_01',
'location_id': 'loc_a1_shelf_3',
'reference_number': 'COUNT_2024_001',
'cost_adjustment': -125.00
})
```
```ruby Ruby theme={null}
adjustment = Stateset::Inventory.adjust({
inventory_item_id: 'inv_abc123',
adjustment_type: 'reconciliation',
quantity_change: -5,
reason: 'Physical count showed 5 less than system',
warehouse_id: 'wh_east_01',
location_id: 'loc_a1_shelf_3',
reference_number: 'COUNT_2024_001',
cost_adjustment: -125.00
})
```
```go Go theme={null}
adjustment, err := stateset.Inventory.adjust({
InventoryItemID: 'inv_abc123',
AdjustmentType: 'reconciliation',
QuantityChange: -5,
Reason: 'Physical count showed 5 less than system',
WarehouseID: 'wh_east_01',
LocationID: 'loc_a1_shelf_3',
ReferenceNumber: 'COUNT_2024_001',
CostAdjustment: -125.00
})
```
```java Java theme={null}
InventoryAdjustment adjustment = stateset.inventory.adjust({
inventoryItemId: 'inv_abc123',
adjustmentType: 'reconciliation',
quantityChange: -5,
reason: 'Physical count showed 5 less than system',
warehouseId: 'wh_east_01',
locationId: 'loc_a1_shelf_3',
referenceNumber: 'COUNT_2024_001',
costAdjustment: -125.00
});
```
```php PHP theme={null}
$adjustment = $stateset->inventory->adjust([
'inventory_item_id' => 'inv_abc123',
'adjustment_type' => 'reconciliation',
'quantity_change' => -5,
'reason' => 'Physical count showed 5 less than system',
'warehouse_id' => 'wh_east_01',
'location_id' => 'loc_a1_shelf_3',
'reference_number' => 'COUNT_2024_001',
'cost_adjustment' => -125.00
]);
```
```csharp C# theme={null}
var adjustment = await stateset.Inventory.Adjust(new {
InventoryItemId = 'inv_abc123',
AdjustmentType = 'reconciliation',
QuantityChange = -5,
Reason = 'Physical count showed 5 less than system',
WarehouseId = 'wh_east_01',
LocationId = 'loc_a1_shelf_3',
ReferenceNumber = 'COUNT_2024_001',
CostAdjustment = -125.00
});
```
```json Response theme={null}
{
"id": "adj_xyz789",
"inventory_item_id": "inv_abc123",
"adjustment_type": "reconciliation",
"quantity_before": 100,
"quantity_after": 95,
"quantity_change": -5,
"cost_impact": -125.00,
"reason": "Physical count showed 5 less than system",
"warehouse_id": "wh_east_01",
"location_id": "loc_a1_shelf_3",
"reference_number": "COUNT_2024_001",
"adjusted_by": "user_123",
"adjusted_at": "2024-01-15T14:30:00Z",
"success": true
}
```
```json Error Response theme={null}
{
"error": {
"code": "insufficient_stock",
"message": "Cannot adjust inventory below zero. Current quantity: 3, requested change: -5",
"details": {
"current_quantity": 3,
"requested_change": -5,
"minimum_allowed": 0
}
}
}
```
# Inventory Analytics
Source: https://docs.stateset.com/api-reference/inventory/analytics
GET /api/v1/inventory/analytics
Retrieve comprehensive analytics and insights about your inventory performance
The Analytics API provides real-time insights into inventory performance, trends, and optimization opportunities.
## Query Parameters
Type of analytics to retrieve:
* `overview` - General inventory metrics
* `turnover` - Inventory turnover analysis
* `aging` - Stock aging report
* `performance` - SKU performance metrics
* `forecast_accuracy` - Forecast vs actual comparison
Filter analytics for specific SKU
Filter by specific location
Start date for analytics period (ISO 8601)
End date for analytics period (ISO 8601)
Group results by: `sku`, `category`, `location`, `supplier`
Include historical trend data. Default: false
## Response
Type of analytics returned
Analytics time period
Start date (ISO 8601)
End date (ISO 8601)
Core metrics based on metric\_type
Total inventory value
Total units in stock
Number of unique SKUs
Average inventory turnover rate
Percentage of SKUs out of stock
Percentage of overstocked items
Value of non-moving inventory
Total inventory carrying cost
Detailed breakdown by grouping
Group identifier (SKU, category, etc.)
Group name
Group-specific metrics
Units in stock
Inventory value
Turnover rate
Days of supply on hand
Movement velocity: `fast`, `medium`, `slow`, `non-moving`
Historical trend data (if requested)
Time series of inventory values
Time series of turnover rates
Historical stockout events
AI-generated insights and recommendations
Insight type: `opportunity`, `warning`, `recommendation`
Severity level: `high`, `medium`, `low`
Insight description
List of affected SKUs
Estimated savings if actioned
```bash cURL theme={null}
curl -X GET "https://api.stateset.com/api/v1/inventory/analytics?metric_type=overview&include_trends=true" \
-H "Authorization: Bearer YOUR_API_KEY"
```
```javascript Node.js theme={null}
const analytics = await stateset.inventory.analytics.get({
metric_type: 'overview',
date_from: '2024-01-01',
date_to: '2024-11-15',
include_trends: true
});
```
```python Python theme={null}
analytics = stateset.inventory.analytics.get(
metric_type='overview',
date_from='2024-01-01',
date_to='2024-11-15',
include_trends=True
)
```
```json Response theme={null}
{
"metric_type": "overview",
"period": {
"from": "2024-01-01T00:00:00Z",
"to": "2024-11-15T23:59:59Z"
},
"metrics": {
"total_value": 485750.00,
"total_units": 12500,
"unique_skus": 256,
"average_turnover": 8.5,
"stockout_rate": 0.03,
"overstock_rate": 0.12,
"dead_stock_value": 15000.00,
"carrying_cost": 121437.50
},
"breakdown": [
{
"group": "Electronics",
"name": "Electronics Category",
"metrics": {
"units": 3500,
"value": 175000.00,
"turnover_rate": 12.5,
"days_of_supply": 29.2,
"velocity": "fast"
}
},
{
"group": "Accessories",
"name": "Accessories Category",
"metrics": {
"units": 5000,
"value": 75000.00,
"turnover_rate": 6.0,
"days_of_supply": 60.8,
"velocity": "medium"
}
}
],
"trends": {
"inventory_value": [
{ "date": "2024-01-01", "value": 450000 },
{ "date": "2024-02-01", "value": 465000 },
{ "date": "2024-03-01", "value": 478000 }
],
"turnover_rate": [
{ "date": "2024-01-01", "rate": 7.5 },
{ "date": "2024-02-01", "rate": 8.0 },
{ "date": "2024-03-01", "rate": 8.5 }
]
},
"insights": [
{
"type": "opportunity",
"severity": "high",
"message": "15 SKUs have been non-moving for 180+ days",
"affected_items": ["OLD-001", "OLD-002", "OLD-003"],
"potential_savings": 15000.00
},
{
"type": "warning",
"severity": "medium",
"message": "Electronics category showing 25% increase in stockouts",
"affected_items": ["ELEC-101", "ELEC-102"],
"potential_savings": 5000.00
},
{
"type": "recommendation",
"severity": "low",
"message": "Consider implementing ABC classification for better control",
"affected_items": [],
"potential_savings": 8000.00
}
]
}
```
## Metric Types
### Overview Analytics
General inventory health metrics and KPIs.
```javascript theme={null}
const overview = await stateset.inventory.analytics.get({
metric_type: 'overview',
group_by: 'category'
});
```
### Turnover Analysis
Detailed inventory turnover rates and velocity metrics.
```javascript theme={null}
const turnover = await stateset.inventory.analytics.get({
metric_type: 'turnover',
group_by: 'sku',
date_from: '2024-01-01'
});
```
### Aging Report
Analysis of stock age and identification of slow-moving items.
```javascript theme={null}
const aging = await stateset.inventory.analytics.get({
metric_type: 'aging',
location_id: 'loc_warehouse_001'
});
```
### Performance Metrics
SKU-level performance including sales velocity and profitability.
```javascript theme={null}
const performance = await stateset.inventory.analytics.get({
metric_type: 'performance',
sku: 'WIDGET-001',
include_trends: true
});
```
### Forecast Accuracy
Compare forecasted demand with actual sales to improve planning.
```javascript theme={null}
const accuracy = await stateset.inventory.analytics.get({
metric_type: 'forecast_accuracy',
date_from: '2024-06-01',
date_to: '2024-11-01'
});
```
## Exporting Analytics
Export analytics data in various formats:
```javascript theme={null}
// Export as CSV
const csvExport = await stateset.inventory.analytics.export({
metric_type: 'overview',
format: 'csv'
});
// Export as PDF report
const pdfReport = await stateset.inventory.analytics.export({
metric_type: 'performance',
format: 'pdf',
include_charts: true
});
```
## Scheduling Reports
Set up automated analytics reports:
```javascript theme={null}
const schedule = await stateset.inventory.analytics.schedule({
name: 'Weekly Inventory Report',
metric_type: 'overview',
frequency: 'weekly',
recipients: ['ops@company.com'],
format: 'pdf'
});
```
## Related Endpoints
* [Inventory Planning](/api-reference/inventory/planning) - Generate inventory plans
* [List Inventory](/api-reference/inventory/get) - View current inventory
* [Inventory Webhooks](/api-reference/webhooks/inventory) - Real-time inventory events
# Batch Operations
Source: https://docs.stateset.com/api-reference/inventory/batch
POST /api/v1/inventory/batch
Perform bulk inventory operations for efficient management at scale
Batch operations allow you to update multiple inventory items in a single API call, significantly improving performance for large-scale operations.
## Request Body
Type of batch operation:
* `update` - Update multiple items
* `adjust` - Bulk quantity adjustments
* `transfer` - Multi-item transfers
* `cycle_count` - Batch cycle counting
* `import` - Import inventory data
Array of items to process (max 1000 per request)
SKU of the inventory item
Operation-specific data (varies by operation type)
Batch operation options
Validate without executing. Default: false
Continue processing on errors. Default: false
Email for completion notification
## Response
Unique identifier for this batch operation
Batch status: `processing`, `completed`, `failed`, `partial`
Operation summary
Total items in batch
Successfully processed items
Failed items
Skipped items
Individual item results
Item SKU
Item status: `success`, `error`, `skipped`
Status message or error details
Operation result data
```bash cURL theme={null}
curl -X POST https://api.stateset.com/api/v1/inventory/batch \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"operation": "adjust",
"items": [
{
"sku": "WIDGET-001",
"data": {
"adjustment_type": "absolute",
"quantity": 150,
"reason": "Cycle count correction"
}
},
{
"sku": "GADGET-002",
"data": {
"adjustment_type": "relative",
"quantity": -25,
"reason": "Damaged goods"
}
}
],
"options": {
"continue_on_error": true
}
}'
```
```javascript Node.js theme={null}
const batchResult = await stateset.inventory.batch.create({
operation: 'adjust',
items: [
{
sku: 'WIDGET-001',
data: {
adjustment_type: 'absolute',
quantity: 150,
reason: 'Cycle count correction'
}
},
{
sku: 'GADGET-002',
data: {
adjustment_type: 'relative',
quantity: -25,
reason: 'Damaged goods'
}
}
],
options: {
continue_on_error: true
}
});
```
```python Python theme={null}
batch_result = stateset.inventory.batch.create(
operation='adjust',
items=[
{
'sku': 'WIDGET-001',
'data': {
'adjustment_type': 'absolute',
'quantity': 150,
'reason': 'Cycle count correction'
}
},
{
'sku': 'GADGET-002',
'data': {
'adjustment_type': 'relative',
'quantity': -25,
'reason': 'Damaged goods'
}
}
],
options={
'continue_on_error': True
}
)
```
```json Response theme={null}
{
"batch_id": "batch_1a2b3c4d5e",
"status": "completed",
"summary": {
"total_items": 2,
"processed": 2,
"failed": 0,
"skipped": 0
},
"results": [
{
"sku": "WIDGET-001",
"status": "success",
"message": "Inventory adjusted successfully",
"data": {
"previous_quantity": 125,
"new_quantity": 150,
"adjustment": 25
}
},
{
"sku": "GADGET-002",
"status": "success",
"message": "Inventory adjusted successfully",
"data": {
"previous_quantity": 200,
"new_quantity": 175,
"adjustment": -25
}
}
]
}
```
## Operation Types
### Bulk Update
Update multiple inventory item properties at once.
```javascript theme={null}
const updates = await stateset.inventory.batch.create({
operation: 'update',
items: [
{
sku: 'WIDGET-001',
data: {
reorder_point: 100,
price: 29.99,
category: 'Electronics'
}
},
{
sku: 'WIDGET-002',
data: {
reorder_point: 150,
price: 34.99,
category: 'Electronics'
}
}
]
});
```
### Bulk Adjust
Adjust quantities for multiple items simultaneously.
```javascript theme={null}
const adjustments = await stateset.inventory.batch.create({
operation: 'adjust',
items: cycleCountResults.map(result => ({
sku: result.sku,
data: {
adjustment_type: 'absolute',
quantity: result.counted_quantity,
reason: 'Monthly cycle count',
reference: `CC-${Date.now()}`
}
}))
});
```
### Bulk Transfer
Transfer multiple items between locations.
```javascript theme={null}
const transfers = await stateset.inventory.batch.create({
operation: 'transfer',
items: [
{
sku: 'WIDGET-001',
data: {
from_location: 'warehouse_001',
to_location: 'warehouse_002',
quantity: 50
}
},
{
sku: 'GADGET-002',
data: {
from_location: 'warehouse_001',
to_location: 'warehouse_002',
quantity: 100
}
}
]
});
```
### Import Inventory
Import inventory data from external systems.
```javascript theme={null}
const importResult = await stateset.inventory.batch.create({
operation: 'import',
items: csvData.map(row => ({
sku: row.sku,
data: {
name: row.product_name,
description: row.description,
quantity: parseInt(row.quantity),
price: parseFloat(row.price),
cost: parseFloat(row.cost),
location_id: row.warehouse,
category: row.category,
reorder_point: parseInt(row.reorder_point)
}
})),
options: {
validate_only: true // Test import first
}
});
```
## Async Operations
For large batches, operations are processed asynchronously:
```javascript theme={null}
// Start batch operation
const batch = await stateset.inventory.batch.create({
operation: 'update',
items: largeItemArray, // 10,000+ items
options: {
notification_email: 'ops@company.com'
}
});
// Check status
const status = await stateset.inventory.batch.get(batch.batch_id);
// Poll for completion
const checkStatus = async () => {
const current = await stateset.inventory.batch.get(batch.batch_id);
if (current.status === 'completed') {
console.log('Batch completed:', current.summary);
} else if (current.status === 'failed') {
console.error('Batch failed:', current.error);
} else {
// Still processing
setTimeout(checkStatus, 5000); // Check again in 5 seconds
}
};
```
## Error Handling
Handle batch operation errors gracefully:
```javascript theme={null}
try {
const batch = await stateset.inventory.batch.create({
operation: 'adjust',
items: adjustmentItems,
options: {
continue_on_error: false // Stop on first error
}
});
// Check for partial failures
const failedItems = batch.results.filter(r => r.status === 'error');
if (failedItems.length > 0) {
console.log('Failed items:', failedItems);
// Retry failed items
const retryBatch = await stateset.inventory.batch.create({
operation: 'adjust',
items: failedItems.map(item => ({
sku: item.sku,
data: adjustmentItems.find(a => a.sku === item.sku).data
}))
});
}
} catch (error) {
console.error('Batch operation failed:', error);
}
```
## Performance Tips
* Batch operations can process up to 1,000 items per request
* For larger datasets, use async operations
* Group similar operations together
* Use `validate_only` to test before executing
* Monitor rate limits for optimal throughput
## Related Endpoints
* [Inventory Planning](/api-reference/inventory/planning) - Plan inventory levels
* [Inventory Analytics](/api-reference/inventory/analytics) - Analyze inventory data
* [Adjust Inventory](/api-reference/inventory/adjust) - Single item adjustments
* [Transfer Inventory](/api-reference/inventory/transfer) - Single item transfers
# Create Inventory
Source: https://docs.stateset.com/api-reference/inventory/create
POST https://api.stateset.com/v1/inventory_items
This endpoint creates a new inventory item
### Body
This is the ID of the inventory item.
This is the SKU of the inventory item.
This is the UPC of the inventory item.
This is the description of the inventory item.
This is the size of the inventory item.
This is the color of the inventory item.
This is the incoming quantity of the inventory item.
This is the available quantity of the inventory item.
This is the warehouse ID of the inventory item.
This is the arrival date of the inventory item.
This is the delivery date of the inventory item.
This is the purchase order ID of the inventory item.
This is the created date of the inventory item.
This is the updated date of the inventory item.
### Response
This is the ID of the inventory item.
This is the SKU of the inventory item.
This is the UPC of the inventory item.
This is the description of the inventory item.
This is the size of the inventory item.
This is the color of the inventory item.
This is the incoming quantity of the inventory item.
This is the available quantity of the inventory item.
This is the warehouse ID of the inventory item.
This is the arrival date of the inventory item.
This is the delivery date of the inventory item.
This is the purchase order ID of the inventory item.
This is the created date of the inventory item.
This is the updated date of the inventory item.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/inventory_items' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```graphQL GraphQL theme={null}
mutation InsertNewInventoryItem(
$inventory_item: inventory_items_insert_input!
) {
insert_inventory_items (
objects: [$inventory_item]
) {
returning {
id
sku
upc
description
size
color
incoming
available
warehouse
arrivalDate
deliveryDate
}
}
}
```
```javascript Node.js theme={null}
var created = await stateset.inventoryItems.create({
sku: "SKU-123",
upc: "UPC-123",
description: "This is a description",
size: "Large",
color: "Red",
incoming: 10,
available: 10,
warehouse: 1,
arrivalDate: "2021-01-01",
deliveryDate: "2021-01-01",
});
```
```python Python theme={null}
created = stateset.inventory_items.create(
sku="SKU-123",
upc="UPC-123",
description="This is a description",
size="Large",
color="Red",
incoming=10,
available=10,
warehouse=1,
arrivalDate="2021-01-01",
deliveryDate="2021-01-01",
)
```
```ruby Ruby theme={null}
created = Stateset::InventoryItem.create(
sku: "SKU-123",
upc: "UPC-123",
description: "This is a description",
size: "Large",
color: "Red",
incoming: 10,
available: 10,
warehouse: 1,
arrivalDate: "2021-01-01",
deliveryDate: "2021-01-01",
)
```
```php PHP theme={null}
$created = $stateset->inventoryItems->create(
array(
"sku" => "SKU-123",
"upc" => "UPC-123",
"description" => "This is a description",
"size" => "Large",
"color" => "Red",
"incoming" => 10,
"available" => 10,
"warehouse" => 1,
"arrivalDate" => "2021-01-01",
"deliveryDate" => "2021-01-01",
)
);
```
```go Go theme={null}
created, err := stateset.InventoryItems.Create(
"SKU-123",
"UPC-123",
"This is a description",
"Large",
"Red",
10,
10,
1,
"2021-01-01",
"2021-01-01",
)
```
```java Java theme={null}
InventoryItem created = stateset.inventoryItems.create(
"SKU-123",
"UPC-123",
"This is a description",
"Large",
"Red",
10,
10,
1,
"2021-01-01",
"2021-01-01",
);
```
```json Response theme={null}
{
"inventory_items": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "SKU-123",
"description": "This is a description",
"size": "Large",
"incoming": 10,
"color": "Red",
"warehouse": 1,
"available": 10,
"arriving": "2021-01-01",
"purchase_order_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
},
]
}
```
# Delete Inventory Item
Source: https://docs.stateset.com/api-reference/inventory/delete
DELETE https://api.return.com/v1/inventory_items/:id
This endpoint deletes an existing inventory item.
### Body
The ID of the inventory item to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/inventory_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "ii_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteInventoryItem ($inventory_item_id: String) {
delete_inventory_item(where: {id: {_eq: $inventory_item_id}}) {
affected_rows
}
}
```
```javascript Node.js theme={null}
const deleted = await stateset.inventoryItems.del(
'ii_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
deleted = stateset.inventory_items.del(
'ii_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
deleted = Stateset::InventoryItems.del(
'ii_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$deleted = $stateset->inventoryItems->del(
'ii_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
deleted, err := stateset.InventoryItems.Del(
"ii_ODkRWQtx9NVsRX"
)
```
```java Java theme={null}
InventoryItem deleted = stateset.inventoryItems.del(
"ii_ODkRWQtx9NVsRX"
);
```
```json Response theme={null}
{
"id": "ii_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "inventory_item",
"deleted": true
}
```
# Get Inventory Item
Source: https://docs.stateset.com/api-reference/inventory/get
GET https://api.stateset.com/v1/inventory_items/:id
This endpoint gets or creates a new inventory item.
### Body
This is the unique identifier for the inventory item.
### Response
This is the unique identifier for the inventory item.
This is the stock keeping unit (SKU) for the inventory item.
This is the description for the inventory item.
This is the size for the inventory item.
This is the number of items incoming for the inventory item.
This is the color for the inventory item.
This is the identifier for the warehouse for the inventory item.
This is the number of items available for the inventory item.
This is the date when the items are expected to arrive for the inventory item.
This is the identifier for the purchase order associated with the inventory item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/inventory_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}'
```
```graphQL GraphQL theme={null}
query {
inventory_item {
id
sku
upc
description
size
color
incoming
available
warehouse
arrivalDate
deliveryDate
}
}
```
```javascript Node.js theme={null}
var inventoryItems = await stateset.inventoryItems.retreive({
id: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
});
```
```python Python theme={null}
inventoryItems = stateset.inventoryItems.retreive({
id: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
})
```
```ruby Ruby theme={null}
inventoryItems = Stateset::InventoryItems.retreive({
id: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
})
```
```php PHP theme={null}
$inventoryItems = $stateset->inventoryItems->retreive([
"id" => "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
]);
```
```go Go theme={null}
inventoryItems, err := stateset.InventoryItems.Retreive(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
)
```
```java Java theme={null}
InventoryItems inventoryItems = stateset.inventoryItems.retreive(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
);
```
```json Response theme={null}
{
"inventory_item": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "SKU-123",
"description": "This is a description",
"size": "Large",
"incoming": 10,
"color": "Red",
"warehouse": 1,
"available": 10,
"arriving": "2021-01-01",
"purchase_order_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
},
]
}
```
```json Error Response (404 Not Found) theme={null}
{
"error": {
"code": "RESOURCE_NOT_FOUND",
"message": "Inventory item not found",
"details": {
"resource": "inventory_item",
"id": "inv_abc123"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (401 Unauthorized) theme={null}
{
"error": {
"code": "INVALID_API_KEY",
"message": "The API key provided is invalid or has been revoked",
"request_id": "req_abc123def456"
}
}
```
### Inventory Item
| Name | Type | Description |
| ------------------- | -------------------------- | ----------------------------------------------------------- |
| id | Text (Primary Key, Unique) | Unique identifier for the entry |
| sku | Text (Nullable) | Stock Keeping Unit (SKU) for the entry |
| description | Text (Nullable) | Description or additional details about the entry |
| size | Text (Nullable) | Size of the item |
| incoming | Integer (Nullable) | Number of items incoming |
| color | Text (Nullable) | Color of the item |
| warehouse | Integer (Nullable) | Identifier for the warehouse |
| available | Integer (Nullable) | Number of items available |
| arriving | Date (Nullable) | Date when the items are expected to arrive |
| purchase\_order\_id | Text (Nullable) | Identifier for the purchase order associated with the entry |
# Inventory Planning
Source: https://docs.stateset.com/api-reference/inventory/planning
POST /api/v1/inventory/planning
Generate intelligent inventory planning recommendations based on demand forecasting and optimization algorithms
The Inventory Planning API uses machine learning to forecast demand and optimize stock levels across your inventory.
## Request Body
Type of planning to generate. Options:
* `demand_forecast` - Predict future demand
* `reorder_optimization` - Calculate optimal reorder points
* `seasonal_planning` - Plan for seasonal variations
* `abc_analysis` - Categorize inventory by value/velocity
Specific SKU to plan for. If omitted, plans all inventory items.
Location ID for location-specific planning
Planning time horizon
Number of time units
Time unit: `days`, `weeks`, `months`, `quarters`
Planning-specific parameters
Target service level (0-1). Default: 0.95
Supplier lead time in days
Annual holding cost as percentage of item value
Fixed cost per order
Include seasonal patterns in forecast. Default: true
## Response
Unique identifier for this planning run
Type of planning performed
ISO 8601 timestamp of when the plan was generated
Array of planning results per inventory item
SKU of the inventory item
Name of the inventory item
Current available stock level
Demand forecast details
Predicted demand for the time horizon
95% confidence interval
Lower bound of prediction
Upper bound of prediction
Demand trend: `increasing`, `decreasing`, `stable`
Current seasonal adjustment factor
Planning recommendations
Recommended reorder point
Recommended safety stock level
Optimal order quantity (EOQ)
Maximum recommended stock level
Recommended date for next order
Recommended quantity for next order
Performance metrics
Annual inventory turnover rate
Probability of stockout (0-1)
Estimated annual carrying cost
ABC classification: `A`, `B`, or `C`
Overall planning summary
Number of items planned
Total inventory value
Items currently below reorder point
List of SKUs requiring immediate reorder
Estimated annual savings from optimization
```bash cURL theme={null}
curl -X POST https://api.stateset.com/api/v1/inventory/planning \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"planning_type": "demand_forecast",
"time_horizon": {
"value": 3,
"unit": "months"
},
"parameters": {
"service_level": 0.95,
"include_seasonality": true
}
}'
```
```javascript Node.js theme={null}
const planning = await stateset.inventory.planning.create({
planning_type: 'demand_forecast',
time_horizon: {
value: 3,
unit: 'months'
},
parameters: {
service_level: 0.95,
include_seasonality: true
}
});
```
```python Python theme={null}
planning = stateset.inventory.planning.create(
planning_type='demand_forecast',
time_horizon={
'value': 3,
'unit': 'months'
},
parameters={
'service_level': 0.95,
'include_seasonality': True
}
)
```
```json Response theme={null}
{
"planning_id": "plan_1a2b3c4d5e",
"planning_type": "demand_forecast",
"generated_at": "2024-11-15T10:30:00Z",
"items": [
{
"sku": "WIDGET-001",
"item_name": "Premium Widget",
"current_stock": 150,
"forecast": {
"predicted_demand": 450,
"confidence_interval": {
"lower": 380,
"upper": 520
},
"trend": "increasing",
"seasonality_factor": 1.2
},
"recommendations": {
"reorder_point": 200,
"safety_stock": 50,
"economic_order_quantity": 300,
"max_stock_level": 500,
"next_order_date": "2024-11-20",
"next_order_quantity": 300
},
"metrics": {
"turnover_rate": 12.5,
"stockout_risk": 0.02,
"carrying_cost": 1250.00,
"abc_category": "A"
}
},
{
"sku": "GADGET-002",
"item_name": "Standard Gadget",
"current_stock": 75,
"forecast": {
"predicted_demand": 180,
"confidence_interval": {
"lower": 150,
"upper": 210
},
"trend": "stable",
"seasonality_factor": 1.0
},
"recommendations": {
"reorder_point": 80,
"safety_stock": 20,
"economic_order_quantity": 150,
"max_stock_level": 250,
"next_order_date": "2024-11-18",
"next_order_quantity": 150
},
"metrics": {
"turnover_rate": 8.0,
"stockout_risk": 0.05,
"carrying_cost": 450.00,
"abc_category": "B"
}
}
],
"summary": {
"total_items": 2,
"total_value": 15750.00,
"items_below_reorder": 1,
"urgent_orders": ["GADGET-002"],
"optimization_savings": 2500.00
}
}
```
## Planning Types
### Demand Forecast
Predicts future demand using historical sales data and machine learning algorithms.
```javascript theme={null}
const forecast = await stateset.inventory.planning.create({
planning_type: 'demand_forecast',
sku: 'WIDGET-001',
time_horizon: { value: 6, unit: 'months' },
parameters: {
include_seasonality: true,
service_level: 0.98
}
});
```
### Reorder Optimization
Calculates optimal reorder points and quantities based on demand patterns and costs.
```javascript theme={null}
const reorderPlan = await stateset.inventory.planning.create({
planning_type: 'reorder_optimization',
parameters: {
holding_cost_rate: 0.25,
ordering_cost: 50,
lead_time_days: 14
}
});
```
### Seasonal Planning
Plans inventory levels for seasonal demand variations.
```javascript theme={null}
const seasonalPlan = await stateset.inventory.planning.create({
planning_type: 'seasonal_planning',
time_horizon: { value: 1, unit: 'quarters' },
parameters: {
service_level: 0.95
}
});
```
### ABC Analysis
Categorizes inventory based on value and velocity for prioritized management.
```javascript theme={null}
const abcAnalysis = await stateset.inventory.planning.create({
planning_type: 'abc_analysis',
location_id: 'loc_warehouse_001'
});
```
## Error Handling
Planning operations may fail if:
* Insufficient historical data (less than 30 days)
* Invalid parameters or constraints
* SKU not found
* Location not authorized
```javascript theme={null}
try {
const planning = await stateset.inventory.planning.create({
planning_type: 'demand_forecast',
sku: 'INVALID-SKU'
});
} catch (error) {
if (error.code === 'sku_not_found') {
console.error('SKU does not exist');
} else if (error.code === 'insufficient_data') {
console.error('Not enough historical data for forecast');
}
}
```
## Webhooks
Subscribe to planning events to automate your inventory workflows:
* `inventory.planning.completed` - Planning run completed
* `inventory.reorder.required` - Item below reorder point
* `inventory.stockout.predicted` - Stockout risk detected
## Related Endpoints
* [Create Inventory Item](/api-reference/inventory/create) - Add items to inventory
* [Adjust Inventory](/api-reference/inventory/adjust) - Make stock adjustments
* [Transfer Inventory](/api-reference/inventory/transfer) - Move stock between locations
* [Get Inventory Analytics](/api-reference/inventory/analytics) - View inventory metrics
# Transfer Inventory
Source: https://docs.stateset.com/api-reference/inventory/transfer
POST https://api.stateset.com/v1/inventory_items/:id/transfer
This endpoint transfers inventory between warehouses or locations.
### Body
The unique identifier of the inventory item to transfer
The quantity to transfer
The source warehouse ID
The source location within the warehouse
The destination warehouse ID
The destination location within the warehouse
The reason for the transfer (e.g., "rebalancing", "fulfillment", "returns\_processing")
Transfer priority (e.g., "standard", "expedited", "urgent")
Expected arrival date at destination
### Response
The unique identifier of the transfer record
The system-generated transfer number for tracking
The inventory item being transferred
The quantity being transferred
Source warehouse details
Warehouse ID
Warehouse name
Location within warehouse
Destination warehouse details
Warehouse ID
Warehouse name
Location within warehouse
Transfer status (e.g., "pending", "in\_transit", "completed", "cancelled")
Timestamp when the transfer was created
Indicates whether the transfer was initiated successfully
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/inventory_items/:id/transfer' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"inventory_item_id": "inv_abc123",
"quantity": 50,
"from_warehouse_id": "wh_east_01",
"from_location_id": "loc_a1_shelf_3",
"to_warehouse_id": "wh_west_01",
"to_location_id": "loc_b2_shelf_1",
"transfer_reason": "rebalancing",
"priority": "standard",
"expected_arrival": "2024-01-20"
}'
```
```graphQL GraphQL theme={null}
mutation inventoryTransferMutation {
inventoryTransfer(
inventoryItemId: "${inventoryItemId}",
quantity: ${quantity},
fromWarehouseId: "${fromWarehouseId}",
fromLocationId: "${fromLocationId}",
toWarehouseId: "${toWarehouseId}",
toLocationId: "${toLocationId}",
transferReason: "${transferReason}",
priority: "${priority}",
expectedArrival: "${expectedArrival}"
) {
transfer {
id
transfer_number
quantity
status
from_warehouse {
id
name
}
to_warehouse {
id
name
}
}
userErrors {
field
message
}
}
}
```
```js Node.js theme={null}
const transfer = await stateset.inventory.transfer({
inventory_item_id: 'inv_abc123',
quantity: 50,
from_warehouse_id: 'wh_east_01',
from_location_id: 'loc_a1_shelf_3',
to_warehouse_id: 'wh_west_01',
to_location_id: 'loc_b2_shelf_1',
transfer_reason: 'rebalancing',
priority: 'standard',
expected_arrival: '2024-01-20'
});
```
```python Python theme={null}
transfer = stateset.inventory.transfer({
'inventory_item_id': 'inv_abc123',
'quantity': 50,
'from_warehouse_id': 'wh_east_01',
'from_location_id': 'loc_a1_shelf_3',
'to_warehouse_id': 'wh_west_01',
'to_location_id': 'loc_b2_shelf_1',
'transfer_reason': 'rebalancing',
'priority': 'standard',
'expected_arrival': '2024-01-20'
})
```
```ruby Ruby theme={null}
transfer = Stateset::Inventory.transfer({
inventory_item_id: 'inv_abc123',
quantity: 50,
from_warehouse_id: 'wh_east_01',
from_location_id: 'loc_a1_shelf_3',
to_warehouse_id: 'wh_west_01',
to_location_id: 'loc_b2_shelf_1',
transfer_reason: 'rebalancing',
priority: 'standard',
expected_arrival: '2024-01-20'
})
```
```go Go theme={null}
transfer, err := stateset.Inventory.transfer({
InventoryItemID: 'inv_abc123',
Quantity: 50,
FromWarehouseID: 'wh_east_01',
FromLocationID: 'loc_a1_shelf_3',
ToWarehouseID: 'wh_west_01',
ToLocationID: 'loc_b2_shelf_1',
TransferReason: 'rebalancing',
Priority: 'standard',
ExpectedArrival: '2024-01-20'
})
```
```java Java theme={null}
InventoryTransfer transfer = stateset.inventory.transfer({
inventoryItemId: 'inv_abc123',
quantity: 50,
fromWarehouseId: 'wh_east_01',
fromLocationId: 'loc_a1_shelf_3',
toWarehouseId: 'wh_west_01',
toLocationId: 'loc_b2_shelf_1',
transferReason: 'rebalancing',
priority: 'standard',
expectedArrival: '2024-01-20'
});
```
```php PHP theme={null}
$transfer = $stateset->inventory->transfer([
'inventory_item_id' => 'inv_abc123',
'quantity' => 50,
'from_warehouse_id' => 'wh_east_01',
'from_location_id' => 'loc_a1_shelf_3',
'to_warehouse_id' => 'wh_west_01',
'to_location_id' => 'loc_b2_shelf_1',
'transfer_reason' => 'rebalancing',
'priority' => 'standard',
'expected_arrival' => '2024-01-20'
]);
```
```csharp C# theme={null}
var transfer = await stateset.Inventory.Transfer(new {
InventoryItemId = 'inv_abc123',
Quantity = 50,
FromWarehouseId = 'wh_east_01',
FromLocationId = 'loc_a1_shelf_3',
ToWarehouseId = 'wh_west_01',
ToLocationId = 'loc_b2_shelf_1',
TransferReason = 'rebalancing',
Priority = 'standard',
ExpectedArrival = '2024-01-20'
});
```
```json Response theme={null}
{
"id": "trans_xyz456",
"transfer_number": "TRF-2024-0001",
"inventory_item_id": "inv_abc123",
"quantity": 50,
"from_warehouse": {
"id": "wh_east_01",
"name": "East Coast Warehouse",
"location_id": "loc_a1_shelf_3"
},
"to_warehouse": {
"id": "wh_west_01",
"name": "West Coast Warehouse",
"location_id": "loc_b2_shelf_1"
},
"transfer_reason": "rebalancing",
"priority": "standard",
"status": "in_transit",
"expected_arrival": "2024-01-20",
"created_at": "2024-01-15T10:00:00Z",
"created_by": "user_123",
"success": true
}
```
```json Error Response theme={null}
{
"error": {
"code": "insufficient_inventory",
"message": "Not enough inventory available for transfer. Available: 30, Requested: 50",
"details": {
"available_quantity": 30,
"requested_quantity": 50,
"warehouse_id": "wh_east_01"
}
}
}
```
# Update Inventory Item
Source: https://docs.stateset.com/api-reference/inventory/update
PUT https://api.stateset.com/v1/inventory_items/:id
This endpoint updates an existing inventory item.
### Body
This is the unique identifier for the inventory item.
This is the stock keeping unit (SKU) for the inventory item.
This is the description for the inventory item.
This is the size for the inventory item.
This is the number of items incoming for the inventory item.
This is the color for the inventory item.
This is the identifier for the warehouse for the inventory item.
This is the number of items available for the inventory item.
This is the date when the items are expected to arrive for the inventory item.
This is the identifier for the purchase order associated with the inventory item.
### Response
This is the unique identifier for the inventory item.
This is the stock keeping unit (SKU) for the inventory item.
This is the description for the inventory item.
This is the size for the inventory item.
This is the number of items incoming for the inventory item.
This is the color for the inventory item.
This is the identifier for the warehouse for the inventory item.
This is the number of items available for the inventory item.
This is the date when the items are expected to arrive for the inventory item.
This is the identifier for the purchase order associated with the inventory item.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/inventory_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation: gql`
mutation (
$id: String
$inventory_item: inventory_item_set_input!
) {
update_inventory_item (
where: { id : { _eq: $id }}
_set: $inventory_item
) {
returning {
id
sku
upc
description
size
color
incoming
warehouse
available
}
}
}
```
```javascript Node.js theme={null}
var updated = await stateset.inventoryItem.update({
id: "example_1",
inventory_item: {
name: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}
})
```
```python Python theme={null}
updated = stateset.inventory_item.modify(
id="example_1",
inventory_item={
"name": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}
)
```
```ruby Ruby theme={null}
updated = Stateset::InventoryItem.update(
id: "example_1",
inventory_item: {
name: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}
)
```
```php PHP theme={null}
$updated = $stateset->inventoryItem->update([
"id" => "example_1",
"inventory_item" => [
"name" => "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
]
]);
```
```go Golang theme={null}
inventory_item := stateset.InventoryItem{
Name: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}
updated, err := stateset.InventoryItem.Update(
"example_1",
inventory_item,
)
```
```java Java theme={null}
InventoryItem inventory_item = new InventoryItem();
inventory_item.setName("0901f083-aa1c-43c5-af5c-0a9d2fc64e30");
InventoryItem updated = stateset.inventoryItem.update(
"example_1",
inventory_item
);
```
```json Response theme={null}
{
"inventory_items": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "SKU-123",
"description": "This is a description",
"size": "Large",
"incoming": 10,
"color": "Red",
"warehouse": 1,
"available": 10,
"arriving": "2021-01-01",
"purchase_order_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
},
]
}
```
# Create Invoice
Source: https://docs.stateset.com/api-reference/invoices/create
POST https://api.stateset.com/v1/invoices
Create an invoice for billing customers
This endpoint creates a new invoice for billing customers. Invoices can be sent immediately or scheduled for future delivery.
## Authentication
This endpoint requires a valid API key with `invoices:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Customer ID to bill
Custom invoice number (auto-generated if not provided)
Invoice issue date (ISO 8601)
Payment due date (ISO 8601)
ISO 4217 currency code
Invoice line items
Item description
Quantity
Unit price in cents
Associated product ID
Tax rate as decimal (e.g., 0.08 for 8%)
Discount rate as decimal
Accounting code
Billing address
Street address
Apartment/Suite
City
State/Province
Postal code
Country code
Payment terms (e.g., "Net 30", "Due on receipt")
Invoice notes or memo
Whether to email invoice to customer (default: false)
Additional custom fields
### Response
Returns the created invoice.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/invoices' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"customer_id": "cust_abc123",
"issue_date": "2024-01-19",
"due_date": "2024-02-18",
"currency": "USD",
"line_items": [
{
"description": "Professional Services - January 2024",
"quantity": 40,
"unit_price": 15000,
"tax_rate": 0.08
},
{
"description": "Software License",
"quantity": 5,
"unit_price": 9900,
"product_id": "prod_xyz789"
}
],
"payment_terms": "Net 30",
"send_email": true
}'
```
```javascript Node.js theme={null}
const invoice = await stateset.invoices.create({
customer_id: "cust_abc123",
issue_date: "2024-01-19",
due_date: "2024-02-18",
currency: "USD",
line_items: [
{
description: "Professional Services - January 2024",
quantity: 40,
unit_price: 15000,
tax_rate: 0.08
},
{
description: "Software License",
quantity: 5,
unit_price: 9900,
product_id: "prod_xyz789"
}
],
payment_terms: "Net 30",
send_email: true
});
```
```json Response theme={null}
{
"id": "inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "invoice",
"invoice_number": "INV-2024-0001",
"status": "sent",
"customer_id": "cust_abc123",
"issue_date": "2024-01-19",
"due_date": "2024-02-18",
"currency": "USD",
"subtotal": 649500,
"tax_amount": 48000,
"total_amount": 697500,
"amount_due": 697500,
"amount_paid": 0,
"line_items": [
{
"id": "li_123456",
"description": "Professional Services - January 2024",
"quantity": 40,
"unit_price": 15000,
"amount": 600000,
"tax_rate": 0.08,
"tax_amount": 48000
},
{
"id": "li_123457",
"description": "Software License",
"quantity": 5,
"unit_price": 9900,
"amount": 49500,
"product_id": "prod_xyz789",
"tax_rate": 0,
"tax_amount": 0
}
],
"payment_terms": "Net 30",
"created_at": "2024-01-19T10:00:00Z",
"sent_at": "2024-01-19T10:01:00Z",
"pdf_url": "https://invoices.stateset.com/inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30.pdf"
}
```
# Get Invoice
Source: https://docs.stateset.com/api-reference/invoices/get
GET https://api.stateset.com/v1/invoices/:id
Retrieve a specific invoice by ID
This endpoint retrieves detailed information about a specific invoice including line items, payments, and status.
## Authentication
This endpoint requires a valid API key with `invoices:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the invoice
## Query Parameters
Expand related objects. Options: "customer", "payments", "credit\_notes", "events"
### Response
Unique invoice identifier
Object type, always "invoice"
Human-readable invoice number
Invoice status: "draft", "sent", "viewed", "partially\_paid", "paid", "overdue", "voided"
Total invoice amount in cents
Outstanding amount in cents
Array of invoice line items
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/invoices/inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const invoice = await stateset.invoices.retrieve(
'inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
invoice = stateset.invoices.retrieve(
'inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "invoice",
"invoice_number": "INV-2024-0001",
"status": "sent",
"customer_id": "cust_abc123",
"customer": {
"id": "cust_abc123",
"name": "Acme Corporation",
"email": "billing@acme.com"
},
"issue_date": "2024-01-19",
"due_date": "2024-02-18",
"currency": "USD",
"subtotal": 649500,
"tax_amount": 48000,
"discount_amount": 0,
"total_amount": 697500,
"amount_paid": 0,
"amount_due": 697500,
"line_items": [
{
"id": "li_123456",
"description": "Professional Services - January 2024",
"quantity": 40,
"unit_price": 15000,
"amount": 600000,
"tax_rate": 0.08,
"tax_amount": 48000,
"account_code": "4000"
},
{
"id": "li_123457",
"description": "Software License",
"quantity": 5,
"unit_price": 9900,
"amount": 49500,
"product_id": "prod_xyz789",
"tax_rate": 0,
"tax_amount": 0,
"account_code": "4100"
}
],
"billing_address": {
"line1": "123 Business St",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"payment_terms": "Net 30",
"notes": "Thank you for your business!",
"created_at": "2024-01-19T10:00:00Z",
"sent_at": "2024-01-19T10:01:00Z",
"viewed_at": "2024-01-19T14:30:00Z",
"pdf_url": "https://invoices.stateset.com/inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30.pdf",
"public_url": "https://pay.stateset.com/inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"metadata": {
"po_number": "PO-12345",
"project_code": "PROJ-2024-001"
}
}
```
# List Invoices
Source: https://docs.stateset.com/api-reference/invoices/list
GET https://api.stateset.com/v1/invoices
List all invoices with filtering and pagination
This endpoint retrieves a paginated list of invoices. Use filters to narrow results by status, customer, date range, and more.
## Authentication
This endpoint requires a valid API key with `invoices:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of items to return (default: 20, max: 100)
Cursor for pagination (invoice ID)
Filter by status: "draft", "sent", "viewed", "partially\_paid", "paid", "overdue", "voided"
Filter by customer ID
Filter by issue date start (YYYY-MM-DD)
Filter by issue date end (YYYY-MM-DD)
Filter by due date start (YYYY-MM-DD)
Filter by due date end (YYYY-MM-DD)
Show only overdue invoices
Sort field: "created\_at", "issue\_date", "due\_date", "total\_amount"
Sort order: "asc" or "desc" (default: "desc")
### Response
Object type, always "list"
Array of invoice objects
Whether more items exist
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/invoices?status=sent&limit=10' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const invoices = await stateset.invoices.list({
status: 'sent',
limit: 10,
overdue_only: false
});
```
```python Python theme={null}
invoices = stateset.invoices.list(
status='sent',
limit=10,
overdue_only=False
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "invoice",
"invoice_number": "INV-2024-0001",
"status": "sent",
"customer_id": "cust_abc123",
"customer_name": "Acme Corporation",
"issue_date": "2024-01-19",
"due_date": "2024-02-18",
"currency": "USD",
"total_amount": 697500,
"amount_due": 697500,
"days_until_due": 30
},
{
"id": "inv_7823f083-bb2c-54d6-bf6d-1b8e3fc75f41",
"object": "invoice",
"invoice_number": "INV-2024-0002",
"status": "partially_paid",
"customer_id": "cust_def456",
"customer_name": "TechCorp Inc",
"issue_date": "2024-01-15",
"due_date": "2024-01-30",
"currency": "USD",
"total_amount": 125000,
"amount_due": 50000,
"days_until_due": 11
}
],
"has_more": true,
"url": "/v1/invoices"
}
```
# Send Invoice
Source: https://docs.stateset.com/api-reference/invoices/send
POST https://api.stateset.com/v1/invoices/:id/send
Send an invoice to the customer via email
This endpoint sends an invoice to the customer via email. The invoice must be in draft or sent status.
## Authentication
This endpoint requires a valid API key with `invoices:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the invoice to send
## Request Body
Email addresses to send to (defaults to customer email)
CC email addresses
BCC email addresses
Custom email subject (defaults to "Invoice \[number] from \[company]")
Custom email message
Whether to attach PDF (default: true)
### Response
Returns the sent invoice with email details.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/invoices/inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/send' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"cc": ["accounting@acme.com"],
"message": "Please find attached invoice for January services. Let me know if you have any questions."
}'
```
```javascript Node.js theme={null}
const invoice = await stateset.invoices.send(
'inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
cc: ["accounting@acme.com"],
message: "Please find attached invoice for January services. Let me know if you have any questions."
}
);
```
```python Python theme={null}
invoice = stateset.invoices.send(
'inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
cc=["accounting@acme.com"],
message="Please find attached invoice for January services. Let me know if you have any questions."
)
```
```json Response theme={null}
{
"id": "inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "invoice",
"status": "sent",
"sent_at": "2024-01-20T12:00:00Z",
"email_details": {
"sent_to": ["billing@acme.com"],
"cc": ["accounting@acme.com"],
"subject": "Invoice INV-2024-0001 from Stateset",
"message": "Please find attached invoice for January services. Let me know if you have any questions.",
"attachments": ["invoice_INV-2024-0001.pdf"]
},
"sent_count": 1,
"last_sent_at": "2024-01-20T12:00:00Z",
"next_reminder_date": "2024-01-27T12:00:00Z"
}
```
# Update Invoice
Source: https://docs.stateset.com/api-reference/invoices/update
PUT https://api.stateset.com/v1/invoices/:id
Update an existing invoice
This endpoint updates an existing invoice. Only draft invoices can have their line items modified. Sent invoices can only update certain fields.
## Authentication
This endpoint requires a valid API key with `invoices:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the invoice
## Request Body
Update due date (YYYY-MM-DD)
Update payment terms
Update invoice notes
Update line items (draft invoices only)
Update billing address
Update custom fields
### Response
Returns the updated invoice object.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/invoices/inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"due_date": "2024-02-28",
"payment_terms": "Net 45",
"notes": "Updated payment terms as discussed"
}'
```
```javascript Node.js theme={null}
const invoice = await stateset.invoices.update(
'inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
due_date: "2024-02-28",
payment_terms: "Net 45",
notes: "Updated payment terms as discussed"
}
);
```
```python Python theme={null}
invoice = stateset.invoices.update(
'inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
due_date="2024-02-28",
payment_terms="Net 45",
notes="Updated payment terms as discussed"
)
```
```json Response theme={null}
{
"id": "inv_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "invoice",
"invoice_number": "INV-2024-0001",
"status": "sent",
"updated_at": "2024-01-20T11:00:00Z",
"due_date": "2024-02-28",
"payment_terms": "Net 45",
"notes": "Updated payment terms as discussed",
"total_amount": 697500,
"amount_due": 697500,
"days_until_due": 40
}
```
# Accept Lead
Source: https://docs.stateset.com/api-reference/leads/accept
POST https://api.stateset.com/v1/leads/:id/accept
This endpoint accepts an existing lead.
### Body
The ID provided in the data tab may be used to identify the lead
### Response
The ID provided in the data tab may be used to identify the lead
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/leads/:id/accept' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation leadAcceptMutation {
leadAccept (id: "${leadId}") {
leads {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const leads = await stateset.leads.accept({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
leads = stateset.leads.accept({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
leads = Stateset::Lead.accept({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
leads, err := stateset.leads.accept({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Lead leads = stateset.leads.accept({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$leads = $stateset->leads->accept({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var leads = await stateset.leads.accept({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "lead",
"accepted": true
}
```
# Convert Lead
Source: https://docs.stateset.com/api-reference/leads/convert
POST https://api.stateset.com/v1/leads/:id/convert
Convert a qualified lead into a customer account
Converting a lead creates an associated customer and/or account record and marks the lead as converted. This action cannot be undone — use the [unconvert endpoint](/api-reference/leads/unconvert) to reverse it.
## Path Parameters
The unique identifier of the lead to convert.
**Example:** `e0901f08-3aa1-43c5-af5c-0a9d2fc64e30`
## Request Body
Whether to create an associated account record during conversion.
Whether to create an associated customer record during conversion.
Override the owner for the newly created account/customer records.
### Response
The ID of the converted lead.
Object type. Always `lead`.
Whether the lead was successfully converted.
Updated lead status. Will be `converted`.
The ID of the newly created customer record (if `create_customer` was true).
The ID of the newly created account record (if `create_account` was true).
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/leads/e0901f08-3aa1-43c5-af5c-0a9d2fc64e30/convert' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer ' \
--data-raw '{
"create_account": true,
"create_customer": true
}'
```
```graphql GraphQL theme={null}
mutation convertLead($id: uuid!) {
leadConvert(id: $id) {
leads {
id
status
}
userErrors {
field
message
}
}
}
```
```javascript Node.js theme={null}
const result = await stateset.leads.convert(
'e0901f08-3aa1-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
result = stateset.leads.convert(
'e0901f08-3aa1-43c5-af5c-0a9d2fc64e30'
)
```
```ruby Ruby theme={null}
result = Stateset::Lead.convert(
'e0901f08-3aa1-43c5-af5c-0a9d2fc64e30'
)
```
```go Go theme={null}
result, err := stateset.Leads.Convert(
"e0901f08-3aa1-43c5-af5c-0a9d2fc64e30",
)
```
```java Java theme={null}
LeadConvertResult result = stateset.leads().convert(
"e0901f08-3aa1-43c5-af5c-0a9d2fc64e30"
);
```
```php PHP theme={null}
$result = $stateset->leads->convert(
'e0901f08-3aa1-43c5-af5c-0a9d2fc64e30'
);
```
```json Response theme={null}
{
"id": "e0901f08-3aa1-43c5-af5c-0a9d2fc64e30",
"object": "lead",
"converted": true,
"status": "converted",
"customer_id": "cust_7b2f4a91-d3e5-4c8a-b1f0-9e6d3c5a7b2f",
"account_id": "acct_3d1e8f72-a5b6-4c9d-8e0f-1a2b3c4d5e6f"
}
```
```json Error Response (404 Not Found) theme={null}
{
"error": {
"code": "RESOURCE_NOT_FOUND",
"message": "Lead not found",
"details": {
"resource": "lead",
"id": "e0901f08-3aa1-43c5-af5c-0a9d2fc64e30"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (409 Conflict) theme={null}
{
"error": {
"code": "ALREADY_CONVERTED",
"message": "This lead has already been converted",
"details": {
"lead_id": "e0901f08-3aa1-43c5-af5c-0a9d2fc64e30",
"converted_at": "2024-06-10T14:30:00.000Z"
},
"request_id": "req_abc123def456"
}
}
```
# Create Lead
Source: https://docs.stateset.com/api-reference/leads/create
POST https://api.stateset.com/v1/leads
Create a new lead record in the CRM pipeline
Creates a lead that can be tracked, engaged, and converted into a customer or account.
## Request Body
First name of the lead.
**Example:** `Sarah`
Last name of the lead.
**Example:** `Johnson`
Email address of the lead. Must be unique.
**Example:** `sarah.johnson@company.com`
Phone number of the lead.
**Example:** `+1-555-234-5678`
Job title or position.
**Example:** `VP of Operations`
Department or division.
**Example:** `Operations`
Source or origin of the lead.
**Options:** `website`, `referral`, `trade_show`, `cold_call`, `social_media`, `partner`, `other`
Additional details or notes about the lead.
Street address.
City.
State or province.
Country.
Whether the lead should not be contacted by phone.
Whether the lead has opted out of email communication.
### Response
Unique identifier for the created lead.
Object type. Always `lead`.
First name of the lead.
Last name of the lead.
Email address of the lead.
Phone number of the lead.
Job title of the lead.
Source of the lead.
Current status of the lead. Starts as `new`.
ISO 8601 timestamp when the lead was created.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/leads' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer ' \
--data-raw '{
"firstName": "Sarah",
"lastName": "Johnson",
"email": "sarah.johnson@company.com",
"phone": "+1-555-234-5678",
"title": "VP of Operations",
"department": "Operations",
"leadSource": "website",
"description": "Interested in returns automation"
}'
```
```graphql GraphQL theme={null}
mutation createLead($input: LeadInput!) {
insert_leads_one(object: $input) {
id
firstName
lastName
email
phone
title
leadSource
status
created_at
}
}
```
```javascript Node.js theme={null}
const lead = await stateset.leads.create({
firstName: 'Sarah',
lastName: 'Johnson',
email: 'sarah.johnson@company.com',
phone: '+1-555-234-5678',
title: 'VP of Operations',
leadSource: 'website',
});
```
```python Python theme={null}
lead = stateset.leads.create(
first_name='Sarah',
last_name='Johnson',
email='sarah.johnson@company.com',
phone='+1-555-234-5678',
title='VP of Operations',
lead_source='website',
)
```
```ruby Ruby theme={null}
lead = Stateset::Lead.create(
firstName: 'Sarah',
lastName: 'Johnson',
email: 'sarah.johnson@company.com',
phone: '+1-555-234-5678',
title: 'VP of Operations',
leadSource: 'website',
)
```
```go Go theme={null}
lead, err := stateset.Leads.Create(&LeadCreateParams{
FirstName: "Sarah",
LastName: "Johnson",
Email: "sarah.johnson@company.com",
Phone: "+1-555-234-5678",
Title: "VP of Operations",
LeadSource: "website",
})
```
```json Response theme={null}
{
"id": "e0901f08-3aa1-43c5-af5c-0a9d2fc64e30",
"object": "lead",
"firstName": "Sarah",
"lastName": "Johnson",
"email": "sarah.johnson@company.com",
"phone": "+1-555-234-5678",
"title": "VP of Operations",
"department": "Operations",
"leadSource": "website",
"status": "new",
"description": "Interested in returns automation",
"created_at": "2024-06-15T10:30:00.000Z"
}
```
```json Error Response (409 Conflict) theme={null}
{
"error": {
"code": "DUPLICATE_RESOURCE",
"message": "A lead with this email already exists",
"details": {
"field": "email",
"value": "sarah.johnson@company.com"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (422 Validation Error) theme={null}
{
"error": {
"code": "VALIDATION_ERROR",
"message": "Required fields are missing",
"details": {
"missing_fields": ["firstName", "email"]
},
"request_id": "req_abc123def456"
}
}
```
# Delete Lead
Source: https://docs.stateset.com/api-reference/leads/delete
Delete a lead by ID.
# Delete Lead
Use this endpoint to delete a lead by ID.
# Engage Lead
Source: https://docs.stateset.com/api-reference/leads/engage
POST https://api.stateset.com/v1/leads/:id/engage
This endpoint engages an existing lead.
### Body
The ID provided in the data tab may be used to identify the lead
### Response
The ID provided in the data tab may be used to identify the lead
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/leads/:id/engages' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation leadEngageMutation {
leadEngage (id: "${leadId}") {
leads {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const leads = await stateset.leads.engage({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
leads = stateset.leads.engage({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
leads = Stateset::Lead.engage({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
leads, err := stateset.leads.engage({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Lead leads = stateset.leads.engage({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$leads = $stateset->leads->engage({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var leads = await stateset.leads.engage({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "lead",
"engaged": true
}
```
# Retrieve Lead
Source: https://docs.stateset.com/api-reference/leads/get
GET https://api.stateset.com/v1/leads/:id/retrieve
This endpoint retrieves a lead
### Body
The ID of the user group to which the lead belongs.
### Response
The ID of the lead.
Name or details of the assistant associated with the lead.
Phone number of the assistant.
URL or path to the lead's avatar image.
Date of birth of the lead.
Name or details of the controller associated with the lead.
Date and time when the lead was created.
Name or details of the person who created the lead.
Department or division associated with the lead.
Description or additional details about the lead.
Indicates whether the lead should not be called.
Email address of the lead.
Indicates whether the lead has opted out of email communication.
Fax number of the lead.
Indicates whether the lead has opted out of fax communication.
First name of the lead.
Handle or username associated with the lead.
Indicates whether the lead is marked as invalid.
Languages known or spoken by the lead.
Last name of the lead.
Last person who modified the lead.
Source or origin of the lead/lead.
City of the mailing address.
Country of the mailing address.
Geocoding accuracy of the mailing address.
State or province of the mailing address.
Street of the mailing address.
Name or details of the owner of the lead.
Phone number of the lead.
URL or path to the lead's photo.
Name or details of the processor associated with the lead.
Title or position of the lead.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/leads/retrieve' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
leads(limit: $limit, offset: $offset, order_by: {created_date: $order_direction}) {
```
```js Node.js theme={null}
const leads = await stateset.leads.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
leads = stateset.leads.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
leads, err := stateset.leads.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
leads = Stateset::leads.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
leads leads = Stateset.leads.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
leads leads = Stateset.leads.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$leads = Stateset\leads::retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/return HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
# List Leads
Source: https://docs.stateset.com/api-reference/leads/list
GET https://api.stateset.com/v1/leads
This endpoint list leads.
### Body
The ID of the user group to which the lead belongs.
### Response
The ID of the lead.
Name or details of the assistant associated with the lead.
Phone number of the assistant.
URL or path to the lead's avatar image.
Date of birth of the lead.
Name or details of the controller associated with the lead.
Date and time when the lead was created.
Name or details of the person who created the lead.
Department or division associated with the lead.
Description or additional details about the lead.
Indicates whether the lead should not be called.
Email address of the lead.
Indicates whether the lead has opted out of email communication.
Fax number of the lead.
Indicates whether the lead has opted out of fax communication.
First name of the lead.
Handle or username associated with the lead.
Indicates whether the lead is marked as invalid.
Languages known or spoken by the lead.
Last name of the lead.
Last person who modified the lead.
Source or origin of the lead/lead.
City of the mailing address.
Country of the mailing address.
Geocoding accuracy of the mailing address.
State or province of the mailing address.
Street of the mailing address.
Name or details of the owner of the lead.
Phone number of the lead.
URL or path to the lead's photo.
Name or details of the processor associated with the lead.
Title or position of the lead.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/leads' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
# Reject Lead
Source: https://docs.stateset.com/api-reference/leads/reject
POST https://api.stateset.com/v1/leads/:id/reject
This endpoint rejects an existing lead.
### Body
The ID provided in the data tab may be used to identify the lead
### Response
The ID provided in the data tab may be used to identify the lead
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/leads/:id/reject' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation leadRejectMutation {
leadReject (id: "${leadId}") {
leads {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const leads = await stateset.leads.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
leads = stateset.leads.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
leads = Stateset::Lead.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
leads, err := stateset.leads.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Lead leads = stateset.leads.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$leads = $stateset->leads->reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var leads = await stateset.leads.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "lead",
"rejected": true
}
```
# UnConvert Lead
Source: https://docs.stateset.com/api-reference/leads/unconvert
POST https://api.stateset.com/v1/leads/:id/unconvert
This endpoint converts an existing lead.
### Body
The ID provided in the data tab may be used to identify the lead
### Response
The ID provided in the data tab may be used to identify the lead
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/leads/:id/unconvert' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation leadUnConvertMutation {
leadUnConvert (id: "${leadId}") {
leads {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const leads = await stateset.leads.unconvert({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
leads = stateset.leads.unconvert({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
leads = Stateset::Lead.unconvert({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
leads, err := stateset.leads.unconvert({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Lead leads = stateset.leads.unconvert({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$leads = $stateset->leads->unconvert({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var leads = await stateset.leads.unconvert({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "lead",
"unconverted": true
}
```
# Create Location
Source: https://docs.stateset.com/api-reference/locations/create
POST https://api.stateset.com/v1/locations
Create a new warehouse or store location
This endpoint creates a new location for inventory management. Locations can be warehouses, stores, or distribution centers.
## Authentication
This endpoint requires a valid API key with `locations:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Location name
Unique location code (e.g., "WH-001", "STORE-NYC-01")
Location type: "warehouse", "store", "distribution\_center", "dropship"
Location address
Street address
Additional address info
City
State/Province code
Postal/ZIP code
ISO 3166-1 alpha-2 country code
Contact information
Contact person name
Contact email
Contact phone
Operating hours
Monday hours with open/close times
Tuesday hours
Wednesday hours
Thursday hours
Friday hours
Saturday hours
Sunday hours
Location capabilities: "storage", "fulfillment", "returns", "cross\_dock", "pickup"
Storage capacity information
Total square footage
Number of storage units/bins
Number of pallet positions
Location timezone (e.g., "America/Los\_Angeles")
Whether location is active (default: true)
Additional custom fields
### Response
Returns the created location.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/locations' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"name": "West Coast Distribution Center",
"code": "WH-WEST-01",
"type": "warehouse",
"address": {
"line1": "1000 Distribution Way",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
},
"contact": {
"name": "John Smith",
"email": "john.smith@warehouse.com",
"phone": "+1-555-123-4567"
},
"capabilities": ["storage", "fulfillment", "returns"],
"capacity": {
"total_sqft": 50000,
"storage_units": 5000,
"pallet_positions": 2000
},
"timezone": "America/Los_Angeles"
}'
```
```javascript Node.js theme={null}
const location = await stateset.locations.create({
name: "West Coast Distribution Center",
code: "WH-WEST-01",
type: "warehouse",
address: {
line1: "1000 Distribution Way",
city: "Los Angeles",
state: "CA",
postal_code: "90001",
country: "US"
},
contact: {
name: "John Smith",
email: "john.smith@warehouse.com",
phone: "+1-555-123-4567"
},
capabilities: ["storage", "fulfillment", "returns"],
capacity: {
total_sqft: 50000,
storage_units: 5000,
pallet_positions: 2000
},
timezone: "America/Los_Angeles"
});
```
```json Response theme={null}
{
"id": "loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "location",
"name": "West Coast Distribution Center",
"code": "WH-WEST-01",
"type": "warehouse",
"status": "active",
"created_at": "2024-01-19T16:00:00Z",
"address": {
"line1": "1000 Distribution Way",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US",
"formatted": "1000 Distribution Way, Los Angeles, CA 90001, US"
},
"contact": {
"name": "John Smith",
"email": "john.smith@warehouse.com",
"phone": "+1-555-123-4567"
},
"capabilities": ["storage", "fulfillment", "returns"],
"capacity": {
"total_sqft": 50000,
"storage_units": 5000,
"pallet_positions": 2000,
"available_units": 4850,
"available_pallets": 1920
},
"operating_hours": {
"monday": { "open": "06:00", "close": "22:00" },
"tuesday": { "open": "06:00", "close": "22:00" },
"wednesday": { "open": "06:00", "close": "22:00" },
"thursday": { "open": "06:00", "close": "22:00" },
"friday": { "open": "06:00", "close": "22:00" },
"saturday": { "open": "08:00", "close": "18:00" },
"sunday": { "closed": true }
},
"timezone": "America/Los_Angeles",
"coordinates": {
"latitude": 34.0522,
"longitude": -118.2437
}
}
```
# Delete Location
Source: https://docs.stateset.com/api-reference/locations/delete
Delete a location by ID.
# Delete Location
Use this endpoint to delete a location by ID.
# Get Location
Source: https://docs.stateset.com/api-reference/locations/get
GET https://api.stateset.com/v1/locations/:id
Retrieve a specific location by ID
This endpoint retrieves detailed information about a specific location including capacity, inventory levels, and operational details.
## Authentication
This endpoint requires a valid API key with `locations:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the location
## Query Parameters
Expand related objects. Options: "inventory\_summary", "staff", "upcoming\_shipments"
### Response
Unique location identifier
Object type, always "location"
Location name
Location code
Location type
Capacity information with available space
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/locations/loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30?expand=inventory_summary' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const location = await stateset.locations.retrieve(
'loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{ expand: ['inventory_summary'] }
);
```
```python Python theme={null}
location = stateset.locations.retrieve(
'loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
expand=['inventory_summary']
)
```
```json Response theme={null}
{
"id": "loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "location",
"name": "West Coast Distribution Center",
"code": "WH-WEST-01",
"type": "warehouse",
"status": "active",
"created_at": "2024-01-19T16:00:00Z",
"updated_at": "2024-01-20T08:00:00Z",
"address": {
"line1": "1000 Distribution Way",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US",
"formatted": "1000 Distribution Way, Los Angeles, CA 90001, US"
},
"contact": {
"name": "John Smith",
"email": "john.smith@warehouse.com",
"phone": "+1-555-123-4567"
},
"capabilities": ["storage", "fulfillment", "returns"],
"capacity": {
"total_sqft": 50000,
"storage_units": 5000,
"pallet_positions": 2000,
"available_units": 4850,
"available_pallets": 1920,
"utilization_percent": 4.0
},
"operating_hours": {
"monday": { "open": "06:00", "close": "22:00" },
"tuesday": { "open": "06:00", "close": "22:00" },
"wednesday": { "open": "06:00", "close": "22:00" },
"thursday": { "open": "06:00", "close": "22:00" },
"friday": { "open": "06:00", "close": "22:00" },
"saturday": { "open": "08:00", "close": "18:00" },
"sunday": { "closed": true }
},
"timezone": "America/Los_Angeles",
"coordinates": {
"latitude": 34.0522,
"longitude": -118.2437
},
"inventory_summary": {
"total_skus": 1250,
"total_units": 125000,
"total_value": 2500000,
"low_stock_alerts": 15,
"out_of_stock": 3
},
"metrics": {
"orders_fulfilled_today": 45,
"orders_fulfilled_week": 312,
"average_fulfillment_time": "2.5 hours",
"accuracy_rate": 99.7
}
}
```
# List Locations
Source: https://docs.stateset.com/api-reference/locations/list
GET https://api.stateset.com/v1/locations
List all locations with filtering and pagination
This endpoint retrieves a paginated list of locations. Use filters to narrow results by type, capabilities, and status.
## Authentication
This endpoint requires a valid API key with `locations:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of items to return (default: 20, max: 100)
Number of items to skip
Filter by type: "warehouse", "store", "distribution\_center", "dropship"
Filter by status: "active", "inactive", "maintenance"
Filter by capabilities: "storage", "fulfillment", "returns", "cross\_dock", "pickup"
Filter by country code
Filter by state/province
Filter by city
Sort field: "created\_at", "name", "code", "capacity"
Sort order: "asc" or "desc"
### Response
Object type, always "list"
Array of location objects
Whether more items exist
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/locations?type=warehouse&status=active' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const locations = await stateset.locations.list({
type: 'warehouse',
status: 'active',
capabilities: ['fulfillment']
});
```
```python Python theme={null}
locations = stateset.locations.list(
type='warehouse',
status='active',
capabilities=['fulfillment']
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "location",
"name": "West Coast Distribution Center",
"code": "WH-WEST-01",
"type": "warehouse",
"status": "active",
"address": {
"city": "Los Angeles",
"state": "CA",
"country": "US"
},
"capabilities": ["storage", "fulfillment", "returns"],
"capacity": {
"utilization_percent": 4.0,
"available_units": 4850
}
},
{
"id": "loc_7823f083-bb2c-54d6-bf6d-1b8e3fc75f41",
"object": "location",
"name": "East Coast Fulfillment Center",
"code": "WH-EAST-01",
"type": "warehouse",
"status": "active",
"address": {
"city": "Newark",
"state": "NJ",
"country": "US"
},
"capabilities": ["storage", "fulfillment", "cross_dock"],
"capacity": {
"utilization_percent": 65.0,
"available_units": 1750
}
}
],
"has_more": true,
"total_count": 8
}
```
# Update Location
Source: https://docs.stateset.com/api-reference/locations/update
PUT https://api.stateset.com/v1/locations/:id
Update location information
This endpoint updates location details including contact information, operating hours, and capabilities.
## Authentication
This endpoint requires a valid API key with `locations:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the location
## Request Body
Update location name
Update contact information
Update operating hours
Update location capabilities
Update capacity information
Update active status
Update custom fields
### Response
Returns the updated location object.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/locations/loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"contact": {
"name": "Jane Doe",
"email": "jane.doe@warehouse.com",
"phone": "+1-555-987-6543"
},
"capabilities": ["storage", "fulfillment", "returns", "pickup"]
}'
```
```javascript Node.js theme={null}
const location = await stateset.locations.update(
'loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
contact: {
name: "Jane Doe",
email: "jane.doe@warehouse.com",
phone: "+1-555-987-6543"
},
capabilities: ["storage", "fulfillment", "returns", "pickup"]
}
);
```
```python Python theme={null}
location = stateset.locations.update(
'loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
contact={
"name": "Jane Doe",
"email": "jane.doe@warehouse.com",
"phone": "+1-555-987-6543"
},
capabilities=["storage", "fulfillment", "returns", "pickup"]
)
```
```json Response theme={null}
{
"id": "loc_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "location",
"updated_at": "2024-01-20T13:00:00Z",
"name": "West Coast Distribution Center",
"code": "WH-WEST-01",
"contact": {
"name": "Jane Doe",
"email": "jane.doe@warehouse.com",
"phone": "+1-555-987-6543"
},
"capabilities": ["storage", "fulfillment", "returns", "pickup"],
"status": "active"
}
```
# Create Manufacture Order
Source: https://docs.stateset.com/api-reference/manufactureorder/create
POST https://api.stateset.com/v1/manufacture_orders
This endpoint creates a new manufacture order
### Body
Unique identifier for the manufacture order
Additional notes or information about the manufacture order
Number assigned to the manufacture order
Priority level of the manufacture order
Site or location associated with the manufacture order
Location where the manufactured product will be stored
Date and time when the manufacture order was created
Expected date of completion for the manufacture order
Date when the manufacture order was issued
### Response
Unique identifier for the manufacture order
Additional notes or information about the manufacture order
Number assigned to the manufacture order
Priority level of the manufacture order
Site or location associated with the manufacture order
Location where the manufactured product will be stored
Date and time when the manufacture order was created
Expected date of completion for the manufacture order
Date when the manufacture order was issued
Name of the bill of materials (BOM) associated with the line item
Number assigned to the bill of materials (BOM)
Unique identifier for the line item
Expected date for the completion of the line item
Status of the line item (e.g., in progress, completed, etc.)
Type or category of the line item
Number of the associated manufacture order
Type of output produced by the line item (e.g., product, component)
Name of the part associated with the line item
Number assigned to the part associated with the line item
Priority level of the line item
Quantity of the part to be manufactured or processed
Site or location associated with the line item
Number of the associated work order
Location of the yield of the manufacture order line item
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/manufacture_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```js Node.js theme={null}
const created = await stateset.manufactureorder.create(
'mo_ODkRWQtx9NVsRX'
);
```
```graphQL GraphQL theme={null}
mutation addManufactureOrderLineItem($manufacture_order_line_item: manufacture_order_line_items_insert_input!) {
insert_manufacture_order_line_items(objects: [$manufacture_order_line_item]) {
returning {
id
}
}
}
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Delete Manufacture Order
Source: https://docs.stateset.com/api-reference/manufactureorder/delete
DELETE https://api.stateset.com/v1/manufacture_orders/:id
This endpoint deletes an existing manufacturer order.
### Body
The ID provided in the data tab may be used to identify the manufacture order
### Response
The ID provided in the data tab may be used to identify the manufacture order
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/manufacture_orders/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "mo_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteManufactureOrder ($id: String!) {
delete_manufacture_orders(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const manufactureorders = await stateset.manufactureorders.del({
'mo_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
manufactureorders = stateset.manufactureorders.del({
'mo_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
manufactureorders, err := stateset.manufactureorders.Del(
"mo_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Return manufactureorders = stateset.manufactureorders.del(
"mo_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const manufactureorders = await stateset.manufactureorders.del({
'mo_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
manufactureorders = Stateset::Return.del({
'mo_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$manufactureorder = $stateset->manufactureorder->del(
'mo_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
DELETE /v1/manufacture_orders HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "mo_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"deleted": true
}
```
# Get Manufacture Order
Source: https://docs.stateset.com/api-reference/manufactureorder/get
GET https://api.stateset.com/v1/manufacture_orders/:id
This endpoint gets or creates a new manufacture order.
### Body
Unique identifier for the manufacture order
### Response
Unique identifier for the manufacture order
Additional notes or information about the manufacture order
Number assigned to the manufacture order
Priority level of the manufacture order
Site or location associated with the manufacture order
Location where the manufactured product will be stored
Date and time when the manufacture order was created
Expected date of completion for the manufacture order
Date when the manufacture order was issued
Name of the bill of materials (BOM) associated with the line item
Number assigned to the bill of materials (BOM)
Unique identifier for the line item
Expected date for the completion of the line item
Status of the line item (e.g., in progress, completed, etc.)
Type or category of the line item
Number of the associated manufacture order
Type of output produced by the line item (e.g., product, component)
Name of the part associated with the line item
Number assigned to the part associated with the line item
Priority level of the line item
Quantity of the part to be manufactured or processed
Site or location associated with the line item
Number of the associated work order
Location of the yield of the manufacture order line item
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/manufacture_orders/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"id": "b1b1b1b1-b1b1-b1b1-b1b1-b1b1b1b1b1b1",
"memo": "This is a manufacture order",
"number": "MO-0001",
"priority": "High",
"site": "Site 1",
"yield_location": "Location 1",
"created_on": "2021-01-01T00:00:00.000000Z",
"expected_completion_date": "2021-01-01",
"issued_on": "2021-01-01",
"manufacture_order_line_items": [
{
"bom_name": "BOM 1",
"bom_number": "BOM-0001",
"id": "b1b1b1b1-b1b1-b1b1-b1b1-b1b1b1b1b1b1",
"expected_date": "2021-01-01",
"line_status": "In Progress",
"line_type": "Manufacture",
"manufacture_order_number": "MO-0001",
"output_type": "Product",
"part_name": "Part 1",
"part_number": "PART-0001",
"priority": "High",
"quantity": 100,
"site": "Site 1",
"work_order_number": "WO-0001",
"yield_location": "Location 1"
}
]
}
]
}
}
```
## Manufacture Order
| Field | Type | Description |
| -------------------------- | -------- | ----------------------------------------------------------- |
| id | String | Unique identifier for the manufacture order |
| memo | String | Additional notes or information about the manufacture order |
| number | String | Number assigned to the manufacture order |
| priority | String | Priority level of the manufacture order |
| site | String | Site or location associated with the manufacture order |
| yield\_location | String | Location where the manufactured product will be stored |
| created\_on | DateTime | Date and time when the manufacture order was created |
| expected\_completion\_date | Date | Expected date of completion for the manufacture order |
| issued\_on | Date | Date when the manufacture order was issued |
## Manufacture Order Line Item
| Field | Type | Description |
| -------------------------- | ------- | ------------------------------------------------------------------- |
| bom\_name | String | Name of the bill of materials (BOM) associated with the line item |
| bom\_number | String | Number assigned to the bill of materials (BOM) |
| id | String | Unique identifier for the line item |
| expected\_date | Date | Expected date for the completion of the line item |
| line\_status | String | Status of the line item (e.g., in progress, completed, etc.) |
| line\_type | String | Type or category of the line item |
| manufacture\_order\_number | String | Number of the associated manufacture order |
| output\_type | String | Type of output produced by the line item (e.g., product, component) |
| part\_name | String | Name of the part associated with the line item |
| part\_number | String | Number assigned to the part associated with the line item |
| priority | String | Priority level of the line item |
| quantity | Integer | Quantity of the part to be manufactured or processed |
| site | String | Site or location associated with the line item |
| work\_order\_number | String | Number of the associated work order |
| yield\_location | String | Location where the manufactured product will be stored |
# List Manufacture Orders
Source: https://docs.stateset.com/api-reference/manufactureorder/list
GET https://api.stateset.com/v1/manufacture_orders/list
This endpoint list manufacture orders.
### Body
This is the limit of the manufacture orders.
This is the offset of the manufacture orders.
This is the order direction of the manufacture orders.
### Response
Unique identifier for the manufacture order
Additional notes or information about the manufacture order
Number assigned to the manufacture order
Priority level of the manufacture order
Site or location associated with the manufacture order
Location where the manufactured product will be stored
Date and time when the manufacture order was created
Expected date of completion for the manufacture order
Date when the manufacture order was issued
Name of the bill of materials (BOM) associated with the line item
Number assigned to the bill of materials (BOM)
Unique identifier for the line item
Expected date for the completion of the line item
Status of the line item (e.g., in progress, completed, etc.)
Type or category of the line item
Number of the associated manufacture order
Type of output produced by the line item (e.g., product, component)
Name of the part associated with the line item
Number assigned to the part associated with the line item
Priority level of the line item
Quantity of the part to be manufactured or processed
Site or location associated with the line item
Number of the associated work order
Location of the yield of the manufacture order line item
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/manufacture_orders' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "ASC"
}'
```
```json Response theme={null}
{
{
"count": 1,
"next": null,
"previous": null,
"results": [
{
"id": "b1b1b1b1-b1b1-b1b1-b1b1-b1b1b1b1b1b1",
"memo": "This is a manufacture order",
"number": "MO-0001",
"priority": "High",
"site": "Site 1",
"yield_location": "Location 1",
"created_on": "2021-01-01T00:00:00.000000Z",
"expected_completion_date": "2021-01-01",
"issued_on": "2021-01-01",
"manufacture_order_line_items": [
{
"bom_name": "BOM 1",
"bom_number": "BOM-0001",
"id": "b1b1b1b1-b1b1-b1b1-b1b1-b1b1b1b1b1b1",
"expected_date": "2021-01-01",
"line_status": "In Progress",
"line_type": "Manufacture",
"manufacture_order_number": "MO-0001",
"output_type": "Product",
"part_name": "Part 1",
"part_number": "PART-0001",
"priority": "High",
"quantity": 100,
"site": "Site 1",
"work_order_number": "WO-0001",
"yield_location": "Location 1"
}
]
}
]
}
}
```
# Update Manufacture Order
Source: https://docs.stateset.com/api-reference/manufactureorder/update
PUT https://api.stateset.com/v1/manufacture_orders/:id
This endpoint updates an existing manufacture order.
### Body
Unique identifier for the manufacture order
Additional notes or information about the manufacture order
Number assigned to the manufacture order
Priority level of the manufacture order
Site or location associated with the manufacture order
Location where the manufactured product will be stored
Date and time when the manufacture order was created
Expected date of completion for the manufacture order
Date when the manufacture order was issued
### Response
Unique identifier for the manufacture order
Additional notes or information about the manufacture order
Number assigned to the manufacture order
Priority level of the manufacture order
Site or location associated with the manufacture order
Location where the manufactured product will be stored
Date and time when the manufacture order was created
Expected date of completion for the manufacture order
Date when the manufacture order was issued
Name of the bill of materials (BOM) associated with the line item
Number assigned to the bill of materials (BOM)
Unique identifier for the line item
Expected date for the completion of the line item
Status of the line item (e.g., in progress, completed, etc.)
Type or category of the line item
Number of the associated manufacture order
Type of output produced by the line item (e.g., product, component)
Name of the part associated with the line item
Number assigned to the part associated with the line item
Priority level of the line item
Quantity of the part to be manufactured or processed
Site or location associated with the line item
Number of the associated work order
Location of the yield of the manufacture order line item
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/manufacture_orders/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1",
"memo": "test",
"number": "1",
"priority": "1",
"site": "1",
"yield_location": "1",
"created_on": "2021-01-01T00:00:00Z",
"expected_completion_date": "2021-01-01"
}'
```
```json Response theme={null}
{
"id": "1",
"memo": "test",
"number": "1",
"priority": "1",
"site": "1",
"yield_location": "1",
"created_on": "2021-01-01T00:00:00Z",
"expected_completion_date": "2021-01-01"
}
```
# Create Manufacture Order Line Item
Source: https://docs.stateset.com/api-reference/manufactureorderlineitem/create
POST https://api.stateset.com/v1/manufacture_order_line_items
This endpoint creates a new manufacture order line item.
### Body
This is the id of the manufacture order line item.
This is the name of the bill of materials (BOM) associated with the line item.
This is the number assigned to the bill of materials (BOM).
This is the expected date for the completion of the line item.
This is the status of the line item (e.g., in progress, completed, etc.).
This is the type or category of the line item.
This is the number of the associated manufacture order.
This is the type of output produced by the line item (e.g., product, component).
This is the name of the part associated with the line item.
This is the number assigned to the part associated with the line item.
This is the priority level of the line item.
This is the quantity of the part to be manufactured or processed.
This is the site or location associated with the line item.
This is the number of the associated work order.
This is the location where the manufactured product will be stored.
### Response
This is the id of the manufacture order line item.
This is the name of the bill of materials (BOM) associated with the line item.
This is the number assigned to the bill of materials (BOM).
This is the expected date for the completion of the line item.
This is the status of the line item (e.g., in progress, completed, etc.).
This is the type or category of the line item.
This is the number of the associated manufacture order.
This is the type of output produced by the line item (e.g., product, component).
This is the name of the part associated with the line item.
This is the number assigned to the part associated with the line item.
This is the priority level of the line item.
This is the quantity of the part to be manufactured or processed.
This is the site or location associated with the line item.
This is the number of the associated work order.
This is the location where the manufactured product will be stored.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/manufacture_order_line_items' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Delete Manufacture Order Line Item
Source: https://docs.stateset.com/api-reference/manufactureorderlineitem/delete
DELETE https://api.stateset.com/v1/manufacture_order_line_items/:id
This endpoint deletes an existing manufacture order line item.
### Body
The ID of the packing list item to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/manufacture_order_line_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "example_1"
}'
```
```json Response theme={null}
{
"id": "example_1",
"object": "manufacture_order_line_item",
"deleted": true,
}
```
# Get Manufacture Order Line Item
Source: https://docs.stateset.com/api-reference/manufactureorderlineitem/get
GET https://api.stateset.com/v1/manufacture_order_line_items/:id
This endpoint gets or creates a new manufacture order line item.
### Body
This is the id of the manufacture order line item.
### Response
This is the id of the manufacture order line item.
This is the name of the bill of materials (BOM) associated with the line item.
This is the number assigned to the bill of materials (BOM).
This is the expected date for the completion of the line item.
This is the status of the line item (e.g., in progress, completed, etc.).
This is the type or category of the line item.
This is the number of the associated manufacture order.
This is the type of output produced by the line item (e.g., product, component).
This is the name of the part associated with the line item.
This is the number assigned to the part associated with the line item.
This is the priority level of the line item.
This is the quantity of the part to be manufactured or processed.
This is the site or location associated with the line item.
This is the number of the associated work order.
This is the location where the manufactured product will be stored.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/work_order_line_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1"
}'
```
```json Response theme={null}
{
"id": "1",
"bom_name": "BOM 1",
"bom_number": "BOM-1",
"expected_date": "2021-01-01",
"line_status": "In Progress",
"line_type": "Manufacture",
"manufacture_order_number": "MO-1",
"output_type": "Product",
"part_name": "Part 1",
"part_number": "PART-1",
"priority": "High",
"quantity": 100,
"site": "Site 1",
"work_order_number": "WO-1",
"yield_location": "Location 1"
}
```
## Manufacture Order Line Item
| Field | Type | Description |
| -------------------------- | ------- | ------------------------------------------------------------------- |
| bom\_name | String | Name of the bill of materials (BOM) associated with the line item |
| bom\_number | String | Number assigned to the bill of materials (BOM) |
| id | String | Unique identifier for the line item |
| expected\_date | Date | Expected date for the completion of the line item |
| line\_status | String | Status of the line item (e.g., in progress, completed, etc.) |
| line\_type | String | Type or category of the line item |
| manufacture\_order\_number | String | Number of the associated manufacture order |
| output\_type | String | Type of output produced by the line item (e.g., product, component) |
| part\_name | String | Name of the part associated with the line item |
| part\_number | String | Number assigned to the part associated with the line item |
| priority | String | Priority level of the line item |
| quantity | Integer | Quantity of the part to be manufactured or processed |
| site | String | Site or location associated with the line item |
| work\_order\_number | String | Number of the associated work order |
| yield\_location | String | Location where the manufactured product will be stored |
# Update Manufacture Order Line Item
Source: https://docs.stateset.com/api-reference/manufactureorderlineitem/update
PUT https://api.stateset.com/v1/manufacture_order_line_items/:id
This endpoint updates an existing manufacture order line item.
### Body
This is the id of the manufacture order line item.
This is the name of the bill of materials (BOM) associated with the line item.
This is the number assigned to the bill of materials (BOM).
This is the expected date for the completion of the line item.
This is the status of the line item (e.g., in progress, completed, etc.).
This is the type or category of the line item.
This is the number of the associated manufacture order.
This is the type of output produced by the line item (e.g., product, component).
This is the name of the part associated with the line item.
This is the number assigned to the part associated with the line item.
This is the priority level of the line item.
This is the quantity of the part to be manufactured or processed.
This is the site or location associated with the line item.
This is the number of the associated work order.
This is the location where the manufactured product will be stored.
### Response
This is the id of the manufacture order line item.
This is the name of the bill of materials (BOM) associated with the line item.
This is the number assigned to the bill of materials (BOM).
This is the expected date for the completion of the line item.
This is the status of the line item (e.g., in progress, completed, etc.).
This is the type or category of the line item.
This is the number of the associated manufacture order.
This is the type of output produced by the line item (e.g., product, component).
This is the name of the part associated with the line item.
This is the number assigned to the part associated with the line item.
This is the priority level of the line item.
This is the quantity of the part to be manufactured or processed.
This is the site or location associated with the line item.
This is the number of the associated work order.
This is the location where the manufactured product will be stored.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/manufacture_order_line_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 113,
"token": "",
"name": "ok",
"provided_id": "6"
}
}
```
# Create Message
Source: https://docs.stateset.com/api-reference/messages/create
POST https://api.stateset.com/v1/messages
This endpoint creates a new message
### Body
This is the ID of the message to be created.
This is the time of the message to be created.
This is the body of the message to be created.
This is the username of the message to be created.
This is the channel\_id of the message to be created.
This is the user\_id of the message to be created.
This is the is\_public of the message to be created.
This is the from of the message to be created.
This is the to of the message to be created.
This is the from\_me of the message to be created.
This is the sent\_receipt of the message to be created.
This is the delivered\_receipt of the message to be created.
This is the message\_number of the message to be created.
This is the date of the message to be created.
This is the timestamp of the message to be created.
This is the created\_at of the message to be created.
This is the updated\_at of the message to be created.
### Response
This is the id of the message.
This is the body of the message.
This is the date and time when the message was created.
This is the date when the message was sent.
This indicates if the message has been delivered.
This is the sender of the message.
This indicates if the message was sent by the user.
This indicates if the message is public or private.
This is the unique number assigned to the message.
This indicates if the message has been sent.
This is the time when the message was sent.
This is the timestamp of the message.
This is the recipient of the message.
This is the unique identifier for the user associated with the message.
This is the username of the user associated with the message.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/message' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```graphQL GraphQL theme={null}
mutation insert_message ($message: message_insert_input! ){
insert_message (
objects: [$message]
) {
returning {
id
time
body
username
}
}
}
```
```javascript Node.js theme={null}
const created = await stateset.message.create({
id: "",
});
```
```json Response theme={null}
{
"data": {
"insert_message": {
"returning": [
{
"id": "",
}
]
}
}
}
```
### Messages
| Field | Type | Description |
| ---------------- | -------- | ---------------------------------------------------------- |
| id | String | Unique identifier for the message |
| body | String | The content or text of the message |
| created\_at | DateTime | The date and time when the message was created |
| date | Date | The date when the message was sent |
| deliveredReceipt | Boolean | Indicates if the message has been delivered |
| from | String | Sender of the message |
| fromMe | Boolean | Indicates if the message was sent by the user |
| is\_public | Boolean | Indicates if the message is public or private |
| messageNumber | Integer | Unique number assigned to the message |
| sentReceipt | Boolean | Indicates if the message has been sent |
| time | Time | The time when the message was sent |
| timestamp | DateTime | The timestamp of the message |
| to | String | Recipient of the message |
| user\_id | String | Unique identifier for the user associated with the message |
| username | String | Username of the user associated with the message |
# Delete Message
Source: https://docs.stateset.com/api-reference/messages/delete
DELETE https://api.stateset.com/v1/messages/:id
This endpoint deletes an existing message.
### Body
The ID provided in the data tab may be used to identify the message
### Response
The ID provided in the data tab may be used to identify the message
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/messages/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "msg_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteMessage ($id: String!) {
delete_message(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const message = await stateset.channelthread.del({
'msg_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
message = stateset.message.del({
'msg_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
message, err := stateset.Cases.Del(
"msg_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Case message = stateset.message.del(
"msg_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const message = await stateset.message.del({
'msg_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
message = Stateset::Return.del({
'msg_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$message = $stateset->message->del(
'msg_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
DELETE /v1/channelthread HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "ct_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "channel_thread",
"deleted": true
}
```
# Get Messages
Source: https://docs.stateset.com/api-reference/messages/get
GET https://api.stateset.com/v1/messages/:id
This endpoint gets a message.
### Body
This is the id of the message.
### Response
This is the id of the message.
This is the body of the message.
This is the date and time when the message was created.
This is the date when the message was sent.
This indicates if the message has been delivered.
This is the sender of the message.
This indicates if the message was sent by the user.
This indicates if the message is public or private.
This is the unique number assigned to the message.
This indicates if the message has been sent.
This is the time when the message was sent.
This is the timestamp of the message.
This is the recipient of the message.
This is the unique identifier for the user associated with the message.
This is the username of the user associated with the message.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/messages/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query MyMessages {
message {
id
body
created_at
date
deliveredReceipt
from
fromMe
is_public
messageNumber
sentReceipt
time
timestamp
to
user_id
username
}
}
```
```js Node.js theme={null}
const messages = await stateset.messages.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
messages = stateset.messages.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
messages, err := stateset.Messages.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
messages = Stateset::Messages.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
Message messages = Stateset.Messages.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
Message messages = Stateset.Messages.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$messages = Stateset\Messages::retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/messages HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"data": {
"message": {
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"body": "Hello World",
"created_at": "2021-01-01T00:00:00.000000Z",
"date": "2021-01-01",
"deliveredReceipt": true,
"from": "user1",
"fromMe": true,
"is_public": true,
"messageNumber": 1,
"sentReceipt": true,
"time": "00:00:00",
"timestamp": "2021-01-01T00:00:00.000000Z",
"to": "user2",
"user_id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"username": "user1"
}
}
}
```
### Messages
| Field | Type | Description |
| ---------------- | -------- | ---------------------------------------------------------- |
| id | String | Unique identifier for the message |
| body | String | The content or text of the message |
| created\_at | DateTime | The date and time when the message was created |
| date | Date | The date when the message was sent |
| deliveredReceipt | Boolean | Indicates if the message has been delivered |
| from | String | Sender of the message |
| fromMe | Boolean | Indicates if the message was sent by the user |
| is\_public | Boolean | Indicates if the message is public or private |
| messageNumber | Integer | Unique number assigned to the message |
| sentReceipt | Boolean | Indicates if the message has been sent |
| time | Time | The time when the message was sent |
| timestamp | DateTime | The timestamp of the message |
| to | String | Recipient of the message |
| user\_id | String | Unique identifier for the user associated with the message |
| username | String | Username of the user associated with the message |
# List Messages
Source: https://docs.stateset.com/api-reference/messages/list
GET https://api.stateset.com/v1/messages
This endpoint lists messages.
### Body
This is the limit of the messages.
This is the offset of the messages
This is the order direction of the messages.
### Response
This is the id of the message.
This is the body of the message.
This is the date and time when the message was created.
This is the date when the message was sent.
This indicates if the message has been delivered.
This is the sender of the message.
This indicates if the message was sent by the user.
This indicates if the message is public or private.
This is the unique number assigned to the message.
This indicates if the message has been sent.
This is the time when the message was sent.
This is the timestamp of the message.
This is the recipient of the message.
This is the unique identifier for the user associated with the message.
This is the username of the user associated with the message.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/messages' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query MyMessages {
message {
id
body
created_at
date
deliveredReceipt
from
fromMe
is_public
messageNumber
sentReceipt
time
timestamp
to
user_id
username
}
}
```
```js Node.js theme={null}
const messages = await stateset.messages.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
messages = stateset.messages.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
messages, err := stateset.Messages.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
messages = Stateset::Messages.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
Message messages = Stateset.Messages.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
Message messages = Stateset.Messages.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$messages = Stateset\Messages::retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/messages HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"data": {
"message": {
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"body": "Hello World",
"created_at": "2021-01-01T00:00:00.000000Z",
"date": "2021-01-01",
"deliveredReceipt": true,
"from": "user1",
"fromMe": true,
"is_public": true,
"messageNumber": 1,
"sentReceipt": true,
"time": "00:00:00",
"timestamp": "2021-01-01T00:00:00.000000Z",
"to": "user2",
"user_id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"username": "user1"
}
}
}
```
### Messages
| Field | Type | Description |
| ---------------- | -------- | ---------------------------------------------------------- |
| id | String | Unique identifier for the message |
| body | String | The content or text of the message |
| created\_at | DateTime | The date and time when the message was created |
| date | Date | The date when the message was sent |
| deliveredReceipt | Boolean | Indicates if the message has been delivered |
| from | String | Sender of the message |
| fromMe | Boolean | Indicates if the message was sent by the user |
| is\_public | Boolean | Indicates if the message is public or private |
| messageNumber | Integer | Unique number assigned to the message |
| sentReceipt | Boolean | Indicates if the message has been sent |
| time | Time | The time when the message was sent |
| timestamp | DateTime | The timestamp of the message |
| to | String | Recipient of the message |
| user\_id | String | Unique identifier for the user associated with the message |
| username | String | Username of the user associated with the message |
# Update Message
Source: https://docs.stateset.com/api-reference/messages/update
POST https://api.stateset.com/v1/messages/:id
This endpoint updates a message
### Body
This is the ID of the message to be created.
This is the time of the message to be created.
This is the body of the message to be created.
This is the username of the message to be created.
This is the channel\_id of the message to be created.
This is the user\_id of the message to be created.
This is the is\_public of the message to be created.
This is the from of the message to be created.
This is the to of the message to be created.
This is the from\_me of the message to be created.
This is the sent\_receipt of the message to be created.
This is the delivered\_receipt of the message to be created.
This is the message\_number of the message to be created.
This is the date of the message to be created.
This is the timestamp of the message to be created.
This is the created\_at of the message to be created.
This is the updated\_at of the message to be created.
### Response
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/messages/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
```graphQL GraphQL theme={null}
mutation insert_message ($message: message_insert_input! ){
insert_message (
objects: [$message]
) {
returning {
id
time
body
username
}
}
}
```
```javascript Node.js theme={null}
const created = await stateset.message.create({
id: "",
});
```
```json Response theme={null}
{
"data": {
"insert_message": {
"returning": [
{
"id": "",
}
]
}
}
}
```
### Messages
| Field | Type | Description |
| ---------------- | -------- | ---------------------------------------------------------- |
| id | String | Unique identifier for the message |
| body | String | The content or text of the message |
| created\_at | DateTime | The date and time when the message was created |
| date | Date | The date when the message was sent |
| deliveredReceipt | Boolean | Indicates if the message has been delivered |
| from | String | Sender of the message |
| fromMe | Boolean | Indicates if the message was sent by the user |
| is\_public | Boolean | Indicates if the message is public or private |
| messageNumber | Integer | Unique number assigned to the message |
| sentReceipt | Boolean | Indicates if the message has been sent |
| time | Time | The time when the message was sent |
| timestamp | DateTime | The timestamp of the message |
| to | String | Recipient of the message |
| user\_id | String | Unique identifier for the user associated with the message |
| username | String | Username of the user associated with the message |
# Create Note
Source: https://docs.stateset.com/api-reference/notes/create
POST https://api.stateset.com/v1/notes
Create a new note record for annotations or comments
This endpoint requires authentication with `notes:write` permission.
### Request Parameters
The title or subject of the note
The main content or body of the note
ID or name of the user creating the note (auto-filled if not provided)
Optional ID of the resource this note is associated with (e.g., order ID)
### Response
Unique identifier for the created note
The title of the note
The content of the note
Timestamp when the note was created
Timestamp when the note was last updated
User who created the note
User who last modified the note
### Request Example
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/notes' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer ' \
--data-raw '{
"title": "Important Update",
"body": "Customer requested expedited shipping",
"associated_id": "order_123"
}'
```
```javascript JavaScript theme={null}
const response = await fetch('https://api.stateset.com/v1/notes', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': 'Bearer YOUR_API_KEY'
},
body: JSON.stringify({
title: 'Important Update',
body: 'Customer requested expedited shipping',
associated_id: 'order_123'
})
});
```
```python Python theme={null}
import requests
response = requests.post(
'https://api.stateset.com/v1/notes',
headers={
'Content-Type': 'application/json',
'Authorization': 'Bearer YOUR_API_KEY'
},
json={
'title': 'Important Update',
'body': 'Customer requested expedited shipping',
'associated_id': 'order_123'
}
)
```
### Response Example
```json Success Response theme={null}
{
"id": "note_001",
"title": "Important Update",
"body": "Customer requested expedited shipping",
"created_date": "2024-01-01T12:00:00Z",
"last_modified_date": "2024-01-01T12:00:00Z",
"created_by": "user_123",
"last_modified_by": "user_123"
}
```
```json Error Response theme={null}
{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "Missing required field: title"
}
}
```
# Delete Note
Source: https://docs.stateset.com/api-reference/notes/delete
DELETE https://api.stateset.com/v1/notes/:id
This endpoint deletes an existing note.
### Body
The ID provided in the data tab may be used to identify the note
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/notes/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteNote($id: String!) {
delete_notes(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const notes = await stateset.notes.del({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
notes = stateset.notes.del({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
notes, err := stateset.notes.Del(
"nt_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Note notes = stateset.notes.del(
"nt_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const notes = await stateset.notes.del({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
notes = Stateset::Note.del({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$notes = $stateset->notes->del(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
DELETE /v1/note HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "note",
"deleted": true
}
```
# Retrieve Note
Source: https://docs.stateset.com/api-reference/notes/get
GET https://api.stateset.com/v1/notes/:id
This endpoint retrieves a note.
### Body
This is the id of the note.
### Response
This is the id of the note
This is the title of the note
This is the body of the note
This is the created date of the note
This is the last modified date of the note
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/note/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
notes(limit: $limit, offset: $offset, order_by: {created_date: $order_direction}) {
id
title
body
createdDate
lastModifiedDate
}
}
```
```js Node.js theme={null}
const notes = await stateset.notes.retrieve({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
notes = stateset.notes.retrieve({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
notes, err := stateset.notes.Retrieve(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
notes = Stateset::Notes.retrieve(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
notes notes = Stateset.notes.retrieve(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
notes notes = Stateset.notes.Retrieve(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$notes = Stateset\notes::retrieve(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/note HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"notes": [
{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE",
},
]
}
```
# List Notes
Source: https://docs.stateset.com/api-reference/notes/list
GET https://api.stateset.com/v1/notes/list
This endpoint list notes.
### Body
This is the limit of the notes.
This is the offset of the notes.
This is the order direction of the notes.
### Response
This is the id of the note
This is the title of the note
This is the body of the note
This is the created date of the note
This is the last modified date of the note
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/note/list' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
notes(limit: $limit, offset: $offset, order_by: {created_date: $order_direction}) {
id
title
body
createdDate
lastModifiedDate
}
}
```
```js Node.js theme={null}
const notes = await stateset.notes.list({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
notes = stateset.notes.list({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
notes, err := stateset.notes.list(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
notes = Stateset::Notes.list(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
notes notes = Stateset.notes.list(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
notes notes = Stateset.notes.list(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$notes = Stateset\notes::list(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/note HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"notes": [
{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE",
},
]
}
```
# Update Note
Source: https://docs.stateset.com/api-reference/notes/update
POST https://api.stateset.com/v1/notes/update
This endpoint updates a note.
### Body
This is the id of the note.
This is the title of the note.
This is the body of the note.
This is the created date of the note.
This is the last modified date of the note.
This is the user that created the note.
This is the user that last modified the note.
### Response
This is the id of the note
This is the title of the note
This is the body of the note
This is the created date of the note
This is the last modified date of the note
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/note' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE",
"title": "Note Title",
"body": "Note Body",
"created_date": "2020-01-01T00:00:00.000Z",
"last_modified_date": "2020-01-01T00:00:00.000Z"
}'
```
```graphQL GraphQL theme={null}
mutation addNote($note: notes_insert_input!) {
insert_notes(objects: [$note]) {
returning {
id
title
body
createdDate
lastModifiedDate
}
}
```
```js Node.js theme={null}
const notes = await stateset.notes.update({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
notes = stateset.notes.update({
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
notes, err := stateset.notes.update(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
notes = Stateset::Notes.update(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
notes notes = Stateset.notes.update(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
notes notes = Stateset.notes.update(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$notes = Stateset\notes::update(
'nt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/note HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"notes": [
{
"id": "nt_1NXWPnCo6bFb1KQto6C8OWvE",
},
]
}
```
# Add Discount
Source: https://docs.stateset.com/api-reference/orders/add-discount
Add a discount to an order.
# Add Discount
Use this endpoint to apply a discount to an existing order.
# Add Item to Order
Source: https://docs.stateset.com/api-reference/orders/add-item
POST https://api.stateset.com/v1/orders/:id/add-item
This endpoint adds an item to an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/add-item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderAddItemMutation {
orderAddItem(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.addItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.addItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.addItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.addItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.addItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->addItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.AddItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"added": true
}
```
# Apply Discount
Source: https://docs.stateset.com/api-reference/orders/apply-discount
POST https://api.stateset.com/v1/orders/:id/apply-discount
This endpoint applies a discount to an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/orders/:id/apply-discount' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderApplyDiscountMutation {
orderApplyDiscount(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.applyDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.applyDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.applyDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.applyDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.applyDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->applyDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.ApplyDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"discount_applied": true
}
```
# Apply Promotion
Source: https://docs.stateset.com/api-reference/orders/apply-promotion
POST https://api.stateset.com/v1/orders/:id/apply-promotion
This endpoint applies a promotion to an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/apply-promotion' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderApplyPromotionMutation {
orderApplyPromotion(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.applyPromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.applyPromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.applyPromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.applyPromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.applyPromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->applyPromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.ApplyPromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"applied": true
}
```
# Cancel Order
Source: https://docs.stateset.com/api-reference/orders/cancel
POST https://api.stateset.com/v1/orders/:id/cancel
This endpoint cancels an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderCancelMutation {
orderCancel(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"cancelled": true
}
```
# Create Order
Source: https://docs.stateset.com/api-reference/orders/create
POST https://api.stateset.com/v1/orders
Create a new order with automatic inventory allocation and fulfillment workflow initiation
This endpoint creates a new order and automatically triggers order processing workflows, including inventory allocation, payment processing, and fulfillment initiation.
## Authentication
This endpoint requires a valid API key with `orders:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Customer information for the order
Customer's email address
Customer's first name
Customer's last name
Customer's phone number (E.164 format recommended)
Existing customer ID if available
Array of items in the order
Product SKU
Quantity ordered (must be positive)
Unit price in cents (e.g., 1999 for \$19.99)
Product name for display
Product variant ID if applicable
Additional item-specific metadata
Shipping address for the order
Street address line 1
Street address line 2
City name
State/Province code (e.g., "CA", "NY")
Postal/ZIP code
ISO 3166-1 alpha-2 country code (e.g., "US", "CA")
Billing address if different from shipping. If not provided, shipping address will be used.
Same structure as shipping\_address
Payment information
Payment method: `card`, `paypal`, `apple_pay`, `google_pay`, `bank_transfer`
Stripe PaymentIntent ID if using Stripe
External payment transaction ID
Shipping preferences
Shipping method: `standard`, `express`, `overnight`, `economy`
Preferred carrier: `ups`, `fedex`, `usps`, `dhl`
Specific service level code
Additional custom metadata to store with the order
Unique key to ensure idempotent order creation
### Response
Unique identifier for the created order
Always "order" for this object type
Human-readable order number (e.g., "ORD-2024-001234")
Order status: `pending`, `processing`, `shipped`, `delivered`, `cancelled`
Customer information associated with the order
Array of order items with calculated totals
Order totals breakdown
Subtotal before tax and shipping (in cents)
Total tax amount (in cents)
Shipping cost (in cents)
Total discount amount (in cents)
Grand total (in cents)
ISO 8601 timestamp of order creation
ISO 8601 timestamp of last update
```bash cURL theme={null}
curl -X POST https://api.stateset.com/v1/orders \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"customer": {
"email": "john.doe@example.com",
"first_name": "John",
"last_name": "Doe",
"phone": "+1234567890"
},
"items": [
{
"sku": "TSHIRT-BLUE-L",
"quantity": 2,
"price": 1999,
"name": "Blue T-Shirt (Large)"
},
{
"sku": "HAT-RED",
"quantity": 1,
"price": 1499,
"name": "Red Baseball Cap"
}
],
"shipping_address": {
"line1": "123 Main Street",
"line2": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"payment": {
"method": "card",
"payment_intent_id": "pi_1234567890"
},
"shipping": {
"method": "standard",
"carrier": "ups"
},
"metadata": {
"source": "web",
"campaign": "summer-sale"
}
}'
```
```graphQL GraphQL theme={null}
mutation CreateOrder($input: OrderCreateInput!) {
orderCreate(input: $input) {
order {
id
orderNumber
status
customer {
email
firstName
lastName
}
items {
sku
quantity
price
total
}
totals {
subtotal
tax
shipping
total
}
createdAt
}
userErrors {
field
message
}
}
}
```
```js Node.js theme={null}
const order = await stateset.orders.create({
customer: {
email: 'john.doe@example.com',
first_name: 'John',
last_name: 'Doe',
phone: '+1234567890'
},
items: [
{
sku: 'TSHIRT-BLUE-L',
quantity: 2,
price: 1999,
name: 'Blue T-Shirt (Large)'
}
],
shipping_address: {
line1: '123 Main Street',
city: 'San Francisco',
state: 'CA',
postal_code: '94105',
country: 'US'
},
payment: {
method: 'card',
payment_intent_id: 'pi_1234567890'
}
});
```
```python Python theme={null}
order = stateset.orders.create(
customer={
'email': 'john.doe@example.com',
'first_name': 'John',
'last_name': 'Doe',
'phone': '+1234567890'
},
items=[
{
'sku': 'TSHIRT-BLUE-L',
'quantity': 2,
'price': 1999,
'name': 'Blue T-Shirt (Large)'
}
],
shipping_address={
'line1': '123 Main Street',
'city': 'San Francisco',
'state': 'CA',
'postal_code': '94105',
'country': 'US'
},
payment={
'method': 'card',
'payment_intent_id': 'pi_1234567890'
}
)
```
```ruby Ruby theme={null}
order = Stateset::Order.create({
customer: {
email: 'john.doe@example.com',
first_name: 'John',
last_name: 'Doe',
phone: '+1234567890'
},
items: [
{
sku: 'TSHIRT-BLUE-L',
quantity: 2,
price: 1999,
name: 'Blue T-Shirt (Large)'
}
],
shipping_address: {
line1: '123 Main Street',
city: 'San Francisco',
state: 'CA',
postal_code: '94105',
country: 'US'
},
payment: {
method: 'card',
payment_intent_id: 'pi_1234567890'
}
})
```
```go Go theme={null}
order, err := stateset.Orders.Create(&stateset.OrderParams{
Customer: &stateset.CustomerParams{
Email: "john.doe@example.com",
FirstName: "John",
LastName: "Doe",
Phone: "+1234567890",
},
Items: []*stateset.OrderItemParams{
{
SKU: "TSHIRT-BLUE-L",
Quantity: 2,
Price: 1999,
Name: "Blue T-Shirt (Large)",
},
},
ShippingAddress: &stateset.AddressParams{
Line1: "123 Main Street",
City: "San Francisco",
State: "CA",
PostalCode: "94105",
Country: "US",
},
Payment: &stateset.PaymentParams{
Method: "card",
PaymentIntentID: "pi_1234567890",
},
})
```
```java Java theme={null}
Map params = new HashMap<>();
params.put("customer", Map.of(
"email", "john.doe@example.com",
"first_name", "John",
"last_name", "Doe",
"phone", "+1234567890"
));
params.put("items", List.of(Map.of(
"sku", "TSHIRT-BLUE-L",
"quantity", 2,
"price", 1999,
"name", "Blue T-Shirt (Large)"
)));
params.put("shipping_address", Map.of(
"line1", "123 Main Street",
"city", "San Francisco",
"state", "CA",
"postal_code", "94105",
"country", "US"
));
params.put("payment", Map.of(
"method", "card",
"payment_intent_id", "pi_1234567890"
));
Order order = stateset.orders().create(params);
```
```php PHP theme={null}
$order = $stateset->orders->create([
'customer' => [
'email' => 'john.doe@example.com',
'first_name' => 'John',
'last_name' => 'Doe',
'phone' => '+1234567890',
],
'items' => [
[
'sku' => 'TSHIRT-BLUE-L',
'quantity' => 2,
'price' => 1999,
'name' => 'Blue T-Shirt (Large)',
],
],
'shipping_address' => [
'line1' => '123 Main Street',
'city' => 'San Francisco',
'state' => 'CA',
'postal_code' => '94105',
'country' => 'US',
],
'payment' => [
'method' => 'card',
'payment_intent_id' => 'pi_1234567890',
],
]);
```
```csharp C# theme={null}
var order = await stateset.Orders.CreateAsync(new OrderCreateParams
{
Customer = new CustomerParams
{
Email = "john.doe@example.com",
FirstName = "John",
LastName = "Doe",
Phone = "+1234567890"
},
Items = new List
{
new OrderItemParams
{
Sku = "TSHIRT-BLUE-L",
Quantity = 2,
Price = 1999,
Name = "Blue T-Shirt (Large)"
}
},
ShippingAddress = new AddressParams
{
Line1 = "123 Main Street",
City = "San Francisco",
State = "CA",
PostalCode = "94105",
Country = "US"
},
Payment = new PaymentParams
{
Method = "card",
PaymentIntentId = "pi_1234567890"
}
});
```
```json Success Response theme={null}
{
"id": "ord_1a2b3c4d5e6f",
"object": "order",
"order_number": "ORD-2024-001234",
"status": "processing",
"customer": {
"id": "cus_9z8y7x6w5v4u",
"email": "john.doe@example.com",
"first_name": "John",
"last_name": "Doe",
"phone": "+1234567890"
},
"items": [
{
"id": "item_abc123",
"sku": "TSHIRT-BLUE-L",
"quantity": 2,
"price": 1999,
"name": "Blue T-Shirt (Large)",
"total": 3998
},
{
"id": "item_def456",
"sku": "HAT-RED",
"quantity": 1,
"price": 1499,
"name": "Red Baseball Cap",
"total": 1499
}
],
"shipping_address": {
"line1": "123 Main Street",
"line2": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"billing_address": {
"line1": "123 Main Street",
"line2": "Apt 4B",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"payment": {
"method": "card",
"payment_intent_id": "pi_1234567890",
"status": "paid"
},
"shipping": {
"method": "standard",
"carrier": "ups",
"tracking_number": null,
"estimated_delivery": "2024-01-22T00:00:00Z"
},
"totals": {
"subtotal": 5497,
"tax": 482,
"shipping": 799,
"discount": 0,
"total": 6778
},
"metadata": {
"source": "web",
"campaign": "summer-sale"
},
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T10:30:00Z"
}
```
```json Error Response - Validation Error theme={null}
{
"success": false,
"error": {
"code": "VALIDATION_ERROR",
"message": "Invalid request parameters",
"details": {
"items[0].quantity": "Quantity must be a positive integer",
"customer.email": "Invalid email format"
}
}
}
```
```json Error Response - Inventory Unavailable theme={null}
{
"success": false,
"error": {
"code": "INVENTORY_UNAVAILABLE",
"message": "Insufficient inventory for requested items",
"details": {
"unavailable_items": [
{
"sku": "TSHIRT-BLUE-L",
"requested": 2,
"available": 1
}
]
}
}
}
```
# Delete Order
Source: https://docs.stateset.com/api-reference/orders/delete
DELETE https://api.stateset.com/v1/orders/:id
This endpoint deletes an order. Only draft or cancelled orders can be deleted.
### Path Parameters
The unique identifier of the order to delete
### Query Parameters
Force deletion even if there are related records (requires admin permission)
Archive the order instead of deleting it (recommended for audit trail)
### Response
The ID of the deleted order
Indicates whether the order was successfully deleted
Indicates if the order was archived instead of deleted
Summary of related records affected
Number of related payment records
Number of related shipment records
Number of related return records
Number of related refund records
Timestamp when the order was deleted
User who deleted the order
### Error Responses
Error object containing details about what went wrong
Error code (e.g., "order\_not\_deletable", "order\_shipped", "active\_refunds")
Human-readable error message
Additional error details including order status and blockers
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/orders/ord_123abc' \
--header 'Authorization: Token '
```
```bash cURL (Archive Instead) theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/orders/ord_123abc?archive_instead=true' \
--header 'Authorization: Token '
```
```graphQL GraphQL theme={null}
mutation orderDeleteMutation {
orderDelete(id: "${orderId}", archiveInstead: false) {
success
order {
id
deleted
}
userErrors {
field
message
}
}
}
```
```js Node.js theme={null}
const deletedOrder = await stateset.orders.delete('ord_123abc');
// Or archive instead
const archivedOrder = await stateset.orders.delete('ord_123abc', {
archive_instead: true
});
```
```python Python theme={null}
deleted_order = stateset.orders.delete('ord_123abc')
# Or archive instead
archived_order = stateset.orders.delete('ord_123abc', {
'archive_instead': True
})
```
```ruby Ruby theme={null}
deleted_order = Stateset::Order.delete('ord_123abc')
# Or archive instead
archived_order = Stateset::Order.delete('ord_123abc', {
archive_instead: true
})
```
```go Go theme={null}
deletedOrder, err := stateset.Orders.Delete("ord_123abc")
// Or archive instead
archivedOrder, err := stateset.Orders.Delete("ord_123abc", DeleteOptions{
ArchiveInstead: true
})
```
```java Java theme={null}
Order deletedOrder = stateset.orders.delete("ord_123abc");
// Or archive instead
DeleteOptions options = new DeleteOptions();
options.setArchiveInstead(true);
Order archivedOrder = stateset.orders.delete("ord_123abc", options);
```
```php PHP theme={null}
$deleted_order = $stateset->orders->delete('ord_123abc');
// Or archive instead
$archived_order = $stateset->orders->delete('ord_123abc', [
'archive_instead' => true
]);
```
```csharp C# theme={null}
var deletedOrder = await stateset.Orders.Delete("ord_123abc");
// Or archive instead
var archivedOrder = await stateset.Orders.Delete("ord_123abc", new DeleteOptions {
ArchiveInstead = true
});
```
```json Success Response theme={null}
{
"id": "ord_123abc",
"deleted": true,
"archived": false,
"related_records": {
"payments": 0,
"shipments": 0,
"returns": 0,
"refunds": 0
},
"deleted_at": "2024-01-15T14:30:00Z",
"deleted_by": "user_123"
}
```
```json Archive Response theme={null}
{
"id": "ord_123abc",
"deleted": false,
"archived": true,
"status": "archived",
"archived_at": "2024-01-15T14:30:00Z",
"archived_by": "user_123",
"archive_reason": "User requested archival instead of deletion"
}
```
```json Error Response - Order Shipped theme={null}
{
"error": {
"code": "order_not_deletable",
"message": "Cannot delete order that has been shipped. Only draft or cancelled orders can be deleted.",
"details": {
"order_id": "ord_123abc",
"current_status": "shipped",
"deletable_statuses": ["draft", "cancelled"],
"suggestion": "Cancel the order first or archive it instead"
}
}
}
```
```json Error Response - Active Returns theme={null}
{
"error": {
"code": "active_returns",
"message": "Cannot delete order with active returns. Please resolve all returns first.",
"details": {
"order_id": "ord_123abc",
"active_returns": 2,
"return_ids": ["ret_456def", "ret_789ghi"]
}
}
}
```
# Exchange Order
Source: https://docs.stateset.com/api-reference/orders/exchange
POST https://api.stateset.com/v1/orders/:id/exchange
This endpoint exchanges an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/orders/:id/exchange' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderExchangeMutation {
orderExchange(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.exchange({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.exchange({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.exchange({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.exchange({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.exchange({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->exchange({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Exchange({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"exchanged": true
}
```
# Retrieve Order
Source: https://docs.stateset.com/api-reference/orders/get
GET https://api.stateset.com/v1/order/:id/retrieve
This endpoint retrieves an order.
### Body
This is the id of the order.
### Response
This is the id of the order.
This is the name of the order.
This is the order number.
This is the date the order was created.
This is the date the order was last updated.
This is the status of the order.
This is the imported status of the order.
This is the delivery date of the order.
This is the person who ordered.
This is the delivery address for the order.
These are additional notes for the order.
This is the date the order was imported.
This is the customer number associated with the order.
This is the name of the customer.
This indicates if the order was imported.
This is the email of the customer.
This is the source of the order.
This is the email of the buyer.
This is a message from the buyer.
This is the SLA time for cancelling the order.
This is the reason for cancellation, if applicable.
This is who initiated the cancellation, if applicable.
This is the type of fulfillment for the order.
This is the type of delivery for the order.
This indicates if the order is cash on delivery.
This indicates if this is a replacement order.
This is a note from the seller.
This is the current status of the order.
This is the tracking number for the order.
This is the id of the warehouse handling the order.
These are the line items associated with the order.
This is the id of the order line item.
This is the id of the associated wholesale order.
This is the name of the product.
This is the quantity of the product ordered.
This is the date the line item was created.
This is the date the line item was last updated.
This is the unit of measurement for the product.
This is the id of the product.
This is the brand of the product.
This is the stock code of the product.
This is the size of the product.
This is the status of the line item.
This is the sale price of the product.
This is the discount offered by the seller.
This is the seller's SKU for the product.
This is the SKU id of the product.
This is the image URL for the product SKU.
This is the name of the product SKU.
This is the type of the product SKU.
This is the original price of the product.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/order/retrieve' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "ord_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query ($id: UUID!) {
order(id: $id) {
id
name
order_number
created_date
updated_date
order_status
imported_status
delivery_date
ordered_by
delivery_address
notes
imported_date
customer_number
customer_name
import
customer_email
source
buyer_email
buyer_message
cancel_order_sla_time
cancel_reason
cancellation_initiator
fulfillment_type
delivery_type
is_cod
is_replacement_order
seller_note
status
tracking_number
warehouse_id
order_line_items {
id
wholesale_order_id
product_name
quantity
created_date
updated_date
unit
product_id
brand
stock_code
size
status
sale_price
seller_discount
seller_sku
sku_id
sku_image
sku_name
sku_type
original_price
}
}
}
```
```js Node.js theme={null}
const order = await stateset.orders.retrieve('ord_1NXWPnCo6bFb1KQto6C8OWvE');
```
```py Python theme={null}
order = stateset.orders.retrieve('ord_1NXWPnCo6bFb1KQto6C8OWvE')
```
```go Golang theme={null}
order, err := stateset.Orders.Retrieve("ord_1NXWPnCo6bFb1KQto6C8OWvE")
```
```ruby Ruby theme={null}
order = Stateset::Order.retrieve('ord_1NXWPnCo6bFb1KQto6C8OWvE')
```
```java Java theme={null}
Order order = Order.retrieve("ord_1NXWPnCo6bFb1KQto6C8OWvE");
```
```csharp C# theme={null}
var order = Order.Retrieve("ord_1NXWPnCo6bFb1KQto6C8OWvE");
```
```php PHP theme={null}
$order = $stateset->orders->retrieve('ord_1NXWPnCo6bFb1KQto6C8OWvE');
```
```http HTTP theme={null}
GET /v1/order/ord_1NXWPnCo6bFb1KQto6C8OWvE HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
Authorization: Bearer
```
```json Response theme={null}
{
"order": {
"id": "ord_1NXWPnCo6bFb1KQto6C8OWvE",
"name": "Example Order",
"order_number": "ORD-12345",
"created_date": "2023-08-23T10:00:00Z",
"updated_date": "2023-08-23T11:00:00Z",
"order_status": "Processing",
"imported_status": "Completed",
"delivery_date": "2023-08-30T14:00:00Z",
"ordered_by": "John Doe",
"delivery_address": "123 Main St, Anytown, AN 12345",
"notes": "Please handle with care",
"imported_date": "2023-08-23T09:00:00Z",
"customer_number": "CUST-6789",
"customer_name": "John Doe",
"import": true,
"customer_email": "john.doe@example.com",
"source": "Online Store",
"buyer_email": "john.doe@example.com",
"buyer_message": "Looking forward to receiving the order!",
"cancel_order_sla_time": null,
"cancel_reason": null,
"cancellation_initiator": null,
"fulfillment_type": "Standard",
"delivery_type": "Home Delivery",
"is_cod": false,
"is_replacement_order": false,
"seller_note": "Thank you for your order",
"status": "Processing",
"tracking_number": "TRACK-98765",
"warehouse_id": "wh_2MXYQoDp7cGc2LRup7D9PXvF",
"order_line_items": [
{
"id": "oli_3OYZRpEq8dHd3MSvq8E0QYwG",
"wholesale_order_id": "ord_1NXWPnCo6bFb1KQto6C8OWvE",
"product_name": "Example Product",
"quantity": "2",
"created_date": "2023-08-23T10:05:00Z",
"updated_date": "2023-08-23T10:05:00Z",
"unit": "piece",
"product_id": "prod_4PZaSqFr9eIe4NTwr9F1RZxH",
"brand": "Example Brand",
"stock_code": "EX-1234",
"size": "Medium",
"status": "In Stock",
"sale_price": 2999,
"seller_discount": 500,
"seller_sku": "SKU-5678",
"sku_id": "sku_6QAbTrGs0fJf5OUxs0G2SZyI",
"sku_image": "https://example.com/images/product.jpg",
"sku_name": "Example Product - Medium",
"sku_type": "Standard",
"original_price": 3499
}
]
}
}
```
```json Error Response (404 Not Found) theme={null}
{
"error": {
"code": "RESOURCE_NOT_FOUND",
"message": "Order not found",
"details": {
"resource": "order",
"id": "ord_1a2b3c4d5e6f"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (401 Unauthorized) theme={null}
{
"error": {
"code": "INVALID_API_KEY",
"message": "The API key provided is invalid or has been revoked",
"request_id": "req_abc123def456"
}
}
```
# Hold Order
Source: https://docs.stateset.com/api-reference/orders/hold
POST https://api.stateset.com/v1/orders/:id/hold
This endpoint holds an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/hold' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderHoldMutation {
orderHold(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.hold({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.hold({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.hold({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.hold({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.hold({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->hold({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Hold({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"held": true
}
```
# List Orders
Source: https://docs.stateset.com/api-reference/orders/list
GET https://api.stateset.com/v1/orders
Retrieve orders with advanced filtering, pagination, and sorting capabilities
This endpoint supports comprehensive filtering, pagination, and sorting. Use query parameters to efficiently retrieve the exact orders you need.
## Pagination Parameters
Maximum number of orders to return per page. Range: 1-100.
Number of orders to skip. Use for pagination.
Cursor-based pagination token. More efficient for large datasets.
## Sorting Parameters
Sort field. Options: `created_at`, `updated_at`, `order_number`, `total_amount`, `status`, `customer_email`
Sort direction. Options: `asc`, `desc`
## Filter Parameters
### Status Filters
Filter by order status. Options: `pending`, `processing`, `shipped`, `delivered`, `cancelled`, `refunded`
Filter by multiple statuses. Example: `status_in=pending,processing`
### Date Filters
Orders created after this date (ISO 8601 format: `2024-01-01T00:00:00Z`)
Orders created before this date (ISO 8601 format: `2024-12-31T23:59:59Z`)
Orders updated after this date
Orders shipped after this date
### Customer Filters
Filter by exact customer email
Filter by customer ID
Filter by customer tier. Options: `bronze`, `silver`, `gold`, `platinum`
### Financial Filters
Orders with total amount greater than or equal to this value
Orders with total amount less than or equal to this value
Filter by currency code (ISO 4217). Example: `USD`, `EUR`, `GBP`
### Location Filters
Filter by shipping country code (ISO 3166-1). Example: `US`, `CA`, `GB`
Filter by shipping state/province
Filter by fulfillment center ID
### Product Filters
Filter orders containing specific SKU
Filter orders containing products from specific category
### Source Filters
Filter by order source. Options: `website`, `mobile_app`, `marketplace`, `phone`, `retail`
Filter by sales channel
### Search
Full-text search across order number, customer name, email, and product names
### Advanced Filters
Filter orders that have associated returns
Filter gift orders
Filter by fraud risk level. Options: `low`, `medium`, `high`
Filter by order priority. Options: `low`, `normal`, `high`, `urgent`
### Include Parameters
Include related data. Options: `line_items`, `customer`, `shipping_address`, `billing_address`, `payments`, `returns`, `fulfillments`
### Response
An array of order objects.
This is the id of the order.
This is the name of the order.
This is the order number.
This is the date the order was created.
This is the date the order was last updated.
This is the status of the order.
This is the imported status of the order.
This is the delivery date of the order.
This is the person who ordered.
This is the delivery address for the order.
These are additional notes for the order.
This is the date the order was imported.
This is the customer number associated with the order.
This is the name of the customer.
This indicates if the order was imported.
This is the email of the customer.
This is the source of the order.
This is the email of the buyer.
This is a message from the buyer.
This is the SLA time for cancelling the order.
This is the reason for cancellation, if applicable.
This is who initiated the cancellation, if applicable.
This is the type of fulfillment for the order.
This is the type of delivery for the order.
This indicates if the order is cash on delivery.
This indicates if this is a replacement order.
This is a note from the seller.
This is the current status of the order.
This is the tracking number for the order.
This is the id of the warehouse handling the order.
These are the line items associated with the order.
This is the id of the order line item.
This is the id of the associated wholesale order.
This is the name of the product.
This is the quantity of the product ordered.
This is the date the line item was created.
This is the date the line item was last updated.
This is the unit of measurement for the product.
This is the id of the product.
This is the brand of the product.
This is the stock code of the product.
This is the size of the product.
This is the status of the line item.
This is the sale price of the product.
This is the discount offered by the seller.
This is the seller's SKU for the product.
This is the SKU id of the product.
This is the image URL for the product SKU.
This is the name of the product SKU.
This is the type of the product SKU.
This is the original price of the product.
The total number of orders matching the query parameters.
```bash Basic Pagination theme={null}
curl -X GET "https://api.stateset.com/v1/orders?limit=20&offset=0" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json"
```
```bash Advanced Filtering theme={null}
curl -X GET "https://api.stateset.com/v1/orders" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-G \
--data-urlencode "status_in=processing,shipped" \
--data-urlencode "created_after=2024-01-01T00:00:00Z" \
--data-urlencode "total_amount_gte=50.00" \
--data-urlencode "shipping_country=US" \
--data-urlencode "include=line_items,customer" \
--data-urlencode "sort=total_amount" \
--data-urlencode "order=desc" \
--data-urlencode "limit=50"
```
```bash Search and Filter theme={null}
curl -X GET "https://api.stateset.com/v1/orders" \
-H "Authorization: Bearer YOUR_API_KEY" \
-G \
--data-urlencode "search=john@example.com" \
--data-urlencode "status=delivered" \
--data-urlencode "created_after=2024-01-01" \
--data-urlencode "created_before=2024-01-31"
```
```bash Cursor-based Pagination theme={null}
curl -X GET "https://api.stateset.com/v1/orders?cursor=eyJpZCI6Im9yZF8xMjM0NSIsImNyZWF0ZWRfYXQiOiIyMDI0LTAxLTE1VDEwOjMwOjAwWiJ9&limit=25" \
-H "Authorization: Bearer YOUR_API_KEY"
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $sort: String!, $order: String!) {
orders(limit: $limit, offset: $offset, sort: $sort, order: $order) {
id
name
order_number
created_date
updated_date
order_status
imported_status
delivery_date
ordered_by
delivery_address
notes
imported_date
customer_number
customer_name
import
customer_email
source
buyer_email
buyer_message
cancel_order_sla_time
cancel_reason
cancellation_initiator
fulfillment_type
delivery_type
is_cod
is_replacement_order
seller_note
status
tracking_number
warehouse_id
order_line_items {
id
wholesale_order_id
product_name
quantity
created_date
updated_date
unit
product_id
brand
stock_code
size
status
sale_price
seller_discount
seller_sku
sku_id
sku_image
sku_name
sku_type
original_price
}
}
total_count
}
```
```js Basic Pagination theme={null}
const orders = await stateset.orders.list({
limit: 20,
offset: 0,
sort: 'created_at',
order: 'desc'
});
```
```js Advanced Filtering theme={null}
const orders = await stateset.orders.list({
status_in: ['processing', 'shipped'],
created_after: '2024-01-01T00:00:00Z',
total_amount_gte: 50.00,
shipping_country: 'US',
include: ['line_items', 'customer'],
sort: 'total_amount',
order: 'desc',
limit: 50
});
```
```js Pagination Helper Function theme={null}
// Paginate through all orders
async function getAllOrders(filters = {}) {
const allOrders = [];
let hasMore = true;
let offset = 0;
const limit = 100;
while (hasMore) {
const response = await stateset.orders.list({
...filters,
limit,
offset
});
allOrders.push(...response.orders);
hasMore = response.orders.length === limit;
offset += limit;
// Add delay to respect rate limits
if (hasMore) {
await new Promise(resolve => setTimeout(resolve, 100));
}
}
return allOrders;
}
// Usage
const allProcessingOrders = await getAllOrders({
status: 'processing',
created_after: '2024-01-01'
});
```
```js Cursor-based Pagination theme={null}
// More efficient for large datasets
async function getOrdersWithCursor(filters = {}) {
const allOrders = [];
let cursor = null;
do {
const response = await stateset.orders.list({
...filters,
cursor,
limit: 100
});
allOrders.push(...response.orders);
cursor = response.next_cursor;
} while (cursor);
return allOrders;
}
```
```js Real-time Filtering Example theme={null}
// Filter orders dynamically based on user input
class OrderFilter {
constructor(client) {
this.client = client;
this.cache = new Map();
}
async searchOrders(query) {
const cacheKey = JSON.stringify(query);
if (this.cache.has(cacheKey)) {
return this.cache.get(cacheKey);
}
const filters = this.buildFilters(query);
const orders = await this.client.orders.list(filters);
// Cache for 5 minutes
this.cache.set(cacheKey, orders);
setTimeout(() => this.cache.delete(cacheKey), 300000);
return orders;
}
buildFilters(query) {
const filters = { limit: 50 };
if (query.search) {
filters.search = query.search;
}
if (query.status && query.status.length > 0) {
filters.status_in = query.status;
}
if (query.dateRange) {
filters.created_after = query.dateRange.start;
filters.created_before = query.dateRange.end;
}
if (query.amountRange) {
if (query.amountRange.min) filters.total_amount_gte = query.amountRange.min;
if (query.amountRange.max) filters.total_amount_lte = query.amountRange.max;
}
if (query.location) {
filters.shipping_country = query.location.country;
if (query.location.state) filters.shipping_state = query.location.state;
}
return filters;
}
}
```
```py Python theme={null}
orders = stateset.orders.list(
limit=10,
offset=0,
sort='created_date',
order='desc'
)
```
```go Golang theme={null}
orders, err := stateset.Orders.List(&stateset.OrderListParams{
Limit: 10,
Offset: 0,
Sort: "created_date",
Order: "desc",
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.list(
limit: 10,
offset: 0,
sort: 'created_date',
order: 'desc'
)
```
```java Java theme={null}
OrderListParams params = new OrderListParams.Builder()
.setLimit(10)
.setOffset(0)
.setSort("created_date")
.setOrder("desc")
.build();
OrderCollection orders = Order.list(params);
```
```csharp C# theme={null}
var orderListOptions = new OrderListOptions
{
Limit = 10,
Offset = 0,
Sort = "created_date",
Order = "desc"
};
var orders = Order.List(orderListOptions);
```
```php PHP theme={null}
$orders = $stateset->orders->list([
'limit' => 10,
'offset' => 0,
'sort' => 'created_date',
'order' => 'desc'
]);
```
```http HTTP theme={null}
GET /v1/orders?limit=10&offset=0&sort=created_date&order=desc HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
Authorization: Bearer
```
```json Response theme={null}
{
"orders": [
{
"id": "ord_1NXWPnCo6bFb1KQto6C8OWvE",
"name": "Example Order 1",
"order_number": "ORD-12345",
"created_date": "2023-08-23T10:00:00Z",
"updated_date": "2023-08-23T11:00:00Z",
"order_status": "Processing",
"imported_status": "Completed",
"delivery_date": "2023-08-30T14:00:00Z",
"ordered_by": "John Doe",
"delivery_address": "123 Main St, Anytown, AN 12345",
"notes": "Please handle with care",
"imported_date": "2023-08-23T09:00:00Z",
"customer_number": "CUST-6789",
"customer_name": "John Doe",
"import": true,
"customer_email": "john.doe@example.com",
"source": "Online Store",
"buyer_email": "john.doe@example.com",
"buyer_message": "Looking forward to receiving the order!",
"cancel_order_sla_time": null,
"cancel_reason": null,
"cancellation_initiator": null,
"fulfillment_type": "Standard",
"delivery_type": "Home Delivery",
"is_cod": false,
"is_replacement_order": false,
"seller_note": "Thank you for your order",
"status": "Processing",
"tracking_number": "TRACK-98765",
"warehouse_id": "wh_2MXYQoDp7cGc2LRup7D9PXvF",
"order_line_items": [
{
"id": "oli_3OYZRpEq8dHd3MSvq8E0QYwG",
"wholesale_order_id": "ord_1NXWPnCo6bFb1KQto6C8OWvE",
"product_name": "Example Product",
"quantity": "2",
"created_date": "2023-08-23T10:05:00Z",
"updated_date": "2023-08-23T10:05:00Z",
"unit": "piece",
"product_id": "prod_4PZaSqFr9eIe4NTwr9F1RZxH",
"brand": "Example Brand",
"stock_code": "EX-1234",
"size": "Medium",
"status": "In Stock",
"sale_price": 2999,
"seller_discount": 500,
"seller_sku": "SKU-5678",
"sku_id": "sku_6QAbTrGs0fJf5OUxs0G2SZyI",
"sku_image": "https://example.com/images/product.jpg",
"sku_name": "Example Product - Medium",
"sku_type": "Standard",
"original_price": 3499
}
]
},
],
"total_count": 1,
"has_more": false,
"next_cursor": null,
"has_more": false,
"next_cursor": null,
"filters_applied": {
"status": "processing",
"created_after": "2024-01-01T00:00:00Z"
},
"pagination": {
"current_page": 1,
"per_page": 20,
"total_pages": 1
}
}
```
# Merge Order
Source: https://docs.stateset.com/api-reference/orders/merge
POST https://api.stateset.com/v1/orders/:id/merge
This endpoint merges an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/merge' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderMergeMutation {
orderMerge(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.merge({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.merge({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.merge({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.merge({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.merge({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->merge({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Merge({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"merged": true
}
```
# Refund Order
Source: https://docs.stateset.com/api-reference/orders/refund
POST https://api.stateset.com/v1/orders/:id/refund
This endpoint refunds an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/refund' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderRefundMutation {
orderRefund(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.refund({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.refund({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.refund({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.refund({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.refund({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->refund({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Refund({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"refunded": true
}
```
# Release Order
Source: https://docs.stateset.com/api-reference/orders/release
POST https://api.stateset.com/v1/orders/:id/release
This endpoint releases an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/release' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderReleaseMutation {
orderRelease(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.release({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.release({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.release({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.release({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.release({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->release({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Release({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"released": true
}
```
# Remove Discount
Source: https://docs.stateset.com/api-reference/orders/remove-discount
POST https://api.stateset.com/v1/orders/:id/remove-discount
This endpoint removes a discount from an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/orders/:id/remove-discount' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderRemoveDiscountMutation {
orderRemoveDiscount(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.removeDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.removeDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.removeDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.removeDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.removeDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->removeDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.RemoveDiscount({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"discount_removed": true
}
```
# Remove Item from Order
Source: https://docs.stateset.com/api-reference/orders/remove-item
POST https://api.stateset.com/v1/orders/:id/remove-item
This endpoint removes an item from an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/remove-item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderRemoveItemMutation {
orderRemoveItem(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.removeItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.removeItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.removeItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.removeItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.removeItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->removeItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.RemoveItem({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"removed": true
}
```
# Remove Promotion
Source: https://docs.stateset.com/api-reference/orders/remove-promotion
POST https://api.stateset.com/v1/orders/:id/remove-promotion
This endpoint removes a promotion from an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/remove-promotion' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderRemovePromotionMutation {
orderRemovePromotion(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.removePromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.removePromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.removePromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.removePromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.removePromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->removePromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.RemovePromotion({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"removed": true
}
```
# Return Order
Source: https://docs.stateset.com/api-reference/orders/return
POST https://api.stateset.com/v1/orders/:id/return
This endpoint returns an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/orders/:id/return' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderReturnMutation {
orderReturn(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.return({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.return({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.return({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.return({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.return({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->return({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Return({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"returned": true
}
```
# Ship Order
Source: https://docs.stateset.com/api-reference/orders/ship
POST https://api.stateset.com/v1/orders/:id/ship
This endpoint ships an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/ship' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderShipMutation {
orderShip(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.ship({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.ship({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.ship({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.ship({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.ship({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->ship({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Ship({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"shipped": true
}
```
# Split Order
Source: https://docs.stateset.com/api-reference/orders/split
POST https://api.stateset.com/v1/orders/:id/split
This endpoint splits an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/split' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderSplitMutation {
orderSplit(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.split({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.split({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.split({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.split({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.split({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->split({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Split({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"split": true
}
```
# Tag Order
Source: https://docs.stateset.com/api-reference/orders/tag
POST https://api.stateset.com/v1/orders/:id/tag
This endpoint tags an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/tag' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderTagMutation {
orderTag(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.tag({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.tag({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.tag({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.tag({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.tag({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->tag({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Tag({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"tagged": true
}
```
# Update Order
Source: https://docs.stateset.com/api-reference/orders/update
POST https://api.stateset.com/v1/orders/:id/update
This endpoint updates an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/order/:id/update' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation orderUpdateMutation {
orderUpdate(id: "${orderId}") {
order {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const orders = await stateset.orders.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
orders = stateset.orders.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
orders = Stateset::Order.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
orders, err := stateset.Orders.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order orders = stateset.Orders.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$orders = $stateset->orders->update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var orders = await stateset.Orders.Update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "order",
"updated": true
}
```
# Overview
Source: https://docs.stateset.com/api-reference/overview
An introduction to the Stateset One Platform
# Stateset One Platform Documentation
## Introduction to Stateset One
Stateset One is an autonomous commerce operating system designed to streamline and optimize the entire commercial lifecycle for direct-to-consumer (DTC) merchants, warehouses, suppliers, and their developer partners. By unifying commerce, logistics, and finance operations, Stateset One enables seamless automation, efficient workflows, and data-driven decision-making. All platform features are accessible via GraphQL Mutations, Queries, and Subscriptions, and the solution is fully localized in English, Spanish, Catalan, Portuguese, French, Italian, Japanese, German, Dutch, and Romanian.
### Who Benefits from Stateset One?
1. **Direct-to-Consumer Merchants:**\
Ideal for brands looking to streamline operations, reduce manual processes, and drive growth with an agile and scalable finance and operations platform.
2. **Warehouses and Suppliers:**\
Enhance collaboration and efficiency with DTC merchants. Stateset One simplifies financial and operational workflows, making it easier to manage, fulfill, and optimize supply chain activities.
3. **Developers and Technical Partners:**\
Built with developers in mind, Stateset One’s modern, interoperable platform supports flexible integrations and smooth development experiences—perfect for agencies and technical teams working with commerce clients.
## Stateset Home & Onboarding
### Stateset Dashboard
#### Examples of Challenges Stateset One Solves
* **Manual Data Entry Across Multiple Apps**
* *Problem:* Merchants often juggle different applications to handle orders, shipping, returns, and other tasks, manually updating each system.
* *Solution:* Stateset One centralizes and automates reverse logistics and refund processing, eliminating manual entry.
* *Value:* Save time, reduce errors, and minimize operational costs.
* *Benefit:* Focus on strategic growth rather than repetitive administrative tasks.
## Core Features
* **3-Factor App Architecture with Durable Execution OS**\
Built to ensure reliability, resilience, and long-term maintainability.
* **Single Point GraphQL API Remote Data Joins**\
Seamlessly integrate and query data across multiple sources through a unified GraphQL endpoint.
* **Event Triggers and Webhooks**\
Automate responses to system events and integrate with external applications effortlessly.
* **Real-Time Global Search**\
Empower customer service and warehouse teams with instant access to the data they need.
* **Data Validation and Synchronization**\
Ensure data accuracy, consistency, and compliance across all connected systems.
* **Workflow Orchestration with Temporal**\
Automate, monitor, and optimize complex intercompany and operational processes.
* **Event-Driven Automation**\
Trigger workflows, notifications, and actions based on business events—no more manual intervention.
* **Automated Label Printing & Refund Processing**\
Streamline shipping, returns, and financial workflows to boost efficiency and reduce errors.
* **Tested QA Paths for Serverless Functions**\
Reliably scale operations and integrations with thoroughly tested serverless components.
## Stateset One Value Proposition
1. **Modern, Agile Technology:**\
Built on next-generation frameworks and distributed consensus protocols, Stateset One replaces outdated, siloed systems with a cutting-edge, integrated approach.
2. **Streamlined Workflows:**\
Automating intercompany processes dramatically reduces coordination time, allowing merchants, suppliers, and agencies to operate faster and more efficiently.
3. **Scalability and Adaptability:**\
Grow without accumulating technical debt. Stateset One’s scalable architecture supports evolving business models and ever-increasing volumes of data.
4. **Developer-Friendly Infrastructure:**\
Designed for integrators, the platform supports seamless third-party integrations, empowering technical partners to deliver robust solutions.
5. **Robust and Reliable:**\
Leveraging proven technologies and cloud services, Stateset One ensures reliability, security, and long-term stability for all customers.
By centralizing, automating, and optimizing commerce operations, Stateset One delivers tangible value, allowing businesses and their partners to focus on innovation, customer satisfaction, and growth.
# Create Packing List
Source: https://docs.stateset.com/api-reference/packinglist/create
POST https://api.stateset.com/v1/packing_lists
This endpoint creates a new packing_list
### Body
The id of the packing\_list to be created. If not provided, a new id will be generated.
The number of the packing\_list to be created. If not provided, a new number will be generated.
The deliveryDate of the packing\_list to be created. If not provided, a new deliveryDate will be generated.
The invoice\_number of the packing\_list to be created. If not provided, a new invoice\_number will be generated.
The arrivalDate of the packing\_list to be created. If not provided, a new arrivalDate will be generated.
The purchase\_order\_number of the packing\_list to be created. If not provided, a new purchase\_order\_number will be generated.
The ship\_per of the packing\_list to be created. If not provided, a new ship\_per will be generated.
The tracking\_number of the packing\_list to be created. If not provided, a new tracking\_number will be generated.
### Response
This is the unique identifier for the packing list.
This is the number associated with the packing list.
This is the date of delivery for the packing list.
This is the invoice number associated with the packing list.
This is the date of arrival for the packing list.
This is the purchase order number associated with the packing list.
This is the shipping information or carrier for the packing list.
This is the tracking number associated with the shipment for the packing list.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/packing_list' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```javascript Node.js theme={null}
var created = await stateset.packinglist.create({
id: ''
});
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"deliveryDate": "2020-01-01",
"arrivalDate": "2020-01-01",
"ship_per": "John Doe",
"tracking_number": "1234567890"
}
```
# Delete Packing List
Source: https://docs.stateset.com/api-reference/packinglist/delete
DELETE https://api.stateset.com/v1/packing_lists/:id
This endpoint deletes an existing packing_list.
### Body
The id of the packing\_list to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/packing_lists/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1"
"current_token": "abcdef"
}'
```
```javascript Node.js theme={null}
const deleted = await stateset.packinglists.del(
'pl_ODkRWQtx9NVsRX'
);
```
```graphQL GraphQL theme={null}
mutation deletePackingList ($packing_list_id: String!) {
delete_packing_list(where: {id: {_eq: $packing_list_id}}) {
affected_rows
}
}
```
```python Python theme={null}
deleted = stateset.packinglists.del(
'pl_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
deleted = Stateset::PackingLists.del(
'pl_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$deleted = $stateset->packinglists->del(
'pl_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
deleted, err := stateset.PackingLists.Del(
'pl_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
PackingLists deleted = stateset.packinglists.del(
'pl_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"id": "pl_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "packinglist",
"deleted": true
}
```
# Get Packing List
Source: https://docs.stateset.com/api-reference/packinglist/get
GET https://api.stateset.com/v1/packing_lists/:id
This endpoint gets or creates a new packing list.
### Body
This is the unique identifier for the packing list. If this is not provided, a new packing list will be created.
### Response
This is the unique identifier for the packing list.
This is the number associated with the packing list.
This is the date of delivery for the packing list.
This is the invoice number associated with the packing list.
This is the date of arrival for the packing list.
This is the purchase order number associated with the packing list.
This is the shipping information or carrier for the packing list.
This is the tracking number associated with the shipment for the packing list.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/packing_lists/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1",
}'
```
```graphQL GraphQL theme={null}
mutation addPackingList($packing_list: packing_list_insert_input!) {
insert_packing_list(objects: [$packing_list]) {
returning {
id
number
deliveryDate
arrivalDate
ship_per
tracking_number
}
}
}
```
```javascript Node.js theme={null}
var packinglists = await stateset.packinglists.retreive({
id: "1"
});
```
```python Python theme={null}
packinglists = stateset.packinglists.retreive({
"id": "1"
})
```
```ruby Ruby theme={null}
packinglists = Stateset::PackingLists.retreive({
"id": "1"
})
```
```php PHP theme={null}
$packinglists = $stateset->packinglists->retreive([
"id" => "1"
]);
```
```go Go theme={null}
packinglists, err := stateset.PackingLists.Retreive("1")
```
```java Java theme={null}
PackingLists packinglists = stateset.packinglists.retreive({
"id": "1"
});
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"deliveryDate": "2020-01-01",
"arrivalDate": "2020-01-01",
"ship_per": "John Doe",
"tracking_number": "1234567890"
}
```
## Packing List
| Name | Type | Description |
| ----------------------- | -------------------------- | ----------------------------------------------------------------- |
| id | Text (Primary Key, Unique) | Unique identifier for the packing list |
| number | Text (Nullable) | Number associated with the packing list |
| deliveryDate | Date (Nullable) | Date of delivery for the packing list |
| invoice\_number | Text (Nullable) | Invoice number associated with the packing list |
| arrivalDate | Date (Nullable) | Date of arrival for the packing list |
| purchase\_order\_number | Text (Nullable) | Purchase order number associated with the packing list |
| ship\_per | Text (Nullable) | Shipping information or carrier for the packing list |
| tracking\_number | Text (Nullable) | Tracking number associated with the shipment for the packing list |
## Packing List Item
| Name | Type | Description |
| ------------- | -------------------------- | -------------------------------------------------- |
| id | Text (Primary Key, Unique) | Unique identifier for the packing list item |
| sku | Text | Stock Keeping Unit (SKU) for the packing list item |
| description | Text | Description or additional details about the item |
| quantity | Integer | Quantity of the item in the packing list item |
| packing\_list | Text | Identifier for the associated packing list |
| arrived | Boolen | Whether or not the packing list item has arrived |
# List Packing List
Source: https://docs.stateset.com/api-reference/packinglist/list
GET https://api.stateset.com/v1/packing_list/:id
This endpoint list packing lists.
### Body
This is the limit of the packing lists.
This is the offset of the packing lists.
This is the order direction of the packing lists.
### Response
This is the unique identifier for the packing list.
This is the number associated with the packing list.
This is the date of delivery for the packing list.
This is the invoice number associated with the packing list.
This is the date of arrival for the packing list.
This is the purchase order number associated with the packing list.
This is the shipping information or carrier for the packing list.
This is the tracking number associated with the shipment for the packing list.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/packing_lists/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1",
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
packing_lists(limit: $limit, offset: $offset, order_by: {createdDate: $order_direction}) {
id
number
deliveryDate
arrivalDate
ship_per
tracking_number
}
}
```
```javascript Node.js theme={null}
var packinglists = await stateset.packinglists.retreive({
id: "1"
});
```
```python Python theme={null}
packinglists = stateset.packinglists.retreive({
"id": "1"
})
```
```ruby Ruby theme={null}
packinglists = Stateset::PackingLists.retreive({
"id": "1"
})
```
```php PHP theme={null}
$packinglists = $stateset->packinglists->retreive([
"id" => "1"
]);
```
```go Go theme={null}
packinglists, err := stateset.PackingLists.Retreive("1")
```
```java Java theme={null}
PackingLists packinglists = stateset.packinglists.retreive({
"id": "1"
});
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"deliveryDate": "2020-01-01",
"arrivalDate": "2020-01-01",
"ship_per": "John Doe",
"tracking_number": "1234567890"
}
```
## Packing List
| Name | Type | Description |
| ----------------------- | -------------------------- | ----------------------------------------------------------------- |
| id | Text (Primary Key, Unique) | Unique identifier for the packing list |
| number | Text (Nullable) | Number associated with the packing list |
| deliveryDate | Date (Nullable) | Date of delivery for the packing list |
| invoice\_number | Text (Nullable) | Invoice number associated with the packing list |
| arrivalDate | Date (Nullable) | Date of arrival for the packing list |
| purchase\_order\_number | Text (Nullable) | Purchase order number associated with the packing list |
| ship\_per | Text (Nullable) | Shipping information or carrier for the packing list |
| tracking\_number | Text (Nullable) | Tracking number associated with the shipment for the packing list |
## Packing List Item
| Name | Type | Description |
| ------------- | -------------------------- | -------------------------------------------------- |
| id | Text (Primary Key, Unique) | Unique identifier for the packing list item |
| sku | Text | Stock Keeping Unit (SKU) for the packing list item |
| description | Text | Description or additional details about the item |
| quantity | Integer | Quantity of the item in the packing list item |
| packing\_list | Text | Identifier for the associated packing list |
| arrived | Boolen | Whether or not the packing list item has arrived |
# Update Packing List
Source: https://docs.stateset.com/api-reference/packinglist/update
PUT https://api.stateset.com/v1/packing_lists/:id
This endpoint updates an existing packing_list.
### Body
The id of the packing\_list to be created. If not provided, a new id will be generated.
The number of the packing\_list to be created. If not provided, a new number will be generated.
The deliveryDate of the packing\_list to be created. If not provided, a new deliveryDate will be generated.
The invoice\_number of the packing\_list to be created. If not provided, a new invoice\_number will be generated.
The arrivalDate of the packing\_list to be created. If not provided, a new arrivalDate will be generated.
The purchase\_order\_number of the packing\_list to be created. If not provided, a new purchase\_order\_number will be generated.
The ship\_per of the packing\_list to be created. If not provided, a new ship\_per will be generated.
The tracking\_number of the packing\_list to be created. If not provided, a new tracking\_number will be generated.
### Response
This is the unique identifier for the packing list.
This is the number associated with the packing list.
This is the date of delivery for the packing list.
This is the invoice number associated with the packing list.
This is the date of arrival for the packing list.
This is the purchase order number associated with the packing list.
This is the shipping information or carrier for the packing list.
This is the tracking number associated with the shipment for the packing list.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/packing_list/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```graphQL GraphQL theme={null}
mutation (
$id: String
$packing_list: packing_list_set_input!
) {
update_packing_list (
where: { id : { _eq: $id }}
_set: $packing_list
) {
returning {
id
number
arrivalDate
deliveryDate
ship_per
shipment_type
invoice_number
purchase_order_number
tracking_number
status
source
destination
units
}
}
}
```
```javascript Node.js theme={null}
const updated = await stateset.packinglists.update(
'pi_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"deliveryDate": "2020-01-01",
"arrivalDate": "2020-01-01",
"ship_per": "John Doe",
"tracking_number": "1234567890"
}
```
# Create Packing List Item
Source: https://docs.stateset.com/api-reference/packinglistitem/create
POST https://api.stateset.com/v1/packing_list_items/:id
This endpoint creates a new packing list item
### Body
The ID of the packing list item to create.
The SKU of the packing list item to create.
The description of the packing list item to create.
The quantity of the packing list item to create.
The packing list of the packing list item to create.
The arrived of the packing list item to create.
### Response
The ID of the packing list item to create.
The SKU of the packing list item to create.
The description of the packing list item to create.
The quantity of the packing list item to create.
The packing list of the packing list item to create.
The arrived of the packing list item to create.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/packing_list_item/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "pi_ODkRWQtx9NVsRX",
"sku": "sku_1",
"description": "description_1",
"quantity": 1,
"packing_list": "pl_1",
"arrived": true
}'
```
```js Node.js theme={null}
const created = await stateset.packingItems.create(
'pi_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"id": "pi_ODkRWQtx9NVsRX",
"sku": "sku_1",
"description": "description_1",
"quantity": 1,
"packing_list": "pl_1",
"arrived": true
}
```
## Packing List Item
| Name | Type | Description |
| ------------- | -------------------------- | -------------------------------------------------- |
| id | Text (Primary Key, Unique) | Unique identifier for the packing list item |
| sku | Text | Stock Keeping Unit (SKU) for the packing list item |
| description | Text | Description or additional details about the item |
| quantity | Integer | Quantity of the item in the packing list item |
| packing\_list | Text | Identifier for the associated packing list |
| arrived | Boolen | Whether or not the packing list item has arrived |
# Delete Packing List Item
Source: https://docs.stateset.com/api-reference/packinglistitem/delete
DELETE https://api.stateset.com/v1/packing_list_items/:id
This endpoint deletes an existing packing list item.
### Body
The ID of the packing list item to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/packing_list_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1"
"current_token": "abcdef"
}'
```
```javascript Node.js theme={null}
const deleted = await stateset.packingItems.del(
'pi_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
deleted = stateset.packingItems.del(
'pi_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
deleted = Stateset::PackingItems.del(
'pi_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$deleted = $stateset->packingItems->del(
'pi_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
deleted, err := stateset.PackingItems.Del(
'pi_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
PackingItems deleted = stateset.packingItems.del(
'pi_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"success": 1
}
```
# Get Packing List Item
Source: https://docs.stateset.com/api-reference/packinglistitem/get
GET https://api.stateset.com/v1/packing_list_items/:id
This endpoint gets or creates a new packing list item.
### Body
This is the id of the packing list item
### Response
This is the id of the packing list item
This is the sku of the packing list item
This is the description of the packing list item
This is the quantity of the packing list item
This is the packing list of the packing list item
This is the arrived of the packing list item
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/packing_list_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1",
}'
```
```json Response theme={null}
{
{
"id": "1",
"sku": "1",
"description": "1",
"quantity": 1,
"packing_list": "1",
"arrived": true
}
}
```
## Packing List Item
| Name | Type | Description |
| ------------- | -------------------------- | -------------------------------------------------- |
| id | Text (Primary Key, Unique) | Unique identifier for the packing list item |
| sku | Text | Stock Keeping Unit (SKU) for the packing list item |
| description | Text | Description or additional details about the item |
| quantity | Integer | Quantity of the item in the packing list item |
| packing\_list | Text | Identifier for the associated packing list |
| arrived | Boolen | Whether or not the packing list item has arrived |
# Update Packing List Item
Source: https://docs.stateset.com/api-reference/packinglistitem/update
PUT https://api.stateset.com/v1/packing_list_items/:id
This endpoint updates an existing packing list item.
### Body
The ID of the packing list item to update.
The SKU of the packing list item to update.
The description of the packing list item to update.
The quantity of the packing list item to update.
The packing list of the packing list item to update.
The arrived of the packing list item to update.
### Response
The ID of the packing list item to update.
The SKU of the packing list item to update.
The description of the packing list item to update.
The quantity of the packing list item to update.
The packing list of the packing list item to update.
The arrived of the packing list item to update.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/packing_list_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1",
"sku": "1",
"description": "1",
"quantity": 1,
"packing_list": "1",
"arrived": true
}'
```
```json Response theme={null}
{
"id": "1",
"sku": "1",
"description": "1",
"quantity": 1,
"packing_list": "1",
"arrived": true
}
```
# Capture Payment
Source: https://docs.stateset.com/api-reference/payments/capture
POST https://api.stateset.com/v1/payments/:id/capture
Capture a previously authorized payment
This endpoint captures a previously authorized payment. Only payments created with `capture: false` can be captured.
## Authentication
This endpoint requires a valid API key with `payments:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The payment ID to capture
## Request Body
Amount to capture in cents (defaults to full authorization amount)
Text for customer's statement (max 22 chars)
Additional metadata to attach to the capture
### Response
Returns the captured payment object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/payments/pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/capture' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"amount": 15000
}'
```
```javascript Node.js theme={null}
const payment = await stateset.payments.capture(
'pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
amount: 15000
}
);
```
```python Python theme={null}
payment = stateset.payments.capture(
'pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
amount=15000
)
```
```json Response theme={null}
{
"id": "pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "payment",
"amount": 15000,
"amount_capturable": 0,
"amount_captured": 15000,
"currency": "USD",
"status": "succeeded",
"captured": true,
"captured_at": "2024-01-19T16:00:00Z",
"created_at": "2024-01-19T15:30:00Z",
"payment_method": {
"type": "card",
"card": {
"last4": "4242",
"brand": "visa"
}
},
"capture_details": {
"captured_amount": 15000,
"capture_time": "2024-01-19T16:00:00Z",
"processor_capture_id": "ch_capture_123456"
}
}
```
# Create Payment
Source: https://docs.stateset.com/api-reference/payments/create
POST https://api.stateset.com/v1/payments
Process a payment for an order or invoice
This endpoint processes payments through various payment methods and gateways. It supports credit cards, ACH, wire transfers, and digital wallets.
## Authentication
This endpoint requires a valid API key with `payments:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Payment amount in cents (e.g., 1000 for \$10.00)
ISO 4217 currency code (e.g., "USD", "EUR")
Payment method details
Payment type: "card", "ach", "wire", "paypal", "crypto"
Credit/debit card details (for type: "card")
Card number (will be tokenized)
Expiration month (1-12)
Expiration year (4 digits)
Card verification code
Pre-tokenized card token (alternative to raw card data)
ACH bank transfer details (for type: "ach")
Bank account number
Bank routing number
Account type: "checking" or "savings"
Associated order ID
Associated invoice ID
Customer ID making the payment
Payment description
Text to appear on customer's statement (max 22 chars)
Whether to immediately capture the payment (default: true)
Billing address for verification
Street address
Apartment/Suite number
City
State/Province code
Postal/ZIP code
ISO 3166-1 alpha-2 country code
Additional custom fields
### Response
Returns the created payment with processing status.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/payments' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"amount": 15000,
"currency": "USD",
"payment_method": {
"type": "card",
"card": {
"token": "tok_1234567890abcdef"
}
},
"order_id": "order_123456",
"customer_id": "cust_abc123",
"description": "Payment for Order #123456",
"capture": true
}'
```
```javascript Node.js theme={null}
const payment = await stateset.payments.create({
amount: 15000,
currency: "USD",
payment_method: {
type: "card",
card: {
token: "tok_1234567890abcdef"
}
},
order_id: "order_123456",
customer_id: "cust_abc123",
description: "Payment for Order #123456",
capture: true
});
```
```json Response theme={null}
{
"id": "pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "payment",
"amount": 15000,
"currency": "USD",
"status": "succeeded",
"captured": true,
"created_at": "2024-01-19T15:30:00Z",
"payment_method": {
"type": "card",
"card": {
"last4": "4242",
"brand": "visa",
"exp_month": 12,
"exp_year": 2025,
"fingerprint": "Xt5EWLLDS7FJjR1c"
}
},
"order_id": "order_123456",
"customer_id": "cust_abc123",
"description": "Payment for Order #123456",
"receipt_url": "https://receipts.stateset.com/pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"processor_response": {
"approved": true,
"authorization_code": "123456",
"avs_result": "Y",
"cvv_result": "M",
"network_transaction_id": "123456789"
}
}
```
# Get Payment
Source: https://docs.stateset.com/api-reference/payments/get
GET https://api.stateset.com/v1/payments/:id
Retrieve a specific payment by ID
This endpoint retrieves detailed information about a specific payment including transaction details and processing status.
## Authentication
This endpoint requires a valid API key with `payments:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the payment
## Query Parameters
Expand related objects. Options: "customer", "order", "invoice", "refunds", "disputes"
### Response
Unique payment identifier
Object type, always "payment"
Payment amount in cents
ISO 4217 currency code
Payment status: "pending", "processing", "succeeded", "failed", "cancelled"
Payment method details
Response from payment processor
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/payments/pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const payment = await stateset.payments.retrieve(
'pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
payment = stateset.payments.retrieve(
'pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "payment",
"amount": 15000,
"currency": "USD",
"status": "succeeded",
"captured": true,
"created_at": "2024-01-19T15:30:00Z",
"updated_at": "2024-01-19T15:30:05Z",
"payment_method": {
"type": "card",
"card": {
"last4": "4242",
"brand": "visa",
"exp_month": 12,
"exp_year": 2025,
"fingerprint": "Xt5EWLLDS7FJjR1c",
"country": "US",
"funding": "credit"
}
},
"order_id": "order_123456",
"invoice_id": null,
"customer_id": "cust_abc123",
"customer": {
"id": "cust_abc123",
"email": "john.doe@example.com",
"name": "John Doe"
},
"description": "Payment for Order #123456",
"statement_descriptor": "STATESET ORDER",
"receipt_url": "https://receipts.stateset.com/pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"receipt_number": "2234-5678",
"billing_address": {
"line1": "123 Main St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
},
"processor_response": {
"approved": true,
"authorization_code": "123456",
"avs_result": "Y",
"cvv_result": "M",
"network_transaction_id": "123456789",
"processor": "stripe",
"risk_score": 32
},
"refunds": {
"total_refunded": 0,
"has_more": false,
"data": []
},
"metadata": {
"order_reference": "ORD-2024-001",
"channel": "web"
}
}
```
# List Payments
Source: https://docs.stateset.com/api-reference/payments/list
GET https://api.stateset.com/v1/payments
List all payments with filtering and pagination
This endpoint retrieves a paginated list of payments. Use filters to narrow results by status, date range, amount, and more.
## Authentication
This endpoint requires a valid API key with `payments:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of items to return (default: 20, max: 100)
Cursor for pagination (payment ID)
Cursor for reverse pagination (payment ID)
Filter by status: "pending", "processing", "succeeded", "failed", "cancelled"
Filter by customer ID
Filter by order ID
Filter by invoice ID
Filter by payment method: "card", "ach", "wire", "paypal"
Filter by creation date start (ISO 8601)
Filter by creation date end (ISO 8601)
Minimum amount in cents
Maximum amount in cents
Filter by currency code
### Response
Object type, always "list"
Array of payment objects
Whether more items exist
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/payments?status=succeeded&limit=10' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const payments = await stateset.payments.list({
status: 'succeeded',
limit: 10,
created_from: '2024-01-01'
});
```
```python Python theme={null}
payments = stateset.payments.list(
status='succeeded',
limit=10,
created_from='2024-01-01'
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "payment",
"amount": 15000,
"currency": "USD",
"status": "succeeded",
"created_at": "2024-01-19T15:30:00Z",
"payment_method": {
"type": "card",
"card": {
"last4": "4242",
"brand": "visa"
}
},
"customer_id": "cust_abc123",
"order_id": "order_123456",
"description": "Payment for Order #123456"
},
{
"id": "pay_7823f083-bb2c-54d6-bf6d-1b8e3fc75f41",
"object": "payment",
"amount": 25000,
"currency": "USD",
"status": "succeeded",
"created_at": "2024-01-19T12:15:00Z",
"payment_method": {
"type": "ach",
"ach": {
"last4": "6789",
"bank_name": "Chase"
}
},
"customer_id": "cust_def456",
"invoice_id": "inv_789012",
"description": "Invoice payment"
}
],
"has_more": true,
"url": "/v1/payments"
}
```
# Refund Payment
Source: https://docs.stateset.com/api-reference/payments/refund
POST https://api.stateset.com/v1/payments/:id/refund
Create a full or partial refund for a payment
This endpoint creates a refund for a captured payment. Refunds can be partial or full amount.
## Authentication
This endpoint requires a valid API key with `payments:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The payment ID to refund
## Request Body
Amount to refund in cents (defaults to full payment amount)
Refund reason: "duplicate", "fraudulent", "requested\_by\_customer", "defective", "other"
Internal notes about the refund
Whether to send refund notification email (default: true)
Additional metadata for the refund
### Response
Returns the refund object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/payments/pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/refund' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"amount": 5000,
"reason": "requested_by_customer",
"notes": "Customer returned item"
}'
```
```javascript Node.js theme={null}
const refund = await stateset.payments.refund(
'pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
amount: 5000,
reason: "requested_by_customer",
notes: "Customer returned item"
}
);
```
```python Python theme={null}
refund = stateset.payments.refund(
'pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
amount=5000,
reason="requested_by_customer",
notes="Customer returned item"
)
```
```json Response theme={null}
{
"id": "ref_1234567890abcdef",
"object": "refund",
"amount": 5000,
"currency": "USD",
"payment_id": "pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"status": "succeeded",
"reason": "requested_by_customer",
"notes": "Customer returned item",
"created_at": "2024-01-20T10:00:00Z",
"processed_at": "2024-01-20T10:00:05Z",
"payment": {
"id": "pay_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"amount": 15000,
"amount_refunded": 5000,
"refunds_count": 1
},
"processor_refund_id": "re_1234567890",
"receipt_url": "https://receipts.stateset.com/ref_1234567890abcdef",
"metadata": {
"return_id": "ret_abc123"
}
}
```
# Create Picks
Source: https://docs.stateset.com/api-reference/picks/create
POST https://api.stateset.com/v1/picks
This endpoint creates a new picks
### Body
The id of the packing\_list to be created. If not provided, a new id will be generated.
The number of the packing\_list to be created. If not provided, a new number will be generated.
The delivery date of the packing\_list to be created. If not provided, a new delivery date will be generated.
The arrival date of the packing\_list to be created. If not provided, a new arrival date will be generated.
The ship per of the packing\_list to be created. If not provided, a new ship per will be generated.
The tracking number of the packing\_list to be created. If not provided, a new tracking number will be generated.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/packing_list' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```javascript Node.js theme={null}
var created = await stateset.packinglist.create({
id: ''
});
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"deliveryDate": "2020-01-01",
"arrivalDate": "2020-01-01",
"ship_per": "John Doe",
"tracking_number": "1234567890"
}
```
# Delete Pick
Source: https://docs.stateset.com/api-reference/picks/delete
DELETE https://api.stateset.com/v1/picks/:id
This endpoint deletes an existing pick.
### Body
The id of the pick to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/picks/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "pl_ODkRWQtx9NVsRX"
}'
```
```javascript Node.js theme={null}
const deleted = await stateset.picks.del(
'pl_ODkRWQtx9NVsRX'
);
```
```graphQL GraphQL theme={null}
mutation deletePicks ($pick_id: String!) {
delete_picks(where: {id: {_eq: $pick_id}}) {
affected_rows
}
}
```
```python Python theme={null}
deleted = stateset.picks.del(
'pl_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
deleted = Stateset::picks.del(
'pl_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$deleted = $stateset->picks->del(
'pl_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
deleted, err := stateset.picks.Del(
'pl_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
picks deleted = stateset.picks.del(
'pl_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"id": "pi_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "picks",
"deleted": true
}
```
# Get Pick
Source: https://docs.stateset.com/api-reference/picks/get
GET https://api.stateset.com/v1/picks
This endpoint gets a pick
### Body
This is the unique identifier for the pick.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/picks' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1",
}'
```
```graphQL GraphQL theme={null}
query MyPicks {
picks {
id
number
date_created
bill_of_materials_number
location
pick_method
site
status
work_order_number
pick_line_items {
id
part_name
part_number
pick_number
pick_plan
quantity_picked
quantity_to_pick
status
}
}
}
```
```javascript Node.js theme={null}
var picks = await stateset.picks.retreive({
id: "1"
});
```
```python Python theme={null}
pickss = stateset.picks.retreive({
"id": "1"
})
```
```ruby Ruby theme={null}
picks = Stateset::Picks.retreive({
"id": "1"
})
```
```php PHP theme={null}
$picks = $stateset->picks->retreive([
"id" => "1"
]);
```
```go Go theme={null}
picks, err := stateset.Picks.Retreive("1")
```
```java Java theme={null}
Picks picks = stateset.picks.retreive({
"id": "1"
});
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"date_created": "2021-01-01T00:00:00Z",
"bill_of_materials_number": "1",
"location": "1",
"pick_method": "1",
"site": "1",
"status": "1",
"work_order_number": "1",
"pick_line_items": [
{
"id": "1",
"part_name": "1",
"part_number": "1",
"pick_number": "1",
"pick_plan": "1",
"quantity_picked": "1",
"quantity_to_pick": "1",
"status": "1"
}
]
}
```
## Picks
# List Picks
Source: https://docs.stateset.com/api-reference/picks/list
GET https://api.stateset.com/v1/picks
This endpoint gets a pick
### Body
This is the limit of the picks.
This is the offset of the picks.
This is the order direction of the picks.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/picks' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "1",
}'
```
```graphQL GraphQL theme={null}
query MyPicks {
picks {
id
number
date_created
bill_of_materials_number
location
pick_method
site
status
work_order_number
pick_line_items {
id
part_name
part_number
pick_number
pick_plan
quantity_picked
quantity_to_pick
status
}
}
}
```
```javascript Node.js theme={null}
var picks = await stateset.picks.list({
id: "1"
});
```
```python Python theme={null}
pickss = stateset.picks.list({
"id": "1"
})
```
```ruby Ruby theme={null}
picks = Stateset::Picks.list({
"id": "1"
})
```
```php PHP theme={null}
$picks = $stateset->picks->list([
"id" => "1"
]);
```
```go Go theme={null}
picks, err := stateset.Picks.list("1")
```
```java Java theme={null}
Picks picks = stateset.picks.list({
"id": "1"
});
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"date_created": "2021-01-01T00:00:00Z",
"bill_of_materials_number": "1",
"location": "1",
"pick_method": "1",
"site": "1",
"status": "1",
"work_order_number": "1",
"pick_line_items": [
{
"id": "1",
"part_name": "1",
"part_number": "1",
"pick_number": "1",
"pick_plan": "1",
"quantity_picked": "1",
"quantity_to_pick": "1",
"status": "1"
}
]
}
```
## Picks
# Update Pick
Source: https://docs.stateset.com/api-reference/picks/update
POST https://api.stateset.com/v1/picks/update
This endpoint updates a pick
### Body
The id of the packing\_list to be created. If not provided, a new id will be generated.
The number of the packing\_list to be created. If not provided, a new number will be generated.
The date\_created of the packing\_list to be created. If not provided, a new date\_created will be generated.
The bill\_of\_materials\_number of the packing\_list to be created. If not provided, a new bill\_of\_materials\_number will be generated.
The location of the packing\_list to be created. If not provided, a new location will be generated.
The pick\_method of the packing\_list to be created. If not provided, a new pick\_method will be generated.
The site of the packing\_list to be created. If not provided, a new site will be generated.
The status of the packing\_list to be created. If not provided, a new status will be generated.
The work\_order\_number of the packing\_list to be created. If not provided, a new work\_order\_number will be generated.
### Response
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
This is the unique identifier for the pick
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/packing_list' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```javascript Node.js theme={null}
var created = await stateset.packinglist.create({
id: ''
});
```
```json Response theme={null}
{
"id": "1",
"number": "1",
"deliveryDate": "2020-01-01",
"arrivalDate": "2020-01-01",
"ship_per": "John Doe",
"tracking_number": "1234567890"
}
```
# Calculate Price
Source: https://docs.stateset.com/api-reference/pricing-rules/calculate
POST https://api.stateset.com/v1/pricing-rules/calculate
Calculate prices with applicable pricing rules
This endpoint calculates final prices for products by applying all applicable pricing rules based on customer, quantity, and other conditions.
## Authentication
This endpoint requires a valid API key with `pricing:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Customer ID for customer-specific pricing
Customer segment if customer\_id not provided
Sales channel: "web", "pos", "b2b", "marketplace"
Products to calculate pricing for
Product ID
Product variant ID
Quantity
Original list price in cents
Product category ID
Product SKU
Currency code (default: account currency)
Date for time-based pricing (ISO 8601)
### Response
Returns calculated prices with applied rules breakdown.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/pricing-rules/calculate' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"customer_segment": "wholesale",
"channel": "b2b",
"items": [
{
"product_id": "prod_electronics_001",
"quantity": 75,
"list_price": 9999,
"category_id": "cat_electronics"
},
{
"product_id": "prod_accessories_001",
"quantity": 10,
"list_price": 1999,
"category_id": "cat_accessories"
}
]
}'
```
```javascript Node.js theme={null}
const calculation = await stateset.pricingRules.calculate({
customer_segment: "wholesale",
channel: "b2b",
items: [
{
product_id: "prod_electronics_001",
quantity: 75,
list_price: 9999,
category_id: "cat_electronics"
},
{
product_id: "prod_accessories_001",
quantity: 10,
list_price: 1999,
category_id: "cat_accessories"
}
]
});
```
```json Response theme={null}
{
"object": "price_calculation",
"items": [
{
"product_id": "prod_electronics_001",
"quantity": 75,
"list_price": 9999,
"final_price": 8499,
"unit_discount": 1500,
"total_discount": 112500,
"subtotal": 637425,
"applied_rules": [
{
"rule_id": "pr_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"rule_name": "B2B Volume Pricing - Electronics",
"type": "volume_based",
"discount_percentage": 15,
"quantity_tier": "50-99"
}
]
},
{
"product_id": "prod_accessories_001",
"quantity": 10,
"list_price": 1999,
"final_price": 1999,
"unit_discount": 0,
"total_discount": 0,
"subtotal": 19990,
"applied_rules": [],
"reason_no_discount": "category_not_eligible"
}
],
"summary": {
"total_list_price": 769915,
"total_discount": 112500,
"total_final_price": 657415,
"discount_percentage": 14.6,
"currency": "USD"
},
"rules_considered": 3,
"rules_applied": 1,
"calculation_timestamp": "2024-06-20T16:30:00Z"
}
```
# Create Pricing Rule
Source: https://docs.stateset.com/api-reference/pricing-rules/create
POST https://api.stateset.com/v1/pricing-rules
Create a dynamic pricing rule for products or customer segments
This endpoint creates a new pricing rule that automatically adjusts product prices based on various conditions like customer type, quantity, date ranges, or inventory levels.
## Authentication
This endpoint requires a valid API key with `pricing:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Pricing rule name
Rule type: "customer\_specific", "volume\_based", "time\_based", "channel\_based", "dynamic"
Rule priority (lower numbers take precedence)
Price adjustment configuration
Adjustment method: "fixed\_price", "percentage\_discount", "fixed\_discount", "markup", "formula"
Adjustment value (percentage for percentage methods, cents for fixed methods)
Pricing formula (for formula method)
Round final price to nearest value in cents
Minimum margin percentage to maintain
Conditions for rule application
Applicable customer segment IDs
Specific customer IDs
Applicable product IDs
Applicable category IDs
SKU patterns (supports wildcards)
Sales channels: "web", "pos", "b2b", "marketplace"
Volume-based pricing tiers
Minimum quantity for this tier
Price adjustment for this tier
Dynamic pricing based on inventory
Low stock threshold
High stock threshold
Price adjustment curve: "linear", "exponential", "stepped"
Rule validity period
Start date (ISO 8601)
End date (ISO 8601)
Time-based schedule
Active days (0-6, Sunday is 0)
Active time ranges
Currency code (defaults to account currency)
Rule status: "active", "scheduled", "inactive"
Additional custom fields
### Response
Returns the created pricing rule object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/pricing-rules' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"name": "B2B Volume Pricing - Electronics",
"type": "volume_based",
"priority": 10,
"price_adjustment": {
"method": "percentage_discount",
"round_to": 99,
"minimum_margin": 15
},
"conditions": {
"customer_segments": ["wholesale", "distributor"],
"category_ids": ["cat_electronics"],
"quantity_breaks": [
{
"min_quantity": 10,
"adjustment": {
"method": "percentage_discount",
"value": 10
}
},
{
"min_quantity": 50,
"adjustment": {
"method": "percentage_discount",
"value": 15
}
},
{
"min_quantity": 100,
"adjustment": {
"method": "percentage_discount",
"value": 20
}
}
]
},
"validity": {
"start_date": "2024-01-01T00:00:00Z"
},
"status": "active"
}'
```
```javascript Node.js theme={null}
const pricingRule = await stateset.pricingRules.create({
name: "B2B Volume Pricing - Electronics",
type: "volume_based",
priority: 10,
price_adjustment: {
method: "percentage_discount",
round_to: 99,
minimum_margin: 15
},
conditions: {
customer_segments: ["wholesale", "distributor"],
category_ids: ["cat_electronics"],
quantity_breaks: [
{
min_quantity: 10,
adjustment: {
method: "percentage_discount",
value: 10
}
},
{
min_quantity: 50,
adjustment: {
method: "percentage_discount",
value: 15
}
},
{
min_quantity: 100,
adjustment: {
method: "percentage_discount",
value: 20
}
}
]
},
validity: {
start_date: "2024-01-01T00:00:00Z"
},
status: "active"
});
```
```json Response theme={null}
{
"id": "pr_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "pricing_rule",
"name": "B2B Volume Pricing - Electronics",
"type": "volume_based",
"priority": 10,
"price_adjustment": {
"method": "percentage_discount",
"round_to": 99,
"minimum_margin": 15
},
"conditions": {
"customer_segments": ["wholesale", "distributor"],
"customer_ids": [],
"product_ids": [],
"category_ids": ["cat_electronics"],
"sku_patterns": [],
"channels": [],
"quantity_breaks": [
{
"min_quantity": 10,
"max_quantity": 49,
"adjustment": {
"method": "percentage_discount",
"value": 10
}
},
{
"min_quantity": 50,
"max_quantity": 99,
"adjustment": {
"method": "percentage_discount",
"value": 15
}
},
{
"min_quantity": 100,
"max_quantity": null,
"adjustment": {
"method": "percentage_discount",
"value": 20
}
}
]
},
"validity": {
"start_date": "2024-01-01T00:00:00Z",
"end_date": null,
"is_active": true,
"schedule": null
},
"currency": "USD",
"status": "active",
"created_at": "2024-01-20T13:00:00Z",
"updated_at": "2024-01-20T13:00:00Z",
"created_by": "user_123",
"statistics": {
"times_applied": 0,
"total_discount_given": 0,
"affected_orders": 0,
"last_applied": null
}
}
```
# Get Pricing Rule
Source: https://docs.stateset.com/api-reference/pricing-rules/get
GET https://api.stateset.com/v1/pricing-rules/:id
Retrieve details of a specific pricing rule
This endpoint retrieves detailed information about a specific pricing rule, including its conditions, application statistics, and current status.
## Authentication
This endpoint requires a valid API key with `pricing:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the pricing rule
### Response
Returns the pricing rule object if found.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/pricing-rules/pr_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const pricingRule = await stateset.pricingRules.retrieve(
'pr_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
pricing_rule = stateset.pricing_rules.retrieve(
'pr_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "pr_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "pricing_rule",
"name": "B2B Volume Pricing - Electronics",
"type": "volume_based",
"priority": 10,
"price_adjustment": {
"method": "percentage_discount",
"round_to": 99,
"minimum_margin": 15
},
"conditions": {
"customer_segments": ["wholesale", "distributor"],
"customer_ids": [],
"product_ids": [],
"category_ids": ["cat_electronics"],
"sku_patterns": [],
"channels": [],
"quantity_breaks": [
{
"min_quantity": 10,
"max_quantity": 49,
"adjustment": {
"method": "percentage_discount",
"value": 10
}
},
{
"min_quantity": 50,
"max_quantity": 99,
"adjustment": {
"method": "percentage_discount",
"value": 15
}
},
{
"min_quantity": 100,
"max_quantity": null,
"adjustment": {
"method": "percentage_discount",
"value": 20
}
}
]
},
"validity": {
"start_date": "2024-01-01T00:00:00Z",
"end_date": null,
"is_active": true,
"schedule": null
},
"currency": "USD",
"status": "active",
"created_at": "2024-01-20T13:00:00Z",
"updated_at": "2024-05-15T09:30:00Z",
"created_by": "user_123",
"statistics": {
"times_applied": 342,
"total_discount_given": 458950,
"affected_orders": 342,
"last_applied": "2024-06-20T15:45:00Z",
"average_discount_per_order": 1342,
"top_customers": [
{
"customer_id": "cust_wholesale_001",
"times_used": 45,
"total_saved": 67500
}
]
}
}
```
# Bulk Update Products
Source: https://docs.stateset.com/api-reference/products/bulk-update
POST https://api.stateset.com/v1/products/bulk-update
Update multiple products in a single request
This endpoint allows updating up to 100 products in a single request. Use this for bulk price changes, inventory updates, or status changes.
### Request Body
Array of product updates (max 100 items)
Product ID to update
Updated pricing information
Updated inventory settings
Updated status
Updated metadata
Updated tags
If true, validates the updates without applying them (default: false)
### Response
Successfully updated products
Products that failed to update with error details
Summary of the bulk operation
Total number of products in request
Number of successfully updated products
Number of failed updates
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/products/bulk-update' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"updates": [
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"price": {
"amount": 11999
},
"tags": ["electronics", "audio", "sale", "clearance"]
},
{
"id": "prod_abc123def456",
"price": {
"amount": 6999
},
"inventory": {
"low_stock_threshold": 25
}
},
{
"id": "prod_xyz789ghi012",
"status": "archived"
}
]
}'
```
```graphQL GraphQL theme={null}
mutation BulkUpdateProducts($updates: [ProductUpdate!]!) {
bulkUpdateProducts(updates: $updates) {
updated {
id
name
sku
updated_at
}
errors {
product_id
error
}
summary {
total
successful
failed
}
}
}
```
```javascript Node.js theme={null}
const result = await stateset.products.bulkUpdate({
updates: [
{
id: "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
price: { amount: 11999 },
tags: ["electronics", "audio", "sale", "clearance"]
},
{
id: "prod_abc123def456",
price: { amount: 6999 },
inventory: { low_stock_threshold: 25 }
},
{
id: "prod_xyz789ghi012",
status: "archived"
}
]
});
```
```python Python theme={null}
result = stateset.products.bulk_update({
"updates": [
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"price": {"amount": 11999},
"tags": ["electronics", "audio", "sale", "clearance"]
},
{
"id": "prod_abc123def456",
"price": {"amount": 6999},
"inventory": {"low_stock_threshold": 25}
},
{
"id": "prod_xyz789ghi012",
"status": "archived"
}
]
})
```
```json Response theme={null}
{
"updated": [
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"updated_at": "2024-01-15T17:30:00Z"
},
{
"id": "prod_abc123def456",
"name": "Sport Wireless Earbuds",
"sku": "SWE-001",
"updated_at": "2024-01-15T17:30:00Z"
}
],
"errors": [
{
"product_id": "prod_xyz789ghi012",
"error": "Product not found"
}
],
"summary": {
"total": 3,
"successful": 2,
"failed": 1
}
}
```
# Create Product
Source: https://docs.stateset.com/api-reference/products/create
POST https://api.stateset.com/v1/products
Create a new product with inventory tracking and variant support
This endpoint creates a new product and automatically initializes inventory tracking. Products support multiple variants and can be associated with suppliers and categories.
## Authentication
This endpoint requires a valid API key with `products:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Product name for display
Unique stock keeping unit (SKU) identifier
Detailed product description
Product category (e.g., "Electronics", "Clothing", "Home & Garden")
Brand or manufacturer name
Pricing information
Price in cents (e.g., 1999 for \$19.99)
ISO 4217 currency code (e.g., "USD", "EUR")
Original price for displaying discounts
Cost information for margin calculations
Cost in cents
ISO 4217 currency code
Inventory settings
Whether to track inventory levels (default: true)
Initial stock quantity
Threshold for low stock alerts
Whether to allow orders when out of stock
Primary warehouse ID for this product
Product dimensions for shipping calculations
Weight in pounds
Length in inches
Width in inches
Height in inches
Product variants (e.g., different sizes, colors)
Variant SKU
Variant name
Variant options (e.g., size: "M", color: "Blue")
Variant-specific pricing (overrides base product price)
Variant-specific inventory settings
UPC, EAN, or other barcode
Product images
Image URL
Alt text for accessibility
Display order (1-based)
Associated variant IDs
Supplier information
Existing supplier ID
Supplier's SKU for this product
Expected days for reordering
Minimum quantity for supplier orders
Additional custom fields as key-value pairs
Array of string tags for categorization and search
Product status: "active", "draft", or "archived" (default: "active")
### Response
Unique product identifier
Always "product"
ISO 8601 timestamp of creation
ISO 8601 timestamp of last update
Product name
Product SKU
Product status
Array of product variants with their IDs
Summary of inventory across all variants
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/products' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"description": "Premium noise-cancelling wireless headphones with 30-hour battery life",
"category": "Electronics",
"brand": "AudioTech",
"price": {
"amount": 14999,
"currency": "USD",
"compare_at": 19999
},
"cost": {
"amount": 7500,
"currency": "USD"
},
"inventory": {
"track_inventory": true,
"quantity": 150,
"low_stock_threshold": 20,
"allow_backorder": false
},
"dimensions": {
"weight": 0.5,
"length": 8,
"width": 7,
"height": 3
},
"variants": [
{
"sku": "WBH-001-BLK",
"name": "Wireless Bluetooth Headphones - Black",
"options": {
"color": "Black"
},
"inventory": {
"quantity": 100
}
},
{
"sku": "WBH-001-WHT",
"name": "Wireless Bluetooth Headphones - White",
"options": {
"color": "White"
},
"inventory": {
"quantity": 50
}
}
],
"images": [
{
"url": "https://example.com/images/headphones-main.jpg",
"alt_text": "Wireless Bluetooth Headphones",
"position": 1
}
],
"tags": ["electronics", "audio", "wireless", "bluetooth"]
}'
```
```graphQL GraphQL theme={null}
mutation CreateProduct {
createProduct(input: {
name: "Wireless Bluetooth Headphones"
sku: "WBH-001"
description: "Premium noise-cancelling wireless headphones with 30-hour battery life"
category: "Electronics"
brand: "AudioTech"
price: {
amount: 14999
currency: "USD"
compare_at: 19999
}
inventory: {
track_inventory: true
quantity: 150
low_stock_threshold: 20
}
}) {
id
name
sku
status
inventory_summary {
total_quantity
available_quantity
reserved_quantity
}
}
}
```
```javascript Node.js theme={null}
const product = await stateset.products.create({
name: "Wireless Bluetooth Headphones",
sku: "WBH-001",
description: "Premium noise-cancelling wireless headphones with 30-hour battery life",
category: "Electronics",
brand: "AudioTech",
price: {
amount: 14999,
currency: "USD",
compare_at: 19999
},
inventory: {
track_inventory: true,
quantity: 150,
low_stock_threshold: 20,
allow_backorder: false
},
variants: [
{
sku: "WBH-001-BLK",
name: "Wireless Bluetooth Headphones - Black",
options: { color: "Black" },
inventory: { quantity: 100 }
},
{
sku: "WBH-001-WHT",
name: "Wireless Bluetooth Headphones - White",
options: { color: "White" },
inventory: { quantity: 50 }
}
]
});
```
```python Python theme={null}
product = stateset.products.create({
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"description": "Premium noise-cancelling wireless headphones with 30-hour battery life",
"category": "Electronics",
"brand": "AudioTech",
"price": {
"amount": 14999,
"currency": "USD",
"compare_at": 19999
},
"inventory": {
"track_inventory": True,
"quantity": 150,
"low_stock_threshold": 20,
"allow_backorder": False
}
})
```
```json Response theme={null}
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "product",
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T10:30:00Z",
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"description": "Premium noise-cancelling wireless headphones with 30-hour battery life",
"category": "Electronics",
"brand": "AudioTech",
"status": "active",
"price": {
"amount": 14999,
"currency": "USD",
"compare_at": 19999
},
"cost": {
"amount": 7500,
"currency": "USD"
},
"inventory": {
"track_inventory": true,
"low_stock_threshold": 20,
"allow_backorder": false
},
"inventory_summary": {
"total_quantity": 150,
"available_quantity": 150,
"reserved_quantity": 0,
"by_warehouse": {
"wh_001": {
"available": 150,
"reserved": 0
}
}
},
"variants": [
{
"id": "var_1234567890",
"sku": "WBH-001-BLK",
"name": "Wireless Bluetooth Headphones - Black",
"options": {
"color": "Black"
},
"inventory": {
"quantity": 100,
"available": 100,
"reserved": 0
}
},
{
"id": "var_0987654321",
"sku": "WBH-001-WHT",
"name": "Wireless Bluetooth Headphones - White",
"options": {
"color": "White"
},
"inventory": {
"quantity": 50,
"available": 50,
"reserved": 0
}
}
],
"images": [
{
"id": "img_abc123",
"url": "https://example.com/images/headphones-main.jpg",
"alt_text": "Wireless Bluetooth Headphones",
"position": 1
}
],
"tags": ["electronics", "audio", "wireless", "bluetooth"],
"metadata": {}
}
```
# Delete Product
Source: https://docs.stateset.com/api-reference/products/delete
DELETE https://api.stateset.com/v1/products/:id
Delete a product from the catalog
Deleting a product is irreversible. Products with existing orders cannot be deleted and must be archived instead.
### Path Parameters
The unique identifier of the product to delete
### Response
The ID of the deleted product
Always "product"
Always true for successful deletion
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/products/prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```graphQL GraphQL theme={null}
mutation DeleteProduct($id: ID!) {
deleteProduct(id: $id) {
id
deleted
}
}
```
```javascript Node.js theme={null}
const result = await stateset.products.delete(
'prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
result = stateset.products.delete(
'prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "product",
"deleted": true
}
```
### Error Responses
Error object when deletion fails
Type of error (e.g., "invalid\_request", "product\_has\_orders")
Human-readable error message
Error code for programmatic handling
```json Error Response theme={null}
{
"error": {
"type": "product_has_orders",
"message": "Cannot delete product with existing orders. Archive the product instead.",
"code": "PRODUCT_HAS_ORDERS"
}
}
```
# Get Product
Source: https://docs.stateset.com/api-reference/products/get
GET https://api.stateset.com/v1/products/:id
Retrieve a single product by ID with full details including variants and inventory
### Path Parameters
The unique identifier of the product to retrieve
### Query Parameters
Include real-time inventory data (default: true)
Include all product variants (default: true)
Filter inventory data by specific warehouse
### Response
Unique product identifier
Always "product"
ISO 8601 timestamp of creation
ISO 8601 timestamp of last update
Product name
Product SKU
Product description
Product category
Brand name
Pricing information including amount, currency, and compare\_at price
Cost information for margin calculations
Product status: "active", "draft", or "archived"
Inventory settings and current levels
Aggregated inventory data across all variants and warehouses
Array of product variants with full details
Product images with URLs and metadata
Product dimensions for shipping calculations
Supplier information if configured
Array of product tags
Custom metadata fields
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/products/prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```graphQL GraphQL theme={null}
query GetProduct($id: ID!) {
product(id: $id) {
id
name
sku
description
category
brand
status
price {
amount
currency
compare_at
}
inventory_summary {
total_quantity
available_quantity
reserved_quantity
}
variants {
id
sku
name
options
inventory {
quantity
available
reserved
}
}
images {
url
alt_text
position
}
}
}
```
```javascript Node.js theme={null}
const product = await stateset.products.retrieve(
'prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
include_inventory: true,
include_variants: true
}
);
```
```python Python theme={null}
product = stateset.products.retrieve(
'prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
include_inventory=True,
include_variants=True
)
```
```json Response theme={null}
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "product",
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T14:22:00Z",
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"description": "Premium noise-cancelling wireless headphones with 30-hour battery life",
"category": "Electronics",
"brand": "AudioTech",
"status": "active",
"price": {
"amount": 14999,
"currency": "USD",
"compare_at": 19999
},
"cost": {
"amount": 7500,
"currency": "USD"
},
"inventory": {
"track_inventory": true,
"low_stock_threshold": 20,
"allow_backorder": false
},
"inventory_summary": {
"total_quantity": 150,
"available_quantity": 145,
"reserved_quantity": 5,
"by_warehouse": {
"wh_001": {
"available": 145,
"reserved": 5
}
}
},
"dimensions": {
"weight": 0.5,
"length": 8,
"width": 7,
"height": 3
},
"variants": [
{
"id": "var_1234567890",
"sku": "WBH-001-BLK",
"name": "Wireless Bluetooth Headphones - Black",
"options": {
"color": "Black"
},
"price": null,
"inventory": {
"quantity": 100,
"available": 97,
"reserved": 3
},
"barcode": null
},
{
"id": "var_0987654321",
"sku": "WBH-001-WHT",
"name": "Wireless Bluetooth Headphones - White",
"options": {
"color": "White"
},
"price": null,
"inventory": {
"quantity": 50,
"available": 48,
"reserved": 2
},
"barcode": null
}
],
"images": [
{
"id": "img_abc123",
"url": "https://example.com/images/headphones-main.jpg",
"alt_text": "Wireless Bluetooth Headphones",
"position": 1,
"variant_ids": []
}
],
"supplier": null,
"tags": ["electronics", "audio", "wireless", "bluetooth"],
"metadata": {}
}
```
```json Error Response (404 Not Found) theme={null}
{
"error": {
"code": "RESOURCE_NOT_FOUND",
"message": "Product not found",
"details": {
"resource": "product",
"id": "prod_abc123"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (401 Unauthorized) theme={null}
{
"error": {
"code": "INVALID_API_KEY",
"message": "The API key provided is invalid or has been revoked",
"request_id": "req_abc123def456"
}
}
```
# List Products
Source: https://docs.stateset.com/api-reference/products/list
GET https://api.stateset.com/v1/products
Retrieve a paginated list of products with filtering and search capabilities
### Query Parameters
Number of products to return (default: 20, max: 100)
Number of products to skip (for pagination)
Cursor for pagination (alternative to offset)
Filter by status: "active", "draft", or "archived"
Filter by product category
Filter by brand name
Search products by name, SKU, or description
Filter by exact SKU match
Filter by tags (comma-separated)
Minimum price filter (in cents)
Maximum price filter (in cents)
Filter products with available inventory
Filter products below low stock threshold
Filter products created after this date (ISO 8601)
Filter products created before this date (ISO 8601)
Filter products updated after this date (ISO 8601)
Sort field: "created\_at", "updated\_at", "name", "price", "sku" (default: "created\_at")
Sort order: "asc" or "desc" (default: "desc")
Include variant details in response (default: false)
Include inventory summary (default: false)
### Response
Always "list"
Array of product objects
Whether there are more products to retrieve
Total number of products matching the filters
Cursor for retrieving the next page
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/products?limit=10&status=active&category=Electronics' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```graphQL GraphQL theme={null}
query ListProducts(
$limit: Int
$offset: Int
$status: ProductStatus
$category: String
$search: String
) {
products(
limit: $limit
offset: $offset
status: $status
category: $category
search: $search
) {
data {
id
name
sku
category
brand
status
price {
amount
currency
}
inventory_summary {
total_quantity
available_quantity
}
}
has_more
total_count
}
}
```
```javascript Node.js theme={null}
const products = await stateset.products.list({
limit: 10,
status: 'active',
category: 'Electronics',
in_stock: true,
sort_by: 'price',
sort_order: 'asc'
});
// Iterate through all products
for await (const product of stateset.products.list()) {
console.log(product.id, product.name);
}
```
```python Python theme={null}
products = stateset.products.list(
limit=10,
status='active',
category='Electronics',
in_stock=True,
sort_by='price',
sort_order='asc'
)
# Iterate through all products
for product in stateset.products.list():
print(product.id, product.name)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "product",
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T14:22:00Z",
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"description": "Premium noise-cancelling wireless headphones with 30-hour battery life",
"category": "Electronics",
"brand": "AudioTech",
"status": "active",
"price": {
"amount": 14999,
"currency": "USD",
"compare_at": 19999
},
"inventory_summary": {
"total_quantity": 150,
"available_quantity": 145,
"reserved_quantity": 5
},
"tags": ["electronics", "audio", "wireless", "bluetooth"]
},
{
"id": "prod_1234567890abcdef",
"object": "product",
"created_at": "2024-01-14T09:15:00Z",
"updated_at": "2024-01-14T09:15:00Z",
"name": "USB-C Charging Cable",
"sku": "USB-C-001",
"description": "Fast charging USB-C cable, 6ft length",
"category": "Electronics",
"brand": "TechConnect",
"status": "active",
"price": {
"amount": 1299,
"currency": "USD",
"compare_at": null
},
"inventory_summary": {
"total_quantity": 500,
"available_quantity": 487,
"reserved_quantity": 13
},
"tags": ["electronics", "cables", "charging"]
}
],
"has_more": true,
"total_count": 42,
"next_cursor": "eyJpZCI6InByb2RfMTIzNDU2Nzg5MGFiY2RlZiJ9"
}
```
# Search Products
Source: https://docs.stateset.com/api-reference/products/search
POST https://api.stateset.com/v1/products/search
Advanced product search with full-text search, filters, and faceted results
This endpoint provides powerful search capabilities including fuzzy matching, relevance scoring, and aggregated facets for building filter UIs.
### Request Body
Search query for full-text search across product names, descriptions, and SKUs
Additional filters to narrow results
Filter by one or more categories
Filter by one or more brands
Price range filter
Minimum price in cents
Maximum price in cents
Only show products with available inventory
Filter by product tags
Filter by status: "active", "draft", or "archived"
Sort options
Sort field: "relevance", "price", "name", "created\_at", "popularity"
Sort order: "asc" or "desc"
Pagination options
Number of results (default: 20, max: 100)
Number of results to skip
Include aggregated facets for building filter UIs (default: true)
### Response
Array of matching products with relevance scores
Total number of matching products
Aggregated data for building filter UIs
Category counts
Brand counts
Price range distributions
Tag counts
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/products/search' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"query": "wireless headphones",
"filters": {
"categories": ["Electronics"],
"price_range": {
"min": 5000,
"max": 20000
},
"in_stock": true
},
"sort": {
"field": "relevance",
"order": "desc"
},
"pagination": {
"limit": 10,
"offset": 0
}
}'
```
```graphQL GraphQL theme={null}
mutation SearchProducts($input: SearchProductsInput!) {
searchProducts(input: $input) {
results {
id
name
sku
description
category
brand
price {
amount
currency
}
relevance_score
}
total_count
facets {
categories {
value
count
}
brands {
value
count
}
}
}
}
```
```javascript Node.js theme={null}
const searchResults = await stateset.products.search({
query: "wireless headphones",
filters: {
categories: ["Electronics"],
price_range: {
min: 5000,
max: 20000
},
in_stock: true
},
sort: {
field: "relevance",
order: "desc"
}
});
```
```python Python theme={null}
search_results = stateset.products.search({
"query": "wireless headphones",
"filters": {
"categories": ["Electronics"],
"price_range": {
"min": 5000,
"max": 20000
},
"in_stock": True
},
"sort": {
"field": "relevance",
"order": "desc"
}
})
```
```json Response theme={null}
{
"results": [
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"description": "Premium noise-cancelling wireless headphones with 30-hour battery life",
"category": "Electronics",
"brand": "AudioTech",
"price": {
"amount": 14999,
"currency": "USD"
},
"relevance_score": 0.98,
"inventory_summary": {
"available": true,
"quantity": 145
}
},
{
"id": "prod_abc123def456",
"name": "Sport Wireless Earbuds",
"sku": "SWE-001",
"description": "Waterproof wireless earbuds perfect for workouts",
"category": "Electronics",
"brand": "FitAudio",
"price": {
"amount": 7999,
"currency": "USD"
},
"relevance_score": 0.85,
"inventory_summary": {
"available": true,
"quantity": 230
}
}
],
"total_count": 15,
"facets": {
"categories": [
{
"value": "Electronics",
"count": 15
}
],
"brands": [
{
"value": "AudioTech",
"count": 5
},
{
"value": "FitAudio",
"count": 3
},
{
"value": "SoundMax",
"count": 4
},
{
"value": "TechConnect",
"count": 3
}
],
"price_ranges": [
{
"range": "50-100",
"count": 3
},
{
"range": "100-150",
"count": 8
},
{
"range": "150-200",
"count": 4
}
],
"tags": [
{
"value": "wireless",
"count": 15
},
{
"value": "bluetooth",
"count": 12
},
{
"value": "noise-cancelling",
"count": 6
}
]
}
}
```
# Update Product
Source: https://docs.stateset.com/api-reference/products/update
PUT https://api.stateset.com/v1/products/:id
Update an existing product's details, pricing, or inventory settings
This endpoint supports partial updates. Only include the fields you want to change.
### Path Parameters
The unique identifier of the product to update
### Request Body
Product name for display
Detailed product description
Product category
Brand or manufacturer name
Updated pricing information
Price in cents
ISO 4217 currency code
Original price for displaying discounts
Updated cost information
Cost in cents
ISO 4217 currency code
Updated inventory settings
Whether to track inventory levels
Threshold for low stock alerts
Whether to allow orders when out of stock
Updated product dimensions
Weight in pounds
Length in inches
Width in inches
Height in inches
Product status: "active", "draft", or "archived"
Additional custom fields as key-value pairs
Array of string tags for categorization
### Response
Returns the updated product object with all fields.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/products/prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"price": {
"amount": 12999,
"compare_at": 14999
},
"inventory": {
"low_stock_threshold": 15
},
"tags": ["electronics", "audio", "wireless", "bluetooth", "sale"]
}'
```
```graphQL GraphQL theme={null}
mutation UpdateProduct($id: ID!, $input: UpdateProductInput!) {
updateProduct(id: $id, input: $input) {
id
name
sku
price {
amount
currency
compare_at
}
inventory {
low_stock_threshold
allow_backorder
}
tags
updated_at
}
}
```
```javascript Node.js theme={null}
const product = await stateset.products.update(
'prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
price: {
amount: 12999,
compare_at: 14999
},
inventory: {
low_stock_threshold: 15
},
tags: ["electronics", "audio", "wireless", "bluetooth", "sale"]
}
);
```
```python Python theme={null}
product = stateset.products.update(
'prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
price={
"amount": 12999,
"compare_at": 14999
},
inventory={
"low_stock_threshold": 15
},
tags=["electronics", "audio", "wireless", "bluetooth", "sale"]
)
```
```json Response theme={null}
{
"id": "prod_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "product",
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T16:45:00Z",
"name": "Wireless Bluetooth Headphones",
"sku": "WBH-001",
"description": "Premium noise-cancelling wireless headphones with 30-hour battery life",
"category": "Electronics",
"brand": "AudioTech",
"status": "active",
"price": {
"amount": 12999,
"currency": "USD",
"compare_at": 14999
},
"cost": {
"amount": 7500,
"currency": "USD"
},
"inventory": {
"track_inventory": true,
"low_stock_threshold": 15,
"allow_backorder": false
},
"inventory_summary": {
"total_quantity": 150,
"available_quantity": 145,
"reserved_quantity": 5
},
"dimensions": {
"weight": 0.5,
"length": 8,
"width": 7,
"height": 3
},
"tags": ["electronics", "audio", "wireless", "bluetooth", "sale"],
"metadata": {}
}
```
# Create Promotion
Source: https://docs.stateset.com/api-reference/promotions/create
POST https://api.stateset.com/v1/promotions
Create a new promotion with flexible discount rules and targeting
This endpoint creates a new promotion that can be applied to orders, products, or customer segments. Promotions support various discount types and complex rule conditions.
## Authentication
This endpoint requires a valid API key with `promotions:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Internal name for the promotion
Promotion code for customers to enter (leave empty for automatic promotions)
Customer-facing description of the promotion
Promotion type: "percentage", "fixed\_amount", "bogo", "tiered", "bundle", "free\_shipping"
Discount value configuration
Discount amount (percentage for percentage type, cents for fixed\_amount)
Tier configuration for tiered discounts
Minimum order amount in cents
Discount for this tier
Buy quantity for BOGO
Get quantity for BOGO
Maximum discount amount in cents (for percentage discounts)
Conditions for promotion eligibility
Minimum order amount in cents
Maximum total uses across all customers
Maximum uses per customer
Eligible customer segment IDs
Applicable product IDs
Applicable category IDs
Excluded product IDs
Whether to exclude items already on sale
Required shipping methods
Required payment methods
Promotion validity period
Start date and time (ISO 8601)
End date and time (ISO 8601)
Timezone for date calculations (default: UTC)
Recurring schedule
Days promotion is active (0-6, Sunday is 0)
Active hours
Start time (HH:MM)
End time (HH:MM)
Rules for combining with other promotions
Whether this promotion can be combined with others
Application priority (lower numbers apply first)
Promotion IDs that cannot be combined with this one
Display configuration
Show promotion badge on products
Show in cart/checkout
Custom badge text
Promotional banner text
Promotion status: "active", "scheduled", "paused", "expired"
Additional custom fields
### Response
Returns the created promotion object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/promotions' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"name": "Summer Sale 2024",
"code": "SUMMER20",
"description": "Get 20% off on all summer collection items",
"type": "percentage",
"value": {
"amount": 20,
"max_discount": 10000
},
"conditions": {
"min_purchase_amount": 5000,
"max_uses_total": 1000,
"max_uses_per_customer": 1,
"category_ids": ["cat_summer_2024"],
"exclude_sale_items": true
},
"validity": {
"start_date": "2024-06-01T00:00:00Z",
"end_date": "2024-08-31T23:59:59Z",
"timezone": "America/Los_Angeles"
},
"stacking": {
"allowed": false,
"priority": 1
},
"display": {
"show_in_catalog": true,
"show_in_cart": true,
"badge_text": "SUMMER SALE"
},
"status": "scheduled"
}'
```
```javascript Node.js theme={null}
const promotion = await stateset.promotions.create({
name: "Summer Sale 2024",
code: "SUMMER20",
description: "Get 20% off on all summer collection items",
type: "percentage",
value: {
amount: 20,
max_discount: 10000
},
conditions: {
min_purchase_amount: 5000,
max_uses_total: 1000,
max_uses_per_customer: 1,
category_ids: ["cat_summer_2024"],
exclude_sale_items: true
},
validity: {
start_date: "2024-06-01T00:00:00Z",
end_date: "2024-08-31T23:59:59Z",
timezone: "America/Los_Angeles"
},
stacking: {
allowed: false,
priority: 1
},
display: {
show_in_catalog: true,
show_in_cart: true,
badge_text: "SUMMER SALE"
},
status: "scheduled"
});
```
```python Python theme={null}
promotion = stateset.promotions.create(
name="Summer Sale 2024",
code="SUMMER20",
description="Get 20% off on all summer collection items",
type="percentage",
value={
"amount": 20,
"max_discount": 10000
},
conditions={
"min_purchase_amount": 5000,
"max_uses_total": 1000,
"max_uses_per_customer": 1,
"category_ids": ["cat_summer_2024"],
"exclude_sale_items": True
},
validity={
"start_date": "2024-06-01T00:00:00Z",
"end_date": "2024-08-31T23:59:59Z",
"timezone": "America/Los_Angeles"
},
stacking={
"allowed": False,
"priority": 1
},
display={
"show_in_catalog": True,
"show_in_cart": True,
"badge_text": "SUMMER SALE"
},
status="scheduled"
)
```
```json Response theme={null}
{
"id": "promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "promotion",
"name": "Summer Sale 2024",
"code": "SUMMER20",
"description": "Get 20% off on all summer collection items",
"type": "percentage",
"value": {
"amount": 20,
"max_discount": 10000
},
"conditions": {
"min_purchase_amount": 5000,
"max_uses_total": 1000,
"max_uses_per_customer": 1,
"used_count": 0,
"category_ids": ["cat_summer_2024"],
"exclude_sale_items": true
},
"validity": {
"start_date": "2024-06-01T00:00:00Z",
"end_date": "2024-08-31T23:59:59Z",
"timezone": "America/Los_Angeles",
"is_active": false,
"days_remaining": 134
},
"stacking": {
"allowed": false,
"priority": 1
},
"display": {
"show_in_catalog": true,
"show_in_cart": true,
"badge_text": "SUMMER SALE"
},
"status": "scheduled",
"created_at": "2024-01-20T10:00:00Z",
"updated_at": "2024-01-20T10:00:00Z",
"created_by": "user_123",
"performance": {
"total_orders": 0,
"total_revenue": 0,
"total_discount_given": 0,
"conversion_rate": 0
}
}
```
# Get Promotion
Source: https://docs.stateset.com/api-reference/promotions/get
GET https://api.stateset.com/v1/promotions/:id
Retrieve details of a specific promotion
This endpoint retrieves detailed information about a specific promotion, including its current usage statistics and performance metrics.
## Authentication
This endpoint requires a valid API key with `promotions:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the promotion
### Response
Returns the promotion object if found.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/promotions/promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const promotion = await stateset.promotions.retrieve(
'promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
promotion = stateset.promotions.retrieve(
'promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "promotion",
"name": "Summer Sale 2024",
"code": "SUMMER20",
"description": "Get 20% off on all summer collection items",
"type": "percentage",
"value": {
"amount": 20,
"max_discount": 10000
},
"conditions": {
"min_purchase_amount": 5000,
"max_uses_total": 1000,
"max_uses_per_customer": 1,
"used_count": 245,
"category_ids": ["cat_summer_2024"],
"exclude_sale_items": true
},
"validity": {
"start_date": "2024-06-01T00:00:00Z",
"end_date": "2024-08-31T23:59:59Z",
"timezone": "America/Los_Angeles",
"is_active": true,
"days_remaining": 72
},
"stacking": {
"allowed": false,
"priority": 1
},
"display": {
"show_in_catalog": true,
"show_in_cart": true,
"badge_text": "SUMMER SALE"
},
"status": "active",
"created_at": "2024-01-20T10:00:00Z",
"updated_at": "2024-06-15T14:30:00Z",
"created_by": "user_123",
"performance": {
"total_orders": 245,
"total_revenue": 489750,
"total_discount_given": 97950,
"conversion_rate": 0.0245,
"average_order_value": 1999,
"daily_usage": [
{
"date": "2024-06-20",
"uses": 12,
"revenue": 23988
}
]
}
}
```
# List Promotions
Source: https://docs.stateset.com/api-reference/promotions/list
GET https://api.stateset.com/v1/promotions
List all promotions with filtering and pagination options
This endpoint returns a paginated list of promotions. You can filter by status, type, validity dates, and more.
## Authentication
This endpoint requires a valid API key with `promotions:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of promotions to return (1-100)
Number of promotions to skip
Filter by status: "active", "scheduled", "paused", "expired"
Filter by promotion type: "percentage", "fixed\_amount", "bogo", "tiered", "bundle", "free\_shipping"
Search by promotion code (partial match)
Filter promotions active on a specific date (ISO 8601)
Filter by eligible customer segment
Sort by field: "created\_at", "start\_date", "end\_date", "priority", "usage\_count"
Sort order: "asc" or "desc"
### Response
Returns a paginated list of promotion objects.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/promotions?status=active&limit=20' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const promotions = await stateset.promotions.list({
status: 'active',
limit: 20
});
```
```python Python theme={null}
promotions = stateset.promotions.list(
status='active',
limit=20
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "promotion",
"name": "Summer Sale 2024",
"code": "SUMMER20",
"description": "Get 20% off on all summer collection items",
"type": "percentage",
"value": {
"amount": 20,
"max_discount": 10000
},
"status": "active",
"validity": {
"start_date": "2024-06-01T00:00:00Z",
"end_date": "2024-08-31T23:59:59Z",
"is_active": true
},
"conditions": {
"used_count": 245,
"max_uses_total": 1000
},
"created_at": "2024-01-20T10:00:00Z"
},
{
"id": "promo_1234f083-bb2d-54d6-bg6d-1b0e3gd75f41",
"object": "promotion",
"name": "First Time Buyer",
"code": "WELCOME10",
"description": "10% off for new customers",
"type": "percentage",
"value": {
"amount": 10
},
"status": "active",
"validity": {
"start_date": "2024-01-01T00:00:00Z",
"end_date": null,
"is_active": true
},
"conditions": {
"used_count": 1523,
"max_uses_per_customer": 1
},
"created_at": "2024-01-01T00:00:00Z"
}
],
"has_more": true,
"total_count": 42,
"url": "/v1/promotions"
}
```
# Update Promotion
Source: https://docs.stateset.com/api-reference/promotions/update
PUT https://api.stateset.com/v1/promotions/:id
Update an existing promotion
This endpoint updates an existing promotion. You can modify conditions, validity periods, and display settings. Some fields cannot be updated after a promotion has been used.
## Authentication
This endpoint requires a valid API key with `promotions:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the promotion to update
## Request Body
All fields are optional. Only provided fields will be updated.
Internal name for the promotion
Customer-facing description
Update promotion conditions
Maximum total uses
Maximum uses per customer
Eligible customer segments
Update validity period
New end date (ISO 8601)
Update status: "active", "paused", "expired"
### Response
Returns the updated promotion object.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/promotions/promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"validity": {
"end_date": "2024-09-30T23:59:59Z"
},
"conditions": {
"max_uses_total": 1500
},
"status": "active"
}'
```
```javascript Node.js theme={null}
const promotion = await stateset.promotions.update(
'promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
validity: {
end_date: "2024-09-30T23:59:59Z"
},
conditions: {
max_uses_total: 1500
},
status: "active"
}
);
```
```python Python theme={null}
promotion = stateset.promotions.update(
'promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
validity={
"end_date": "2024-09-30T23:59:59Z"
},
conditions={
"max_uses_total": 1500
},
status="active"
)
```
```json Response theme={null}
{
"id": "promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "promotion",
"name": "Summer Sale 2024",
"code": "SUMMER20",
"description": "Get 20% off on all summer collection items",
"type": "percentage",
"value": {
"amount": 20,
"max_discount": 10000
},
"conditions": {
"min_purchase_amount": 5000,
"max_uses_total": 1500,
"max_uses_per_customer": 1,
"used_count": 245,
"category_ids": ["cat_summer_2024"],
"exclude_sale_items": true
},
"validity": {
"start_date": "2024-06-01T00:00:00Z",
"end_date": "2024-09-30T23:59:59Z",
"timezone": "America/Los_Angeles",
"is_active": true,
"days_remaining": 102
},
"status": "active",
"updated_at": "2024-06-20T15:00:00Z",
"updated_by": "user_456"
}
```
# Validate Promotion
Source: https://docs.stateset.com/api-reference/promotions/validate
POST https://api.stateset.com/v1/promotions/validate
Validate a promotion code and check eligibility for a specific cart
This endpoint validates whether a promotion code can be applied to a given cart, checking all conditions and returning applicable discounts.
## Authentication
This endpoint requires a valid API key with `promotions:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Promotion code to validate
Customer ID for personalized validation
Cart details for validation
Cart items
Product ID
Product variant ID
Item quantity
Unit price in cents
Product category ID
Whether item is already on sale
Cart subtotal in cents
Selected shipping method
Selected payment method
Already applied promotion IDs for stacking validation
### Response
Returns validation result with applicable discount details.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/promotions/validate' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"code": "SUMMER20",
"customer_id": "cust_abc123",
"cart": {
"items": [
{
"product_id": "prod_123",
"quantity": 2,
"price": 2999,
"category_id": "cat_summer_2024"
},
{
"product_id": "prod_456",
"quantity": 1,
"price": 4999,
"category_id": "cat_accessories"
}
],
"subtotal": 10997,
"shipping_method": "standard"
}
}'
```
```javascript Node.js theme={null}
const validation = await stateset.promotions.validate({
code: "SUMMER20",
customer_id: "cust_abc123",
cart: {
items: [
{
product_id: "prod_123",
quantity: 2,
price: 2999,
category_id: "cat_summer_2024"
},
{
product_id: "prod_456",
quantity: 1,
price: 4999,
category_id: "cat_accessories"
}
],
subtotal: 10997,
shipping_method: "standard"
}
});
```
```python Python theme={null}
validation = stateset.promotions.validate(
code="SUMMER20",
customer_id="cust_abc123",
cart={
"items": [
{
"product_id": "prod_123",
"quantity": 2,
"price": 2999,
"category_id": "cat_summer_2024"
},
{
"product_id": "prod_456",
"quantity": 1,
"price": 4999,
"category_id": "cat_accessories"
}
],
"subtotal": 10997,
"shipping_method": "standard"
}
)
```
```json Response theme={null}
{
"valid": true,
"promotion": {
"id": "promo_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"code": "SUMMER20",
"name": "Summer Sale 2024",
"type": "percentage",
"description": "Get 20% off on all summer collection items"
},
"eligibility": {
"is_eligible": true,
"customer_eligible": true,
"cart_eligible": true,
"within_usage_limits": true,
"within_date_range": true,
"meets_minimum_purchase": true
},
"discount_calculation": {
"applicable_items": [
{
"product_id": "prod_123",
"quantity": 2,
"original_amount": 5998,
"discount_amount": 1200,
"final_amount": 4798
}
],
"excluded_items": [
{
"product_id": "prod_456",
"reason": "category_not_eligible"
}
],
"discount_amount": 1200,
"final_subtotal": 9797
},
"warnings": [],
"metadata": {
"customer_usage_count": 0,
"total_usage_count": 245,
"days_until_expiry": 134
}
}
```
# Cancel Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/cancel
POST https://api.stateset.com/v1/purchase_orders/:id/cancel
This endpoint cancels an existing purchase order.
### Body
The ID provided in the data tab may be used to identify the purchase order
### Response
The ID provided in the data tab may be used to identify the purchase order
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/purchase_order/:id/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation cancelPurchaseOrder ($id: String!) {
cance_purchaseorder(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const purchaseorders = await stateset.purchaseorders.cancel({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
purchaseorders = stateset.purchaseorders.cancel({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
purchaseorders, err := stateset.purchaseorders.cancel.(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Return purchaseorders = stateset.purchaseorders.cancel(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const purchaseorders = await stateset.purchaseorders.cancel({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
purchaseorders = Stateset::PurchaseOrder.cancel({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$purchaseorders = $stateset->purchaseorders->cancel(
'po_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
POST /v1/purchaseorder/:id/cancel HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "purchaseorder",
"cancelled": true
}
```
# Complete Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/complete
POST https://api.stateset.com/v1/purchase_orders/:id/complete
This endpoint completes an existing purchase order.
### Body
The ID provided in the data tab may be used to identify the purchase order
### Response
The ID provided in the data tab may be used to identify the purchase order
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/purchase_order/:id/complete' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation completePurchaseOrder ($id: String!) {
cance_purchaseorder(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const purchaseorders = await stateset.purchaseorders.complete({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
purchaseorders = stateset.purchaseorders.complete({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
purchaseorders, err := stateset.purchaseorders.complete.(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Return purchaseorders = stateset.purchaseorders.complete(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const purchaseorders = await stateset.purchaseorders.complete({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
purchaseorders = Stateset::PurchaseOrder.complete({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$purchaseorders = $stateset->purchaseorders->complete(
'po_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
POST /v1/purchaseorder/:id/complete HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "purchaseorder",
"completed": true
}
```
# Create Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/create
POST https://api.stateset.com/v1/purchase_orders
This endpoint creates a new purchase order
### Body
This is the id of the purchase order.
This is the date the purchase order was created.
This is the date the purchase order was delivered.
This is the description of the purchase order.
This is the external id of the purchase order.
This is the financer of the purchase order.
This is the fulfiller of the purchase order.
This is the date the purchase order was last updated.
This is the date the purchase order was purchased.
This is the hash of the purchase order.
This is the name of the purchase order.
This is the number of the purchase order.
This is the status of the purchase order.
This is the purchaser of the purchase order.
This is the subtotal of the purchase order.
This is the total of the purchase order.
This is the vendor of the purchase order.
This is the transaction id of the purchase order.
### Response
This is the id of the purchase order.
This is the date the purchase order was created.
This is the date the purchase order was delivered.
This is the description of the purchase order.
This is the external id of the purchase order.
This is the financer of the purchase order.
This is the fulfiller of the purchase order.
This is the date the purchase order was last updated.
This is the date the purchase order was purchased.
This is the hash of the purchase order.
This is the name of the purchase order.
This is the number of the purchase order.
This is the status of the purchase order.
This is the purchaser of the purchase order.
This is the subtotal of the purchase order.
This is the total of the purchase order.
This is the vendor of the purchase order.
This is the transaction id of the purchase order.
```bash cURL theme={null}
curl -X POST https://api.stateset.com/v1/purchaseorders \
-H "Authorization: Bearer ${STATESET_API_KEY}" \
-H "Content-Type: application/json" \
-d '{
"purchase_order_number": "PO-2026-001234",
"description": "Q1 inventory restock — blue t-shirts",
"vendor": "Acme Textiles Inc.",
"total": "4500.00",
"subtotal": "4200.00",
"purchase_date": "2026-01-15T00:00:00.000Z",
"delivery_date": "2026-02-01T00:00:00.000Z"
}'
```
```graphQL GraphQL theme={null}
mutation InsertNewPurchaseOrder(
$po: purchaseorders_insert_input!
) {
insert_purchaseorders(objects: [$po]) {
returning {
id
purchase_order_number
description
vendor
total
subtotal
purchase_order_status
purchase_date
delivery_date
}
}
}
```
```js Node.js theme={null}
const purchaseOrder = await stateset.purchaseOrders.create({
purchase_order_number: 'PO-2026-001234',
description: 'Q1 inventory restock — blue t-shirts',
vendor: 'Acme Textiles Inc.',
total: '4500.00',
subtotal: '4200.00',
purchase_date: '2026-01-15T00:00:00.000Z',
delivery_date: '2026-02-01T00:00:00.000Z',
});
```
```python Python theme={null}
purchase_order = stateset.purchase_orders.create(
purchase_order_number="PO-2026-001234",
description="Q1 inventory restock — blue t-shirts",
vendor="Acme Textiles Inc.",
total="4500.00",
subtotal="4200.00",
purchase_date="2026-01-15T00:00:00.000Z",
delivery_date="2026-02-01T00:00:00.000Z",
)
```
```ruby Ruby theme={null}
purchase_order = Stateset::PurchaseOrder.create({
purchase_order_number: 'PO-2026-001234',
description: 'Q1 inventory restock — blue t-shirts',
vendor: 'Acme Textiles Inc.',
total: '4500.00',
subtotal: '4200.00',
purchase_date: '2026-01-15T00:00:00.000Z',
delivery_date: '2026-02-01T00:00:00.000Z',
})
```
```go Go theme={null}
purchaseOrder, err := stateset.PurchaseOrders.Create(&stateset.PurchaseOrderParams{
PurchaseOrderNumber: "PO-2026-001234",
Description: "Q1 inventory restock — blue t-shirts",
Vendor: "Acme Textiles Inc.",
Total: "4500.00",
Subtotal: "4200.00",
PurchaseDate: "2026-01-15T00:00:00.000Z",
DeliveryDate: "2026-02-01T00:00:00.000Z",
})
```
```java Java theme={null}
Map params = new HashMap<>();
params.put("purchase_order_number", "PO-2026-001234");
params.put("description", "Q1 inventory restock — blue t-shirts");
params.put("vendor", "Acme Textiles Inc.");
params.put("total", "4500.00");
params.put("subtotal", "4200.00");
params.put("purchase_date", "2026-01-15T00:00:00.000Z");
params.put("delivery_date", "2026-02-01T00:00:00.000Z");
PurchaseOrder purchaseOrder = stateset.purchaseOrders().create(params);
```
```php PHP theme={null}
$purchaseOrder = $stateset->purchaseOrders->create([
'purchase_order_number' => 'PO-2026-001234',
'description' => 'Q1 inventory restock — blue t-shirts',
'vendor' => 'Acme Textiles Inc.',
'total' => '4500.00',
'subtotal' => '4200.00',
'purchase_date' => '2026-01-15T00:00:00.000Z',
'delivery_date' => '2026-02-01T00:00:00.000Z',
]);
```
```csharp C# theme={null}
var purchaseOrder = await stateset.PurchaseOrders.CreateAsync(
new PurchaseOrderCreateParams
{
PurchaseOrderNumber = "PO-2026-001234",
Description = "Q1 inventory restock — blue t-shirts",
Vendor = "Acme Textiles Inc.",
Total = "4500.00",
Subtotal = "4200.00",
PurchaseDate = "2026-01-15T00:00:00.000Z",
DeliveryDate = "2026-02-01T00:00:00.000Z"
}
);
```
```json Response theme={null}
{
"id": "po_1a2b3c4d5e6f",
"createdat": "2026-01-15T12:00:00.000Z",
"delivery_date": "2026-02-01T00:00:00.000Z",
"description": "Q1 inventory restock — blue t-shirts",
"external_id": "ext_po_98765",
"financer": "fin_abc123",
"fulfiller": "ful_def456",
"lastupdated": "2026-01-15T12:00:00.000Z",
"purchase_date": "2026-01-15T00:00:00.000Z",
"purchase_order_hash": "a1b2c3d4e5f6",
"purchase_order_name": "Q1 Blue T-Shirt Restock",
"purchase_order_number": "PO-2026-001234",
"purchase_order_status": "created",
"purchaser": "usr_abc123",
"subtotal": "4200.00",
"total": "4500.00",
"vendor": "Acme Textiles Inc.",
"transaction_id": "txn_789xyz"
}
```
# Delete Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/delete
DELETE https://api.stateset.com/v1/purchase_orders/:id
This endpoint deletes an existing purchase order.
### Body
The ID provided in the data tab may be used to identify the purchase order
### Response
The ID provided in the data tab may be used to identify the purchase order
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/purchase_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deletePurchaseOrder ($id: String!) {
delete_purchaseorder(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const purchaseorders = await stateset.purchaseorders.del({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
purchaseorders = stateset.purchaseorders.del({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
purchaseorders, err := stateset.purchaseorders.Del(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Return purchaseorders = stateset.purchaseorders.del(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const purchaseorders = await stateset.purchaseorders.del({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
purchaseorders = Stateset::PurchaseOrder.del({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$purchaseorders = $stateset->purchaseorders->del(
'po_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
DELETE /v1/purchaseorder HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "purchaseorder",
"deleted": true
}
```
# Finance Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/finance
POST https://api.stateset.com/v1/purchase_orders/:id/finance
This endpoint finances an existing purchase order.
### Body
The ID provided in the data tab may be used to identify the purchase order
### Response
The ID provided in the data tab may be used to identify the purchase order
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/purchase_order/:id/finance' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation financePurchaseOrder ($id: String!) {
cance_purchaseorder(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const purchaseorders = await stateset.purchaseorders.finance({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
purchaseorders = stateset.purchaseorders.finance({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
purchaseorders, err := stateset.purchaseorders.finance.(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Return purchaseorders = stateset.purchaseorders.finance(
"po_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const purchaseorders = await stateset.purchaseorders.finance({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
purchaseorders = Stateset::PurchaseOrder.finance({
'po_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$purchaseorders = $stateset->purchaseorders->finance(
'po_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
POST /v1/purchaseorder/:id/finance HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "purchaseorder",
"financed": true
}
```
# Get Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/get
GET https://api.stateset.com/v1/purchase_orders
This endpoint gets or creates a new purchase order.
### Body
This is the id of the purchase order.
### Response
This is the id of the purchase order.
This is the date the purchase order was created.
This is the date the purchase order was delivered.
This is the description of the purchase order.
This is the external id of the purchase order.
This is the financer of the purchase order.
This is the fulfiller of the purchase order.
This is the date the purchase order was last updated.
This is the date the purchase order was purchased.
This is the hash of the purchase order.
This is the name of the purchase order.
This is the number of the purchase order.
This is the status of the purchase order.
This is the purchaser of the purchase order.
This is the subtotal of the purchase order.
This is the total of the purchase order.
This is the vendor of the purchase order.
This is the transaction id of the purchase order.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/purchaseorder' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query {
purchaseorder {
id
createdat
delivery_date
description
external_id
financer
fulfiller
lastupdated
purchase_date
purchase_order_hash
purchase_order_name
purchase_order_number
purchase_order_status
purchaser
subtotal
total
vendor
transaction_id
}
}
```
```js Node.js theme={null}
const purchaseorders = await stateset.purchaseorders.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
purchaseorders = stateset.purchaseorders.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
purchaseorders, err := stateset.purchaseorders.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
purchaseorders = Stateset::purchaseorders.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
purchaseorders = Stateset.purchaseorders.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
purchaseorders s = Stateset.purchaseorders.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$purchaseorders = Stateset\purchaseorders::retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/purchaseorder HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"createdat": "2021-04-20T20:00:00.000Z",
"delivery_date": "2021-04-20T20:00:00.000Z",
"description": "This is a purchase order.",
"external_id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"financer": "0x00000000",
"fulfiller": "0x00000000",
"lastupdated": "2021-04-20T20:00:00.000Z",
"purchase_date": "2021-04-20T20:00:00.000Z",
"purchase_order_hash": "0x00000000",
"purchase_order_name": "Purchase Order",
"purchase_order_number": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"purchase_order_status": "0x00000000",
"purchaser": "0x00000000",
"subtotal": "0.00",
"total": "0.00",
"vendor": "0x00000000",
"transaction_id": "0x00000000"
}
}
```
# List Purchase Orders
Source: https://docs.stateset.com/api-reference/purchaseorders/list
GET https://api.stateset.com/v1/purchase_orders/list
This lists purchase orders.
### Body
This is the limit of the purchase orders.
This is the offset of the purchase orders.
This is the order direction of the purchase orders.
### Response
This is the id of the purchase order.
This is the date the purchase order was created.
This is the date the purchase order was delivered.
This is the description of the purchase order.
This is the external id of the purchase order.
This is the financer of the purchase order.
This is the fulfiller of the purchase order.
This is the date the purchase order was last updated.
This is the date the purchase order was purchased.
This is the hash of the purchase order.
This is the name of the purchase order.
This is the number of the purchase order.
This is the status of the purchase order.
This is the purchaser of the purchase order.
This is the subtotal of the purchase order.
This is the total of the purchase order.
This is the vendor of the purchase order.
This is the transaction id of the purchase order.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/purchase_order/list' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
purchasorder(limit: $limit, offset: $offset, order_by: {createdDate: $order_direction}) {
id
createdat
delivery_date
description
external_id
financer
fulfiller
lastupdated
purchase_date
purchase_order_hash
purchase_order_name
purchase_order_number
purchase_order_status
purchaser
subtotal
total
vendor
transaction_id
}
}
```
```js Node.js theme={null}
const purchaseorders = await stateset.purchaseorders.list({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
purchaseorders = stateset.purchaseorders.list({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
purchaseorders, err := stateset.purchaseorders.list(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
purchaseorders = Stateset::purchaseorders.List(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
purchaseorders = Stateset.purchaseorders.list(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
purchaseorders s = Stateset.purchaseorders.list(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$purchaseorders = Stateset\purchaseorders::List(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/purchaseorder HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
{
"id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"createdat": "2021-04-20T20:00:00.000Z",
"delivery_date": "2021-04-20T20:00:00.000Z",
"description": "This is a purchase order.",
"external_id": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"financer": "0x00000000",
"fulfiller": "0x00000000",
"lastupdated": "2021-04-20T20:00:00.000Z",
"purchase_date": "2021-04-20T20:00:00.000Z",
"purchase_order_hash": "0x00000000",
"purchase_order_name": "Purchase Order",
"purchase_order_number": "po_1NXWPnCo6bFb1KQto6C8OWvE",
"purchase_order_status": "0x00000000",
"purchaser": "0x00000000",
"subtotal": "0.00",
"total": "0.00",
"vendor": "0x00000000",
"transaction_id": "0x00000000"
}
}
```
# Receive Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/receive
Mark a purchase order as received.
# Receive Purchase Order
Use this endpoint to record receipt of a purchase order.
# Update Purchase Order
Source: https://docs.stateset.com/api-reference/purchaseorders/update
PUT https://api.stateset.com/v1/purchase_orders/:id
This endpoint updates an existing purchase order
### Body
This is the id of the purchase order.
This is the date the purchase order was created.
This is the date the purchase order was delivered.
This is the description of the purchase order.
This is the external id of the purchase order.
This is the financer of the purchase order.
This is the fulfiller of the purchase order.
This is the date the purchase order was last updated.
This is the date the purchase order was purchased.
This is the hash of the purchase order.
This is the name of the purchase order.
This is the number of the purchase order.
This is the status of the purchase order.
This is the purchaser of the purchase order.
This is the subtotal of the purchase order.
This is the total of the purchase order.
This is the vendor of the purchase order.
This is the transaction id of the purchase order.
### Response
This is the id of the purchase order.
This is the date the purchase order was created.
This is the date the purchase order was delivered.
This is the description of the purchase order.
This is the external id of the purchase order.
This is the financer of the purchase order.
This is the fulfiller of the purchase order.
This is the date the purchase order was last updated.
This is the date the purchase order was purchased.
This is the hash of the purchase order.
This is the name of the purchase order.
This is the number of the purchase order.
This is the status of the purchase order.
This is the purchaser of the purchase order.
This is the subtotal of the purchase order.
This is the total of the purchase order.
This is the vendor of the purchase order.
This is the transaction id of the purchase order.
```bash cURL theme={null}
curl -X PUT https://api.stateset.com/v1/purchaseorders/po_1a2b3c4d5e6f \
-H "Authorization: Bearer ${STATESET_API_KEY}" \
-H "Content-Type: application/json" \
-d '{
"purchase_order_status": "received",
"delivery_date": "2026-01-28T00:00:00.000Z"
}'
```
```graphQL GraphQL theme={null}
mutation UpdatePurchaseOrder(
$purchaseorder_id: String!
$purchaseorder_x: purchaseorders_set_input!
) {
update_purchaseorders(
where: { id: { _eq: $purchaseorder_id } }
_set: $purchaseorder_x
) {
returning {
id
purchase_order_number
purchase_order_status
description
vendor
total
subtotal
delivery_date
lastupdated
}
}
}
```
```js Node.js theme={null}
const purchaseOrder = await stateset.purchaseOrders.update(
'po_1a2b3c4d5e6f',
{
purchase_order_status: 'received',
delivery_date: '2026-01-28T00:00:00.000Z',
}
);
```
```python Python theme={null}
purchase_order = stateset.purchase_orders.update(
"po_1a2b3c4d5e6f",
purchase_order_status="received",
delivery_date="2026-01-28T00:00:00.000Z",
)
```
```ruby Ruby theme={null}
purchase_order = Stateset::PurchaseOrder.update(
'po_1a2b3c4d5e6f',
{
purchase_order_status: 'received',
delivery_date: '2026-01-28T00:00:00.000Z',
}
)
```
```go Go theme={null}
purchaseOrder, err := stateset.PurchaseOrders.Update(
"po_1a2b3c4d5e6f",
&stateset.PurchaseOrderUpdateParams{
PurchaseOrderStatus: "received",
DeliveryDate: "2026-01-28T00:00:00.000Z",
},
)
```
```java Java theme={null}
Map params = new HashMap<>();
params.put("purchase_order_status", "received");
params.put("delivery_date", "2026-01-28T00:00:00.000Z");
PurchaseOrder purchaseOrder = stateset.purchaseOrders().update(
"po_1a2b3c4d5e6f", params
);
```
```php PHP theme={null}
$purchaseOrder = $stateset->purchaseOrders->update(
'po_1a2b3c4d5e6f',
[
'purchase_order_status' => 'received',
'delivery_date' => '2026-01-28T00:00:00.000Z',
]
);
```
```json Response theme={null}
{
"id": "po_1a2b3c4d5e6f",
"createdat": "2026-01-15T12:00:00.000Z",
"delivery_date": "2026-01-28T00:00:00.000Z",
"description": "Q1 inventory restock — blue t-shirts",
"external_id": "ext_po_98765",
"financer": "fin_abc123",
"fulfiller": "ful_def456",
"lastupdated": "2026-01-28T09:30:00.000Z",
"purchase_date": "2026-01-15T00:00:00.000Z",
"purchase_order_hash": "a1b2c3d4e5f6",
"purchase_order_name": "Q1 Blue T-Shirt Restock",
"purchase_order_number": "PO-2026-001234",
"purchase_order_status": "received",
"purchaser": "usr_abc123",
"subtotal": "4200.00",
"total": "4500.00",
"vendor": "Acme Textiles Inc.",
"transaction_id": "txn_789xyz"
}
```
# API Quickstart
Source: https://docs.stateset.com/api-reference/quickstart
Get up and running with the StateSet API in 5 minutes
**Time to first API call:** Less than 5 minutes\
**Prerequisites:** Basic programming knowledge and a StateSet account
## Overview
This quickstart guide will walk you through making your first StateSet API call, then progressively build up to a complete integration. By the end, you'll be able to:
* ✅ Authenticate with the API
* ✅ Create and manage orders
* ✅ Handle webhooks
* ✅ Implement error handling
* ✅ Use advanced features
## Step 1: Get Your API Keys
Create your account at [stateset.com/sign-up](https://stateset.com/sign-up)
Go to **Dashboard → Settings → API Keys**
Click **"Create API Key"** and save it securely - you'll only see it once!
**Security First:** Never commit API keys to version control. Use environment variables instead.
## Step 2: Set Up Your Environment
```bash theme={null}
# Install the StateSet SDK
npm install stateset-node dotenv
# Create .env file
echo "STATESET_API_KEY=sk_test_your_key_here" > .env
```
```javascript theme={null}
// index.js
require('dotenv').config();
const { StateSetClient } = require('stateset-node');
const stateset = new StateSetClient({
apiKey: process.env.STATESET_API_KEY
});
console.log('StateSet client initialized!');
```
```bash theme={null}
# Install the StateSet SDK
pip install stateset-python python-dotenv
# Create .env file
echo "STATESET_API_KEY=sk_test_your_key_here" > .env
```
```python theme={null}
# main.py
import os
from dotenv import load_dotenv
from stateset import StateSet
load_dotenv()
stateset = StateSet(
api_key=os.getenv('STATESET_API_KEY')
)
print('StateSet client initialized!')
```
```bash theme={null}
# Set your API key as an environment variable
export STATESET_API_KEY="sk_test_your_key_here"
# Test the connection
curl https://api.stateset.com/v1/ping \
-H "Authorization: Bearer $STATESET_API_KEY"
```
## Step 3: Make Your First API Call
Let's start with a simple request to list orders:
```javascript Node.js theme={null}
async function getOrders() {
try {
const orders = await stateset.orders.list({
limit: 10,
status: 'pending'
});
console.log(`Found ${orders.data.length} orders`);
orders.data.forEach(order => {
console.log(`- Order ${order.order_number}: ${order.status}`);
});
} catch (error) {
console.error('Error fetching orders:', error.message);
}
}
getOrders();
```
```python Python theme={null}
def get_orders():
try:
orders = stateset.orders.list(
limit=10,
status='pending'
)
print(f"Found {len(orders.data)} orders")
for order in orders.data:
print(f"- Order {order.order_number}: {order.status}")
except Exception as e:
print(f"Error fetching orders: {e}")
get_orders()
```
```bash cURL theme={null}
curl https://api.stateset.com/v1/orders?limit=10&status=pending \
-H "Authorization: Bearer $STATESET_API_KEY" \
-H "Content-Type: application/json"
```
## Step 4: Create Your First Resource
Now let's create an order:
```javascript Node.js theme={null}
async function createOrder() {
try {
const order = await stateset.orders.create({
customer: {
email: 'customer@example.com',
first_name: 'John',
last_name: 'Doe'
},
items: [
{
sku: 'WIDGET-001',
quantity: 2,
price: 2999, // in cents
name: 'Premium Widget'
}
],
shipping_address: {
line1: '123 Main St',
city: 'San Francisco',
state: 'CA',
postal_code: '94105',
country: 'US'
},
payment: {
method: 'card',
payment_intent_id: 'pi_test_123'
}
});
console.log('Order created successfully!');
console.log(`Order ID: ${order.id}`);
console.log(`Order Number: ${order.order_number}`);
console.log(`Total: $${(order.totals.total / 100).toFixed(2)}`);
return order;
} catch (error) {
console.error('Error creating order:', error.message);
if (error.details) {
console.error('Validation errors:', error.details);
}
}
}
createOrder();
```
```python Python theme={null}
def create_order():
try:
order = stateset.orders.create(
customer={
'email': 'customer@example.com',
'first_name': 'John',
'last_name': 'Doe'
},
items=[
{
'sku': 'WIDGET-001',
'quantity': 2,
'price': 2999, # in cents
'name': 'Premium Widget'
}
],
shipping_address={
'line1': '123 Main St',
'city': 'San Francisco',
'state': 'CA',
'postal_code': '94105',
'country': 'US'
},
payment={
'method': 'card',
'payment_intent_id': 'pi_test_123'
}
)
print('Order created successfully!')
print(f'Order ID: {order.id}')
print(f'Order Number: {order.order_number}')
print(f'Total: ${order.totals.total / 100:.2f}')
return order
except Exception as e:
print(f'Error creating order: {e}')
if hasattr(e, 'details'):
print(f'Validation errors: {e.details}')
create_order()
```
## Step 5: Handle Webhooks
Set up webhook handling for real-time events:
```javascript Express.js theme={null}
const express = require('express');
const crypto = require('crypto');
const app = express();
// Middleware to capture raw body for signature verification
app.use('/webhooks', express.raw({ type: 'application/json' }));
function verifyWebhookSignature(payload, signature, secret) {
const elements = signature.split(' ');
const timestamp = elements.find(e => e.startsWith('t=')).slice(2);
const signatures = elements.filter(e => e.startsWith('v1='));
const signedPayload = `${timestamp}.${payload}`;
const expectedSignature = crypto
.createHmac('sha256', secret)
.update(signedPayload)
.digest('hex');
return signatures.some(sig =>
sig.slice(3) === expectedSignature
);
}
app.post('/webhooks/stateset', async (req, res) => {
const signature = req.headers['stateset-signature'];
const secret = process.env.STATESET_WEBHOOK_SECRET;
try {
// Verify webhook signature
if (!verifyWebhookSignature(req.body, signature, secret)) {
return res.status(401).json({ error: 'Invalid signature' });
}
const event = JSON.parse(req.body);
// Handle different event types
switch (event.type) {
case 'order.created':
console.log('New order:', event.data.object.id);
await handleNewOrder(event.data.object);
break;
case 'order.shipped':
console.log('Order shipped:', event.data.object.id);
await notifyCustomerShipped(event.data.object);
break;
case 'return.created':
console.log('Return initiated:', event.data.object.id);
await processReturn(event.data.object);
break;
default:
console.log('Unhandled event type:', event.type);
}
res.json({ received: true });
} catch (error) {
console.error('Webhook error:', error);
res.status(400).json({ error: 'Webhook processing failed' });
}
});
app.listen(3000, () => {
console.log('Webhook server listening on port 3000');
});
```
```python Flask theme={null}
from flask import Flask, request, jsonify
import hmac
import hashlib
import json
import os
app = Flask(__name__)
def verify_webhook_signature(payload, signature, secret):
elements = signature.split(' ')
timestamp = next(e[2:] for e in elements if e.startswith('t='))
signatures = [e[3:] for e in elements if e.startswith('v1=')]
signed_payload = f"{timestamp}.{payload}"
expected_sig = hmac.new(
secret.encode(),
signed_payload.encode(),
hashlib.sha256
).hexdigest()
return expected_sig in signatures
@app.route('/webhooks/stateset', methods=['POST'])
def handle_webhook():
signature = request.headers.get('stateset-signature')
secret = os.getenv('STATESET_WEBHOOK_SECRET')
payload = request.get_data(as_text=True)
try:
# Verify webhook signature
if not verify_webhook_signature(payload, signature, secret):
return jsonify({'error': 'Invalid signature'}), 401
event = json.loads(payload)
# Handle different event types
if event['type'] == 'order.created':
print(f"New order: {event['data']['object']['id']}")
handle_new_order(event['data']['object'])
elif event['type'] == 'order.shipped':
print(f"Order shipped: {event['data']['object']['id']}")
notify_customer_shipped(event['data']['object'])
elif event['type'] == 'return.created':
print(f"Return initiated: {event['data']['object']['id']}")
process_return(event['data']['object'])
else:
print(f"Unhandled event type: {event['type']}")
return jsonify({'received': True})
except Exception as e:
print(f"Webhook error: {e}")
return jsonify({'error': 'Webhook processing failed'}), 400
if __name__ == '__main__':
app.run(port=3000)
```
## Step 6: Implement Error Handling
Add robust error handling to your integration:
```javascript Node.js theme={null}
class StateSetAPIHandler {
constructor(apiKey) {
this.client = new StateSetClient({ apiKey });
this.maxRetries = 3;
}
async executeWithRetry(operation, data) {
let lastError;
for (let attempt = 1; attempt <= this.maxRetries; attempt++) {
try {
return await operation(data);
} catch (error) {
lastError = error;
// Don't retry on validation errors
if (error.code === 'VALIDATION_ERROR') {
throw error;
}
// Retry with exponential backoff for rate limits
if (error.code === 'RATE_LIMITED' && attempt < this.maxRetries) {
const delay = Math.min(1000 * Math.pow(2, attempt), 10000);
console.log(`Rate limited. Retrying in ${delay}ms...`);
await new Promise(resolve => setTimeout(resolve, delay));
continue;
}
// Retry on network errors
if (error.code === 'NETWORK_ERROR' && attempt < this.maxRetries) {
const delay = 1000 * attempt;
console.log(`Network error. Retrying in ${delay}ms...`);
await new Promise(resolve => setTimeout(resolve, delay));
continue;
}
}
}
throw lastError;
}
async createOrder(orderData) {
return this.executeWithRetry(
async (data) => await this.client.orders.create(data),
orderData
);
}
handleError(error) {
const errorHandlers = {
'VALIDATION_ERROR': () => {
console.error('Validation failed:', error.details);
// Show validation errors to user
},
'INSUFFICIENT_INVENTORY': () => {
console.error('Not enough inventory:', error.details);
// Update UI with available quantity
},
'PAYMENT_FAILED': () => {
console.error('Payment failed:', error.message);
// Prompt for different payment method
},
'RATE_LIMITED': () => {
console.error('Rate limited. Please slow down requests.');
// Implement request queuing
},
'UNAUTHORIZED': () => {
console.error('Authentication failed. Check API key.');
// Refresh authentication
}
};
const handler = errorHandlers[error.code] || (() => {
console.error('Unexpected error:', error.message);
});
handler();
}
}
```
```python Python theme={null}
import time
from typing import Optional, Callable, Any
class StateSetAPIHandler:
def __init__(self, api_key: str):
self.client = StateSet(api_key=api_key)
self.max_retries = 3
def execute_with_retry(
self,
operation: Callable,
data: Any,
max_retries: Optional[int] = None
) -> Any:
max_retries = max_retries or self.max_retries
last_error = None
for attempt in range(1, max_retries + 1):
try:
return operation(data)
except Exception as error:
last_error = error
# Don't retry on validation errors
if hasattr(error, 'code') and error.code == 'VALIDATION_ERROR':
raise error
# Retry with exponential backoff for rate limits
if hasattr(error, 'code') and error.code == 'RATE_LIMITED':
if attempt < max_retries:
delay = min(2 ** attempt, 10)
print(f"Rate limited. Retrying in {delay}s...")
time.sleep(delay)
continue
# Retry on network errors
if hasattr(error, 'code') and error.code == 'NETWORK_ERROR':
if attempt < max_retries:
delay = attempt
print(f"Network error. Retrying in {delay}s...")
time.sleep(delay)
continue
raise last_error
def create_order(self, order_data: dict) -> dict:
return self.execute_with_retry(
lambda data: self.client.orders.create(**data),
order_data
)
def handle_error(self, error: Exception) -> None:
error_handlers = {
'VALIDATION_ERROR': lambda: print(f"Validation failed: {error.details}"),
'INSUFFICIENT_INVENTORY': lambda: print(f"Not enough inventory: {error.details}"),
'PAYMENT_FAILED': lambda: print(f"Payment failed: {error.message}"),
'RATE_LIMITED': lambda: print("Rate limited. Please slow down requests."),
'UNAUTHORIZED': lambda: print("Authentication failed. Check API key.")
}
handler = error_handlers.get(
getattr(error, 'code', 'UNKNOWN'),
lambda: print(f"Unexpected error: {error}")
)
handler()
```
## Step 7: Use Advanced Features
### Pagination
Handle large datasets efficiently:
```javascript theme={null}
async function getAllOrders() {
const allOrders = [];
let cursor = null;
do {
const response = await stateset.orders.list({
limit: 100,
cursor: cursor
});
allOrders.push(...response.data);
cursor = response.pagination.next_cursor;
} while (cursor);
console.log(`Total orders: ${allOrders.length}`);
return allOrders;
}
```
### Filtering and Searching
```javascript theme={null}
// Complex filtering
const orders = await stateset.orders.list({
status_in: ['pending', 'processing'],
created_after: '2024-01-01T00:00:00Z',
total_amount_gte: 10000, // $100.00 in cents
customer_email_like: '%@example.com',
sort: 'created_at',
order: 'desc'
});
// Full-text search
const searchResults = await stateset.orders.search({
query: 'john doe widget',
fields: ['customer.email', 'customer.name', 'items.name'],
limit: 20
});
```
### Batch Operations
```javascript theme={null}
// Batch update multiple orders
const updates = await stateset.orders.batchUpdate({
filters: {
status: 'pending',
created_before: '2024-01-01T00:00:00Z'
},
updates: {
status: 'cancelled',
metadata: {
cancelled_reason: 'expired'
}
}
});
console.log(`Updated ${updates.affected_count} orders`);
```
### Idempotency
Ensure safe retries with idempotency keys:
```javascript theme={null}
const { v4: uuidv4 } = require('uuid');
async function createOrderSafely(orderData) {
const idempotencyKey = `order-${uuidv4()}`;
try {
return await stateset.orders.create(orderData, {
idempotencyKey: idempotencyKey
});
} catch (error) {
if (error.code === 'DUPLICATE_REQUEST') {
console.log('Order already created:', error.details.existing_id);
return error.details.existing_resource;
}
throw error;
}
}
```
## Complete Example: Order Management System
Here's a complete example that ties everything together:
```javascript Node.js theme={null}
const { StateSetClient } = require('stateset-node');
const express = require('express');
require('dotenv').config();
class OrderManagementSystem {
constructor() {
this.stateset = new StateSetClient({
apiKey: process.env.STATESET_API_KEY
});
this.app = express();
this.setupRoutes();
}
setupRoutes() {
this.app.use(express.json());
// Create order endpoint
this.app.post('/api/orders', async (req, res) => {
try {
const order = await this.createOrder(req.body);
res.json({ success: true, order });
} catch (error) {
this.handleApiError(error, res);
}
});
// Get orders endpoint
this.app.get('/api/orders', async (req, res) => {
try {
const orders = await this.getOrders(req.query);
res.json({ success: true, orders });
} catch (error) {
this.handleApiError(error, res);
}
});
// Update order status
this.app.patch('/api/orders/:id/status', async (req, res) => {
try {
const order = await this.updateOrderStatus(
req.params.id,
req.body.status
);
res.json({ success: true, order });
} catch (error) {
this.handleApiError(error, res);
}
});
// Webhook endpoint
this.app.post('/webhooks/stateset',
express.raw({ type: 'application/json' }),
async (req, res) => {
await this.handleWebhook(req, res);
}
);
}
async createOrder(orderData) {
// Validate order data
this.validateOrderData(orderData);
// Check inventory
await this.checkInventory(orderData.items);
// Create order with idempotency
const idempotencyKey = `order-${Date.now()}-${orderData.customer.email}`;
const order = await this.stateset.orders.create(orderData, {
idempotencyKey
});
// Send confirmation email
await this.sendOrderConfirmation(order);
return order;
}
async getOrders(filters) {
const orders = await this.stateset.orders.list({
limit: filters.limit || 20,
status: filters.status,
created_after: filters.from_date,
created_before: filters.to_date,
sort: filters.sort || 'created_at',
order: filters.order || 'desc'
});
return orders;
}
async updateOrderStatus(orderId, newStatus) {
// Validate status transition
const order = await this.stateset.orders.get(orderId);
this.validateStatusTransition(order.status, newStatus);
// Update order
const updated = await this.stateset.orders.update(orderId, {
status: newStatus
});
// Trigger relevant workflows
await this.triggerStatusWorkflow(updated);
return updated;
}
async handleWebhook(req, res) {
// Verify signature
if (!this.verifyWebhook(req)) {
return res.status(401).json({ error: 'Invalid signature' });
}
const event = JSON.parse(req.body);
try {
switch (event.type) {
case 'order.created':
await this.onOrderCreated(event.data.object);
break;
case 'order.shipped':
await this.onOrderShipped(event.data.object);
break;
case 'return.created':
await this.onReturnCreated(event.data.object);
break;
}
res.json({ received: true });
} catch (error) {
console.error('Webhook processing error:', error);
res.status(500).json({ error: 'Processing failed' });
}
}
validateOrderData(data) {
const required = ['customer', 'items', 'shipping_address'];
for (const field of required) {
if (!data[field]) {
throw new Error(`Missing required field: ${field}`);
}
}
if (!data.items.length) {
throw new Error('Order must contain at least one item');
}
}
async checkInventory(items) {
for (const item of items) {
const inventory = await this.stateset.inventory.get(item.sku);
if (inventory.available < item.quantity) {
throw new Error(
`Insufficient inventory for ${item.sku}. ` +
`Available: ${inventory.available}`
);
}
}
}
validateStatusTransition(currentStatus, newStatus) {
const validTransitions = {
'pending': ['processing', 'cancelled'],
'processing': ['shipped', 'cancelled'],
'shipped': ['delivered', 'returned'],
'delivered': ['returned'],
'cancelled': [],
'returned': []
};
if (!validTransitions[currentStatus].includes(newStatus)) {
throw new Error(
`Invalid status transition from ${currentStatus} to ${newStatus}`
);
}
}
handleApiError(error, res) {
const statusMap = {
'VALIDATION_ERROR': 400,
'UNAUTHORIZED': 401,
'FORBIDDEN': 403,
'NOT_FOUND': 404,
'RATE_LIMITED': 429,
'INTERNAL_ERROR': 500
};
const status = statusMap[error.code] || 500;
res.status(status).json({
success: false,
error: {
code: error.code,
message: error.message,
details: error.details
}
});
}
start(port = 3000) {
this.app.listen(port, () => {
console.log(`Order Management System running on port ${port}`);
});
}
}
// Start the system
const oms = new OrderManagementSystem();
oms.start();
```
```python Python theme={null}
from flask import Flask, request, jsonify
from stateset import StateSet
import os
from datetime import datetime
from dotenv import load_dotenv
load_dotenv()
class OrderManagementSystem:
def __init__(self):
self.stateset = StateSet(api_key=os.getenv('STATESET_API_KEY'))
self.app = Flask(__name__)
self.setup_routes()
def setup_routes(self):
@self.app.route('/api/orders', methods=['POST'])
def create_order():
try:
order = self.create_order(request.json)
return jsonify({'success': True, 'order': order})
except Exception as e:
return self.handle_api_error(e)
@self.app.route('/api/orders', methods=['GET'])
def get_orders():
try:
orders = self.get_orders(request.args)
return jsonify({'success': True, 'orders': orders})
except Exception as e:
return self.handle_api_error(e)
@self.app.route('/api/orders//status', methods=['PATCH'])
def update_status(order_id):
try:
order = self.update_order_status(
order_id,
request.json['status']
)
return jsonify({'success': True, 'order': order})
except Exception as e:
return self.handle_api_error(e)
@self.app.route('/webhooks/stateset', methods=['POST'])
def handle_webhook():
return self.handle_webhook(request)
def create_order(self, order_data):
# Validate order data
self.validate_order_data(order_data)
# Check inventory
self.check_inventory(order_data['items'])
# Create order with idempotency
idempotency_key = f"order-{datetime.now().timestamp()}-{order_data['customer']['email']}"
order = self.stateset.orders.create(
**order_data,
idempotency_key=idempotency_key
)
# Send confirmation
self.send_order_confirmation(order)
return order
def get_orders(self, filters):
orders = self.stateset.orders.list(
limit=filters.get('limit', 20),
status=filters.get('status'),
created_after=filters.get('from_date'),
created_before=filters.get('to_date'),
sort=filters.get('sort', 'created_at'),
order=filters.get('order', 'desc')
)
return orders
def update_order_status(self, order_id, new_status):
# Get current order
order = self.stateset.orders.get(order_id)
# Validate transition
self.validate_status_transition(order.status, new_status)
# Update order
updated = self.stateset.orders.update(
order_id,
status=new_status
)
# Trigger workflows
self.trigger_status_workflow(updated)
return updated
def validate_order_data(self, data):
required = ['customer', 'items', 'shipping_address']
for field in required:
if field not in data:
raise ValueError(f"Missing required field: {field}")
if not data['items']:
raise ValueError("Order must contain at least one item")
def check_inventory(self, items):
for item in items:
inventory = self.stateset.inventory.get(item['sku'])
if inventory.available < item['quantity']:
raise ValueError(
f"Insufficient inventory for {item['sku']}. "
f"Available: {inventory.available}"
)
def validate_status_transition(self, current_status, new_status):
valid_transitions = {
'pending': ['processing', 'cancelled'],
'processing': ['shipped', 'cancelled'],
'shipped': ['delivered', 'returned'],
'delivered': ['returned'],
'cancelled': [],
'returned': []
}
if new_status not in valid_transitions.get(current_status, []):
raise ValueError(
f"Invalid status transition from {current_status} to {new_status}"
)
def handle_api_error(self, error):
status_map = {
'VALIDATION_ERROR': 400,
'UNAUTHORIZED': 401,
'FORBIDDEN': 403,
'NOT_FOUND': 404,
'RATE_LIMITED': 429,
'INTERNAL_ERROR': 500
}
error_code = getattr(error, 'code', 'INTERNAL_ERROR')
status = status_map.get(error_code, 500)
return jsonify({
'success': False,
'error': {
'code': error_code,
'message': str(error),
'details': getattr(error, 'details', None)
}
}), status
def start(self, port=3000):
self.app.run(port=port, debug=True)
# Start the system
if __name__ == '__main__':
oms = OrderManagementSystem()
oms.start()
```
## Next Steps
Now that you have a working integration, explore these advanced features:
Use our GraphQL API for flexible queries
Process multiple resources efficiently
Subscribe to real-time events via WebSockets
Implement full-text search and filtering
## Resources
### Documentation
* [API Reference](/api-reference/introduction) - Complete API documentation
* [SDKs](/api-reference/sdks) - Language-specific SDKs
* [Authentication](/api-reference/authentication) - Auth methods and security
* [Error Handling](/api-reference/errors) - Error codes and handling
### Code Examples
* [GitHub Examples](https://github.com/stateset/examples) - Sample implementations
* [Postman Collection](https://postman.com/stateset) - Pre-built API requests
* [CodeSandbox Templates](https://codesandbox.io/s/stateset) - Live playground
### Support
* [Discord Community](https://discord.gg/VfcaqgZywq) - Get help from the community
* [API Status](https://status.stateset.com) - Check service status
* [Support Email](mailto:api-support@stateset.com) - Direct support
## Troubleshooting
**Problem:** Getting 401 Unauthorized errors
**Solutions:**
* Verify your API key is correct and active
* Check you're using the right environment (test vs live)
* Ensure Bearer prefix in Authorization header
* Verify API key has required permissions
**Problem:** Getting 429 Too Many Requests errors
**Solutions:**
* Implement exponential backoff
* Cache frequently accessed data
* Use batch operations where possible
* Consider upgrading your plan for higher limits
**Problem:** Webhooks not being received
**Solutions:**
* Verify webhook URL is publicly accessible
* Check webhook signature verification
* Ensure your server responds with 2xx status
* Test with webhook simulator in dashboard
**Problem:** Getting validation errors
**Solutions:**
* Check required fields are included
* Verify data types match specification
* Ensure enum values are valid
* Review error details for specific issues
***
🎉 **Congratulations!** You've successfully integrated with the StateSet API. You're now ready to build powerful commerce applications!
For questions or feedback, reach out on [Discord](https://discord.gg/VfcaqgZywq) or email [api-support@stateset.com](mailto:api-support@stateset.com).
# Rate Limiting & Performance
Source: https://docs.stateset.com/api-reference/rate-limiting
Optimize your API usage with rate limiting strategies and performance best practices
Understanding and working with StateSet's rate limits ensures reliable, high-performance integrations.
## Overview
StateSet implements intelligent rate limiting to ensure fair usage and maintain optimal performance for all users. Our system uses a sliding window algorithm with burst capacity to handle traffic spikes while preventing abuse.
### Key Concepts
* **Request Quota**: Maximum requests allowed per time window
* **Burst Capacity**: Short-term allowance for traffic spikes
* **Sliding Window**: Continuous evaluation of request rate
* **Adaptive Throttling**: Dynamic adjustment based on system load
* **Priority Queuing**: Critical endpoints get preferential treatment
## Rate Limits by Plan
| Plan | Requests/Min | Requests/Hour | Requests/Day | Burst Capacity | Concurrent |
| -------------- | ------------ | ------------- | ------------ | -------------- | ---------- |
| **Free** | 60 | 1,000 | 10,000 | 100/sec | 10 |
| **Starter** | 100 | 5,000 | 50,000 | 200/sec | 25 |
| **Growth** | 1,000 | 30,000 | 500,000 | 1,000/sec | 100 |
| **Scale** | 5,000 | 150,000 | 2,000,000 | 5,000/sec | 500 |
| **Enterprise** | Custom | Custom | Unlimited | Custom | Unlimited |
| Endpoint Category | Multiplier | Example Endpoints |
| -------------------- | ---------- | ---------------------------- |
| **Read Operations** | 1x | GET /orders, GET /customers |
| **Write Operations** | 2x | POST /orders, PUT /products |
| **Search/Analytics** | 5x | POST /search, GET /analytics |
| **Bulk Operations** | 10x | POST /batch, POST /import |
| **Webhooks** | 0.5x | POST /webhooks/simulate |
| **Health Checks** | 0x | GET /health, GET /ping |
| Resource | Limit | Notes |
| ------------------ | ---------- | ----------------------------------- |
| Max request size | 10 MB | 100 MB for file uploads |
| Max response size | 50 MB | Use pagination for larger datasets |
| Max items per page | 1,000 | Default: 100 |
| Max batch size | 1,000 | Async processing for larger batches |
| Max search results | 10,000 | Use cursor for deep pagination |
| Request timeout | 30 seconds | 5 minutes for bulk operations |
## Rate Limit Headers
Every API response includes rate limit information:
```http theme={null}
HTTP/1.1 200 OK
X-RateLimit-Limit: 1000
X-RateLimit-Remaining: 995
X-RateLimit-Reset: 1704070800
X-RateLimit-Reset-After: 45
X-RateLimit-Bucket: api
X-RateLimit-Retry-After: 0
X-Request-Id: req_1NXWPnCo6bFb1KQto6C8OWvE
```
### Header Descriptions
| Header | Description | Example |
| ------------------------- | -------------------------------- | ------------ |
| `X-RateLimit-Limit` | Max requests in current window | `1000` |
| `X-RateLimit-Remaining` | Requests remaining in window | `995` |
| `X-RateLimit-Reset` | Unix timestamp when limit resets | `1704070800` |
| `X-RateLimit-Reset-After` | Seconds until limit resets | `45` |
| `X-RateLimit-Bucket` | Rate limit bucket identifier | `api` |
| `X-RateLimit-Retry-After` | Seconds to wait if rate limited | `10` |
## Handling Rate Limits
### Exponential Backoff Implementation
```javascript Node.js theme={null}
class RateLimitHandler {
constructor(options = {}) {
this.maxRetries = options.maxRetries || 5;
this.baseDelay = options.baseDelay || 1000;
this.maxDelay = options.maxDelay || 32000;
this.jitter = options.jitter || true;
}
async executeWithRetry(fn) {
let lastError;
for (let attempt = 0; attempt <= this.maxRetries; attempt++) {
try {
const response = await fn();
// Check rate limit headers
this.trackRateLimit(response.headers);
return response;
} catch (error) {
lastError = error;
if (error.status === 429) {
const delay = this.calculateDelay(error, attempt);
console.log(`Rate limited. Waiting ${delay}ms before retry ${attempt + 1}/${this.maxRetries}`);
if (attempt < this.maxRetries) {
await this.sleep(delay);
continue;
}
}
// Don't retry on other errors
throw error;
}
}
throw lastError;
}
calculateDelay(error, attempt) {
// Use server-provided retry delay if available
const retryAfter = error.headers?.['x-ratelimit-retry-after'];
if (retryAfter) {
return parseInt(retryAfter) * 1000;
}
// Calculate exponential backoff
let delay = Math.min(
this.baseDelay * Math.pow(2, attempt),
this.maxDelay
);
// Add jitter to prevent thundering herd
if (this.jitter) {
delay = delay * (0.5 + Math.random() * 0.5);
}
return Math.floor(delay);
}
trackRateLimit(headers) {
const remaining = parseInt(headers['x-ratelimit-remaining']);
const limit = parseInt(headers['x-ratelimit-limit']);
if (remaining < limit * 0.2) {
console.warn(`Rate limit warning: ${remaining}/${limit} requests remaining`);
}
}
sleep(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
}
// Usage
const rateLimiter = new RateLimitHandler();
async function makeApiCall() {
return rateLimiter.executeWithRetry(async () => {
return await fetch('https://api.stateset.com/v1/orders', {
headers: {
'Authorization': `Bearer ${API_KEY}`
}
});
});
}
```
```python Python theme={null}
import time
import random
from typing import Callable, Optional, Any
import requests
class RateLimitHandler:
def __init__(
self,
max_retries: int = 5,
base_delay: float = 1.0,
max_delay: float = 32.0,
jitter: bool = True
):
self.max_retries = max_retries
self.base_delay = base_delay
self.max_delay = max_delay
self.jitter = jitter
def execute_with_retry(self, fn: Callable) -> Any:
last_error = None
for attempt in range(self.max_retries + 1):
try:
response = fn()
# Track rate limit status
self.track_rate_limit(response.headers)
return response
except requests.HTTPError as error:
last_error = error
if error.response.status_code == 429:
delay = self.calculate_delay(error.response, attempt)
print(f"Rate limited. Waiting {delay:.2f}s before retry {attempt + 1}/{self.max_retries}")
if attempt < self.max_retries:
time.sleep(delay)
continue
# Don't retry other errors
raise error
raise last_error
def calculate_delay(
self,
response: requests.Response,
attempt: int
) -> float:
# Use server-provided retry delay if available
retry_after = response.headers.get('X-RateLimit-Retry-After')
if retry_after:
return float(retry_after)
# Calculate exponential backoff
delay = min(
self.base_delay * (2 ** attempt),
self.max_delay
)
# Add jitter to prevent thundering herd
if self.jitter:
delay *= (0.5 + random.random() * 0.5)
return delay
def track_rate_limit(self, headers: dict) -> None:
remaining = int(headers.get('X-RateLimit-Remaining', 0))
limit = int(headers.get('X-RateLimit-Limit', 1))
if remaining < limit * 0.2:
print(f"Rate limit warning: {remaining}/{limit} requests remaining")
# Usage
rate_limiter = RateLimitHandler()
def make_api_call():
return rate_limiter.execute_with_retry(lambda: requests.get(
'https://api.stateset.com/v1/orders',
headers={'Authorization': f'Bearer {API_KEY}'}
))
```
### Circuit Breaker Pattern
Prevent cascading failures with circuit breaker:
```javascript theme={null}
class CircuitBreaker {
constructor(options = {}) {
this.failureThreshold = options.failureThreshold || 5;
this.successThreshold = options.successThreshold || 2;
this.timeout = options.timeout || 60000;
this.state = 'CLOSED';
this.failures = 0;
this.successes = 0;
this.nextAttempt = Date.now();
}
async execute(fn) {
if (this.state === 'OPEN') {
if (Date.now() < this.nextAttempt) {
throw new Error('Circuit breaker is OPEN');
}
this.state = 'HALF_OPEN';
}
try {
const result = await fn();
this.onSuccess();
return result;
} catch (error) {
this.onFailure();
throw error;
}
}
onSuccess() {
this.failures = 0;
if (this.state === 'HALF_OPEN') {
this.successes++;
if (this.successes >= this.successThreshold) {
this.state = 'CLOSED';
this.successes = 0;
}
}
}
onFailure() {
this.successes = 0;
this.failures++;
if (this.failures >= this.failureThreshold) {
this.state = 'OPEN';
this.nextAttempt = Date.now() + this.timeout;
console.error(`Circuit breaker opened. Will retry at ${new Date(this.nextAttempt)}`);
}
}
getState() {
return {
state: this.state,
failures: this.failures,
successes: this.successes,
nextAttempt: this.state === 'OPEN' ? new Date(this.nextAttempt) : null
};
}
}
```
## Performance Optimization
### 1. Request Batching
Combine multiple operations into single requests:
```javascript theme={null}
// Instead of multiple individual requests
const orders = [];
for (const customerId of customerIds) {
const order = await stateset.orders.list({ customer_id: customerId });
orders.push(...order.data);
}
// Use batch operations
const orders = await stateset.orders.batchGet({
customer_ids: customerIds
});
// Or use GraphQL for complex queries
const query = `
query GetMultipleOrders($customerIds: [ID!]!) {
orders(where: { customer_id: { _in: $customerIds } }) {
id
status
total
customer {
email
}
}
}
`;
```
### 2. Response Caching
Implement intelligent caching to reduce API calls:
```javascript theme={null}
class CachedAPIClient {
constructor(client, cache) {
this.client = client;
this.cache = cache;
}
async get(resource, id, options = {}) {
const cacheKey = `${resource}:${id}`;
const ttl = options.ttl || 300; // 5 minutes default
// Check cache
const cached = await this.cache.get(cacheKey);
if (cached && !options.force) {
return JSON.parse(cached);
}
// Fetch from API
const data = await this.client[resource].get(id);
// Cache result
await this.cache.setex(cacheKey, ttl, JSON.stringify(data));
return data;
}
async list(resource, filters = {}, options = {}) {
const cacheKey = `${resource}:list:${JSON.stringify(filters)}`;
const ttl = options.ttl || 60; // 1 minute for lists
// Check cache
const cached = await this.cache.get(cacheKey);
if (cached && !options.force) {
return JSON.parse(cached);
}
// Fetch from API
const data = await this.client[resource].list(filters);
// Cache result
await this.cache.setex(cacheKey, ttl, JSON.stringify(data));
return data;
}
async invalidate(resource, id = null) {
if (id) {
await this.cache.del(`${resource}:${id}`);
} else {
// Invalidate all cached lists for this resource
const keys = await this.cache.keys(`${resource}:list:*`);
if (keys.length) {
await this.cache.del(...keys);
}
}
}
}
```
### 3. Pagination Strategies
Efficiently handle large datasets:
```javascript theme={null}
class PaginationHelper {
async *iterateAll(resource, filters = {}) {
let cursor = null;
do {
const response = await stateset[resource].list({
...filters,
limit: 100,
cursor
});
for (const item of response.data) {
yield item;
}
cursor = response.pagination.next_cursor;
// Rate limit friendly delay
await new Promise(r => setTimeout(r, 100));
} while (cursor);
}
async getAllPages(resource, filters = {}) {
const items = [];
for await (const item of this.iterateAll(resource, filters)) {
items.push(item);
}
return items;
}
async getParallel(resource, filters = {}, concurrency = 3) {
// First request to get total count
const first = await stateset[resource].list({
...filters,
limit: 100
});
const totalPages = Math.ceil(first.pagination.total_count / 100);
const results = [first.data];
// Parallel fetch remaining pages
const promises = [];
for (let page = 2; page <= totalPages; page++) {
promises.push(
this.fetchPage(resource, filters, page, concurrency)
);
}
const pages = await Promise.all(promises);
results.push(...pages.flat());
return results.flat();
}
async fetchPage(resource, filters, page, concurrency) {
// Rate limiting with concurrency control
await this.rateLimitQueue(concurrency);
const response = await stateset[resource].list({
...filters,
limit: 100,
offset: (page - 1) * 100
});
return response.data;
}
}
```
### 4. Field Selection
Request only the data you need:
```javascript theme={null}
// REST API - Use sparse fieldsets
const orders = await stateset.orders.list({
fields: ['id', 'status', 'total', 'customer.email']
});
// GraphQL - Precise field selection
const query = `
query GetOrders {
orders(limit: 10) {
id
status
total
customer {
email
}
}
}
`;
```
### 5. Compression
Enable response compression:
```javascript theme={null}
const response = await fetch('https://api.stateset.com/v1/orders', {
headers: {
'Authorization': `Bearer ${API_KEY}`,
'Accept-Encoding': 'gzip, deflate, br'
}
});
// SDK automatically handles compression
const stateset = new StateSetClient({
apiKey: API_KEY,
compression: true // Default: true
});
```
## Request Prioritization
### Priority Queuing System
```javascript theme={null}
class PriorityRequestQueue {
constructor() {
this.queues = {
high: [],
medium: [],
low: []
};
this.processing = false;
this.concurrency = 5;
this.active = 0;
}
async add(request, priority = 'medium') {
return new Promise((resolve, reject) => {
this.queues[priority].push({
request,
resolve,
reject,
timestamp: Date.now()
});
this.process();
});
}
async process() {
if (this.processing) return;
this.processing = true;
while (this.hasRequests() && this.active < this.concurrency) {
const item = this.getNext();
if (!item) break;
this.active++;
this.execute(item).finally(() => {
this.active--;
this.process();
});
}
this.processing = false;
}
getNext() {
// Priority order: high > medium > low
for (const priority of ['high', 'medium', 'low']) {
if (this.queues[priority].length > 0) {
return this.queues[priority].shift();
}
}
return null;
}
hasRequests() {
return Object.values(this.queues).some(q => q.length > 0);
}
async execute(item) {
try {
const result = await item.request();
item.resolve(result);
} catch (error) {
item.reject(error);
}
}
}
// Usage
const queue = new PriorityRequestQueue();
// High priority request
const criticalOrder = await queue.add(
() => stateset.orders.create(orderData),
'high'
);
// Low priority analytics
const analytics = await queue.add(
() => stateset.analytics.get(query),
'low'
);
```
## Monitoring and Analytics
### Rate Limit Monitoring
```javascript theme={null}
class RateLimitMonitor {
constructor() {
this.metrics = {
requests: 0,
rateLimited: 0,
remaining: null,
limit: null
};
}
track(response) {
this.metrics.requests++;
const headers = response.headers;
this.metrics.remaining = parseInt(headers['x-ratelimit-remaining']);
this.metrics.limit = parseInt(headers['x-ratelimit-limit']);
if (response.status === 429) {
this.metrics.rateLimited++;
this.onRateLimit(headers);
}
// Alert when approaching limit
const usage = (this.metrics.limit - this.metrics.remaining) / this.metrics.limit;
if (usage > 0.8) {
this.alertHighUsage(usage);
}
}
onRateLimit(headers) {
console.error('Rate limited!', {
retryAfter: headers['x-ratelimit-retry-after'],
resetAt: new Date(parseInt(headers['x-ratelimit-reset']) * 1000)
});
// Send alert
alerting.send({
type: 'RATE_LIMIT',
severity: 'high',
details: this.metrics
});
}
alertHighUsage(usage) {
console.warn(`High API usage: ${(usage * 100).toFixed(1)}%`);
if (usage > 0.9) {
// Implement throttling
this.throttle();
}
}
throttle() {
// Add delay between requests
this.throttleDelay = 1000;
console.log('Throttling enabled: 1s delay between requests');
}
getMetrics() {
return {
...this.metrics,
usagePercent: ((this.metrics.limit - this.metrics.remaining) / this.metrics.limit * 100).toFixed(1),
rateLimitPercent: (this.metrics.rateLimited / this.metrics.requests * 100).toFixed(2)
};
}
}
```
### Performance Metrics
```javascript theme={null}
class PerformanceTracker {
constructor() {
this.metrics = new Map();
}
async track(name, fn) {
const start = performance.now();
const startMemory = process.memoryUsage();
try {
const result = await fn();
const duration = performance.now() - start;
const memoryDelta = process.memoryUsage().heapUsed - startMemory.heapUsed;
this.record(name, {
duration,
memoryDelta,
success: true
});
return result;
} catch (error) {
const duration = performance.now() - start;
this.record(name, {
duration,
success: false,
error: error.message
});
throw error;
}
}
record(name, metrics) {
if (!this.metrics.has(name)) {
this.metrics.set(name, {
count: 0,
totalDuration: 0,
avgDuration: 0,
maxDuration: 0,
minDuration: Infinity,
errors: 0
});
}
const stats = this.metrics.get(name);
stats.count++;
stats.totalDuration += metrics.duration;
stats.avgDuration = stats.totalDuration / stats.count;
stats.maxDuration = Math.max(stats.maxDuration, metrics.duration);
stats.minDuration = Math.min(stats.minDuration, metrics.duration);
if (!metrics.success) {
stats.errors++;
}
// Log slow requests
if (metrics.duration > 5000) {
console.warn(`Slow API call: ${name} took ${metrics.duration.toFixed(2)}ms`);
}
}
getReport() {
const report = {};
for (const [name, stats] of this.metrics) {
report[name] = {
...stats,
avgDuration: stats.avgDuration.toFixed(2),
errorRate: ((stats.errors / stats.count) * 100).toFixed(2) + '%'
};
}
return report;
}
}
// Usage
const tracker = new PerformanceTracker();
const orders = await tracker.track('fetchOrders', async () => {
return await stateset.orders.list({ limit: 100 });
});
console.log(tracker.getReport());
```
## Best Practices
### 1. Implement Graceful Degradation
```javascript theme={null}
class ResilientAPIClient {
async getOrdersWithFallback() {
try {
// Try primary method
return await this.fetchFromAPI();
} catch (error) {
if (error.status === 429) {
// Fall back to cached data
return await this.fetchFromCache();
} else if (error.status >= 500) {
// Fall back to secondary system
return await this.fetchFromBackup();
}
throw error;
}
}
}
```
### 2. Use Webhooks Instead of Polling
```javascript theme={null}
// Bad: Polling for updates
setInterval(async () => {
const orders = await stateset.orders.list({
updated_after: lastCheck
});
processUpdates(orders);
}, 60000);
// Good: Use webhooks
app.post('/webhook', (req, res) => {
const event = req.body;
if (event.type === 'order.updated') {
processUpdate(event.data.object);
}
res.sendStatus(200);
});
```
### 3. Optimize Batch Sizes
```javascript theme={null}
class BatchProcessor {
async processBatch(items, batchSize = 100) {
const results = [];
for (let i = 0; i < items.length; i += batchSize) {
const batch = items.slice(i, i + batchSize);
const result = await stateset.batch.process(batch);
results.push(...result);
// Rate limit friendly delay
if (i + batchSize < items.length) {
await new Promise(r => setTimeout(r, 1000));
}
}
return results;
}
}
```
## Troubleshooting
**Solutions:**
* Implement request queuing and batching
* Cache frequently accessed data
* Use webhooks instead of polling
* Consider upgrading your plan
* Optimize request patterns
**Solutions:**
* Use field selection to reduce payload size
* Enable compression
* Implement pagination for large datasets
* Use regional endpoints if available
* Check network latency
**Possible causes:**
* Hitting endpoint-specific limits
* Burst rate exceeded
* Account-level restrictions
* Check rate limit headers for details
**Solutions:**
* Increase failure threshold
* Implement better error handling
* Check for systematic issues
* Review timeout settings
* Monitor API status page
## Related Resources
* [API Quickstart](/api-reference/quickstart) - Get started quickly
* [Error Handling](/api-reference/errors) - Handle errors gracefully
* [Webhooks](/api-reference/webhooks) - Real-time event notifications
* [Batch Operations](/api-reference/batch) - Process data efficiently
***
**Need help optimizing your integration?** Contact [api-support@stateset.com](mailto:api-support@stateset.com) or visit our [Discord community](https://discord.gg/VfcaqgZywq).
# Cancel Refund
Source: https://docs.stateset.com/api-reference/refunds/cancel
POST https://api.stateset.com/v1/refunds/:id/cancel
Cancel a pending or processing refund
This endpoint cancels a refund that is in pending or processing status. Once a refund is completed, it cannot be cancelled.
## Authentication
This endpoint requires a valid API key with `refunds:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the refund to cancel
## Request Body
Reason for cancellation
Whether to notify customer of cancellation
### Response
Returns the cancelled refund object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/refunds/refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"reason": "Customer requested to keep the product",
"notify_customer": true
}'
```
```javascript Node.js theme={null}
const refund = await stateset.refunds.cancel(
'refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
reason: "Customer requested to keep the product",
notify_customer: true
}
);
```
```python Python theme={null}
refund = stateset.refunds.cancel(
'refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
reason="Customer requested to keep the product",
notify_customer=True
)
```
```json Response theme={null}
{
"id": "refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "refund",
"order_id": "order_123456",
"customer_id": "cust_abc123",
"type": "partial",
"status": "cancelled",
"previous_status": "processing",
"reason": "product_damaged",
"reason_details": "Item arrived with scratches on the surface",
"cancellation": {
"reason": "Customer requested to keep the product",
"cancelled_at": "2024-06-21T10:00:00Z",
"cancelled_by": "user_456"
},
"amounts": {
"subtotal": 4999,
"tax": 450,
"shipping": 0,
"total": 5449,
"currency": "USD"
},
"timeline": [
{
"status": "created",
"timestamp": "2024-01-20T13:30:00Z",
"actor": "customer"
},
{
"status": "approved",
"timestamp": "2024-01-20T13:30:01Z",
"actor": "system"
},
{
"status": "processing",
"timestamp": "2024-01-20T13:30:02Z",
"actor": "system"
},
{
"status": "cancelled",
"timestamp": "2024-06-21T10:00:00Z",
"actor": "user_456",
"note": "Customer requested to keep the product"
}
],
"updated_at": "2024-06-21T10:00:00Z",
"notifications": {
"customer_notified": true,
"notification_sent_at": "2024-06-21T10:00:05Z"
}
}
```
# Create Refund
Source: https://docs.stateset.com/api-reference/refunds/create
POST https://api.stateset.com/v1/refunds
Create a refund for an order or specific items
This endpoint creates a refund request that can process partial or full refunds. It handles payment reversals, inventory adjustments, and customer notifications.
## Authentication
This endpoint requires a valid API key with `refunds:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Original order ID to refund
Refund type: "full", "partial", "item\_return", "shipping", "tax\_only"
Refund reason code
Detailed explanation of refund reason
Items to refund (required for partial/item refunds)
Original order line item ID
Quantity to refund
Override refund amount in cents
Whether to restock this item
Location to restock to
Refund amounts breakdown
Items subtotal to refund in cents
Tax amount to refund in cents
Shipping amount to refund in cents
Manual adjustment amount (positive or negative)
Total refund amount in cents
Refund payment method
Refund method: "original\_payment", "store\_credit", "gift\_card", "check", "manual"
Original payment ID to refund to
Store credit account ID
Return shipping details
Whether return shipping label is needed
Return carrier
Return service type
Pre-generated return label ID
Processing options
Auto-approve if within policy
Send customer notification
Process payment refund immediately
Internal notes about the refund
Additional custom fields
### Response
Returns the created refund object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/refunds' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"order_id": "order_123456",
"type": "partial",
"reason": "product_damaged",
"reason_details": "Item arrived with scratches on the surface",
"items": [
{
"line_item_id": "li_abc123",
"quantity": 1,
"restock": false
}
],
"amounts": {
"subtotal": 4999,
"tax": 450,
"shipping": 0,
"total": 5449
},
"payment_method": {
"type": "original_payment",
"payment_id": "pay_xyz789"
},
"processing": {
"auto_approve": true,
"notify_customer": true,
"process_immediately": true
}
}'
```
```javascript Node.js theme={null}
const refund = await stateset.refunds.create({
order_id: "order_123456",
type: "partial",
reason: "product_damaged",
reason_details: "Item arrived with scratches on the surface",
items: [
{
line_item_id: "li_abc123",
quantity: 1,
restock: false
}
],
amounts: {
subtotal: 4999,
tax: 450,
shipping: 0,
total: 5449
},
payment_method: {
type: "original_payment",
payment_id: "pay_xyz789"
},
processing: {
auto_approve: true,
notify_customer: true,
process_immediately: true
}
});
```
```python Python theme={null}
refund = stateset.refunds.create(
order_id="order_123456",
type="partial",
reason="product_damaged",
reason_details="Item arrived with scratches on the surface",
items=[
{
"line_item_id": "li_abc123",
"quantity": 1,
"restock": False
}
],
amounts={
"subtotal": 4999,
"tax": 450,
"shipping": 0,
"total": 5449
},
payment_method={
"type": "original_payment",
"payment_id": "pay_xyz789"
},
processing={
"auto_approve": True,
"notify_customer": True,
"process_immediately": True
}
)
```
```json Response theme={null}
{
"id": "refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "refund",
"order_id": "order_123456",
"customer_id": "cust_abc123",
"type": "partial",
"status": "processing",
"reason": "product_damaged",
"reason_details": "Item arrived with scratches on the surface",
"items": [
{
"line_item_id": "li_abc123",
"product_id": "prod_123",
"product_name": "Wireless Headphones",
"quantity": 1,
"refund_amount": 4999,
"restock": false,
"restock_status": "not_restocking"
}
],
"amounts": {
"subtotal": 4999,
"tax": 450,
"shipping": 0,
"adjustment": 0,
"total": 5449,
"currency": "USD"
},
"payment_method": {
"type": "original_payment",
"payment_id": "pay_xyz789",
"last4": "4242",
"brand": "visa"
},
"payment_status": "pending",
"transaction_id": null,
"processing": {
"auto_approved": true,
"approved_at": "2024-01-20T13:30:00Z",
"approved_by": "system"
},
"shipping": {
"return_required": false,
"return_label_id": null
},
"timeline": [
{
"status": "created",
"timestamp": "2024-01-20T13:30:00Z",
"actor": "customer"
},
{
"status": "approved",
"timestamp": "2024-01-20T13:30:01Z",
"actor": "system"
},
{
"status": "processing",
"timestamp": "2024-01-20T13:30:02Z",
"actor": "system"
}
],
"created_at": "2024-01-20T13:30:00Z",
"updated_at": "2024-01-20T13:30:02Z",
"estimated_completion": "2024-01-23T13:30:00Z",
"notes": null,
"metadata": {}
}
```
# Get Refund
Source: https://docs.stateset.com/api-reference/refunds/get
GET https://api.stateset.com/v1/refunds/:id
Retrieve details of a specific refund
This endpoint retrieves detailed information about a specific refund, including its current status, timeline, and associated transactions.
## Authentication
This endpoint requires a valid API key with `refunds:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the refund
### Response
Returns the refund object if found.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/refunds/refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const refund = await stateset.refunds.retrieve(
'refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
refund = stateset.refunds.retrieve(
'refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "refund",
"order_id": "order_123456",
"customer_id": "cust_abc123",
"type": "partial",
"status": "completed",
"reason": "product_damaged",
"reason_details": "Item arrived with scratches on the surface",
"items": [
{
"line_item_id": "li_abc123",
"product_id": "prod_123",
"product_name": "Wireless Headphones",
"sku": "WH-001",
"quantity": 1,
"refund_amount": 4999,
"restock": false,
"restock_status": "not_restocking",
"images": [
"https://refunds.stateset.com/images/refund_0901f083_damage_1.jpg"
]
}
],
"amounts": {
"subtotal": 4999,
"tax": 450,
"shipping": 0,
"adjustment": 0,
"total": 5449,
"currency": "USD"
},
"payment_method": {
"type": "original_payment",
"payment_id": "pay_xyz789",
"last4": "4242",
"brand": "visa"
},
"payment_status": "completed",
"transaction_id": "txn_refund_456789",
"processing": {
"auto_approved": true,
"approved_at": "2024-01-20T13:30:00Z",
"approved_by": "system",
"completed_at": "2024-01-23T13:30:00Z"
},
"shipping": {
"return_required": false,
"return_label_id": null,
"return_tracking": null
},
"timeline": [
{
"status": "created",
"timestamp": "2024-01-20T13:30:00Z",
"actor": "customer",
"note": "Refund requested by customer"
},
{
"status": "approved",
"timestamp": "2024-01-20T13:30:01Z",
"actor": "system",
"note": "Auto-approved per return policy"
},
{
"status": "processing",
"timestamp": "2024-01-20T13:30:02Z",
"actor": "system",
"note": "Payment refund initiated"
},
{
"status": "completed",
"timestamp": "2024-01-23T13:30:00Z",
"actor": "system",
"note": "Refund processed successfully"
}
],
"created_at": "2024-01-20T13:30:00Z",
"updated_at": "2024-01-23T13:30:00Z",
"notes": "Customer contacted support about damage during shipping",
"metadata": {
"support_ticket_id": "ticket_789",
"quality_issue_logged": true
}
}
```
# List Refunds
Source: https://docs.stateset.com/api-reference/refunds/list
GET https://api.stateset.com/v1/refunds
List all refunds with filtering and pagination options
This endpoint returns a paginated list of refunds. You can filter by status, date range, customer, and more.
## Authentication
This endpoint requires a valid API key with `refunds:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of refunds to return (1-100)
Number of refunds to skip
Filter by status: "pending", "approved", "processing", "completed", "rejected", "cancelled"
Filter by type: "full", "partial", "item\_return", "shipping", "tax\_only"
Filter by specific order
Filter by customer
Filter refunds created after date (ISO 8601)
Filter refunds created before date (ISO 8601)
Filter by refund reason code
Sort by field: "created\_at", "updated\_at", "amount", "status"
Sort order: "asc" or "desc"
### Response
Returns a paginated list of refund objects.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/refunds?status=processing&limit=20' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const refunds = await stateset.refunds.list({
status: 'processing',
limit: 20
});
```
```python Python theme={null}
refunds = stateset.refunds.list(
status='processing',
limit=20
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "refund_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "refund",
"order_id": "order_123456",
"customer_id": "cust_abc123",
"type": "partial",
"status": "processing",
"reason": "product_damaged",
"amounts": {
"total": 5449,
"currency": "USD"
},
"created_at": "2024-06-20T13:30:00Z",
"estimated_completion": "2024-06-23T13:30:00Z"
},
{
"id": "refund_1234f083-bb2d-54d6-bg6d-1b0e3gd75f41",
"object": "refund",
"order_id": "order_234567",
"customer_id": "cust_def456",
"type": "full",
"status": "processing",
"reason": "order_cancelled",
"amounts": {
"total": 15999,
"currency": "USD"
},
"created_at": "2024-06-20T12:00:00Z",
"estimated_completion": "2024-06-23T12:00:00Z"
}
],
"has_more": true,
"total_count": 156,
"url": "/v1/refunds",
"summary": {
"total_amount": 847532,
"average_processing_time": 72,
"status_breakdown": {
"pending": 12,
"approved": 8,
"processing": 45,
"completed": 87,
"rejected": 3,
"cancelled": 1
}
}
}
```
# Reporting
Source: https://docs.stateset.com/api-reference/reporting
Overview of the Stateset One Platform Reporting
# Reporting
## Advanced Reporting Capabilities
Stateset One offers a comprehensive set of advanced reporting capabilities to help users analyze and visualize their data effectively. Some of the key features include:
### Customizable Reports
Users can create customized reports tailored to their specific needs. The platform provides a user-friendly interface to define report parameters, select relevant data sources, apply filters, and specify the desired output format.
### Data Visualization
Stateset One includes & integrates a range of data visualization tools to transform raw data into meaningful visual representations. Users can create charts, graphs, dashboards, and other visual elements to gain insights into their data quickly. The platform supports various visualization types, such as bar charts, pie charts, line graphs, and heatmaps.
### Drill-Down Capabilities
With drill-down capabilities, users can dig deeper into their data to uncover more granular details. By interacting with visualizations or reports, users can access underlying data layers, enabling a more comprehensive analysis of trends, patterns, and outliers.
### Filtering and Segmentation
Stateset One allows users to apply filters and segment their data for focused analysis. Users can define criteria based on specific dimensions or variables, such as time periods, geographical locations, customer segments, or product categories. This feature enables users to examine data subsets and compare performance across different segments.
### Scheduled Exports
Stateset One provides scheduled export functionality, allowing users to automate the generation and delivery of reports at specified intervals. Key features of this capability include:
#### Flexible Export Formats
Users can choose from a variety of export formats for their reports, such as PDF, Excel, CSV, or HTML. This flexibility ensures compatibility with different systems and caters to the diverse needs of stakeholders who may require specific file formats.
### Example Code for Exporting Data
```javascript theme={null}
const returnFields = [
"id",
"status",
"order_id",
"rma",
"tracking_number",
"description",
"customerEmail",
"zendesk_number",
"action_needed",
"reason_category",
"issue",
"order_date",
"shipped_date",
"requested_date",
"serial_number",
"scanned_serial_number",
"condition",
"amount",
"customer_id",
"tax_refunded",
"total_refunded",
"created_date",
"flat_rate_shipping",
"warehouse_received_date",
"warehouse_condition_date",
"country"
];
const opts = { returnFields };
// Current Time
var time = Math.floor(Date.now() / 1000);
// The ID of your GCS bucket
const bucketName = 'returns';
// The path to your file to upload
const filePath = `../stateset-app/static/data/returns/returns-data-${time}.csv`;
// The new ID for your GCS file
const destFileName = `returns-data-${time}.csv`;
// Upload to Google Cloud Function
async function uploadFile() {
// Uploads a local file to the bucket
await storage.bucket(bucketName).upload(filePath, {
destination: destFileName,
});
return res.status(200).json({ status: `${filename}-${time} uploaded to ${bucketName}.` })
}
// Get the Return Data
const return_records = await graphQLClient.request(GET_MY_RETURNS);
// JSON 2 CSV Parser
const json2csvParser = new Parser({ returnFields, quote: '', delimiter: ',' });
// Stateset CSV
const statesetCSV = json2csvParser.parse(return_records.returns);
// Parse the Response convert to CSV
let statesetWriter = createWriteStream(`../stateset-app/static/data/returns/returns-data-${time}.csv`)
statesetWriter.write(statesetCSV);
// Upload File
uploadFile().catch(console.error);
```
#### Example for Sending Email with Attachment
```Python theme={null}
import base64
import io
import os
from google.cloud import storage
from sendgrid import SendGridAPIClient
from sendgrid.helpers.mail import (
Mail, Attachment, FileContent, FileName,
FileType, To, Disposition)
sg = SendGridAPIClient(process.env.SENDGRID_API)
def send_mail(data, context):
message = Mail(
from_email='',
to_emails= [To('email@customer.com'), To('partner@customer.com'), To('manager@customer.com')],
subject='Returns Report',
html_content='This is the returns report autogenerated via Stateset.'
)
storage_client = storage.Client(process.env.STORAGE_CLIENT)
bucket = storage_client.get_bucket(process.env.STORAGE_BUCKET)
blob = bucket.blob(data['name'])
data = blob.download_as_bytes()
bytes = io.BytesIO(data)
bytes.seek(0)
data = bytes.read()
encoded = base64.b64encode(data)
csv_file = str(encoded,'utf-8')
attachment = Attachment()
attachment.file_content = FileContent(csv_file)
attachment.file_type = FileType('text/csv')
attachment.file_name = FileName('returns-export.csv')
attachment.disposition = Disposition('attachment')
message.attachment = attachment
response = sg.send(message)
print(response.status_code, response.body, response.headers)
```
# Approve Return
Source: https://docs.stateset.com/api-reference/return/approve
POST https://api.stateset.com/v1/returns/:id/approve
This endpoint approves a return.
### Body
The ID provided in the data tab may be used to identify the return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return/:id/approve' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation returnApproveMutation {
returnApprove(id: "${returnId}") {
return {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
returns = stateset.returns.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
returns, err := stateset.Returns.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Return returns = stateset.Returns.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$returns = $stateset->returns->approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var returns = await stateset.Returns.Approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "return",
"approved": true
}
```
# Cancel Return
Source: https://docs.stateset.com/api-reference/return/cancel
POST https://api.stateset.com/v1/returns/:id/cancel
This endpoint updates an existing return.
### Body
The ID provided in the data tab may be used to identify the return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return/:id/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation returnCancelMutation {
returnCancel(id: "${returnId}") {
return {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
returns = stateset.returns.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
returns, err := stateset.Returns.Cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Return returns = stateset.Returns.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$returns = $stateset->returns->cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var returns = await stateset.Returns.Cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "return",
"cancelled": true
}
```
# Close Return
Source: https://docs.stateset.com/api-reference/return/close
POST https://api.stateset.com/v1/returns/:id/close
This endpoint closes an existing return.
### Body
The ID provided in the data tab may be used to identify the return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return/:id/close' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation returnCloseMutation {
returnClose(id: "${returnId}") {
return {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```python Python theme={null}
returns = stateset.returns.close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
returns, err := stateset.Returns.Close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```java Java theme={null}
Return returns = stateset.Returns.close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```php PHP theme={null}
$returns = $stateset->returns->close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```csharp C# theme={null}
var returns = await stateset.Returns.Close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```cpp C++ theme={null}
auto returns = stateset.returns.close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```rust Rust theme={null}
let returns = stateset.returns.close({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```json Response theme={null}
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"closed": true
}
```
# Create Return
Source: https://docs.stateset.com/api-reference/return/create
POST https://api.stateset.com/v1/return
Create a new return record with automatic RMA generation and workflow initiation
This endpoint creates a new return and automatically triggers the returns management workflow, including label generation and customer notifications.
## Authentication
This endpoint requires a valid API key with `returns:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
The unique identifier of the order being returned. Must be a valid existing order.
Array of items being returned from the order.
Product SKU being returned
Number of units being returned
Return reason. Options: `defective`, `not_as_described`, `wrong_item`, `damaged`, `other`
Item condition. Options: `A` (like new), `B` (good), `C` (fair), `D` (poor)
Email address of the customer. Used for sending return labels and notifications.
Primary reason for the return. Options: `defective`, `not_satisfied`, `wrong_item`, `arrived_late`, `damaged_in_transit`, `other`
Type of return. Options: `replacement`, `refund`, `store_credit`
Additional notes or comments from the customer about the return.
Customer's address for pickup (if different from order address).
Street address line 1
Street address line 2
City name
State/Province code (e.g., "CA", "NY")
Postal/ZIP code
ISO 3166-1 alpha-2 country code (e.g., "US", "CA")
Associated support ticket ID for tracking.
Additional custom metadata to store with the return.
### Response
The ID provided in the data tab may be used to identify the return
The order ID provided in the data tab may be used to identify the order
The serial number provided in the data tab may be used to identify the serial number
The description provided in the data tab may be used to identify the description
The status provided in the data tab may be used to identify the status
The reported condition provided in the data tab may be used to identify the reported condition
The tracking number provided in the data tab may be used to identify the tracking number
The zendesk number provided in the data tab may be used to identify the zendesk number
The action needed provided in the data tab may be used to identify the action needed
The rma provided in the data tab may be used to identify the rma
The country provided in the data tab may be used to identify the country
```bash Basic Return theme={null}
curl -X POST https://api.stateset.com/v1/return \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"order_id": "ORD-789456",
"customer_email": "customer@example.com",
"reason_code": "defective",
"type": "replacement",
"items": [
{
"sku": "SHOE-RED-10",
"quantity": 1,
"reason": "defective",
"condition": "B"
}
],
"customer_notes": "Sole is separating from the shoe"
}'
```
```bash Complete Return with Address theme={null}
curl -X POST https://api.stateset.com/v1/return \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-H "Idempotency-Key: unique-return-key-123" \
-d '{
"order_id": "ORD-789456",
"customer_email": "customer@example.com",
"reason_code": "wrong_item",
"type": "refund",
"items": [
{
"sku": "SHIRT-BLUE-L",
"quantity": 2,
"reason": "wrong_item",
"condition": "A"
},
{
"sku": "PANTS-BLACK-32",
"quantity": 1,
"reason": "not_as_described",
"condition": "A"
}
],
"shipping_address": {
"street1": "123 Main Street",
"street2": "Apt 4B",
"city": "New York",
"state": "NY",
"zip": "10001",
"country": "US"
},
"zendesk_ticket_id": "TICKET-98765",
"metadata": {
"source": "web_portal",
"priority": "high"
}
}'
```
```graphQL GraphQL theme={null}
mutation InsertNewReturn(
$return_x: returns_insert_input!
) {
insert_returns (
objects: [$return_x]
) {
returning {
id
order_id
serial_number
description
status
reported_condition
tracking_number
zendesk_number
action_needed
rma
country
}
}
}`;
```
```js Node.js theme={null}
const returns = await stateset.returns.create({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'order_id': 'O-12332312',
'serial_number': 'st123976879tm',
'description:' 'Return for different type',
'status': 'NEW'
'reported_condition': 'A',
'tracking_number': '132908231098120921',
'zendesk_number': '123313',
'action_needed': 'Replacement'
'rma': 'R-123312',
'country': 'US'
});
```
```python Python theme={null}
returns = stateset.returns.create({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'order_id': 'O-12332312',
'serial_number': 'st123976879tm',
'description:' 'Return for different type',
'status': 'NEW'
'reported_condition': 'A',
'tracking_number': '132908231098120921',
'zendesk_number': '123313',
'action_needed': 'Replacement'
'rma': 'R-123312',
'country': 'US'
})
```
```ruby Ruby theme={null}
returns = stateset.returns.create({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'order_id': 'O-12332312',
'serial_number': 'st123976879tm',
'description:' 'Return for different type',
'status': 'NEW'
'reported_condition': 'A',
'tracking_number': '132908231098120921',
'zendesk_number': '123313',
'action_needed': 'Replacement'
'rma': 'R-123312',
'country': 'US'
})
```
```go Go theme={null}
returns, err := stateset.Returns.Create(
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'order_id': 'O-12332312',
'serial_number': 'st123976879tm',
'description:' 'Return for different type',
'status': 'NEW'
'reported_condition': 'A',
'tracking_number': '132908231098120921',
'zendesk_number': '123313',
'action_needed': 'Replacement'
'rma': 'R-123312',
'country': 'US'
)
```
```java Java theme={null}
Returns returns = stateset.returns.create({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'order_id': 'O-12332312',
'serial_number': 'st123976879tm',
'description:' 'Return for different type',
'status': 'NEW'
'reported_condition': 'A',
'tracking_number': '132908231098120921',
'zendesk_number': '123313',
'action_needed': 'Replacement'
'rma': 'R-123312',
'country': 'US'
})
```
```php PHP theme={null}
$returns = $stateset->returns->create({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'order_id': 'O-12332312',
'serial_number': 'st123976879tm',
'description:' 'Return for different type',
'status': 'NEW'
'reported_condition': 'A',
'tracking_number': '132908231098120921',
'zendesk_number': '123313',
'action_needed': 'Replacement'
'rma': 'R-123312',
'country': 'US'
})
```
```csharp C# theme={null}
var returns = stateset.Returns.Create(
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'order_id': 'O-12332312',
'serial_number': 'st123976879tm',
'description:' 'Return for different type',
'status': 'NEW'
'reported_condition': 'A',
'tracking_number': '132908231098120921',
'zendesk_number': '123313',
'action_needed': 'Replacement'
'rma': 'R-123312',
'country': 'US'
);
```
```json Success Response (201) theme={null}
{
"id": "RET-0901f083-aa1c-43c5-af5c",
"rma": "RMA-2024-1014",
"order_id": "ORD-789456",
"customer_email": "customer@example.com",
"status": "NEW",
"type": "replacement",
"reason_code": "defective",
"created_at": "2024-01-15T10:30:00Z",
"updated_at": "2024-01-15T10:30:00Z",
"workflow_id": "wf-return-0901f083",
"items": [
{
"id": "RLI-123",
"sku": "SHOE-RED-10",
"quantity": 1,
"reason": "defective",
"condition": "B",
"product_name": "Red Running Shoe Size 10",
"refund_amount": 89.99
}
],
"shipping": {
"carrier": "fedex",
"tracking_number": "7799832198765",
"label_url": "https://api.stateset.com/labels/RET-0901f083.pdf",
"label_created_at": "2024-01-15T10:30:15Z"
},
"totals": {
"subtotal": 89.99,
"tax_refund": 7.20,
"shipping_refund": 0.00,
"total_refund": 97.19
},
"timeline": [
{
"event": "return_created",
"timestamp": "2024-01-15T10:30:00Z",
"description": "Return request created"
},
{
"event": "label_generated",
"timestamp": "2024-01-15T10:30:15Z",
"description": "Shipping label generated and emailed"
}
]
}
```
```json Error Response (400) theme={null}
{
"error": {
"code": "INVALID_ORDER",
"message": "Order ORD-789456 not found or not eligible for return",
"details": {
"order_status": "returned",
"days_since_purchase": 45,
"return_window": 30
}
}
}
```
```json Error Response (422) theme={null}
{
"error": {
"code": "VALIDATION_ERROR",
"message": "Request validation failed",
"errors": [
{
"field": "items[0].quantity",
"message": "Quantity cannot exceed original order quantity",
"original_quantity": 1,
"requested_quantity": 2
},
{
"field": "reason_code",
"message": "Invalid reason code. Must be one of: defective, not_satisfied, wrong_item, arrived_late, damaged_in_transit, other"
}
]
}
}
```
# Delete Return
Source: https://docs.stateset.com/api-reference/return/delete
DELETE https://api.return.com/v1/returns/:id
This endpoint deletes an existing return.
### Body
The ID provided in the data tab may be used to identify the return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/return' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteReturn ($id: String!) {
delete_returns(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```js Node.js theme={null}
const returns = await stateset.returns.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
returns = stateset.returns.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
returns, err := stateset.Returns.Del(
"rt_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```java Java theme={null}
Return returns = stateset.returns.del(
"rt_1NXWPnCo6bFb1KQto6C8OWvE"
);
```
```js Javascript theme={null}
const returns = await stateset.returns.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```ruby Ruby theme={null}
returns = Stateset::Return.del({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```php PHP theme={null}
$returns = $stateset->returns->del(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
DELETE /v1/return HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"deleted": true
}
```
# Exchange Return
Source: https://docs.stateset.com/api-reference/return/exchange
POST https://api.stateset.com/v1/returns/:id/exchange
This endpoint processes an exchange for a returned item.
### Body
The ID provided in the data tab may be used to identify the return
The product ID of the item to exchange for
The variant ID if exchanging for a different variant (size, color, etc.)
The reason for the exchange
The price difference between original and exchange items (positive if customer owes, negative if refund due)
The shipping method for the exchange item
Whether to expedite the exchange shipment
### Response
The ID provided in the data tab may be used to identify the return
The object type
The new order ID for the exchange
The status of the exchange (e.g., "pending", "processing", "shipped")
The original product that was returned
The new product being sent as exchange
The price difference between items
Status of any additional payment or refund
Tracking number for the exchange shipment
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/returns/:id/exchange' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"exchange_product_id": "prod_abc789",
"exchange_variant_id": "var_size_large",
"exchange_reason": "Wrong size ordered",
"price_difference": 0,
"shipping_method": "standard",
"expedited": false
}'
```
```graphQL GraphQL theme={null}
mutation returnExchangeMutation {
returnExchange(
id: "${returnId}",
exchangeProductId: "${exchangeProductId}",
exchangeVariantId: "${exchangeVariantId}",
exchangeReason: "${exchangeReason}",
priceDifference: ${priceDifference},
shippingMethod: "${shippingMethod}",
expedited: ${expedited}
) {
return {
id,
status,
exchange_order_id,
exchange_status,
tracking_number
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.exchange({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
exchange_product_id: 'prod_abc789',
exchange_variant_id: 'var_size_large',
exchange_reason: 'Wrong size ordered',
price_difference: 0,
shipping_method: 'standard',
expedited: false
});
```
```python Python theme={null}
returns = stateset.returns.exchange({
'id': 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
'exchange_product_id': 'prod_abc789',
'exchange_variant_id': 'var_size_large',
'exchange_reason': 'Wrong size ordered',
'price_difference': 0,
'shipping_method': 'standard',
'expedited': False
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.exchange({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
exchange_product_id: 'prod_abc789',
exchange_variant_id: 'var_size_large',
exchange_reason: 'Wrong size ordered',
price_difference: 0,
shipping_method: 'standard',
expedited: false
})
```
```go Go theme={null}
returns, err := stateset.Returns.exchange({
ID: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
ExchangeProductID: 'prod_abc789',
ExchangeVariantID: 'var_size_large',
ExchangeReason: 'Wrong size ordered',
PriceDifference: 0,
ShippingMethod: 'standard',
Expedited: false
})
```
```java Java theme={null}
Return returns = stateset.Returns.exchange({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
exchangeProductId: 'prod_abc789',
exchangeVariantId: 'var_size_large',
exchangeReason: 'Wrong size ordered',
priceDifference: 0,
shippingMethod: 'standard',
expedited: false
});
```
```php PHP theme={null}
$returns = $stateset->returns->exchange([
'id' => 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
'exchange_product_id' => 'prod_abc789',
'exchange_variant_id' => 'var_size_large',
'exchange_reason' => 'Wrong size ordered',
'price_difference' => 0,
'shipping_method' => 'standard',
'expedited' => false
]);
```
```csharp C# theme={null}
var returns = await stateset.Returns.Exchange(new {
Id = 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
ExchangeProductId = 'prod_abc789',
ExchangeVariantId = 'var_size_large',
ExchangeReason = 'Wrong size ordered',
PriceDifference = 0,
ShippingMethod = 'standard',
Expedited = false
});
```
```json Response theme={null}
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"exchanged": true,
"exchange_order_id": "ord_exch_789xyz",
"exchange_status": "processing",
"original_product_id": "prod_xyz123",
"exchange_product_id": "prod_abc789",
"exchange_variant_id": "var_size_large",
"price_difference": 0,
"payment_status": "no_payment_required",
"tracking_number": "1Z999AA10123456785",
"estimated_delivery": "2024-01-18"
}
```
# Retrieve Return
Source: https://docs.stateset.com/api-reference/return/get
GET https://api.stateset.com/v1/return/:id/retrieve
This endpoint retrieves a return.
### Body
This is the id of the return.
### Response
This is the id of the return.
This is the date the return was created.
This is the amount of the return.
This is the action needed for the return.
This is the condition of the return.
This is the email of the customer.
This is the id of the customer.
This is the description of the return.
This is the id of the user who entered the return.
This is the flat rate shipping of the return.
This is the date of the order.
This is the id of the order.
This is the reason category of the return.
This is the reported condition of the return.
This is the requested date of the return.
This is the rma of the return.
This is the serial number of the return.
This is the shipped date of the return.
This is the status of the return.
This is the tax refunded of the return.
This is the total refunded of the return.
This is the tracking number of the return.
This is the line items of the return.
This is the id of the return line item.
This is the amount of the return line item.
This is the condition of the return line item.
This is the flat rate shipping of the return line item.
This is the name of the return line item.
This is the price of the return line item.
This is the id of the return associated with the line item.
This is the serial number of the return line item.
This is the sku of the return line item.
This is the tax refunded of the return line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/return/retrieve' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
returns(limit: $limit, offset: $offset, order_by: {created_date: $order_direction}) {
id
created_date
amount
action_needed
condition
customerEmail
customer_id
description
enteredBy
flat_rate_shipping
order_date
order_id
reason_category
reported_condition
requested_date
rma
serial_number
shipped_date
status
tax_refunded
total_refunded
tracking_number
return_line_items {
amount
condition
flat_rate_shipping
id
name
price
return_id
serial_number
sku
tax_refunded
}
}
}
```
```js Node.js theme={null}
const returns = await stateset.returns.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```py Python theme={null}
returns = stateset.returns.retrieve({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Golang theme={null}
returns, err := stateset.Returns.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
returns = Stateset::Returns.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
Returns returns = Stateset.Returns.retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
Returns returns = Stateset.Returns.Retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$returns = Stateset\Returns::retrieve(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```http HTTP theme={null}
GET /v1/return HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"returns": [
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"created_date": "2023-06-28T19:34:59.189838+00:00",
"amount": null,
"action_needed": null,
"condition": null,
"customerEmail": "customer@gmail.com",
"customer_id": null,
"description": null,
"enteredBy": null,
"flat_rate_shipping": null,
"order_date": null,
"order_id": "524213310335630636",
"reason_category": null,
"reported_condition": null,
"requested_date": null,
"rma": "#1014-R5",
"serial_number": null,
"shipped_date": null,
"status": "RCV",
"tax_refunded": null,
"total_refunded": null,
"tracking_number": null,
"return_line_items": []
},
]
}
```
```json Error Response (404 Not Found) theme={null}
{
"error": {
"code": "RESOURCE_NOT_FOUND",
"message": "Return not found",
"details": {
"resource": "return",
"id": "ret_abc123"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (401 Unauthorized) theme={null}
{
"error": {
"code": "INVALID_API_KEY",
"message": "The API key provided is invalid or has been revoked",
"request_id": "req_abc123def456"
}
}
```
# Inspect Return
Source: https://docs.stateset.com/api-reference/return/inspect
POST https://api.stateset.com/v1/returns/:id/inspect
This endpoint records inspection details for a returned item.
### Body
The ID provided in the data tab may be used to identify the return
The type of inspection performed (e.g., "physical", "functional", "cosmetic")
The assessed condition of the returned item (e.g., "like\_new", "good", "fair", "poor", "damaged")
Detailed notes from the inspection
List of defects or issues found during inspection
Whether the item can be resold
Recommended restocking fee based on condition
### Response
The ID provided in the data tab may be used to identify the return
The object type
The unique identifier for the inspection record
The date when the inspection was performed
The final condition assessment
Whether the item can be resold
The recommended action based on inspection (e.g., "restock", "liquidate", "dispose")
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/returns/:id/inspect' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"inspection_type": "physical",
"condition_assessment": "good",
"inspector_notes": "Minor wear on packaging, product unused",
"defects_found": ["packaging_damage"],
"resellable": true,
"restocking_fee": 15.00
}'
```
```graphQL GraphQL theme={null}
mutation returnInspectMutation {
returnInspect(
id: "${returnId}",
inspectionType: "${inspectionType}",
conditionAssessment: "${conditionAssessment}",
inspectorNotes: "${inspectorNotes}",
defectsFound: ${defectsFound},
resellable: ${resellable},
restockingFee: ${restockingFee}
) {
return {
id,
status,
inspection_id,
condition_assessment,
resellable,
recommended_action
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.inspect({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
inspection_type: 'physical',
condition_assessment: 'good',
inspector_notes: 'Minor wear on packaging, product unused',
defects_found: ['packaging_damage'],
resellable: true,
restocking_fee: 15.00
});
```
```python Python theme={null}
returns = stateset.returns.inspect({
'id': 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
'inspection_type': 'physical',
'condition_assessment': 'good',
'inspector_notes': 'Minor wear on packaging, product unused',
'defects_found': ['packaging_damage'],
'resellable': True,
'restocking_fee': 15.00
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.inspect({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
inspection_type: 'physical',
condition_assessment: 'good',
inspector_notes: 'Minor wear on packaging, product unused',
defects_found: ['packaging_damage'],
resellable: true,
restocking_fee: 15.00
})
```
```go Go theme={null}
returns, err := stateset.Returns.inspect({
ID: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
InspectionType: 'physical',
ConditionAssessment: 'good',
InspectorNotes: 'Minor wear on packaging, product unused',
DefectsFound: []string{'packaging_damage'},
Resellable: true,
RestockingFee: 15.00
})
```
```java Java theme={null}
Return returns = stateset.Returns.inspect({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
inspectionType: 'physical',
conditionAssessment: 'good',
inspectorNotes: 'Minor wear on packaging, product unused',
defectsFound: ['packaging_damage'],
resellable: true,
restockingFee: 15.00
});
```
```php PHP theme={null}
$returns = $stateset->returns->inspect([
'id' => 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
'inspection_type' => 'physical',
'condition_assessment' => 'good',
'inspector_notes' => 'Minor wear on packaging, product unused',
'defects_found' => ['packaging_damage'],
'resellable' => true,
'restocking_fee' => 15.00
]);
```
```csharp C# theme={null}
var returns = await stateset.Returns.Inspect(new {
Id = 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
InspectionType = 'physical',
ConditionAssessment = 'good',
InspectorNotes = 'Minor wear on packaging, product unused',
DefectsFound = new[] { 'packaging_damage' },
Resellable = true,
RestockingFee = 15.00
});
```
```json Response theme={null}
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"inspected": true,
"inspection_id": "insp_ret_123",
"inspection_date": "2024-01-15T10:45:00Z",
"condition_assessment": "good",
"resellable": true,
"restocking_fee": 15.00,
"defects_found": ["packaging_damage"],
"recommended_action": "restock"
}
```
# List Returns
Source: https://docs.stateset.com/api-reference/return/list
GET https://api.stateset.com/api/returns
This endpoint retrieves a paginated list of return requests based on specified filters and sorting options.
### Body
This is the limit of the returns.
This is the offset of the returns.
This is the order direction of the returns.
This is the status of the returns.
### Response
This is the id of the return.
This is the date the return was created.
This is the amount of the return.
This is the action needed for the return.
This is the condition of the return.
This is the email of the customer.
This is the id of the customer.
This is the description of the return.
This is the id of the user who entered the return.
This is the flat rate shipping of the return.
This is the date of the order.
This is the id of the order.
This is the reason category of the return.
This is the reported condition of the return.
This is the requested date of the return.
This is the rma of the return.
This is the serial number of the return.
This is the shipped date of the return.
This is the status of the return.
This is the tax refunded of the return.
This is the total refunded of the return.
This is the tracking number of the return.
This is the line items of the return.
This is the id of the return line item.
This is the amount of the return line item.
This is the condition of the return line item.
This is the flat rate shipping of the return line item.
This is the name of the return line item.
This is the price of the return line item.
This is the id of the return associated with the line item.
This is the serial number of the return line item.
This is the sku of the return line item.
This is the tax refunded of the return line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.app/api/returns' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "desc",
"status": "Requested"
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: OrderDirection!, $status: ReturnStatus!) {
returns(limit: $limit, offset: $offset, order_by: {created_date: $order_direction}, where: {status: {_eq: $status }}) {
id
created_date
amount
action_needed
condition
customerEmail
customer_id
description
enteredBy
flat_rate_shipping
order_date
order_id
reason_category
reported_condition
requested_date
rma
serial_number
shipped_date
status
tax_refunded
total_refunded
tracking_number
return_line_items {
id
amount
condition
flat_rate_shipping
name
price
return_id
serial_number
sku
tax_refunded
}
}
}
```
```js Node.js theme={null}
const returns = await stateset.returns.list({
limit: 10,
offset: 0,
order_direction: 'desc',
status: 'Requested'
});
```
```py Python theme={null}
returns = stateset.returns.list({
"limit": 10,
"offset": 0,
"order_direction": "desc",
"status": "Requested"
})
```
```go Golang theme={null}
returns, err := stateset.Returns.List(
10, // limit
0, // offset
"desc", // order_direction
"Requested", // status
)
if err != nil {
// Handle error
}
```
```ruby Ruby theme={null}
returns = Stateset::Returns.list(
limit: 10,
offset: 0,
order_direction: 'desc',
status: 'Requested'
)
```
```java Java theme={null}
Returns returns = Stateset.Returns.list(
10, // limit
0, // offset
"desc", // order_direction
"Requested" // status
);
```
```csharp C# theme={null}
Returns returns = Stateset.Returns.List(
limit: 10,
offset: 0,
order_direction: "desc",
status: "Requested"
);
```
```php PHP theme={null}
$returns = Stateset\Returns::list([
'limit' => 10,
'offset' => 0,
'order_direction' => 'desc',
'status' => 'Requested'
]);
```
```http HTTP theme={null}
GET /api/returns HTTP/1.1
Host: stateset-proxy-server.stateset.cloud.stateset.app
Content-Type: application/json
Authorization: Bearer
{
"limit": 10,
"offset": 0,
"order_direction": "desc",
"status": "Requested"
}
```
```json Response theme={null}
{
"returns": [
{
"id": "f47ac10b-58cc-4372-a567-0e02b2c3d479",
"created_date": "2023-06-28T19:34:59.189838+00:00",
"amount": "150.00",
"action_needed": "Inspection",
"condition": "Damaged",
"customerEmail": "customer@example.com",
"customer_id": "3fa85f64-5717-4562-b3fc-2c963f66afa6",
"description": "The product arrived damaged.",
"enteredBy": "1c0a3e4b-7e2d-4b1a-8d6c-3f2e4a5b6c7d",
"flat_rate_shipping": "10.00",
"order_date": "2023-06-20T15:30:00+00:00",
"order_id": "2b8e4f64-1234-5678-9abc-def012345678",
"reason_category": "Product Damage",
"reported_condition": "Damaged",
"requested_date": "2023-06-28T19:30:00+00:00",
"rma": "RMA123456",
"serial_number": "SN789456123",
"shipped_date": "2023-06-29T10:00:00+00:00",
"status": "Approved",
"tax_refunded": "5.00",
"total_refunded": "165.00",
"tracking_number": "TRK1234567890",
"return_line_items": [
{
"id": "a3f5c10b-58cc-4372-a567-0e02b2c3d480",
"amount": "75.00",
"condition": "Damaged",
"flat_rate_shipping": "5.00",
"name": "Widget Pro",
"price": "75.00",
"return_id": "f47ac10b-58cc-4372-a567-0e02b2c3d479",
"serial_number": "SN789456123",
"sku": "SKU12345",
"tax_refunded": "2.50"
}
]
}
]
}
```
# Refund Return
Source: https://docs.stateset.com/api-reference/return/refund
POST https://api.stateset.com/v1/return/:id/refund
This endpoint refunds an existing return.
### Body
The ID provided in the data tab may be used to identify the return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return/:id/refund' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation returnRefundMutation(
$returnLineItems: [ReturnRefundLineItemInput!]!,
$refundShipping: RefundShippingInput,
$orderTransactions: [ReturnRefundOrderTransactionInput!]
) {
returnRefund(
returnRefundInput: {
returnId: "${returnId}",
returnRefundLineItems: $returnLineItems,
refundShipping: $refundShipping,
orderTransactions: $orderTransactions
}
)
{
refund {
id
}
userErrors {
field
message
}
}
}
```
```js Node.js theme={null}
const returns = await stateset.returns.refund({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```python Python theme={null}
returns = stateset.returns.refund({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.refund({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
returns, err := stateset.Returns.Refund(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
Return returns = stateset.returns.refund(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```php PHP theme={null}
$returns = $stateset->returns->refund(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```csharp C# theme={null}
var returns = stateset.Returns.Refund(
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```vb Visual Basic .NET theme={null}
Dim returns = stateset.Returns.Refund(
"rt_1NXWPnCo6bFb1KQto6C8OWvE"
)
```
```json Response theme={null}
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"refunded": true
}
```
# Reject Return
Source: https://docs.stateset.com/api-reference/return/reject
POST https://api.stateset.com/v1/returns/:id/reject
This endpoint rejects a return.
### Body
The ID provided in the data tab may be used to identify the return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return/:id/reject' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation returnRejectMutation {
returnreject(id: "${returnId}") {
return {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
returns = stateset.returns.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
returns, err := stateset.Returns.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Return returns = stateset.Returns.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$returns = $stateset->returns->reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var returns = await stateset.Returns.reject({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "return",
"rejected": true
}
```
# ReOpen Return
Source: https://docs.stateset.com/api-reference/return/reopen
POST https://api.stateset.com/v1/return/:id/reopen
This endpoint updates an existing return.
### Body
The ID provided in the data tab may be used to identify the return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return/:id/reopen' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation returnReopenMutation {
returnReopen(id: "${returnId}") {
return {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.reopen({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```python Python theme={null}
returns = stateset.returns.reopen({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.reopen({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```go Go theme={null}
returns, err := stateset.Returns.Reopen({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
})
```
```java Java theme={null}
Return returns = stateset.Returns.reopen({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```php PHP theme={null}
$returns = $stateset->returns->reopen({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```csharp C# theme={null}
var returns = await stateset.Returns.Reopen({
'rt_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```json Response theme={null}
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"reopened": true
}
```
# Restock Return
Source: https://docs.stateset.com/api-reference/return/restock
POST https://api.stateset.com/v1/returns/:id/restock
This endpoint restocks a returned item back into inventory.
### Body
The ID provided in the data tab may be used to identify the return
The warehouse ID where the item will be restocked
The specific location within the warehouse
The condition code for inventory classification (e.g., "new", "refurbished", "open\_box")
The quantity to restock
Whether a restocking fee was applied to this return
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the item was successfully restocked
The ID of the inventory adjustment record
The new inventory level after restocking
The warehouse where the item was restocked
The timestamp when the item was restocked
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/returns/:id/restock' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"warehouse_id": "wh_east_01",
"location_id": "loc_a1_shelf_3",
"condition_code": "new",
"quantity": 1,
"restocking_fee_applied": true
}'
```
```graphQL GraphQL theme={null}
mutation returnRestockMutation {
returnRestock(
id: "${returnId}",
warehouseId: "${warehouseId}",
locationId: "${locationId}",
conditionCode: "${conditionCode}",
quantity: ${quantity},
restockingFeeApplied: ${restockingFeeApplied}
) {
return {
id,
status,
inventory_adjustment_id,
new_inventory_level,
restocked_at
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const returns = await stateset.returns.restock({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
warehouse_id: 'wh_east_01',
location_id: 'loc_a1_shelf_3',
condition_code: 'new',
quantity: 1,
restocking_fee_applied: true
});
```
```python Python theme={null}
returns = stateset.returns.restock({
'id': 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
'warehouse_id': 'wh_east_01',
'location_id': 'loc_a1_shelf_3',
'condition_code': 'new',
'quantity': 1,
'restocking_fee_applied': True
})
```
```ruby Ruby theme={null}
returns = Stateset::Return.restock({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
warehouse_id: 'wh_east_01',
location_id: 'loc_a1_shelf_3',
condition_code: 'new',
quantity: 1,
restocking_fee_applied: true
})
```
```go Go theme={null}
returns, err := stateset.Returns.restock({
ID: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
WarehouseID: 'wh_east_01',
LocationID: 'loc_a1_shelf_3',
ConditionCode: 'new',
Quantity: 1,
RestockingFeeApplied: true
})
```
```java Java theme={null}
Return returns = stateset.Returns.restock({
id: 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
warehouseId: 'wh_east_01',
locationId: 'loc_a1_shelf_3',
conditionCode: 'new',
quantity: 1,
restockingFeeApplied: true
});
```
```php PHP theme={null}
$returns = $stateset->returns->restock([
'id' => 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
'warehouse_id' => 'wh_east_01',
'location_id' => 'loc_a1_shelf_3',
'condition_code' => 'new',
'quantity' => 1,
'restocking_fee_applied' => true
]);
```
```csharp C# theme={null}
var returns = await stateset.Returns.Restock(new {
Id = 'rt_1NXWPnCo6bFb1KQto6C8OWvE',
WarehouseId = 'wh_east_01',
LocationId = 'loc_a1_shelf_3',
ConditionCode = 'new',
Quantity = 1,
RestockingFeeApplied = true
});
```
```json Response theme={null}
{
"id": "rt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return",
"restocked": true,
"inventory_adjustment_id": "inv_adj_456",
"new_inventory_level": 150,
"warehouse_id": "wh_east_01",
"location_id": "loc_a1_shelf_3",
"condition_code": "new",
"restocked_at": "2024-01-15T11:00:00Z"
}
```
# Update Return
Source: https://docs.stateset.com/api-reference/return/update
PUT https://api.stateset.com/v1/returns/
This endpoint updates an existing return.
### Body
The ID provided in the data tab may be used to identify the return
The return object
### Response
The ID of the return
The ID of the order
The description of the return
The issue of the return
The status of the return
The tracking number of the return
The action needed of the return
The customer email of the return
The RMA of the return
The serial number of the return
The scanned serial number of the return
The zendesk number of the return
The entered by of the return
The order date of the return
The shipped date of the return
The requested date of the return
The condition of the return
The reported condition of the return
The created date of the return
The amount of the return
The flat rate shipping of the return
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'status': 'RCV'
'condition': 'B'
}'
```
```graphQL GraphQL theme={null}
mutation (
$return_id: String
$return_x: returns_set_input!
) {
update_returns (
where: { id : { _eq: $return_id }}
_set: $return_x
) {
returning {
id
order_id
description
issue
status
tracking_number
action_needed
customerEmail
rma
serial_number
scanned_serial_number
zendesk_number
enteredBy
order_date
shipped_date
requested_date
condition
reported_condition
created_date
amount
flat_rate_shipping
}
}
}`;
```
```js Node.js theme={null}
const returns = await stateset.returns.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
returns = stateset.Return.modify(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```ruby Ruby theme={null}
returns = Stateset::Return.update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```go Go theme={null}
returns, err := stateset.Returns.Update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```java Java theme={null}
Return[] returns = stateset.returns.update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```php PHP theme={null}
$returns = $stateset->returns->update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```json Response theme={null}
{
"returns": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"created_date": "2023-06-28T19:34:59.189838+00:00",
"amount": null,
"action_needed": null,
"condition": null,
"customerEmail": "customer@gmail.com",
"customer_id": null,
"description": null,
"enteredBy": null,
"flat_rate_shipping": null,
"order_date": null,
"order_id": "524213310335630636",
"reason_category": null,
"reported_condition": null,
"requested_date": null,
"rma": "#1014-R5",
"serial_number": null,
"shipped_date": null,
"status": "RCV",
"tax_refunded": null,
"total_refunded": null,
"tracking_number": null,
},
]
}
```
# Create Return Line Item
Source: https://docs.stateset.com/api-reference/returnlineitem/create
POST https://api.stateset.com/v1/return_line_items/create
This endpoint creates a new return line item.
### Body
This is the id of the return line item.
This is the amount of the return line item.
This is the condition of the return line item.
This is the flat rate shipping of the return line item.
This is the name of the return line item.
This is the price of the return line item.
This is the id of the return associated with the line item.
This is the serial number of the return line item.
This is the sku of the return line item.
This is the tax refunded of the return line item.
### Response
This is the id of the return line item.
This is the amount of the return line item.
This is the condition of the return line item.
This is the flat rate shipping of the return line item.
This is the name of the return line item.
This is the price of the return line item.
This is the id of the return associated with the line item.
This is the serial number of the return line item.
This is the sku of the return line item.
This is the tax refunded of the return line item.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/return_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```graphQL GraphQL theme={null}
mutation addReturnLineItem($return_line_item: return_line_items_insert_input!) {
insert_return_line_items(objects: [$return_line_item]) {
returning {
id
sku
name
price
condition
serial_number
amount
return_id
}
}
}
```
```js Node.js theme={null}
const returnLineItem = await stateset.returnItem.create({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
return_line_item = stateset.return_line_item.create(
{
"return_line_item": {
"sku": "123456789",
"name": "Example Item",
"price": 100,
"condition": "New",
"serial_number": "123456789",
"amount": 1,
"return_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}
}
)
```
```ruby Ruby theme={null}
return_line_item = Stateset::ReturnItem.create(
{
"return_line_item": {
"sku": "123456789",
"name": "Example Item",
"price": 100,
"condition": "New",
"serial_number": "123456789",
"amount": 1,
"return_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}
}
)
```
```php PHP theme={null}
$return_line_item = $stateset->return_line_item->create(
[
"return_line_item" => [
"sku" => "123456789",
"name" => "Example Item",
"price" => 100,
"condition" => "New",
"serial_number" => "123456789",
"amount" => 1,
"return_id" => "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
]
]
);
```
```go Golang theme={null}
ReturnLineItem , err := stateset.ReturnLineItem.Create(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"123456789",
"Example Item",
100,
"New",
"123456789",
1,
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
)
```
```java Java theme={null}
ReturnLineItem returnLineItem = stateset.returnLineItem.create(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"123456789",
"Example Item",
100,
"New",
"123456789",
1,
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
);
```
```csharp C# theme={null}
var returnLineItem = stateset.ReturnLineItem.Create(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"123456789",
"Example Item",
100,
"New",
"123456789",
1,
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
);
```
```json Response theme={null}
{
"data": {
"insert_return_line_items": {
"returning": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "123456789",
"name": "Example Item",
"price": 100,
"condition": "New",
"serial_number": "123456789",
"amount": 1,
"return_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}
]
}
}
}
```
# Delete Return Line Item
Source: https://docs.stateset.com/api-reference/returnlineitem/delete
DELETE https://api.return.com/v1/return_line_items/:id
This endpoint deletes an existing return line item.
### Body
The ID of the return line item you want to delete
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.return.com/v1/return_line_items/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1"
"current_token": "abcdef"
}'
```
```js Node.js theme={null}
const returnLineItem = await stateset.returnItem.del({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```graphQL GraphQL theme={null}
mutation deleteReturnLineItem ($return_line_item_id: uuid!) {
delete_return_line_items(where: {id: {_eq: $return_line_item_id}}) {
affected_rows
}
}
```
```python Python theme={null}
return_line_item = stateset.return_line_item.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```ruby Ruby theme={null}
return_line_item = Stateset::ReturnLineItem.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```php PHP theme={null}
$return_line_item = Stateset\ReturnItem::del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```go Golang theme={null}
returnLineItem, err := stateset.ReturnLineItem.Delete(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```java Java theme={null}
ReturnLineItem returnLineItem = stateset.returnLineItem.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```csharp C# theme={null}
var returnLineItem = await Stateset.ReturnLineItem.Delete(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```json Response theme={null}
{
"id": "rli_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return_line_item",
"deleted": true
}
```
# Get Return Line Item
Source: https://docs.stateset.com/api-reference/returnlineitem/get
GET https://api.stateset.com/v1/return_line_item
This endpoint gets or creates a new return line item.
### Body
This is the id of the return line item.
### Response
This is the id of the return line item.
This is the amount of the return line item.
This is the condition of the return line item.
This is the flat rate shipping of the return line item.
This is the name of the return line item.
This is the price of the return line item.
This is the id of the return associated with the line item.
This is the serial number of the return line item.
This is the sku of the return line item.
This is the tax refunded of the return line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/return_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}'
```
```javascript Node.js theme={null}
var returnLineItem = await stateset.returnItem.retreive({
id: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
});
```
```python Python theme={null}
return_line_item = stateset.return_line_item.retrieve(
id="0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
)
```
```ruby Ruby theme={null}
return_line_item = Stateset::ReturnLineItem.retrieve(
id: "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
)
```
```php PHP theme={null}
$return_line_item = Stateset\ReturnLineItem::retrieve(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
);
```
```go Go theme={null}
returnLineItem, err := stateset.ReturnLineItem.Retrieve(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
)
```
```java Java theme={null}
ReturnLineItem returnLineItem = stateset.returnLineItem.retrieve(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
);
```
```json Response theme={null}
{
"data": {
"insert_return_line_items": {
"returning": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "123456789",
"name": "Example Item",
"price": 100,
"condition": "New",
"serial_number": "123456789",
"amount": 1,
"return_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}
]
}
}
}
```
# Update Return Line Item
Source: https://docs.stateset.com/api-reference/returnlineitem/update
PUT https://api.stateset.com/v1/return_line_items/:id
This endpoint updates an existing return line item.
### Body
This is the id of the return line item.
This is the amount of the return line item.
This is the condition of the return line item.
This is the flat rate shipping of the return line item.
This is the name of the return line item.
This is the price of the return line item.
This is the id of the return associated with the line item.
This is the serial number of the return line item.
This is the sku of the return line item.
This is the tax refunded of the return line item.
### Response
This is the id of the return line item.
This is the amount of the return line item.
This is the condition of the return line item.
This is the flat rate shipping of the return line item.
This is the name of the return line item.
This is the price of the return line item.
This is the id of the return associated with the line item.
This is the serial number of the return line item.
This is the sku of the return line item.
This is the tax refunded of the return line item.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/return_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```js Node.js theme={null}
const returnLineItem = await stateset.returnItem.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```graphQL GraphQL theme={null}
mutation (
$id: uuid
$return_line_item: return_line_items_set_input!
) {
update_return_line_items (
where: { id : { _eq: $id }}
_set: $return_line_item
) {
returning {
id
sku
name
price
tax_refunded
condition
amount
flat_rate_shipping
}
}
}
```
```python Python theme={null}
return_line_item = stateset.ReturnItem.modify(
id='0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
return_line_item={
'sku': 'example_1',
'name': 'Example 1',
'price': 100,
'tax_refunded': 0,
'condition': 'new',
'amount': 1,
'flat_rate_shipping': 0
}
)
```
```ruby Ruby theme={null}
return_line_item = Stateset::ReturnItem.update(
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
return_line_item: {
sku: 'example_1',
name: 'Example 1',
price: 100,
tax_refunded: 0,
condition: 'new',
amount: 1,
flat_rate_shipping: 0
}
)
```
```php PHP theme={null}
$return_line_item = $stateset->return_line_item->update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
[
'sku' => 'example_1',
'name' => 'Example 1',
'price' => 100,
'tax_refunded' => 0,
'condition' => 'new',
'amount' => 1,
'flat_rate_shipping' => 0
]
);
```
```go Golang theme={null}
returnLineItem, err := stateset.ReturnLineItem.Update(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
stateset.ReturnLineItem{
Sku: "example_1",
Name: "Example 1",
Price: 100,
TaxRefunded: 0,
Condition: "new",
Amount: 1,
FlatRateShipping: 0
}
)
```
```java Java theme={null}
ReturnLineItem returnLineItem = stateset.returnLineItem.update(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
new ReturnLineItem(
"example_1",
"Example 1",
100,
0,
"new",
1,
0
)
);
```
```csharp CSharp theme={null}
var returnLineItem = await stateset.ReturnLineItem.Update(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
new ReturnLineItem()
{
Sku = "example_1",
Name = "Example 1",
Price = 100,
TaxRefunded = 0,
Condition = "new",
Amount = 1,
FlatRateShipping = 0
}
);
```
```json Response theme={null}
{
"data": {
"insert_return_line_items": {
"returning": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "123456789",
"name": "Example Item",
"price": 100,
"condition": "New",
"serial_number": "123456789",
"amount": 1,
"return_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}
]
}
}
}
```
# SDKs & Libraries
Source: https://docs.stateset.com/api-reference/sdks
Official and community SDKs for integrating with StateSet
StateSet provides official SDKs for popular languages to accelerate your integration development.
## Official SDKs
Full-featured SDK with TypeScript support
Pythonic interface with async support
High-performance SDK for Go applications
Idiomatic Ruby SDK with Rails integration
Modern PHP SDK with PSR compliance
.NET SDK with async/await support
Enterprise-ready Java SDK
Native iOS/macOS SDK
## Node.js / TypeScript
### Installation
```bash npm theme={null}
npm install @stateset/stateset-node
```
```bash yarn theme={null}
yarn add @stateset/stateset-node
```
```bash pnpm theme={null}
pnpm add @stateset/stateset-node
```
### Quick Start
```typescript theme={null}
import { StateSet } from '@stateset/stateset-node';
// Initialize client
const stateset = new StateSet({
apiKey: process.env.STATESET_API_KEY,
// Optional configuration
environment: 'production', // or 'sandbox'
timeout: 30000, // 30 seconds
maxRetries: 3,
apiVersion: '2024-01-01'
});
// TypeScript types are included
const order: StateSet.Order = await stateset.orders.create({
customer: {
email: 'customer@example.com',
first_name: 'John',
last_name: 'Doe'
},
items: [{
sku: 'WIDGET-001',
quantity: 2,
price: 2999
}],
shipping_address: {
line1: '123 Main St',
city: 'San Francisco',
state: 'CA',
postal_code: '94105',
country: 'US'
}
});
```
### Advanced Features
#### Async Iteration
```typescript theme={null}
// Iterate through all orders
for await (const order of stateset.orders.list()) {
console.log(order.id);
}
// With filters
for await (const order of stateset.orders.list({
status: 'pending'
})) {
await processOrder(order);
}
```
#### Request Interceptors
```typescript theme={null}
// Add request interceptor
stateset.interceptors.request.use((config) => {
config.headers['X-Custom-Header'] = 'value';
console.log(`Making request to ${config.url}`);
return config;
});
// Add response interceptor
stateset.interceptors.response.use(
(response) => {
console.log(`Request completed in ${response.duration}ms`);
return response;
},
(error) => {
console.error('Request failed:', error);
throw error;
}
);
```
#### Event Emitters
```typescript theme={null}
// Listen for events
stateset.on('request', (event) => {
console.log('Request:', event);
});
stateset.on('response', (event) => {
console.log('Response:', event);
});
stateset.on('error', (error) => {
console.error('Error:', error);
});
stateset.on('rateLimit', (info) => {
console.warn('Rate limited:', info);
});
```
#### Custom HTTP Client
```typescript theme={null}
import axios from 'axios';
const stateset = new StateSet({
apiKey: process.env.STATESET_API_KEY,
httpClient: axios.create({
timeout: 60000,
proxy: {
host: 'proxy.example.com',
port: 8080
}
})
});
```
### TypeScript Support
```typescript theme={null}
import { StateSet } from '@stateset/stateset-node';
import type {
Order,
Customer,
Return,
OrderCreateParams,
PaginatedResponse
} from '@stateset/stateset-node';
// Full type safety
async function createOrder(
params: OrderCreateParams
): Promise {
return await stateset.orders.create(params);
}
// Generic pagination
async function getAllOrders(): Promise {
const response: PaginatedResponse =
await stateset.orders.list();
return response.data;
}
// Type guards
function isOrder(obj: any): obj is Order {
return obj && obj.object === 'order';
}
```
## Python
### Installation
```bash theme={null}
pip install stateset-python
```
### Quick Start
```python theme={null}
from stateset import StateSet
import os
# Initialize client
stateset = StateSet(
api_key=os.getenv('STATESET_API_KEY'),
# Optional configuration
environment='production', # or 'sandbox'
timeout=30, # seconds
max_retries=3,
api_version='2024-01-01'
)
# Create an order
order = stateset.orders.create(
customer={
'email': 'customer@example.com',
'first_name': 'John',
'last_name': 'Doe'
},
items=[{
'sku': 'WIDGET-001',
'quantity': 2,
'price': 2999
}],
shipping_address={
'line1': '123 Main St',
'city': 'San Francisco',
'state': 'CA',
'postal_code': '94105',
'country': 'US'
}
)
```
### Async Support
```python theme={null}
import asyncio
from stateset import AsyncStateSet
async def main():
# Async client
async with AsyncStateSet(api_key=api_key) as stateset:
# Concurrent requests
orders = await asyncio.gather(
stateset.orders.get('ord_123'),
stateset.orders.get('ord_456'),
stateset.orders.get('ord_789')
)
# Async iteration
async for order in stateset.orders.list_async():
print(order.id)
asyncio.run(main())
```
### Context Managers
```python theme={null}
from stateset import StateSet
# Automatic resource cleanup
with StateSet(api_key=api_key) as stateset:
orders = stateset.orders.list()
for order in orders:
print(order.id)
```
### Type Hints
```python theme={null}
from typing import List, Optional
from stateset import StateSet
from stateset.types import Order, Customer, OrderCreateParams
def create_order(
stateset: StateSet,
params: OrderCreateParams
) -> Order:
"""Create a new order with type safety."""
return stateset.orders.create(**params)
def get_customer_orders(
stateset: StateSet,
customer_id: str,
status: Optional[str] = None
) -> List[Order]:
"""Get all orders for a customer."""
filters = {'customer_id': customer_id}
if status:
filters['status'] = status
return list(stateset.orders.list(**filters))
```
## Go
### Installation
```bash theme={null}
go get github.com/stateset/stateset-go
```
### Quick Start
```go theme={null}
package main
import (
"context"
"fmt"
"os"
"github.com/stateset/stateset-go"
"github.com/stateset/stateset-go/order"
)
func main() {
// Initialize client
client := stateset.NewClient(
os.Getenv("STATESET_API_KEY"),
&stateset.Config{
Environment: stateset.Production,
Timeout: 30 * time.Second,
MaxRetries: 3,
},
)
// Create an order
params := &order.CreateParams{
Customer: &order.CustomerParams{
Email: stateset.String("customer@example.com"),
FirstName: stateset.String("John"),
LastName: stateset.String("Doe"),
},
Items: []*order.ItemParams{{
SKU: stateset.String("WIDGET-001"),
Quantity: stateset.Int64(2),
Price: stateset.Int64(2999),
}},
ShippingAddress: &order.AddressParams{
Line1: stateset.String("123 Main St"),
City: stateset.String("San Francisco"),
State: stateset.String("CA"),
PostalCode: stateset.String("94105"),
Country: stateset.String("US"),
},
}
order, err := client.Orders.Create(context.Background(), params)
if err != nil {
panic(err)
}
fmt.Printf("Order created: %s\n", order.ID)
}
```
### Error Handling
```go theme={null}
import (
"errors"
"github.com/stateset/stateset-go"
)
func handleOrder(client *stateset.Client, orderID string) error {
order, err := client.Orders.Get(context.Background(), orderID)
if err != nil {
var statesetErr *stateset.Error
if errors.As(err, &statesetErr) {
switch statesetErr.Code {
case stateset.ErrorCodeRateLimit:
// Handle rate limiting
time.Sleep(time.Duration(statesetErr.RetryAfter) * time.Second)
return handleOrder(client, orderID) // Retry
case stateset.ErrorCodeNotFound:
// Handle not found
return fmt.Errorf("order %s not found", orderID)
default:
return fmt.Errorf("API error: %v", statesetErr)
}
}
return err
}
// Process order
return nil
}
```
### Concurrent Operations
```go theme={null}
func fetchOrdersConcurrently(client *stateset.Client, orderIDs []string) ([]*order.Order, error) {
var wg sync.WaitGroup
orders := make([]*order.Order, len(orderIDs))
errors := make([]error, len(orderIDs))
for i, id := range orderIDs {
wg.Add(1)
go func(index int, orderID string) {
defer wg.Done()
ord, err := client.Orders.Get(context.Background(), orderID)
orders[index] = ord
errors[index] = err
}(i, id)
}
wg.Wait()
// Check for errors
for _, err := range errors {
if err != nil {
return nil, err
}
}
return orders, nil
}
```
## Ruby
### Installation
```ruby theme={null}
# Gemfile
gem 'stateset-ruby'
```
```bash theme={null}
bundle install
# or
gem install stateset-ruby
```
### Quick Start
```ruby theme={null}
require 'stateset'
# Initialize client
Stateset.api_key = ENV['STATESET_API_KEY']
# Or configure globally
Stateset.configure do |config|
config.api_key = ENV['STATESET_API_KEY']
config.environment = :production # or :sandbox
config.timeout = 30
config.max_retries = 3
end
# Create an order
order = Stateset::Order.create(
customer: {
email: 'customer@example.com',
first_name: 'John',
last_name: 'Doe'
},
items: [{
sku: 'WIDGET-001',
quantity: 2,
price: 2999
}],
shipping_address: {
line1: '123 Main St',
city: 'San Francisco',
state: 'CA',
postal_code: '94105',
country: 'US'
}
)
puts "Order created: #{order.id}"
```
### Rails Integration
```ruby theme={null}
# config/initializers/stateset.rb
Stateset.configure do |config|
config.api_key = Rails.application.credentials.stateset[:api_key]
config.environment = Rails.env.production? ? :production : :sandbox
config.logger = Rails.logger
end
# app/models/concerns/stateset_syncable.rb
module StatesetSyncable
extend ActiveSupport::Concern
included do
after_create :sync_to_stateset
after_update :update_in_stateset
end
def sync_to_stateset
StatesetSyncJob.perform_later(self)
end
def update_in_stateset
StatesetUpdateJob.perform_later(self)
end
end
# app/models/order.rb
class Order < ApplicationRecord
include StatesetSyncable
def to_stateset_params
{
external_id: id,
customer: {
email: customer.email,
first_name: customer.first_name,
last_name: customer.last_name
},
items: items.map(&:to_stateset_params)
}
end
end
```
### Error Handling
```ruby theme={null}
begin
order = Stateset::Order.create(params)
rescue Stateset::RateLimitError => e
# Handle rate limiting
sleep(e.retry_after)
retry
rescue Stateset::ValidationError => e
# Handle validation errors
e.errors.each do |error|
puts "#{error.field}: #{error.message}"
end
rescue Stateset::APIError => e
# Handle other API errors
puts "API Error: #{e.message}"
end
```
## PHP
### Installation
```bash theme={null}
composer require stateset/stateset-php
```
### Quick Start
```php theme={null}
$_ENV['STATESET_API_KEY'],
'environment' => 'production', // or 'sandbox'
'timeout' => 30,
'maxRetries' => 3
]);
// Create an order
try {
$order = $stateset->orders->create([
'customer' => [
'email' => 'customer@example.com',
'first_name' => 'John',
'last_name' => 'Doe'
],
'items' => [[
'sku' => 'WIDGET-001',
'quantity' => 2,
'price' => 2999
]],
'shipping_address' => [
'line1' => '123 Main St',
'city' => 'San Francisco',
'state' => 'CA',
'postal_code' => '94105',
'country' => 'US'
]
]);
echo "Order created: {$order->id}\n";
} catch (ApiException $e) {
echo "Error: {$e->getMessage()}\n";
}
```
### Laravel Integration
```php theme={null}
// config/stateset.php
return [
'api_key' => env('STATESET_API_KEY'),
'environment' => env('STATESET_ENVIRONMENT', 'production'),
'timeout' => 30,
'max_retries' => 3,
];
// app/Providers/StatesetServiceProvider.php
namespace App\Providers;
use Illuminate\Support\ServiceProvider;
use Stateset\StatesetClient;
class StatesetServiceProvider extends ServiceProvider
{
public function register()
{
$this->app->singleton(StatesetClient::class, function ($app) {
return new StatesetClient(config('stateset'));
});
}
}
// app/Services/OrderService.php
namespace App\Services;
use Stateset\StatesetClient;
class OrderService
{
protected $stateset;
public function __construct(StatesetClient $stateset)
{
$this->stateset = $stateset;
}
public function createOrder(array $data)
{
return $this->stateset->orders->create($data);
}
}
```
## .NET / C\#
### Installation
```bash theme={null}
dotnet add package StateSet.Net
```
### Quick Start
```csharp theme={null}
using StateSet;
using StateSet.Models;
using System;
using System.Threading.Tasks;
class Program
{
static async Task Main(string[] args)
{
// Initialize client
var client = new StateSetClient(
Environment.GetEnvironmentVariable("STATESET_API_KEY"),
new StateSetOptions
{
Environment = StateSetEnvironment.Production,
Timeout = TimeSpan.FromSeconds(30),
MaxRetries = 3
}
);
// Create an order
var order = await client.Orders.CreateAsync(new OrderCreateParams
{
Customer = new CustomerParams
{
Email = "customer@example.com",
FirstName = "John",
LastName = "Doe"
},
Items = new List
{
new OrderItemParams
{
Sku = "WIDGET-001",
Quantity = 2,
Price = 2999
}
},
ShippingAddress = new AddressParams
{
Line1 = "123 Main St",
City = "San Francisco",
State = "CA",
PostalCode = "94105",
Country = "US"
}
});
Console.WriteLine($"Order created: {order.Id}");
}
}
```
### Dependency Injection (ASP.NET Core)
```csharp theme={null}
// Startup.cs or Program.cs
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddStateSet(options =>
{
options.ApiKey = Configuration["StateSet:ApiKey"];
options.Environment = StateSetEnvironment.Production;
});
services.AddScoped();
}
}
// Services/OrderService.cs
public interface IOrderService
{
Task CreateOrderAsync(OrderDto orderDto);
}
public class OrderService : IOrderService
{
private readonly IStateSetClient _stateset;
public OrderService(IStateSetClient stateset)
{
_stateset = stateset;
}
public async Task CreateOrderAsync(OrderDto orderDto)
{
return await _stateset.Orders.CreateAsync(orderDto.ToStateSetParams());
}
}
```
## Java
### Installation
#### Maven
```xml theme={null}
com.statesetstateset-java3.0.0
```
#### Gradle
```gradle theme={null}
implementation 'com.stateset:stateset-java:3.0.0'
```
### Quick Start
```java theme={null}
import com.stateset.StateSet;
import com.stateset.model.Order;
import com.stateset.param.OrderCreateParams;
import com.stateset.exception.StateSetException;
public class Main {
public static void main(String[] args) {
// Initialize client
StateSet.apiKey = System.getenv("STATESET_API_KEY");
// Or use builder
StateSet stateset = StateSet.builder()
.setApiKey(System.getenv("STATESET_API_KEY"))
.setEnvironment(StateSet.Environment.PRODUCTION)
.setTimeout(30000)
.setMaxRetries(3)
.build();
try {
// Create an order
OrderCreateParams params = OrderCreateParams.builder()
.setCustomer(
OrderCreateParams.Customer.builder()
.setEmail("customer@example.com")
.setFirstName("John")
.setLastName("Doe")
.build()
)
.addItem(
OrderCreateParams.Item.builder()
.setSku("WIDGET-001")
.setQuantity(2)
.setPrice(2999L)
.build()
)
.setShippingAddress(
OrderCreateParams.Address.builder()
.setLine1("123 Main St")
.setCity("San Francisco")
.setState("CA")
.setPostalCode("94105")
.setCountry("US")
.build()
)
.build();
Order order = Order.create(params);
System.out.println("Order created: " + order.getId());
} catch (StateSetException e) {
System.err.println("Error: " + e.getMessage());
}
}
}
```
### Spring Boot Integration
```java theme={null}
// Configuration
@Configuration
public class StateSetConfig {
@Value("${stateset.api-key}")
private String apiKey;
@Bean
public StateSet statesetClient() {
return StateSet.builder()
.setApiKey(apiKey)
.setEnvironment(StateSet.Environment.PRODUCTION)
.build();
}
}
// Service
@Service
public class OrderService {
private final StateSet stateset;
@Autowired
public OrderService(StateSet stateset) {
this.stateset = stateset;
}
public Order createOrder(OrderRequest request) throws StateSetException {
OrderCreateParams params = convertToParams(request);
return Order.create(params);
}
}
```
## Swift
### Installation
#### Swift Package Manager
```swift theme={null}
dependencies: [
.package(url: "https://github.com/stateset/stateset-swift.git", from: "2.0.0")
]
```
#### CocoaPods
```ruby theme={null}
pod 'StateSet', '~> 2.0'
```
### Quick Start
```swift theme={null}
import StateSet
// Initialize client
let client = StateSetClient(
apiKey: ProcessInfo.processInfo.environment["STATESET_API_KEY"]!,
environment: .production,
timeout: 30,
maxRetries: 3
)
// Create an order
let customer = CustomerParams(
email: "customer@example.com",
firstName: "John",
lastName: "Doe"
)
let item = OrderItemParams(
sku: "WIDGET-001",
quantity: 2,
price: 2999
)
let address = AddressParams(
line1: "123 Main St",
city: "San Francisco",
state: "CA",
postalCode: "94105",
country: "US"
)
let params = OrderCreateParams(
customer: customer,
items: [item],
shippingAddress: address
)
client.orders.create(params) { result in
switch result {
case .success(let order):
print("Order created: \(order.id)")
case .failure(let error):
print("Error: \(error.localizedDescription)")
}
}
```
### Async/Await Support
```swift theme={null}
// iOS 13+, macOS 10.15+
@available(iOS 13.0, *)
func createOrder() async throws {
let order = try await client.orders.create(params)
print("Order created: \(order.id)")
}
// SwiftUI Integration
struct OrderView: View {
@StateObject private var viewModel = OrderViewModel()
var body: some View {
Button("Create Order") {
Task {
await viewModel.createOrder()
}
}
}
}
@MainActor
class OrderViewModel: ObservableObject {
@Published var order: Order?
@Published var isLoading = false
@Published var error: Error?
private let client = StateSetClient()
func createOrder() async {
isLoading = true
do {
order = try await client.orders.create(params)
} catch {
self.error = error
}
isLoading = false
}
}
```
## SDK Features Comparison
| Feature | Node.js | Python | Go | Ruby | PHP | .NET | Java | Swift |
| ---------------- | ------------ | ------------ | -------- | ------ | -------- | ------ | ------------------- | ------ |
| **Type Safety** | ✅ TypeScript | ✅ Type Hints | ✅ | ❌ | ❌ | ✅ | ✅ | ✅ |
| **Async/Await** | ✅ | ✅ | ✅ | ✅ | ❌ | ✅ | ✅ CompletableFuture | ✅ |
| **Auto-Retry** | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
| **Webhooks** | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
| **Pagination** | ✅ Auto | ✅ Auto | ✅ Manual | ✅ Auto | ✅ Manual | ✅ Auto | ✅ Manual | ✅ Auto |
| **Streaming** | ✅ | ✅ | ✅ | ✅ | ❌ | ✅ | ✅ | ✅ |
| **Interceptors** | ✅ | ✅ | ✅ | ✅ | ❌ | ✅ | ✅ | ✅ |
| **File Upload** | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
| **GraphQL** | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ |
## Common Patterns
### Error Handling Across SDKs
All SDKs follow similar error handling patterns:
```javascript theme={null}
// JavaScript/TypeScript
try {
const order = await stateset.orders.create(params);
} catch (error) {
if (error.code === 'rate_limited') {
// Handle rate limiting
} else if (error.code === 'validation_error') {
// Handle validation errors
} else {
// Handle other errors
}
}
```
```python theme={null}
# Python
try:
order = stateset.orders.create(**params)
except RateLimitError as e:
# Handle rate limiting
pass
except ValidationError as e:
# Handle validation errors
pass
except StateSetError as e:
# Handle other errors
pass
```
### Idempotency Across SDKs
All SDKs support idempotency keys:
```javascript theme={null}
// JavaScript
const order = await stateset.orders.create(params, {
idempotencyKey: 'unique-key-123'
});
```
```python theme={null}
# Python
order = stateset.orders.create(
**params,
idempotency_key='unique-key-123'
)
```
```go theme={null}
// Go
params.IdempotencyKey = stateset.String("unique-key-123")
order, err := client.Orders.Create(ctx, params)
```
## Community SDKs
Community SDKs are not officially maintained by StateSet. Use at your own discretion.
* **Rust**: [stateset-rust](https://github.com/community/stateset-rust)
* **Kotlin**: [stateset-kotlin](https://github.com/community/stateset-kotlin)
* **Dart/Flutter**: [stateset-dart](https://github.com/community/stateset-dart)
* **Elixir**: [stateset-elixir](https://github.com/community/stateset-elixir)
* **Clojure**: [stateset-clj](https://github.com/community/stateset-clj)
## SDK Development
### Contributing
We welcome contributions to our SDKs! See our [SDK Development Guide](https://github.com/stateset/sdk-development) for:
* Code style guidelines
* Testing requirements
* Release process
* API coverage requirements
### Reporting Issues
* **Bug Reports**: [GitHub Issues](https://github.com/stateset/stateset-\{language}/issues)
* **Feature Requests**: [Discord Community](https://discord.gg/VfcaqgZywq)
* **Security Issues**: [security@stateset.com](mailto:security@stateset.com)
## Related Resources
* [API Reference](/api-reference/introduction) - Complete API documentation
* [Quickstart Guide](/api-reference/quickstart) - Get started quickly
* [Authentication](/api-reference/authentication) - Auth methods
* [Error Handling](/api-reference/errors) - Error codes and handling
* [Code Examples](https://github.com/stateset/examples) - Sample implementations
***
**Need SDK support?** Contact [sdk-support@stateset.com](mailto:sdk-support@stateset.com) or visit our [Discord community](https://discord.gg/VfcaqgZywq).
# Search API
Source: https://docs.stateset.com/api-reference/search
POST https://api.stateset.com/v1/search
Powerful search endpoint for finding records across multiple resources with advanced filtering and faceting.
### Body
The search query string. Supports fuzzy matching and operators
Array of resource types to search. If empty, searches all resources.
Options: \["orders", "customers", "products", "inventory", "returns", "warranties", "tickets"]
Advanced filters to narrow search results
Filter by date range
Date field to filter on (e.g., "created\_at", "updated\_at")
Start date (ISO 8601)
End date (ISO 8601)
Filter by status values
Filter by tags
Filter by custom field values
Fields to generate facet counts for
Sort configuration
Field to sort by
Sort order: "asc" or "desc"
Pagination configuration
Page number (1-based)
Results per page (max 100)
Whether to include highlighted snippets in results
Whether to include search suggestions for typos
### Response
Array of search results
Unique identifier of the result
Type of resource (e.g., "order", "customer")
Relevance score
The actual resource data
Highlighted text snippets (if enabled)
Facet counts for requested fields
Search suggestions for possible typos
Total number of results found
Current page number
Results per page
Time taken to execute the query in milliseconds
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/search' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"query": "john doe refund",
"resources": ["orders", "customers", "returns"],
"filters": {
"date_range": {
"field": "created_at",
"from": "2024-01-01",
"to": "2024-12-31"
},
"status": ["active", "pending"]
},
"facets": ["resource_type", "status", "tags"],
"sort": {
"field": "created_at",
"order": "desc"
},
"pagination": {
"page": 1,
"per_page": 20
},
"highlight": true,
"suggest": true
}'
```
```graphQL GraphQL theme={null}
query searchQuery {
search(
query: "${query}",
resources: ${resources},
filters: ${filters},
facets: ${facets},
sort: ${sort},
pagination: ${pagination},
highlight: ${highlight},
suggest: ${suggest}
) {
results {
id
resource_type
score
data
highlights
}
facets
suggestions
total_results
query_time_ms
}
}
```
```js Node.js theme={null}
const searchResults = await stateset.search({
query: 'john doe refund',
resources: ['orders', 'customers', 'returns'],
filters: {
date_range: {
field: 'created_at',
from: '2024-01-01',
to: '2024-12-31'
},
status: ['active', 'pending']
},
facets: ['resource_type', 'status', 'tags'],
sort: {
field: 'created_at',
order: 'desc'
},
pagination: {
page: 1,
per_page: 20
},
highlight: true,
suggest: true
});
```
```python Python theme={null}
search_results = stateset.search({
'query': 'john doe refund',
'resources': ['orders', 'customers', 'returns'],
'filters': {
'date_range': {
'field': 'created_at',
'from': '2024-01-01',
'to': '2024-12-31'
},
'status': ['active', 'pending']
},
'facets': ['resource_type', 'status', 'tags'],
'sort': {
'field': 'created_at',
'order': 'desc'
},
'pagination': {
'page': 1,
'per_page': 20
},
'highlight': True,
'suggest': True
})
```
```ruby Ruby theme={null}
search_results = Stateset.search({
query: 'john doe refund',
resources: ['orders', 'customers', 'returns'],
filters: {
date_range: {
field: 'created_at',
from: '2024-01-01',
to: '2024-12-31'
},
status: ['active', 'pending']
},
facets: ['resource_type', 'status', 'tags'],
sort: {
field: 'created_at',
order: 'desc'
},
pagination: {
page: 1,
per_page: 20
},
highlight: true,
suggest: true
})
```
```go Go theme={null}
searchResults, err := stateset.Search(SearchParams{
Query: "john doe refund",
Resources: []string{"orders", "customers", "returns"},
Filters: Filters{
DateRange: DateRange{
Field: "created_at",
From: "2024-01-01",
To: "2024-12-31"
},
Status: []string{"active", "pending"}
},
Facets: []string{"resource_type", "status", "tags"},
Sort: Sort{
Field: "created_at",
Order: "desc"
},
Pagination: Pagination{
Page: 1,
PerPage: 20
},
Highlight: true,
Suggest: true
})
```
```java Java theme={null}
SearchResults searchResults = stateset.search(new SearchParams()
.setQuery("john doe refund")
.setResources(Arrays.asList("orders", "customers", "returns"))
.setFilters(new Filters()
.setDateRange(new DateRange()
.setField("created_at")
.setFrom("2024-01-01")
.setTo("2024-12-31"))
.setStatus(Arrays.asList("active", "pending")))
.setFacets(Arrays.asList("resource_type", "status", "tags"))
.setSort(new Sort()
.setField("created_at")
.setOrder("desc"))
.setPagination(new Pagination()
.setPage(1)
.setPerPage(20))
.setHighlight(true)
.setSuggest(true));
```
```php PHP theme={null}
$search_results = $stateset->search([
'query' => 'john doe refund',
'resources' => ['orders', 'customers', 'returns'],
'filters' => [
'date_range' => [
'field' => 'created_at',
'from' => '2024-01-01',
'to' => '2024-12-31'
],
'status' => ['active', 'pending']
],
'facets' => ['resource_type', 'status', 'tags'],
'sort' => [
'field' => 'created_at',
'order' => 'desc'
],
'pagination' => [
'page' => 1,
'per_page' => 20
],
'highlight' => true,
'suggest' => true
]);
```
```csharp C# theme={null}
var searchResults = await stateset.Search(new SearchParams {
Query = "john doe refund",
Resources = new[] { "orders", "customers", "returns" },
Filters = new Filters {
DateRange = new DateRange {
Field = "created_at",
From = "2024-01-01",
To = "2024-12-31"
},
Status = new[] { "active", "pending" }
},
Facets = new[] { "resource_type", "status", "tags" },
Sort = new Sort {
Field = "created_at",
Order = "desc"
},
Pagination = new Pagination {
Page = 1,
PerPage = 20
},
Highlight = true,
Suggest = true
});
```
```json Response theme={null}
{
"results": [
{
"id": "ord_123abc",
"resource_type": "order",
"score": 0.95,
"data": {
"id": "ord_123abc",
"customer_name": "John Doe",
"total": 299.99,
"status": "pending",
"created_at": "2024-03-15T10:30:00Z"
},
"highlights": {
"customer_name": "John Doe",
"notes": "Customer requested refund for damaged item"
}
},
{
"id": "cust_456def",
"resource_type": "customer",
"score": 0.88,
"data": {
"id": "cust_456def",
"name": "John Doe",
"email": "john.doe@example.com",
"status": "active"
},
"highlights": {
"name": "John Doe"
}
}
],
"facets": {
"resource_type": {
"order": 5,
"customer": 3,
"return": 2
},
"status": {
"active": 6,
"pending": 4
},
"tags": {
"vip": 2,
"priority": 3
}
},
"suggestions": [
{
"text": "john doe refunded",
"score": 0.92
}
],
"total_results": 10,
"page": 1,
"per_page": 20,
"query_time_ms": 23
}
```
```json Error Response theme={null}
{
"error": {
"code": "invalid_query",
"message": "Search query cannot be empty",
"details": {
"min_query_length": 1,
"max_query_length": 1000
}
}
}
```
# Cancel Shipment
Source: https://docs.stateset.com/api-reference/shipments/cancel
POST https://api.stateset.com/v1/shipments/:id/cancel
Cancel a shipment and void the shipping label
This endpoint cancels a shipment and voids the shipping label. Refunds are processed automatically based on carrier policies.
## Authentication
This endpoint requires a valid API key with `shipments:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the shipment to cancel
## Request Body
Cancellation reason: "order\_cancelled", "incorrect\_address", "changed\_shipping\_method", "duplicate", "other"
Additional notes about the cancellation
### Response
Returns the cancelled shipment with refund information.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/shipments/ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"reason": "order_cancelled",
"notes": "Customer requested cancellation before shipment"
}'
```
```javascript Node.js theme={null}
const shipment = await stateset.shipments.cancel(
'ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
reason: "order_cancelled",
notes: "Customer requested cancellation before shipment"
}
);
```
```python Python theme={null}
shipment = stateset.shipments.cancel(
'ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
reason="order_cancelled",
notes="Customer requested cancellation before shipment"
)
```
```json Response theme={null}
{
"id": "ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "shipment",
"status": "cancelled",
"cancelled_at": "2024-01-19T17:00:00Z",
"cancellation": {
"reason": "order_cancelled",
"notes": "Customer requested cancellation before shipment",
"cancelled_by": "user_123"
},
"refund": {
"status": "processed",
"amount": 1250,
"currency": "USD",
"processed_at": "2024-01-19T17:00:15Z",
"reference": "REF-SHIP-001"
},
"tracking_number": "1Z999AA10123456784",
"carrier": "ups",
"metadata": {
"cancellation_reference": "CANCEL-2024-001"
}
}
```
# Create Shipment
Source: https://docs.stateset.com/api-reference/shipments/create
POST https://api.stateset.com/v1/shipments
Create a shipment for outbound orders
This endpoint creates a new shipment for one or more orders. It handles carrier integration, label generation, and tracking initialization.
## Authentication
This endpoint requires a valid API key with `shipments:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Array of order IDs to include in this shipment
Origin warehouse ID
Carrier for shipment (e.g., "ups", "fedex", "usps", "dhl")
Service level (e.g., "ground", "express", "overnight", "2day")
Scheduled ship date (ISO 8601)
Destination address
Recipient name
Company name
Street address line 1
Street address line 2
City
State/Province code
Postal/ZIP code
ISO 3166-1 alpha-2 country code
Contact phone number
Contact email for delivery notifications
Array of packages in the shipment
Package weight
Weight value
Weight unit ("lb" or "kg")
Package dimensions
Length
Width
Height
Dimension unit ("in" or "cm")
Items in this package
Package type (e.g., "box", "envelope", "tube")
Insurance options
Whether to insure the shipment
Insurance value in cents
ISO 4217 currency code
Whether signature is required on delivery
Whether to enable Saturday delivery
Customs information for international shipments
Type of contents (e.g., "merchandise", "gift", "sample")
Array of customs line items
Electronic Export Information or Proof of Filing Citation
Reference numbers for tracking
Purchase order number
Invoice number
Custom reference 1
Custom reference 2
Label format preference ("pdf", "zpl", "png")
Additional custom fields
### Response
Returns the created shipment with tracking information and label URLs.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/shipments' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"order_ids": ["order_123456", "order_123457"],
"warehouse_id": "wh_001",
"carrier": "ups",
"service_type": "ground",
"ship_date": "2024-01-20T08:00:00Z",
"shipping_address": {
"name": "John Doe",
"company": "Acme Corp",
"line1": "123 Main St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US",
"phone": "+1-555-123-4567",
"email": "john.doe@example.com"
},
"packages": [
{
"weight": {
"value": 5.5,
"unit": "lb"
},
"dimensions": {
"length": 12,
"width": 10,
"height": 8,
"unit": "in"
},
"package_type": "box"
}
],
"insurance": {
"enabled": true,
"amount": 15000,
"currency": "USD"
},
"signature_required": true
}'
```
```javascript Node.js theme={null}
const shipment = await stateset.shipments.create({
order_ids: ["order_123456", "order_123457"],
warehouse_id: "wh_001",
carrier: "ups",
service_type: "ground",
ship_date: "2024-01-20T08:00:00Z",
shipping_address: {
name: "John Doe",
company: "Acme Corp",
line1: "123 Main St",
city: "Los Angeles",
state: "CA",
postal_code: "90001",
country: "US",
phone: "+1-555-123-4567",
email: "john.doe@example.com"
},
packages: [
{
weight: { value: 5.5, unit: "lb" },
dimensions: { length: 12, width: 10, height: 8, unit: "in" },
package_type: "box"
}
],
signature_required: true
});
```
```json Response theme={null}
{
"id": "ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "shipment",
"status": "label_created",
"created_at": "2024-01-19T14:30:00Z",
"ship_date": "2024-01-20T08:00:00Z",
"carrier": "ups",
"service_type": "ground",
"tracking_number": "1Z999AA10123456784",
"tracking_url": "https://www.ups.com/track?tracknum=1Z999AA10123456784",
"label_url": "https://labels.stateset.com/ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30.pdf",
"rate": {
"amount": 1250,
"currency": "USD",
"estimated_delivery_date": "2024-01-23T18:00:00Z"
},
"packages": [
{
"tracking_number": "1Z999AA10123456784",
"label_url": "https://labels.stateset.com/ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30.pdf",
"weight": {
"value": 5.5,
"unit": "lb"
},
"dimensions": {
"length": 12,
"width": 10,
"height": 8,
"unit": "in"
}
}
],
"from_address": {
"name": "Main Distribution Center",
"line1": "456 Warehouse Blvd",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
},
"to_address": {
"name": "John Doe",
"company": "Acme Corp",
"line1": "123 Main St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
},
"order_ids": ["order_123456", "order_123457"],
"insurance": {
"enabled": true,
"amount": 15000,
"currency": "USD",
"provider": "ups"
}
}
```
# Get Shipment
Source: https://docs.stateset.com/api-reference/shipments/get
GET https://api.stateset.com/v1/shipments/:id
Retrieve a specific shipment by ID
This endpoint retrieves detailed information about a specific shipment including tracking, packages, and delivery status.
## Authentication
This endpoint requires a valid API key with `shipments:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the shipment
## Query Parameters
Expand related objects. Options: "orders", "packages.items", "events", "documents"
### Response
Unique shipment identifier
Object type, always "shipment"
Current shipment status
Master tracking number
Tracking URL for customer
Shipping carrier
Service level
Actual or scheduled ship date
Actual or estimated delivery date
Array of packages in shipment
Tracking events (when expanded)
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/shipments/ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30?expand=events' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const shipment = await stateset.shipments.retrieve(
'ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{ expand: ['events'] }
);
```
```python Python theme={null}
shipment = stateset.shipments.retrieve(
'ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
expand=['events']
)
```
```json Response theme={null}
{
"id": "ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "shipment",
"status": "in_transit",
"created_at": "2024-01-19T14:30:00Z",
"updated_at": "2024-01-20T10:15:00Z",
"ship_date": "2024-01-20T08:00:00Z",
"delivery_date": "2024-01-23T18:00:00Z",
"carrier": "ups",
"service_type": "ground",
"tracking_number": "1Z999AA10123456784",
"tracking_url": "https://www.ups.com/track?tracknum=1Z999AA10123456784",
"label_url": "https://labels.stateset.com/ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30.pdf",
"rate": {
"amount": 1250,
"currency": "USD",
"carrier_account": "ups_12345"
},
"packages": [
{
"id": "pkg_abc123",
"tracking_number": "1Z999AA10123456784",
"label_url": "https://labels.stateset.com/ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30.pdf",
"weight": {
"value": 5.5,
"unit": "lb"
},
"dimensions": {
"length": 12,
"width": 10,
"height": 8,
"unit": "in"
},
"value": 15000,
"reference_number": "PKG-2024-001"
}
],
"from_address": {
"name": "Main Distribution Center",
"company": "Stateset",
"line1": "456 Warehouse Blvd",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US",
"phone": "+1-555-987-6543"
},
"to_address": {
"name": "John Doe",
"company": "Acme Corp",
"line1": "123 Main St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US",
"phone": "+1-555-123-4567",
"email": "john.doe@example.com"
},
"order_ids": ["order_123456", "order_123457"],
"warehouse_id": "wh_001",
"insurance": {
"enabled": true,
"amount": 15000,
"currency": "USD",
"provider": "ups",
"confirmation_number": "INS123456"
},
"signature_required": true,
"saturday_delivery": false,
"events": [
{
"id": "evt_123",
"created_at": "2024-01-20T08:05:00Z",
"status": "label_created",
"description": "Shipping label created",
"location": {
"city": "Los Angeles",
"state": "CA",
"country": "US"
}
},
{
"id": "evt_124",
"created_at": "2024-01-20T09:30:00Z",
"status": "picked_up",
"description": "Package picked up by carrier",
"location": {
"city": "Los Angeles",
"state": "CA",
"country": "US"
}
},
{
"id": "evt_125",
"created_at": "2024-01-20T10:15:00Z",
"status": "in_transit",
"description": "Package in transit",
"location": {
"city": "Los Angeles",
"state": "CA",
"country": "US",
"facility": "Los Angeles Distribution Center"
}
}
],
"metadata": {
"internal_reference": "SHIP-2024-001",
"priority": "standard"
}
}
```
```json Error Response (404 Not Found) theme={null}
{
"error": {
"code": "RESOURCE_NOT_FOUND",
"message": "Shipment not found",
"details": {
"resource": "shipment",
"id": "shp_abc123"
},
"request_id": "req_abc123def456"
}
}
```
```json Error Response (401 Unauthorized) theme={null}
{
"error": {
"code": "INVALID_API_KEY",
"message": "The API key provided is invalid or has been revoked",
"request_id": "req_abc123def456"
}
}
```
# List Shipments
Source: https://docs.stateset.com/api-reference/shipments/list
GET https://api.stateset.com/v1/shipments
List all shipments with filtering and pagination
This endpoint retrieves a paginated list of shipments. Use filters to narrow results by status, date range, carrier, and more.
## Authentication
This endpoint requires a valid API key with `shipments:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of items to return (default: 20, max: 100)
Number of items to skip
Filter by status: "label\_created", "picked\_up", "in\_transit", "out\_for\_delivery", "delivered", "returned", "failed"
Filter by carrier: "ups", "fedex", "usps", "dhl"
Filter by origin warehouse
Filter by associated order
Filter by tracking number
Filter by ship date start (ISO 8601)
Filter by ship date end (ISO 8601)
Filter by delivery date start (ISO 8601)
Filter by delivery date end (ISO 8601)
Filter by destination country code
Filter by destination state/province
Sort field: "created\_at", "ship\_date", "delivery\_date", "status"
Sort order: "asc" or "desc" (default: "desc")
### Response
Object type, always "list"
Array of shipment objects
Whether more items exist
Total number of matching shipments
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/shipments?status=in_transit&limit=10' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const shipments = await stateset.shipments.list({
status: 'in_transit',
limit: 10,
sort_by: 'ship_date',
sort_order: 'desc'
});
```
```python Python theme={null}
shipments = stateset.shipments.list(
status='in_transit',
limit=10,
sort_by='ship_date',
sort_order='desc'
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "shipment",
"status": "in_transit",
"created_at": "2024-01-19T14:30:00Z",
"ship_date": "2024-01-20T08:00:00Z",
"delivery_date": "2024-01-23T18:00:00Z",
"carrier": "ups",
"service_type": "ground",
"tracking_number": "1Z999AA10123456784",
"tracking_url": "https://www.ups.com/track?tracknum=1Z999AA10123456784",
"packages_count": 1,
"total_weight": {
"value": 5.5,
"unit": "lb"
},
"from_address": {
"city": "Los Angeles",
"state": "CA",
"country": "US"
},
"to_address": {
"name": "John Doe",
"city": "Los Angeles",
"state": "CA",
"country": "US"
},
"order_ids": ["order_123456", "order_123457"],
"rate": {
"amount": 1250,
"currency": "USD"
}
},
{
"id": "ship_7823f083-bb2c-54d6-bf6d-1b8e3fc75f41",
"object": "shipment",
"status": "in_transit",
"created_at": "2024-01-19T10:15:00Z",
"ship_date": "2024-01-19T14:00:00Z",
"delivery_date": "2024-01-22T18:00:00Z",
"carrier": "fedex",
"service_type": "express",
"tracking_number": "772123456789",
"tracking_url": "https://www.fedex.com/apps/fedextrack/?tracknumbers=772123456789",
"packages_count": 2,
"total_weight": {
"value": 12.3,
"unit": "lb"
},
"from_address": {
"city": "New York",
"state": "NY",
"country": "US"
},
"to_address": {
"name": "Jane Smith",
"city": "Chicago",
"state": "IL",
"country": "US"
},
"order_ids": ["order_789012"],
"rate": {
"amount": 2850,
"currency": "USD"
}
}
],
"has_more": true,
"total_count": 156,
"page_info": {
"limit": 10,
"offset": 0
}
}
```
# Update Shipment
Source: https://docs.stateset.com/api-reference/shipments/update
PUT https://api.stateset.com/v1/shipments/:id
Update shipment details before shipping
This endpoint updates shipment details. Only shipments with status "label\_created" can be modified. Once picked up, use the cancel endpoint to void.
## Authentication
This endpoint requires a valid API key with `shipments:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the shipment
## Request Body
New scheduled ship date (ISO 8601)
Updated service level
Update signature requirement
Update Saturday delivery option
Update insurance options
Enable/disable insurance
Insurance value in cents
Update reference numbers
Update custom fields
### Response
Returns the updated shipment object.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/shipments/ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"ship_date": "2024-01-21T08:00:00Z",
"service_type": "express",
"insurance": {
"enabled": true,
"amount": 20000
}
}'
```
```javascript Node.js theme={null}
const shipment = await stateset.shipments.update(
'ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
ship_date: "2024-01-21T08:00:00Z",
service_type: "express",
insurance: {
enabled: true,
amount: 20000
}
}
);
```
```json Response theme={null}
{
"id": "ship_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "shipment",
"status": "label_created",
"updated_at": "2024-01-19T16:00:00Z",
"ship_date": "2024-01-21T08:00:00Z",
"carrier": "ups",
"service_type": "express",
"rate": {
"amount": 2850,
"currency": "USD",
"estimated_delivery_date": "2024-01-22T18:00:00Z"
},
"insurance": {
"enabled": true,
"amount": 20000,
"currency": "USD"
}
}
```
# Cancel Subscription
Source: https://docs.stateset.com/api-reference/subscriptions/cancel
POST https://api.stateset.com/v1/subscriptions/:id/cancel
Cancel an active subscription
This endpoint cancels a subscription. You can choose to cancel immediately or at the end of the current billing period.
## Authentication
This endpoint requires a valid API key with `subscriptions:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the subscription to cancel
## Request Body
If true, cancel at end of current period. If false, cancel immediately (default: true)
Cancellation reason: "too\_expensive", "missing\_features", "not\_using", "switching\_provider", "other"
Additional feedback about cancellation
Override to cancel immediately regardless of period
### Response
Returns the cancelled subscription object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/subscriptions/sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"cancel_at_period_end": true,
"reason": "too_expensive",
"feedback": "The pricing increased beyond our budget"
}'
```
```javascript Node.js theme={null}
const subscription = await stateset.subscriptions.cancel(
'sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
cancel_at_period_end: true,
reason: "too_expensive",
feedback: "The pricing increased beyond our budget"
}
);
```
```python Python theme={null}
subscription = stateset.subscriptions.cancel(
'sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
cancel_at_period_end=True,
reason="too_expensive",
feedback="The pricing increased beyond our budget"
)
```
```json Response theme={null}
{
"id": "sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "subscription",
"status": "active",
"cancel_at_period_end": true,
"cancel_at": "2024-03-01T00:00:00Z",
"cancelled_at": "2024-01-20T15:00:00Z",
"cancellation_details": {
"reason": "too_expensive",
"feedback": "The pricing increased beyond our budget",
"cancelled_by": "user_123"
},
"current_period_end": "2024-03-01",
"ended_at": null,
"customer_id": "cust_abc123",
"plan": {
"id": "plan_monthly_pro",
"name": "Professional Monthly"
},
"metadata": {
"cancellation_flow": "customer_portal",
"retention_offered": true,
"retention_accepted": false
}
}
```
# Create Subscription
Source: https://docs.stateset.com/api-reference/subscriptions/create
POST https://api.stateset.com/v1/subscriptions
Create a recurring subscription for a customer
This endpoint creates a new subscription for recurring billing. Subscriptions automatically generate invoices and process payments based on the billing cycle.
## Authentication
This endpoint requires a valid API key with `subscriptions:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Customer ID for the subscription
Subscription plan ID
Subscription start date (ISO 8601)
Default payment method for automatic billing
Number of subscriptions (default: 1)
Trial period end date (ISO 8601)
Date to anchor billing cycles (ISO 8601)
Additional subscription items
Product ID
Quantity
Override price in cents
Coupon to apply to subscription
Shipping address for physical subscriptions
Street address
Apartment/Suite
City
State/Province
Postal code
Country code
Additional custom fields
### Response
Returns the created subscription.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/subscriptions' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"customer_id": "cust_abc123",
"plan_id": "plan_monthly_pro",
"start_date": "2024-02-01",
"payment_method_id": "pm_card_visa",
"trial_end": "2024-02-14",
"items": [
{
"product_id": "prod_addon_storage",
"quantity": 2
}
],
"shipping_address": {
"line1": "123 Main St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
}
}'
```
```javascript Node.js theme={null}
const subscription = await stateset.subscriptions.create({
customer_id: "cust_abc123",
plan_id: "plan_monthly_pro",
start_date: "2024-02-01",
payment_method_id: "pm_card_visa",
trial_end: "2024-02-14",
items: [
{
product_id: "prod_addon_storage",
quantity: 2
}
],
shipping_address: {
line1: "123 Main St",
city: "Los Angeles",
state: "CA",
postal_code: "90001",
country: "US"
}
});
```
```json Response theme={null}
{
"id": "sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "subscription",
"customer_id": "cust_abc123",
"status": "trialing",
"created_at": "2024-01-19T17:00:00Z",
"start_date": "2024-02-01",
"current_period_start": "2024-02-01",
"current_period_end": "2024-03-01",
"trial_start": "2024-02-01",
"trial_end": "2024-02-14",
"plan": {
"id": "plan_monthly_pro",
"name": "Professional Monthly",
"amount": 9900,
"currency": "USD",
"interval": "month",
"interval_count": 1
},
"items": [
{
"id": "si_123456",
"product_id": "prod_addon_storage",
"product_name": "Additional Storage (10GB)",
"quantity": 2,
"unit_price": 500,
"amount": 1000
}
],
"quantity": 1,
"subtotal": 10900,
"tax_amount": 872,
"total_amount": 11772,
"payment_method_id": "pm_card_visa",
"default_payment_method": {
"id": "pm_card_visa",
"type": "card",
"card": {
"brand": "visa",
"last4": "4242",
"exp_month": 12,
"exp_year": 2025
}
},
"shipping_address": {
"line1": "123 Main St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
},
"next_invoice_date": "2024-03-01",
"cancel_at_period_end": false
}
```
# Get Subscription
Source: https://docs.stateset.com/api-reference/subscriptions/get
GET https://api.stateset.com/v1/subscriptions/:id
Retrieve a specific subscription by ID
This endpoint retrieves detailed information about a specific subscription including plan details, billing history, and upcoming invoices.
## Authentication
This endpoint requires a valid API key with `subscriptions:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the subscription
## Query Parameters
Expand related objects. Options: "customer", "payment\_method", "invoices", "upcoming\_invoice"
### Response
Unique subscription identifier
Object type, always "subscription"
Subscription status: "trialing", "active", "past\_due", "cancelled", "unpaid"
Start of current billing period
End of current billing period
Subscription plan details
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/subscriptions/sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30?expand=upcoming_invoice' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const subscription = await stateset.subscriptions.retrieve(
'sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{ expand: ['upcoming_invoice'] }
);
```
```python Python theme={null}
subscription = stateset.subscriptions.retrieve(
'sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
expand=['upcoming_invoice']
)
```
```json Response theme={null}
{
"id": "sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "subscription",
"customer_id": "cust_abc123",
"status": "active",
"created_at": "2024-01-19T17:00:00Z",
"start_date": "2024-02-01",
"current_period_start": "2024-02-01",
"current_period_end": "2024-03-01",
"trial_start": "2024-02-01",
"trial_end": "2024-02-14",
"plan": {
"id": "plan_monthly_pro",
"name": "Professional Monthly",
"amount": 9900,
"currency": "USD",
"interval": "month",
"interval_count": 1,
"features": [
"Unlimited orders",
"Advanced analytics",
"Priority support",
"API access"
]
},
"items": [
{
"id": "si_123456",
"product_id": "prod_addon_storage",
"product_name": "Additional Storage (10GB)",
"quantity": 2,
"unit_price": 500,
"amount": 1000
}
],
"quantity": 1,
"subtotal": 10900,
"tax_amount": 872,
"total_amount": 11772,
"payment_method_id": "pm_card_visa",
"default_payment_method": {
"id": "pm_card_visa",
"type": "card",
"card": {
"brand": "visa",
"last4": "4242",
"exp_month": 12,
"exp_year": 2025
}
},
"shipping_address": {
"line1": "123 Main St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
},
"next_invoice_date": "2024-03-01",
"cancel_at_period_end": false,
"upcoming_invoice": {
"amount_due": 11772,
"currency": "USD",
"period_start": "2024-03-01",
"period_end": "2024-04-01",
"lines": [
{
"description": "Professional Monthly",
"amount": 9900
},
{
"description": "Additional Storage (10GB) × 2",
"amount": 1000
}
]
},
"metadata": {
"sales_rep": "john_smith",
"campaign": "Q1_2024"
}
}
```
# List Subscriptions
Source: https://docs.stateset.com/api-reference/subscriptions/list
GET https://api.stateset.com/v1/subscriptions
List all subscriptions with filtering and pagination
This endpoint retrieves a paginated list of subscriptions. Use filters to narrow results by status, customer, plan, and more.
## Authentication
This endpoint requires a valid API key with `subscriptions:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of items to return (default: 20, max: 100)
Cursor for pagination (subscription ID)
Filter by status: "trialing", "active", "past\_due", "cancelled", "unpaid"
Filter by customer ID
Filter by plan ID
Filter by creation date start (ISO 8601)
Filter by creation date end (ISO 8601)
Show subscriptions ending before date
Sort field: "created\_at", "start\_date", "total\_amount"
Sort order: "asc" or "desc"
### Response
Object type, always "list"
Array of subscription objects
Whether more items exist
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/subscriptions?status=active&limit=10' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const subscriptions = await stateset.subscriptions.list({
status: 'active',
limit: 10,
sort_by: 'created_at'
});
```
```python Python theme={null}
subscriptions = stateset.subscriptions.list(
status='active',
limit=10,
sort_by='created_at'
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "subscription",
"customer_id": "cust_abc123",
"customer_name": "Acme Corporation",
"status": "active",
"plan": {
"id": "plan_monthly_pro",
"name": "Professional Monthly",
"amount": 9900
},
"total_amount": 11772,
"current_period_end": "2024-03-01",
"next_invoice_date": "2024-03-01"
},
{
"id": "sub_7823f083-bb2c-54d6-bf6d-1b8e3fc75f41",
"object": "subscription",
"customer_id": "cust_def456",
"customer_name": "TechCorp Inc",
"status": "active",
"plan": {
"id": "plan_annual_enterprise",
"name": "Enterprise Annual",
"amount": 99900
},
"total_amount": 99900,
"current_period_end": "2025-01-15",
"next_invoice_date": "2025-01-15"
}
],
"has_more": true,
"url": "/v1/subscriptions"
}
```
# Update Subscription
Source: https://docs.stateset.com/api-reference/subscriptions/update
PUT https://api.stateset.com/v1/subscriptions/:id
Update an existing subscription
This endpoint updates subscription details including items, quantities, and payment methods. Plan changes take effect at the next billing cycle.
## Authentication
This endpoint requires a valid API key with `subscriptions:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the subscription
## Request Body
Change to a different plan (takes effect next billing cycle)
Update subscription quantity
Update subscription items
Item ID to update (omit for new items)
Product ID
Item quantity
Set to true to remove item
Update default payment method
Apply a coupon
Extend or end trial period
Update custom fields
### Response
Returns the updated subscription object.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/subscriptions/sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"items": [
{
"id": "si_123456",
"quantity": 3
},
{
"product_id": "prod_premium_support",
"quantity": 1
}
],
"coupon_id": "SAVE20"
}'
```
```javascript Node.js theme={null}
const subscription = await stateset.subscriptions.update(
'sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
{
items: [
{
id: "si_123456",
quantity: 3
},
{
product_id: "prod_premium_support",
quantity: 1
}
],
coupon_id: "SAVE20"
}
);
```
```python Python theme={null}
subscription = stateset.subscriptions.update(
'sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
items=[
{
"id": "si_123456",
"quantity": 3
},
{
"product_id": "prod_premium_support",
"quantity": 1
}
],
coupon_id="SAVE20"
)
```
```json Response theme={null}
{
"id": "sub_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "subscription",
"updated_at": "2024-01-20T14:00:00Z",
"status": "active",
"items": [
{
"id": "si_123456",
"product_id": "prod_addon_storage",
"product_name": "Additional Storage (10GB)",
"quantity": 3,
"unit_price": 500,
"amount": 1500
},
{
"id": "si_789012",
"product_id": "prod_premium_support",
"product_name": "Premium Support",
"quantity": 1,
"unit_price": 2900,
"amount": 2900
}
],
"discount": {
"coupon": {
"id": "SAVE20",
"percent_off": 20,
"duration": "repeating",
"duration_in_months": 3
}
},
"subtotal": 14300,
"discount_amount": 2860,
"tax_amount": 915,
"total_amount": 12355
}
```
# Create Supplier
Source: https://docs.stateset.com/api-reference/suppliers/create
POST https://api.stateset.com/v1/suppliers
This endpoint creates a new supplier
### Body
This is the current user group token you have for the user group that you want
to rotate.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
The contents of the user group
This is the internal ID for this user group. You don't need to record this
information, since you will not need to use it.
This is the user group token (userGroupToken or USER\_GROUP\_TOKEN) that will be
used to identify which user group is viewing the dashboard. You should save
this on your end to use when rendering an embedded dashboard.
This is the name of the user group provided in the request body.
This is the user\_group\_id provided in the request body.
This is the environment tag of the user group. Possible values are 'Customer'
and 'Testing'. User group id's must be unique to each environment, so you can
not create multiple user groups with with same id. If you have a production
customer and a test user group with the same id, you will be required to label
one as 'Customer' and another as 'Testing'
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/supplier' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Delete Supplier
Source: https://docs.stateset.com/api-reference/suppliers/delete
DELETE https://api.return.com/v1/suppliers/:id
This endpoint deletes an existing supplier.
### Body
The data source ID provided in the data tab may be used to identify the data
source for the user group
This is the current user group token you have for the user group you want to
delete
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/suppliers/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1"
"current_token": "abcdef"
}'
```
```json Response theme={null}
{
"success": 1
}
```
# Get Supplier
Source: https://docs.stateset.com/api-reference/suppliers/get
GET https://api.stateset.com/v1/suppliers/:id
This endpoint gets or creates a new supplier.
### Body
This is the name of the user group.
This is the ID you use to identify this user group in your database.
This is a JSON mapping of schema id to either the data source that this user group should be
associated with or id of the datasource you provided when creating it.
This is a JSON object for properties assigned to this user group. These will be accessible through
variables in the dashboards and SQL editor
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
Indicates whether a new user group was created.
The contents of the user group
This is the internal ID for this user group. You don't need to record this information, since
you will not need to use it.
This is the user group token (userGroupToken or USER\_GROUP\_TOKEN) that will be used to identify
which user group is viewing the dashboard. You should save this on your end to use when rendering
an embedded dashboard.
This is the name of the user group provided in the request body.
This is the user\_group\_id provided in the request body.
This is the properties object if it was provided in the request body
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/supplier' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"new_user_group": true,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# List Suppliers
Source: https://docs.stateset.com/api-reference/suppliers/list
List suppliers.
# List Suppliers
Use this endpoint to list suppliers.
# Update Supplier
Source: https://docs.stateset.com/api-reference/suppliers/update
PUT https://api.stateset.com/v1/suppliers/:id
This endpoint updates an existing supplier.
### Body
This is the name of the user group.
This is the ID you use to identify this user group in your database.
This is a JSON mapping of schema id to either the data source that this user
group should be associated with or id of the datasource you provided when
creating it.
This is a JSON object for properties assigned to this user group. These will
be accessible through variables in the dashboards and SQL editor
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
The contents of the user group
Indicates whether a new user group was created.
This is the user group token (userGroupToken or USER\_GROUP\_TOKEN) that will be
used to identify which user group is viewing the dashboard. You should save
this on your end to use when rendering an embedded dashboard.
This is the name of the user group provided in the request body.
This is the user\_group\_id provided in the request body.
This is the properties object if it was provided in the request body
This is the environment tag of the user group. Possible values are 'Customer'
and 'Testing'
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/suppliers/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 113,
"token": "",
"name": "ok",
"provided_id": "6"
}
}
```
# Calculate Tax
Source: https://docs.stateset.com/api-reference/tax/calculate
POST https://api.stateset.com/v1/tax/calculate
Calculate taxes for an order based on location and items
This endpoint calculates applicable taxes for a given order, considering all active tax rates, exemptions, and nexus rules. It returns a detailed breakdown of all taxes to be collected.
## Authentication
This endpoint requires a valid API key with `tax:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Origin address (seller location)
Street address
City
State/Province code
Postal/ZIP code
ISO 3166-1 alpha-2 country code
Destination address (buyer location)
Street address
City
State/Province code
Postal/ZIP code
ISO 3166-1 alpha-2 country code
Items to calculate tax for
Line item identifier
Quantity
Unit price in cents
Product category for tax rules
Specific tax code override
Discount amount in cents
Shipping details
Shipping cost in cents
Override shipping taxability
Customer details for exemptions
Customer ID
Customer type for exemptions
Whether customer is tax exempt
Tax exemption certificate numbers
Transaction date for rate determination (ISO 8601)
ISO 4217 currency code (default: USD)
### Response
Returns detailed tax calculation breakdown.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/tax/calculate' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"from_address": {
"line1": "100 Commerce Way",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
},
"to_address": {
"line1": "123 Main St",
"city": "San Francisco",
"state": "CA",
"postal_code": "94105",
"country": "US"
},
"line_items": [
{
"id": "item_1",
"quantity": 2,
"unit_price": 2999,
"product_category": "clothing"
},
{
"id": "item_2",
"quantity": 1,
"unit_price": 999,
"product_category": "food_grocery"
}
],
"shipping": {
"amount": 1000
},
"customer": {
"id": "cust_abc123",
"type": "retail"
}
}'
```
```javascript Node.js theme={null}
const taxCalculation = await stateset.tax.calculate({
from_address: {
line1: "100 Commerce Way",
city: "Los Angeles",
state: "CA",
postal_code: "90001",
country: "US"
},
to_address: {
line1: "123 Main St",
city: "San Francisco",
state: "CA",
postal_code: "94105",
country: "US"
},
line_items: [
{
id: "item_1",
quantity: 2,
unit_price: 2999,
product_category: "clothing"
},
{
id: "item_2",
quantity: 1,
unit_price: 999,
product_category: "food_grocery"
}
],
shipping: {
amount: 1000
},
customer: {
id: "cust_abc123",
type: "retail"
}
});
```
```json Response theme={null}
{
"object": "tax_calculation",
"order_total": 7997,
"taxable_amount": 6998,
"tax_amount": 613,
"effective_rate": 0.0876,
"line_items": [
{
"id": "item_1",
"amount": 5998,
"taxable_amount": 5998,
"tax_amount": 540,
"tax_breakdown": [
{
"name": "California State Sales Tax",
"rate": 0.0725,
"amount": 435,
"taxable_amount": 5998
},
{
"name": "San Francisco County Tax",
"rate": 0.0175,
"amount": 105,
"taxable_amount": 5998
}
]
},
{
"id": "item_2",
"amount": 999,
"taxable_amount": 0,
"tax_amount": 0,
"exemption_reason": "food_grocery_exempt"
}
],
"shipping": {
"amount": 1000,
"taxable_amount": 1000,
"tax_amount": 73,
"tax_breakdown": [
{
"name": "California State Sales Tax",
"rate": 0.0725,
"amount": 73
}
]
},
"jurisdictions": [
{
"name": "California",
"type": "state",
"rate": 0.0725,
"tax_amount": 508
},
{
"name": "San Francisco County",
"type": "county",
"rate": 0.0175,
"tax_amount": 105
}
],
"has_nexus": true,
"tax_registration": {
"state": "CA",
"registration_number": "CA-123456789"
},
"warnings": [],
"metadata": {
"calculation_timestamp": "2024-01-20T11:30:00Z",
"tax_engine_version": "2024.1"
}
}
```
# Create Tax Rate
Source: https://docs.stateset.com/api-reference/tax/create-rate
POST https://api.stateset.com/v1/tax/rates
Create a new tax rate for a specific jurisdiction
This endpoint creates a new tax rate that can be applied to orders based on location, product category, or customer type. Tax rates support complex jurisdiction hierarchies and exemptions.
## Authentication
This endpoint requires a valid API key with `tax:write` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Request Body
Tax rate name (e.g., "California State Sales Tax")
Unique tax code identifier
Tax rate as a decimal (e.g., 0.0725 for 7.25%)
Tax type: "sales", "vat", "gst", "pst", "hst", "custom"
Tax jurisdiction details
ISO 3166-1 alpha-2 country code
State/Province code (ISO 3166-2)
County name
City name
Applicable postal/ZIP codes (empty for all)
Special tax district name
Tax application rules
Applicable product categories (empty for all)
Exempt product categories
Applicable customer types (empty for all)
Exempt customer types (e.g., "wholesale", "government")
Minimum order amount for tax to apply (in cents)
Whether shipping is taxable
Whether this tax compounds on other taxes
Application order (lower applies first)
Tax rate validity period
When tax rate becomes effective (ISO 8601)
When tax rate expires (ISO 8601)
Tax registration details
Tax registration/license number
Registered business name
Registered address
Whether prices include this tax (common for VAT)
Tax rate status: "active", "pending", "inactive"
Additional custom fields
### Response
Returns the created tax rate object.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/tax/rates' \
--header 'Content-Type: application/json' \
--header 'Authorization: Bearer YOUR_API_KEY' \
--data-raw '{
"name": "California State Sales Tax",
"code": "CA_STATE_SALES",
"rate": 0.0725,
"type": "sales",
"jurisdiction": {
"country": "US",
"state": "CA"
},
"rules": {
"exempt_categories": ["food_grocery", "prescription_drugs"],
"exempt_customer_types": ["wholesale", "government"],
"shipping_taxable": true,
"compound": false,
"priority": 1
},
"validity": {
"effective_date": "2024-01-01T00:00:00Z"
},
"registration": {
"registration_number": "CA-123456789"
},
"is_inclusive": false,
"status": "active"
}'
```
```javascript Node.js theme={null}
const taxRate = await stateset.tax.rates.create({
name: "California State Sales Tax",
code: "CA_STATE_SALES",
rate: 0.0725,
type: "sales",
jurisdiction: {
country: "US",
state: "CA"
},
rules: {
exempt_categories: ["food_grocery", "prescription_drugs"],
exempt_customer_types: ["wholesale", "government"],
shipping_taxable: true,
compound: false,
priority: 1
},
validity: {
effective_date: "2024-01-01T00:00:00Z"
},
registration: {
registration_number: "CA-123456789"
},
is_inclusive: false,
status: "active"
});
```
```python Python theme={null}
tax_rate = stateset.tax.rates.create(
name="California State Sales Tax",
code="CA_STATE_SALES",
rate=0.0725,
type="sales",
jurisdiction={
"country": "US",
"state": "CA"
},
rules={
"exempt_categories": ["food_grocery", "prescription_drugs"],
"exempt_customer_types": ["wholesale", "government"],
"shipping_taxable": True,
"compound": False,
"priority": 1
},
validity={
"effective_date": "2024-01-01T00:00:00Z"
},
registration={
"registration_number": "CA-123456789"
},
is_inclusive=False,
status="active"
)
```
```json Response theme={null}
{
"id": "tax_rate_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "tax_rate",
"name": "California State Sales Tax",
"code": "CA_STATE_SALES",
"rate": 0.0725,
"type": "sales",
"jurisdiction": {
"country": "US",
"state": "CA",
"level": "state",
"display_name": "California, United States"
},
"rules": {
"product_categories": [],
"exempt_categories": ["food_grocery", "prescription_drugs"],
"customer_types": [],
"exempt_customer_types": ["wholesale", "government"],
"minimum_amount": null,
"shipping_taxable": true,
"compound": false,
"priority": 1
},
"validity": {
"effective_date": "2024-01-01T00:00:00Z",
"expiration_date": null,
"is_active": true
},
"registration": {
"registration_number": "CA-123456789",
"registered_name": null,
"registered_address": null
},
"is_inclusive": false,
"status": "active",
"created_at": "2024-01-20T11:00:00Z",
"updated_at": "2024-01-20T11:00:00Z",
"created_by": "user_123",
"statistics": {
"orders_count": 0,
"total_tax_collected": 0,
"last_applied": null
}
}
```
# Get Tax Rate
Source: https://docs.stateset.com/api-reference/tax/get-rate
GET https://api.stateset.com/v1/tax/rates/:id
Retrieve details of a specific tax rate
This endpoint retrieves detailed information about a specific tax rate, including its jurisdiction details and application statistics.
## Authentication
This endpoint requires a valid API key with `tax:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Path Parameters
The unique identifier of the tax rate
### Response
Returns the tax rate object if found.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/tax/rates/tax_rate_0901f083-aa1c-43c5-af5c-0a9d2fc64e30' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const taxRate = await stateset.tax.rates.retrieve(
'tax_rate_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```python Python theme={null}
tax_rate = stateset.tax.rates.retrieve(
'tax_rate_0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```json Response theme={null}
{
"id": "tax_rate_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "tax_rate",
"name": "California State Sales Tax",
"code": "CA_STATE_SALES",
"rate": 0.0725,
"type": "sales",
"jurisdiction": {
"country": "US",
"state": "CA",
"county": null,
"city": null,
"postal_codes": [],
"district": null,
"level": "state",
"display_name": "California, United States"
},
"rules": {
"product_categories": [],
"exempt_categories": ["food_grocery", "prescription_drugs"],
"customer_types": [],
"exempt_customer_types": ["wholesale", "government"],
"minimum_amount": null,
"shipping_taxable": true,
"compound": false,
"priority": 1
},
"validity": {
"effective_date": "2024-01-01T00:00:00Z",
"expiration_date": null,
"is_active": true
},
"registration": {
"registration_number": "CA-123456789",
"registered_name": "Acme Corporation",
"registered_address": {
"line1": "123 Commerce St",
"city": "Los Angeles",
"state": "CA",
"postal_code": "90001",
"country": "US"
}
},
"is_inclusive": false,
"status": "active",
"created_at": "2024-01-20T11:00:00Z",
"updated_at": "2024-01-20T11:00:00Z",
"created_by": "user_123",
"statistics": {
"orders_count": 15234,
"total_tax_collected": 1847532,
"last_applied": "2024-06-20T14:45:00Z",
"monthly_collections": [
{
"month": "2024-06",
"amount": 342150,
"orders": 2834
}
]
}
}
```
# List Tax Rates
Source: https://docs.stateset.com/api-reference/tax/list-rates
GET https://api.stateset.com/v1/tax/rates
List all tax rates with filtering options
This endpoint returns a paginated list of tax rates. You can filter by jurisdiction, type, status, and more.
## Authentication
This endpoint requires a valid API key with `tax:read` permissions.
```bash theme={null}
Authorization: Bearer YOUR_API_KEY
```
## Query Parameters
Number of tax rates to return (1-100)
Number of tax rates to skip
Filter by country code (ISO 3166-1 alpha-2)
Filter by state/province code
Filter by tax type: "sales", "vat", "gst", "pst", "hst", "custom"
Filter by status: "active", "pending", "inactive"
Filter by inclusive/exclusive taxes
Filter rates effective on a specific date (ISO 8601)
### Response
Returns a paginated list of tax rate objects.
```bash cURL theme={null}
curl --location 'https://api.stateset.com/v1/tax/rates?country=US&status=active' \
--header 'Authorization: Bearer YOUR_API_KEY'
```
```javascript Node.js theme={null}
const taxRates = await stateset.tax.rates.list({
country: 'US',
status: 'active'
});
```
```python Python theme={null}
tax_rates = stateset.tax.rates.list(
country='US',
status='active'
)
```
```json Response theme={null}
{
"object": "list",
"data": [
{
"id": "tax_rate_0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "tax_rate",
"name": "California State Sales Tax",
"code": "CA_STATE_SALES",
"rate": 0.0725,
"type": "sales",
"jurisdiction": {
"country": "US",
"state": "CA",
"level": "state",
"display_name": "California, United States"
},
"is_inclusive": false,
"status": "active",
"created_at": "2024-01-20T11:00:00Z"
},
{
"id": "tax_rate_1234f083-bb2d-54d6-bg6d-1b0e3gd75f41",
"object": "tax_rate",
"name": "San Francisco County Tax",
"code": "SF_COUNTY_SALES",
"rate": 0.0175,
"type": "sales",
"jurisdiction": {
"country": "US",
"state": "CA",
"county": "San Francisco",
"level": "county",
"display_name": "San Francisco County, California, United States"
},
"is_inclusive": false,
"status": "active",
"created_at": "2024-01-20T11:05:00Z"
}
],
"has_more": true,
"total_count": 127,
"url": "/v1/tax/rates"
}
```
# Workflow Framework with Temporal
Source: https://docs.stateset.com/api-reference/temporal
Building resilient and scalable web workflows using the Temporal framework.
# StateSet Workflow Framework with Temporal
## Introduction
StateSet leverages the Temporal framework to build robust and scalable workflows. Temporal's open-source programming model simplifies complex application logic, enhances reliability, and accelerates feature delivery. By combining serverless API calls with a deterministic execution engine, Temporal provides the backbone for automating critical business processes.
In particular, StateSet's Return Management (RMA) process is fully automated using Temporal. This includes: generating and emailing return labels, creating return records in StateSet, facilitating record retrieval, updating customer support platforms, and processing instant refunds. This automation significantly streamlines the return process, improves customer satisfaction, and allows businesses to manage returns more efficiently.
## Core Components of StateSet Workflows
StateSet Workflows are built using the following components within the Temporal framework:
* **Temporal Client:** The entry point for starting workflows and signaling their execution.
* **Temporal Worker:** Executes the workflows and activities, polling the task queue for work.
* **Temporal Workflow:** Defines the sequence of steps in the business process to be automated.
* **Temporal Activities:** Represents atomic units of work that a workflow executes.
## Temporal Client: Initiating Workflows
The Temporal Client is used to start workflows, and send signals. In StateSet, the Temporal client is configured with:
* **Namespace:** A logical grouping of workflows. (Stateset is using the `stateset` namespace)
* **Task Queue:** A queue that workers poll for workflows and activities. (Stateset is using `stateset-returns-automation`)
* **Workflow Path:** The location of the Workflow definition.
Here's an example of how Stateset's Return API uses the Temporal Client to initiate a return workflow.
```javascript theme={null}
import { Connection, WorkflowClient } from '@temporalio/client';
import { returnApprovedWorkflow } from './workflows.js'; // Import our return workflow
import { v4 as uuidv4 } from "uuid";
async function run() {
// Connect to the Temporal service
const connection = await Connection.connect({
address: 'https://api.stateset.com/temporal/api/namespaces/default',
});
// Create a WorkflowClient instance
const client = new WorkflowClient({
connection,
namespace: 'stateset',
});
const return_id = uuidv4();
// Execute the `returnApprovedWorkflow`
const return_workflow_result = await client.execute(returnApprovedWorkflow, {
taskQueue: 'stateset-returns-automation', // the task queue which the worker will monitor
workflowId: 'workflow-' + return_id, // unique ID of this workflow
args: [
{
"cancel_subscription": true,
"condition": "A",
"match": true,
"country": "US",
"customer_email": "john.doe@example.com"
},
'228476' // ticket id
], // Arguments for the workflow
});
console.log(return_workflow_result); // Logs the workflow result
}
run().catch((err) => {
console.error(err);
process.exit(1);
});
```
> The code shows how we connect to the Temporal cluster and execute the `returnApprovedWorkflow` workflow by passing some initial arguments.
## Temporal Worker: Executing Workflows and Activities
The Temporal Worker is responsible for executing workflows and activities. It polls the specified task queue for pending tasks and executes them.
Here is an example of how a worker is set up to process return workflow:
```javascript theme={null}
import { Worker } from '@temporalio/worker';
import { URL } from 'url';
import * as activities from './activities.js'; // Import our activity functions
async function run() {
// Create a worker instance
const worker = await Worker.create({
workflowsPath: new URL('./workflows/return-ticket-approved.js', import.meta.url).pathname, // Path to our workflows
activities, // Our activity functions
taskQueue: 'stateset-returns-automation', // Task queue to listen on
namespace: 'stateset' // The namespace that we're using
});
// Start the worker
await worker.run();
}
run().catch((err) => {
console.error(err);
process.exit(1);
});
```
> This worker is configured to pick up workflow tasks on the `stateset-returns-automation` task queue and use the code in the `activities.js` file.
## Return Approved Workflow: Orchestrating the Process
The `returnApprovedWorkflow` orchestrates the various steps when a return request is approved. It's triggered by the Temporal Client, and it executes the following activities:
```javascript theme={null}
import { proxyActivities } from '@temporalio/workflow';
import * as wf from '@temporalio/workflow';
// Proxy Activities (configure activity timeouts)
const { generateResponse, createZendeskComment, createReturnRecord, generateUSLabel, generateCALabel, updateWorkflowId, updateMatch, cancelSubscription } = proxyActivities({
startToCloseTimeout: '1 minute',
});
/** A workflow that orchestrates a return process*/
export async function returnApprovedWorkflow(body, ticket_id_int) {
let workflow_state = []; // Example to track workflow execution.
// Extract data from the input body.
var cancel_subscription = body.cancel_subscription;
var condition = body.condition;
var match = body.match;
var country = body.country;
var customer_email = body.customer_email;
// 1. Generate a Customer Response
await generateResponse(body);
// 2. Generate a Return Label based on Country
if (country == "US") {
await generateUSLabel(ticket_id_int);
} else {
await generateCALabel(ticket_id_int);
}
// 3. Create a Return Record in our system
var return_id = await createReturnRecord(ticket_id_int);
// 4. Update the Return Record with the Temporal Workflow ID
await updateWorkflowId(return_id, wf.workflowInfo().workflowId);
// 5. Cancels the customer subscription if cancel_subscription is set to true
if (cancel_subscription) {
await cancelSubscription(customer_email, ticket_id_int);
};
// 6. Wait 3 Days
await wf.sleep('3 days');
// 7. Process Instant Refund based on Condition and Match
if (condition == "A" && match == true) {
const matched_return = await updateMatch(return_id, wf.workflowInfo().workflowId);
// refundOrder is not an activity, so it runs synchronously inside of the workflow
await refundOrder(return_id);
// Creates a comment in zendesk for auditing purposes
await createZendeskComment(ticket_id_int, condition);
return 'return_and_refund_processed';
}
return 'return_processed';
}
```
> This workflow defines the sequence of steps to execute when a return is approved. The workflow is composed of activities which are executed by the temporal worker.
### Activities: The Atomic Units of Work
Activities encapsulate the atomic units of work that a workflow executes. Here is an example of a few of the activities that we use in the workflow above. These are the actual calls that are executed by the Temporal Worker.
```javascript theme={null}
import axios from 'axios';
// Activity to Generate a Customer Response
export async function generateResponse(body) {
console.log("generating response");
return true;
}
// Activity to generate a return label in the US
export async function generateUSLabel(ticket_id_int) {
console.log("generating US label");
return true;
}
// Activity to generate a return label in Canada
export async function generateCALabel(ticket_id_int) {
console.log("generating CA label");
return true;
}
// Activity to create a record in our system
export async function createReturnRecord(ticket_id_int) {
console.log("creating return record");
return 'return_' + ticket_id_int;
}
// Activity to update the record with the workflow id
export async function updateWorkflowId(return_id, workflow_id) {
console.log("updating workflow id");
return true;
}
// Activity to update if it was a match for instant refunds
export async function updateMatch(return_id, workflow_id) {
console.log("updating return match");
return true;
}
// Activity to create a comment in Zendesk
export async function createZendeskComment(ticket_id_int, condition) {
console.log("creating zendesk comment");
return true;
}
// Activity to cancel the customer subscription
export async function cancelSubscription(customer_email, ticket_id_int) {
console.log("cancelling customer subscription");
return true;
}
```
> These activities are functions that do the actual work for the workflow. In this case they're just logging the activity for the sake of example. In a production system, these functions would call our APIs to perform business logic
### Stateset Cloud: Hosted Temporal
StateSet provides a hosted Temporal workflow service with deterministic execution and state-of-the-art infrastructure. The hosted service can be accessed at [https://cloud.stateset.com](https://cloud.stateset.com).
```mermaid theme={null}
graph LR
A[Temporal Client] --> B(Temporal Workflow);
B --> C{Temporal Activities};
C --> D[External Services/APIs];
E[Temporal Worker] --> B;
E --> C;
F[StateSet Cloud] -- Temporal Cluster --> E
```
> This diagram shows the different parts of the temporal framework and how they're organized.
## Conclusion
By leveraging the Temporal framework, StateSet implements complex workflow orchestration in a safe, reliable, and scalable way. The separation of concerns between workflows and activities enables StateSet to develop complex features quickly while relying on the powerful Temporal platform.
# Create User
Source: https://docs.stateset.com/api-reference/users/create
POST https://api.stateset.com/v1/users
This endpoint creates a new user
### Body
This is the id of the user. It is used to identify the user.
Indicates if the user is currently active
URL or path to the user's avatar image
Biography or description of the user
Date of birth of the user
Country of residence of the user
Email address of the user
First name of the user
Last name of the user
Date and time when the user was last seen
Date and time when the user last typed a message
Location or address of the user
Organization or company the user belongs to
Phone number of the user
Regions or areas associated with the user
Title or job position of the user
Twitter handle or username of the user
Unique username of the user
### Response
This is the id of the user. It is used to identify the user.
Indicates if the user is currently active
URL or path to the user's avatar image
Biography or description of the user
Date of birth of the user
Country of residence of the user
Email address of the user
First name of the user
Last name of the user
Date and time when the user was last seen
Date and time when the user last typed a message
Location or address of the user
Organization or company the user belongs to
Phone number of the user
Regions or areas associated with the user
Title or job position of the user
Twitter handle or username of the user
Unique username of the user
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/users' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "8"
}'
```
```json Response theme={null}
{
"id": "8"
}
```
# Delete User
Source: https://docs.stateset.com/api-reference/users/delete
DELETE https://api.stateset.com/v1/users/:id
This endpoint deletes an existing user.
### Body
The ID of the user to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/users/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id: "1234",
}'
```
````graphQL GraphQL theme={null}
mutation {
deleteUser(
input: {
id: "1234"
}
) {
success
}
}
```javascript Node.js
var deleted = await stateset.users.del({
id: "1234"
});
````
```python Python theme={null}
deleted = stateset.users.del({
"id": "1234"
})
```
```ruby Ruby theme={null}
deleted = Stateset::Users.del({
"id": "1234"
})
```
```php PHP theme={null}
$deleted = $stateset->users->del([
"id" => "1234"
]);
```
```go Go theme={null}
deleted, err := stateset.Users.Del(
"1234"
)
```
```java Java theme={null}
Stateset.Users.del(
"1234"
);
```
```json Response theme={null}
{
"id": "1234",
"object": "user",
"deleted": true
}
```
# Get User
Source: https://docs.stateset.com/api-reference/users/get
GET https://api.stateset.com/v1/users/:id
This endpoint gets or creates a new user.
### Body
This is the id of the user.
### Response
This is the id of the user.
This is the active of the user.
This is the avatar of the user.
This is the bio of the user.
This is the birthday of the user.
This is the country of the user.
This is the email of the user.
This is the firstName of the user.
This is the lastName of the user.
This is the last\_seen of the user.
This is the last\_typed of the user.
This is the location of the user.
This is the organization of the user.
This is the phone of the user.
This is the regions of the user.
This is the title of the user.
This is the twitter of the user.
This is the username of the user.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/users/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": 1
}'
```
```graphQL GraphQL theme={null}
query {
user {
id
active
avatar
bio
birthday
country
email
firstName
lastName
last_seen
last_typed
location
organization
phone
regions
title
twitter
username
}
}
```
```javascript Node.js theme={null}
var user = await stateset.users.get({
"id"
})
```
```python Python theme={null}
user = stateset.users.get(
"id"
)
```
```ruby Ruby theme={null}
user = Stateset::Users.get(
"id"
)
```
```php PHP theme={null}
$user = Stateset\Users::get([
"id" => "1"
]);
```
```go Go theme={null}
user, err := stateset.Users.get(
"id"
)
```
````
```java Java
User user = stateset.users.get(
"id"
);
````
```json Response theme={null}
{
"id": 1,
"active": true,
"avatar": "",
"bio": "This is the bio of the user.",
"birthday": "2020-01-01",
"country": "US",
"email": "someone@there.com",
}
```
# List Users
Source: https://docs.stateset.com/api-reference/users/list
GET https://api.stateset.com/v1/users/:id
This endpoint gets or creates a new user.
### Body
This is the limit of the users.
This is the offset of the users.
This is the order direction of the users.
### Response
This is the id of the user.
This is the active of the user.
This is the avatar of the user.
This is the bio of the user.
This is the birthday of the user.
This is the country of the user.
This is the email of the user.
This is the firstName of the user.
This is the lastName of the user.
This is the last\_seen of the user.
This is the last\_typed of the user.
This is the location of the user.
This is the organization of the user.
This is the phone of the user.
This is the regions of the user.
This is the title of the user.
This is the twitter of the user.
This is the username of the user.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/users/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "asc"
}'
```
```graphQL GraphQL theme={null}
query {
user {
id
active
avatar
bio
birthday
country
email
firstName
lastName
last_seen
last_typed
location
organization
phone
regions
title
twitter
username
}
}
```
```javascript Node.js theme={null}
var user = await stateset.users.list({
limit: 10,
offset: 0,
order_direction: "asc"
})
```
```python Python theme={null}
user = stateset.users.list(
limit=10,
offset=0,
order_direction="asc"
)
```
```ruby Ruby theme={null}
user = Stateset::Users.list(
limit: 10,
offset: 0,
order_direction: "asc"
)
```
```php PHP theme={null}
$user = Stateset\Users::list([
"limit" => 10,
"offset" => 0,
"order_direction" => "asc"
]);
```
```go Go theme={null}
user, err := stateset.Users.List(
10,
0,
"asc"
)
```
```java Java theme={null}
User user = stateset.users.list(
10,
0,
"asc"
);
```
```json Response theme={null}
{
"id": 1,
"active": true,
"avatar": "",
"bio": "This is the bio of the user.",
"birthday": "2020-01-01",
"country": "US",
"email": "someone@there.com",
}
```
## Users
| Name | Type | Description |
| ------------ | -------------------------- | ------------------------------------------------ |
| id | Text (Primary Key, Unique) | Unique identifier for the user |
| active | Boolean | Indicates if the user is currently active |
| avatar | Text | URL or path to the user's avatar image |
| bio | Text | Biography or description of the user |
| birthday | Date | Date of birth of the user |
| country | Text | Country of residence of the user |
| email | Text | Email address of the user |
| firstName | Text | First name of the user |
| lastName | Text | Last name of the user |
| last\_seen | Date/Time | Date and time when the user was last seen |
| last\_typed | Date/Time | Date and time when the user last typed a message |
| location | Text | Location or address of the user |
| organization | Text | Organization or company the user belongs to |
| phone | Text | Phone number of the user |
| regions | Text | Regions or areas associated with the user |
| title | Text | Title or job position of the user |
| twitter | Text | Twitter handle or username of the user |
| username | Text | Unique username of the user |
# Update User
Source: https://docs.stateset.com/api-reference/users/update
PUT https://api.stateset.com/v1/users/:id
This endpoint updates an existing user.
### Body
This is the id of the user. It is used to identify the user.
Indicates if the user is currently active
URL or path to the user's avatar image
Biography or description of the user
Date of birth of the user
Country of residence of the user
Email address of the user
First name of the user
Last name of the user
Date and time when the user was last seen
Date and time when the user last typed a message
Location or address of the user
Organization or company the user belongs to
Phone number of the user
Regions or areas associated with the user
Title or job position of the user
Twitter handle or username of the user
Unique username of the user
### Response
This is the id of the user. It is used to identify the user.
Indicates if the user is currently active
URL or path to the user's avatar image
Biography or description of the user
Date of birth of the user
Country of residence of the user
Email address of the user
First name of the user
Last name of the user
Date and time when the user was last seen
Date and time when the user last typed a message
Location or address of the user
Organization or company the user belongs to
Phone number of the user
Regions or areas associated with the user
Title or job position of the user
Twitter handle or username of the user
Unique username of the user
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/users/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 113,
"token": "",
"name": "ok",
"provided_id": "6"
}
}
```
# Create Vendor
Source: https://docs.stateset.com/api-reference/vendors/create
POST https://api.stateset.com/v1/vendors
This endpoint creates a new vendor
### Body
This is the current user group token you have for the user group that you want
to rotate.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
The contents of the user group
This is the internal ID for this user group. You don't need to record this
information, since you will not need to use it.
This is the user group token (userGroupToken or USER\_GROUP\_TOKEN) that will be
used to identify which user group is viewing the dashboard. You should save
this on your end to use when rendering an embedded dashboard.
This is the name of the user group provided in the request body.
This is the user\_group\_id provided in the request body.
This is the environment tag of the user group. Possible values are 'Customer'
and 'Testing'. User group id's must be unique to each environment, so you can
not create multiple user groups with with same id. If you have a production
customer and a test user group with the same id, you will be required to label
one as 'Customer' and another as 'Testing'
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/vendor' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Delete Vendor
Source: https://docs.stateset.com/api-reference/vendors/delete
DELETE https://api.return.com/v1/vendors/:id
This endpoint deletes an existing vendor.
### Body
The data source ID provided in the data tab may be used to identify the data
source for the user group
This is the current user group token you have for the user group you want to
delete
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/vendors/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1"
"current_token": "abcdef"
}'
```
```json Response theme={null}
{
"success": 1
}
```
# Get Vendor
Source: https://docs.stateset.com/api-reference/vendors/get
GET https://api.stateset.com/v1/vendors/:id
This endpoint gets or creates a new vendor.
### Body
This is the id of the vendor.
### Response
This is the id of the vendor.
This is the name of the vendor.
This is the notes of the vendor.
This is the subtype of the vendor.
This is the type of the vendor.
This is the owner of the vendor.
This is the source of the vendor.
This is the annual revenue of the vendor.
This is the avatar of the vendor.
This is the billing city of the vendor.
This is the billing country of the vendor.
This is the billing latitude of the vendor.
This is the billing longitude of the vendor.
This is the billing state of the vendor.
This is the billing street of the vendor.
This is the created at of the vendor.
This is the description of the vendor.
This is the employees of the vendor.
This is the fax of the vendor.
This is the industry of the vendor.
This is the is active of the vendor.
This is the is public of the vendor.
This is the last modified by of the vendor.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/vendor' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"new_user_group": true,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Vendors
Vendors describes the general data about the vendor in Stateset.
## The vendor object
#### Attributes
| Name | Type | Description |
| ------------------ | --------- | ------------------------------------------------------- |
| id | Text | Unique identifier for the vendor |
| vendorName | Text | Name of the vendor |
| vendorNotes | Text | Notes or additional information about the vendor |
| vendorSubtype | Text | Subtype or specific category of the vendor |
| vendorType | Text | Type or general category of the vendor |
| vendor\_owner | Text | Owner or responsible person for the vendor |
| vendor\_source | Text | Source or origin of the vendor |
| annualRevenue | Text | Annual revenue associated with the vendor |
| avatar | Text | URL or path to the vendor's avatar image |
| billingCity | Text | City of the billing address |
| billingCountry | Text | Country of the billing address |
| billingLatitude | Text | Latitude coordinate of the billing address |
| billingLongitude | Text | Longitude coordinate of the billing address |
| billingState | Text | State or province of the billing address |
| billingStreet | Text | Street address of the billing address |
| created\_at | Date/Time | Date and time when the vendor was created |
| description | Text | Description or additional details about the vendor |
| employees | Text | Number or range of employees associated with the vendor |
| fax | Text | Fax number of the vendor |
| industry | Text | Industry or sector of the vendor |
| is\_active | Boolean | Indicates whether the vendor is currently active |
| is\_public | Boolean | Indicates whether the vendor is public or private |
| last\_modified\_by | Text | Last person who modified the vendor |
| numberOfEmployees | Text | Number of employees associated with the vendor |
| ownership | Text | Ownership type or structure of the vendor |
| parentVendor | Text | Parent vendor associated with the vendor |
| phone | Text | Phone number of the vendor |
| rating | Text | Rating or evaluation of the vendor |
| shippingCity | Text | City of the shipping address |
| shippingCountry | Text | Country of the shipping address |
| shippingLatitude | Text | Latitude coordinate of the shipping address |
| shippingLongitude | Text | Longitude coordinate of the shipping address |
| shippingState | Text | State or province of the shipping address |
| shippingStreet | Text | Street address of the shipping address |
| stockTicker | Text | Stock ticker symbol associated with the vendor |
| website | Text | Website URL of the vendor |
| yearStarted | Text | Year the vendor started or established |
# List Vendor
Source: https://docs.stateset.com/api-reference/vendors/list
GET https://api.stateset.com/v1/vendor/list
This endpoint gets or creates a new vendor.
### Body
This is the limit of the vendors.
This is the offset of the vendors.
This is the order direction of the vendors.
### Response
This is the id of the vendor.
This is the name of the vendor.
This is the notes of the vendor.
This is the subtype of the vendor.
This is the type of the vendor.
This is the owner of the vendor.
This is the source of the vendor.
This is the annual revenue of the vendor.
This is the avatar of the vendor.
This is the billing city of the vendor.
This is the billing country of the vendor.
This is the billing latitude of the vendor.
This is the billing longitude of the vendor.
This is the billing state of the vendor.
This is the billing street of the vendor.
This is the created at of the vendor.
This is the description of the vendor.
This is the employees of the vendor.
This is the fax of the vendor.
This is the industry of the vendor.
This is the is active of the vendor.
This is the is public of the vendor.
This is the last modified by of the vendor.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/vendor' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"new_user_group": true,
"user_group": {
"team_id": 3,
"token": "",
"name": "Example 1",
"provided_id": "example_1"
}
}
```
# Vendors
Vendors describes the general data about the vendor in Stateset.
## The vendor object
#### Attributes
| Name | Type | Description |
| ------------------ | --------- | ------------------------------------------------------- |
| id | Text | Unique identifier for the vendor |
| vendorName | Text | Name of the vendor |
| vendorNotes | Text | Notes or additional information about the vendor |
| vendorSubtype | Text | Subtype or specific category of the vendor |
| vendorType | Text | Type or general category of the vendor |
| vendor\_owner | Text | Owner or responsible person for the vendor |
| vendor\_source | Text | Source or origin of the vendor |
| annualRevenue | Text | Annual revenue associated with the vendor |
| avatar | Text | URL or path to the vendor's avatar image |
| billingCity | Text | City of the billing address |
| billingCountry | Text | Country of the billing address |
| billingLatitude | Text | Latitude coordinate of the billing address |
| billingLongitude | Text | Longitude coordinate of the billing address |
| billingState | Text | State or province of the billing address |
| billingStreet | Text | Street address of the billing address |
| created\_at | Date/Time | Date and time when the vendor was created |
| description | Text | Description or additional details about the vendor |
| employees | Text | Number or range of employees associated with the vendor |
| fax | Text | Fax number of the vendor |
| industry | Text | Industry or sector of the vendor |
| is\_active | Boolean | Indicates whether the vendor is currently active |
| is\_public | Boolean | Indicates whether the vendor is public or private |
| last\_modified\_by | Text | Last person who modified the vendor |
| numberOfEmployees | Text | Number of employees associated with the vendor |
| ownership | Text | Ownership type or structure of the vendor |
| parentVendor | Text | Parent vendor associated with the vendor |
| phone | Text | Phone number of the vendor |
| rating | Text | Rating or evaluation of the vendor |
| shippingCity | Text | City of the shipping address |
| shippingCountry | Text | Country of the shipping address |
| shippingLatitude | Text | Latitude coordinate of the shipping address |
| shippingLongitude | Text | Longitude coordinate of the shipping address |
| shippingState | Text | State or province of the shipping address |
| shippingStreet | Text | Street address of the shipping address |
| stockTicker | Text | Stock ticker symbol associated with the vendor |
| website | Text | Website URL of the vendor |
| yearStarted | Text | Year the vendor started or established |
# Update Vendor
Source: https://docs.stateset.com/api-reference/vendors/update
PUT https://api.stateset.com/v1/vendors/:id
This endpoint updates an existing vendor.
### Body
This is the name of the user group.
This is the ID you use to identify this user group in your database.
This is a JSON mapping of schema id to either the data source that this user
group should be associated with or id of the datasource you provided when
creating it.
This is a JSON object for properties assigned to this user group. These will
be accessible through variables in the dashboards and SQL editor
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
The contents of the user group
Indicates whether a new user group was created.
This is the user group token (userGroupToken or USER\_GROUP\_TOKEN) that will be
used to identify which user group is viewing the dashboard. You should save
this on your end to use when rendering an embedded dashboard.
This is the name of the user group provided in the request body.
This is the user\_group\_id provided in the request body.
This is the properties object if it was provided in the request body
This is the environment tag of the user group. Possible values are 'Customer'
and 'Testing'
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/vendor' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```json Response theme={null}
{
"success": 1,
"user_group": {
"team_id": 113,
"token": "",
"name": "ok",
"provided_id": "6"
}
}
```
# Approve Warranty
Source: https://docs.stateset.com/api-reference/warranty/approve
POST https://api.stateset.com/v1/warranties/:id/approve
This endpoint approves a warranty.
### Body
The ID provided in the data tab may be used to identify the warranty
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty/:id/approve' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyApproveMutation {
warrantyApprove(id: "${warrantyId}") {
warranty {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
warranties = stateset.warranties.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Approve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"approved": true
}
```
# Cancel Warranty
Source: https://docs.stateset.com/api-reference/warranty/cancel
POST https://api.stateset.com/v1/warranties/:id/cancel
This endpoint cancels a warranty.
### Body
The ID provided in the data tab may be used to identify the warranty
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty/:id/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyCancelMutation {
warrantyCancel(id: "${warrantyId}") {
warranty {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
warranties = stateset.warranties.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"cancelled": true
}
```
# Close Warranty
Source: https://docs.stateset.com/api-reference/warranty/close
POST https://api.stateset.com/v1/warranties/:id/close
This endpoint closes a warranty.
### Body
The ID provided in the data tab may be used to identify the warranty
The resolution or outcome of the warranty claim
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
The timestamp when the warranty was closed
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty/:id/close' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"resolution": "Replaced product under warranty"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyCloseMutation {
warrantyClose(id: "${warrantyId}", resolution: "${resolution}") {
warranty {
id,
status,
closed_at
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.close({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
resolution: 'Replaced product under warranty'
});
```
```python Python theme={null}
warranties = stateset.warranties.close({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'resolution': 'Replaced product under warranty'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.close({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
resolution: 'Replaced product under warranty'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.close({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
Resolution: 'Replaced product under warranty'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.close({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
resolution: 'Replaced product under warranty'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->close([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'resolution' => 'Replaced product under warranty'
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Close(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
Resolution = 'Replaced product under warranty'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"closed": true,
"closed_at": "2024-01-15T10:30:00Z",
"resolution": "Replaced product under warranty"
}
```
# Create Warranty
Source: https://docs.stateset.com/api-reference/warranty/create
POST https://api.stateset.com/v1/warranty
This endpoint creates a new warranty
### Body
This is the unique identifier for the warranty.
This is the unique identifier for the order.
This is the unique identifier for the serial number.
This is the description of the warranty.
This is the status of the warranty.
This is the reported condition of the warranty.
This is the tracking number of the warranty.
This is the zendesk number of the warranty.
This is the action needed of the warranty.
This is the rma of the warranty.
This is the country of the warranty.
This is the created date of the warranty.
### Response
This is the id of the warranty.
Indicates whether any action is needed for the warranty.
Indicates if advanced replacement is available for the warranty.
The monetary amount associated with the warranty.
Describes the condition of the item or situation.
Date and time when the condition was recorded or observed.
Country associated with the warranty entry.
Date and time when the warranty entry was created.
Email address of the customer associated with the warranty.
Unique identifier for the customer associated with the warranty.
Brief description or additional details about the warranty.
Name or identifier of the person who entered the warranty.
Issue or problem associated with the warranty.
Indicates whether the warranty matches the specified conditions.
Date and time when the order associated with the warranty was placed.
Unique identifier for the order associated with the warranty.
Category or reason associated with the warranty.
Color of the replacement item for the warranty.
Model of the replacement item for the warranty.
Indicates if a replacement order has been created for the warranty.
Condition as reported by the customer or user.
Date and time when a specific request was made for the warranty.
Return Merchandise Authorization (RMA) number for the warranty.
Serial number obtained through scanning for the warranty.
Unique serial number associated with the item in the warranty.
ShipStation order ID associated with the warranty.
Date and time when the item was shipped or dispatched.
Single Sign-On (SSO) ID associated with the warranty.
Current status or state of the warranty.
Stripe invoice ID associated with the warranty.
The amount of tax refunded for the warranty.
The total amount refunded for the warranty.
Tracking number associated with the shipment for the warranty.
Date and time when the item was received in the warehouse.
This is an array of warranty line items.
The monetary amount associated with the warranty line item.
Describes the condition of the replaced item.
Indicates whether the shipping rate is a flat rate.
Unique identifier for the warranty line item.
Name or description of the warranty line item.
The price of the warranty line item.
Unique identifier for the warranty associated with the line item.
Unique serial number associated with the warranty item.
Stock Keeping Unit (SKU) of the replaced item.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/warranty' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```graphQL GraphQL theme={null}
mutation InsertNewWarranty(
$warranty: warranties_insert_input!
) {
insert_warranties (
objects: [$warranty]
) {
returning {
id
order_id
serial_number
customer_id
description
status
tracking_number
zendesk_number
action_needed
issue
shipped_date
requested_date
enteredBy
customerEmail
rma
country
}
}
}
```
```js Node.js theme={null}
const warranty = await stateset.warranties.create({
warranty: 'W-23213322',
warranty_line_items: [
{id: 'WI-232133223'},
],
});
```
```py Python theme={null}
warranty = stateset.warranties.create({
warranty: 'W-23213322',
warranty_line_items: [
{id: 'WI-232133223'},
],
})
```
```go Golang theme={null}
warranty, err := stateset.Warranties.Create(&stateset.WarrantyParams{
Warranty: 'W-23213322',
WarrantyLineItems: []*stateset.WarrantyLineItemParams{
{ID: 'WI-232133223'},
},
})
```
```rb Ruby theme={null}
warranty = Stateset::Warranty.create({
warranty: 'W-23213322',
warranty_line_items: [
{id: 'WI-232133223'},
],
})
```
```java Java theme={null}
Warranty warranty = Warranty.create({
warranty: 'W-23213322',
warranty_line_items: [
{id: 'WI-232133223'},
],
})
```
```php PHP theme={null}
$warranty = Warranty::create([
'warranty' => 'W-23213322',
'warranty_line_items' => [
['id' => 'WI-232133223'],
],
]);
```
```json Response theme={null}
{
"warranties": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"created_date": "2023-06-28T19:34:59.189838+00:00",
"amount": null,
"action_needed": null,
"condition": null,
"customerEmail": "customer@gmail.com",
"customer_id": null,
"description": null,
"enteredBy": null,
"flat_rate_shipping": null,
"order_date": null,
"order_id": "524213310335630636",
"reason_category": null,
"reported_condition": null,
"requested_date": null,
"rma": "#1014-R5",
"serial_number": null,
"shipped_date": null,
"status": "RCV",
"tax_refunded": null,
"total_refunded": null,
"tracking_number": null,
"warranty_line_items": []
},
]
}
```
# Delete Warranty
Source: https://docs.stateset.com/api-reference/warranty/delete
DELETE https://api.stateset.com/v1/warranty
This endpoint deletes an existing warranty.
### Body
The ID provided in the data tab may be used to identify the warranty
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/warranty' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "w_1NXWPnCo6bFb1KQto6C8OWvE"
}'
```
```graphQL GraphQL theme={null}
mutation deleteWarranty ($id: String!) {
delete_warranties(where: {id: {_eq: $id}}) {
affected_rows
}
}
```
```javascript Node.js theme={null}
const deleted = await stateset.warranty.del(
'w_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```python Python theme={null}
deleted = stateset.warranty.del(
'w_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
deleted = Stateset::Warranty.del(
'w_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```php PHP theme={null}
$deleted = $stateset->warranty->del(
'w_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```go Go theme={null}
Warranty, err := stateset.Warranty.Delete(
'w_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
Warranty warranties = stateset.warranties.del(
"0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
);
```
```json Response theme={null}
{
"id": "w_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "warranty",
"deleted": true
}
```
# Extend Warranty
Source: https://docs.stateset.com/api-reference/warranty/extend
POST https://api.stateset.com/v1/warranties/:id/extend
This endpoint extends a warranty period.
### Body
The ID provided in the data tab may be used to identify the warranty
The number of days to extend the warranty
The new expiry date for the warranty
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
The original expiry date of the warranty
The new expiry date of the warranty
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty/:id/extend' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"extension_period": 365,
"new_expiry_date": "2025-12-31"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyExtendMutation {
warrantyExtend(id: "${warrantyId}", extensionPeriod: ${extensionPeriod}, newExpiryDate: "${newExpiryDate}") {
warranty {
id,
original_expiry_date,
new_expiry_date
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.extend({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
extension_period: 365,
new_expiry_date: '2025-12-31'
});
```
```python Python theme={null}
warranties = stateset.warranties.extend({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'extension_period': 365,
'new_expiry_date': '2025-12-31'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.extend({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
extension_period: 365,
new_expiry_date: '2025-12-31'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.extend({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
ExtensionPeriod: 365,
NewExpiryDate: '2025-12-31'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.extend({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
extensionPeriod: 365,
newExpiryDate: '2025-12-31'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->extend([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'extension_period' => 365,
'new_expiry_date' => '2025-12-31'
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Extend(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
ExtensionPeriod = 365,
NewExpiryDate = '2025-12-31'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"extended": true,
"original_expiry_date": "2024-12-31",
"new_expiry_date": "2025-12-31",
"extension_period": 365
}
```
# Get Warranty
Source: https://docs.stateset.com/api-reference/warranty/get
GET https://api.stateset.com/v1/warranty
This endpoint gets or creates a new warranty.
### Body
This is the id of the warranty.
### Response
This is the id of the warranty.
Indicates whether any action is needed for the warranty.
Indicates if advanced replacement is available for the warranty.
The monetary amount associated with the warranty.
Describes the condition of the item or situation.
Date and time when the condition was recorded or observed.
Country associated with the warranty entry.
Date and time when the warranty entry was created.
Email address of the customer associated with the warranty.
Unique identifier for the customer associated with the warranty.
Brief description or additional details about the warranty.
Name or identifier of the person who entered the warranty.
Issue or problem associated with the warranty.
Indicates whether the warranty matches the specified conditions.
Date and time when the order associated with the warranty was placed.
Unique identifier for the order associated with the warranty.
Category or reason associated with the warranty.
Color of the replacement item for the warranty.
Model of the replacement item for the warranty.
Indicates if a replacement order has been created for the warranty.
Condition as reported by the customer or user.
Date and time when a specific request was made for the warranty.
Return Merchandise Authorization (RMA) number for the warranty.
Serial number obtained through scanning for the warranty.
Unique serial number associated with the item in the warranty.
ShipStation order ID associated with the warranty.
Date and time when the item was shipped or dispatched.
Single Sign-On (SSO) ID associated with the warranty.
Current status or state of the warranty.
Stripe invoice ID associated with the warranty.
The amount of tax refunded for the warranty.
The total amount refunded for the warranty.
Tracking number associated with the shipment for the warranty.
Date and time when the item was received in the warehouse.
This is an array of warranty line items.
The monetary amount associated with the warranty line item.
Describes the condition of the replaced item.
Indicates whether the shipping rate is a flat rate.
Unique identifier for the warranty line item.
Name or description of the warranty line item.
The price of the warranty line item.
Unique identifier for the warranty associated with the line item.
Unique serial number associated with the warranty item.
Stock Keeping Unit (SKU) of the replaced item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/return' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
query getMyWarrantyData($last_received_id: String, $last_received_ts: String, $first_received_date: date, $id: String) {
warranties(where: {id: {_eq: $id}}) {
id
order_id
description
status
issue
tracking_number
action_needed
customerEmail
rma
serial_number
scanned_serial_number
zendesk_number
enteredBy
order_date
shipped_date
requested_date
condition
reported_condition
amount
tax_refunded
total_refunded
created_date
reason_category
country
advanced_replacement
replacement_color
stripe_invoice_id
shipstation_order_id
}
warranty_line_items(where: {warranty_id: {_eq: $id}}) {
id
sku
name
price
condition
tax_refunded
flat_rate_shipping
warranty_id
serial_number
amount
image_1
image_2
image_3
match
}
}`;
```
```javascript Node.js theme={null}
const warranties = await stateset.warranties.retrieve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
warranties = stateset.warranties.retrieve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.retrieve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```php PHP theme={null}
$warranties = $stateset->warranties->retrieve([
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
]);
```
```http HTTP theme={null}
GET /v1/warranty HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"warranties": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"created_date": "2023-06-28T19:34:59.189838+00:00",
"amount": null,
"action_needed": null,
"condition": null,
"customerEmail": "customer@gmail.com",
"customer_id": null,
"description": null,
"enteredBy": null,
"flat_rate_shipping": null,
"order_date": null,
"order_id": "524213310335630636",
"reason_category": null,
"reported_condition": null,
"requested_date": null,
"rma": "#1014-R5",
"serial_number": null,
"shipped_date": null,
"status": "RCV",
"tax_refunded": null,
"total_refunded": null,
"tracking_number": null,
"warranty_line_items": []
},
]
}
```
### Warranty
| Name | Type | Description |
| --------------------------- | --------- | -------------------------------------------------------------------- |
| id | Integer | Unique identifier for the warranty entry |
| action\_needed | Boolean | Indicates whether any action is needed for the warranty |
| advanced\_replacement | Boolean | Indicates if advanced replacement is available for the warranty |
| amount | Decimal | The monetary amount associated with the warranty |
| condition | String | Describes the condition of the item or situation |
| condition\_date | Date/Time | Date and time when the condition was recorded or observed |
| country | String | Country associated with the warranty entry |
| created\_date | Date/Time | Date and time when the warranty entry was created |
| customerEmail | String | Email address of the customer associated with the warranty |
| customer\_id | Integer | Unique identifier for the customer associated with the warranty |
| description | String | Brief description or additional details about the warranty |
| enteredBy | String | Name or identifier of the person who entered the warranty |
| issue | String | Issue or problem associated with the warranty |
| match | Boolean | Indicates whether the warranty matches the specified conditions |
| order\_date | Date/Time | Date and time when the order associated with the warranty was placed |
| order\_id | Integer | Unique identifier for the order associated with the warranty |
| reason\_category | String | Category or reason associated with the warranty |
| replacement\_color | String | Color of the replacement item for the warranty |
| replacement\_order\_created | Boolean | Indicates if a replacement order has been created for the warranty |
| reported\_condition | String | Condition as reported by the customer or user |
| requested\_date | Date/Time | Date and time when a specific request was made for the warranty |
| rma | String | Return Merchandise Authorization (RMA) number for the warranty |
| scanned\_serial\_number | String | Serial number obtained through scanning for the warranty |
| serial\_number | String | Unique serial number associated with the item in the warranty |
| shipstation\_order\_id | String | ShipStation order ID associated with the warranty |
| shipped\_date | Date/Time | Date and time when the item was shipped or dispatched |
| sso\_id | String | Single Sign-On (SSO) ID associated with the warranty |
| status | String | Current status or state of the warranty |
| stripe\_invoice\_id | String | Stripe invoice ID associated with the warranty |
| tax\_refunded | Decimal | The amount of tax refunded for the warranty |
| total\_refunded | Decimal | The total amount refunded for the warranty |
| tracking\_number | String | Tracking number associated with the shipment for the warranty |
| warehouse\_received\_date | Date/Time | Date and time when the item was received in the warehouse |
### Warranty Line Item
| Name | Type | Description |
| -------------------- | ------- | ---------------------------------------------------------------- |
| amount | Decimal | The monetary amount associated with the warranty line item |
| condition | String | Describes the condition of the replaced item |
| flat\_rate\_shipping | Boolean | Indicates whether the shipping rate is a flat rate |
| id | Integer | Unique identifier for the warranty line item |
| name | String | Name or description of the warranty line item |
| price | Decimal | The price of the warranty line item |
| warranty\_id | Integer | Unique identifier for the warranty associated with the line item |
| serial\_number | String | Unique serial number associated with the warranty item |
| sku | String | Stock Keeping Unit (SKU) of the replaced item |
# Inspect Warranty Item
Source: https://docs.stateset.com/api-reference/warranty/inspect
POST https://api.stateset.com/v1/warranties/:id/inspect
This endpoint records inspection details for a warranty claim.
### Body
The ID provided in the data tab may be used to identify the warranty
The type of inspection performed (e.g., "physical", "diagnostic", "functional")
The ID of the inspector or technician
Detailed notes from the inspection
List of defects found during inspection
URLs of images taken during inspection
Whether the issue is covered under warranty
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
The unique identifier for the inspection record
The status of the inspection (e.g., "completed", "pending\_review")
The date when the inspection was performed
Whether the warranty claim is valid based on inspection
The recommended action based on inspection results
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/warranties/:id/inspect' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"inspection_type": "diagnostic",
"inspector_id": "tech_456",
"inspection_notes": "Device shows signs of manufacturing defect in display panel",
"defects_found": ["dead_pixels", "backlight_bleeding"],
"inspection_images": ["https://images.stateset.com/inspect/img1.jpg", "https://images.stateset.com/inspect/img2.jpg"],
"warranty_valid": true
}'
```
```graphQL GraphQL theme={null}
mutation warrantyInspectMutation {
warrantyInspect(
id: "${warrantyId}",
inspectionType: "${inspectionType}",
inspectorId: "${inspectorId}",
inspectionNotes: "${inspectionNotes}",
defectsFound: ${defectsFound},
inspectionImages: ${inspectionImages},
warrantyValid: ${warrantyValid}
) {
warranty {
id,
status,
inspection_id,
inspection_status,
warranty_valid,
recommended_action
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.inspect({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
inspection_type: 'diagnostic',
inspector_id: 'tech_456',
inspection_notes: 'Device shows signs of manufacturing defect in display panel',
defects_found: ['dead_pixels', 'backlight_bleeding'],
inspection_images: ['https://images.stateset.com/inspect/img1.jpg', 'https://images.stateset.com/inspect/img2.jpg'],
warranty_valid: true
});
```
```python Python theme={null}
warranties = stateset.warranties.inspect({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'inspection_type': 'diagnostic',
'inspector_id': 'tech_456',
'inspection_notes': 'Device shows signs of manufacturing defect in display panel',
'defects_found': ['dead_pixels', 'backlight_bleeding'],
'inspection_images': ['https://images.stateset.com/inspect/img1.jpg', 'https://images.stateset.com/inspect/img2.jpg'],
'warranty_valid': True
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.inspect({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
inspection_type: 'diagnostic',
inspector_id: 'tech_456',
inspection_notes: 'Device shows signs of manufacturing defect in display panel',
defects_found: ['dead_pixels', 'backlight_bleeding'],
inspection_images: ['https://images.stateset.com/inspect/img1.jpg', 'https://images.stateset.com/inspect/img2.jpg'],
warranty_valid: true
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.inspect({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
InspectionType: 'diagnostic',
InspectorID: 'tech_456',
InspectionNotes: 'Device shows signs of manufacturing defect in display panel',
DefectsFound: []string{'dead_pixels', 'backlight_bleeding'},
InspectionImages: []string{'https://images.stateset.com/inspect/img1.jpg', 'https://images.stateset.com/inspect/img2.jpg'},
WarrantyValid: true
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.inspect({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
inspectionType: 'diagnostic',
inspectorId: 'tech_456',
inspectionNotes: 'Device shows signs of manufacturing defect in display panel',
defectsFound: ['dead_pixels', 'backlight_bleeding'],
inspectionImages: ['https://images.stateset.com/inspect/img1.jpg', 'https://images.stateset.com/inspect/img2.jpg'],
warrantyValid: true
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->inspect([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'inspection_type' => 'diagnostic',
'inspector_id' => 'tech_456',
'inspection_notes' => 'Device shows signs of manufacturing defect in display panel',
'defects_found' => ['dead_pixels', 'backlight_bleeding'],
'inspection_images' => ['https://images.stateset.com/inspect/img1.jpg', 'https://images.stateset.com/inspect/img2.jpg'],
'warranty_valid' => true
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Inspect(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
InspectionType = 'diagnostic',
InspectorId = 'tech_456',
InspectionNotes = 'Device shows signs of manufacturing defect in display panel',
DefectsFound = new[] { 'dead_pixels', 'backlight_bleeding' },
InspectionImages = new[] { 'https://images.stateset.com/inspect/img1.jpg', 'https://images.stateset.com/inspect/img2.jpg' },
WarrantyValid = true
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"inspected": true,
"inspection_id": "insp_abc123",
"inspection_status": "completed",
"inspection_date": "2024-01-15T14:30:00Z",
"warranty_valid": true,
"defects_found": ["dead_pixels", "backlight_bleeding"],
"recommended_action": "replace",
"inspector_id": "tech_456"
}
```
# List Warranty
Source: https://docs.stateset.com/api-reference/warranty/list
GET https://api.stateset.com/v1/warranty/list
This endpoint gets warranties.
### Body
This is the limit of the warranties.
This is the offset of the warranties.
This is the order direction of the warranties.
### Response
This is the id of the warranty.
Indicates whether any action is needed for the warranty.
Indicates if advanced replacement is available for the warranty.
The monetary amount associated with the warranty.
Describes the condition of the item or situation.
Date and time when the condition was recorded or observed.
Country associated with the warranty entry.
Date and time when the warranty entry was created.
Email address of the customer associated with the warranty.
Unique identifier for the customer associated with the warranty.
Brief description or additional details about the warranty.
Name or identifier of the person who entered the warranty.
Issue or problem associated with the warranty.
Indicates whether the warranty matches the specified conditions.
Date and time when the order associated with the warranty was placed.
Unique identifier for the order associated with the warranty.
Category or reason associated with the warranty.
Color of the replacement item for the warranty.
Model of the replacement item for the warranty.
Indicates if a replacement order has been created for the warranty.
Condition as reported by the customer or user.
Date and time when a specific request was made for the warranty.
Return Merchandise Authorization (RMA) number for the warranty.
Serial number obtained through scanning for the warranty.
Unique serial number associated with the item in the warranty.
ShipStation order ID associated with the warranty.
Date and time when the item was shipped or dispatched.
Single Sign-On (SSO) ID associated with the warranty.
Current status or state of the warranty.
Stripe invoice ID associated with the warranty.
The amount of tax refunded for the warranty.
The total amount refunded for the warranty.
Tracking number associated with the shipment for the warranty.
Date and time when the item was received in the warehouse.
This is an array of warranty line items.
The monetary amount associated with the warranty line item.
Describes the condition of the replaced item.
Indicates whether the shipping rate is a flat rate.
Unique identifier for the warranty line item.
Name or description of the warranty line item.
The price of the warranty line item.
Unique identifier for the warranty associated with the line item.
Unique serial number associated with the warranty item.
Stock Keeping Unit (SKU) of the replaced item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/return' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "desc"
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
warranties(limit: $limit, offset: $offset, order_by: {created_date: $order_direction}) {
id
order_id
description
status
issue
tracking_number
action_needed
customerEmail
rma
serial_number
scanned_serial_number
zendesk_number
enteredBy
order_date
shipped_date
requested_date
condition
reported_condition
amount
tax_refunded
total_refunded
created_date
reason_category
country
advanced_replacement
replacement_color
stripe_invoice_id
shipstation_order_id
}
warranty_line_items(where: {warranty_id: {_eq: $id}}) {
id
sku
name
price
condition
tax_refunded
flat_rate_shipping
warranty_id
serial_number
amount
image_1
image_2
image_3
match
}
}`;
```
```javascript Node.js theme={null}
const warranties = await stateset.warranties.list({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
warranties = stateset.warranties.list({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.list({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```php PHP theme={null}
$warranties = $stateset->warranties->list([
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
]);
```
```http HTTP theme={null}
GET /v1/warranty HTTP/1.1
Host: api.stateset.com
Content-Type: application/json
```
```json Response theme={null}
{
"warranties": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"created_date": "2023-06-28T19:34:59.189838+00:00",
"amount": null,
"action_needed": null,
"condition": null,
"customerEmail": "customer@gmail.com",
"customer_id": null,
"description": null,
"enteredBy": null,
"flat_rate_shipping": null,
"order_date": null,
"order_id": "524213310335630636",
"reason_category": null,
"reported_condition": null,
"requested_date": null,
"rma": "#1014-R5",
"serial_number": null,
"shipped_date": null,
"status": "RCV",
"tax_refunded": null,
"total_refunded": null,
"tracking_number": null,
"warranty_line_items": []
},
]
}
```
### Warranty
| Name | Type | Description |
| --------------------------- | --------- | -------------------------------------------------------------------- |
| id | Integer | Unique identifier for the warranty entry |
| action\_needed | Boolean | Indicates whether any action is needed for the warranty |
| advanced\_replacement | Boolean | Indicates if advanced replacement is available for the warranty |
| amount | Decimal | The monetary amount associated with the warranty |
| condition | String | Describes the condition of the item or situation |
| condition\_date | Date/Time | Date and time when the condition was recorded or observed |
| country | String | Country associated with the warranty entry |
| created\_date | Date/Time | Date and time when the warranty entry was created |
| customerEmail | String | Email address of the customer associated with the warranty |
| customer\_id | Integer | Unique identifier for the customer associated with the warranty |
| description | String | Brief description or additional details about the warranty |
| enteredBy | String | Name or identifier of the person who entered the warranty |
| issue | String | Issue or problem associated with the warranty |
| match | Boolean | Indicates whether the warranty matches the specified conditions |
| order\_date | Date/Time | Date and time when the order associated with the warranty was placed |
| order\_id | Integer | Unique identifier for the order associated with the warranty |
| reason\_category | String | Category or reason associated with the warranty |
| replacement\_color | String | Color of the replacement item for the warranty |
| replacement\_order\_created | Boolean | Indicates if a replacement order has been created for the warranty |
| reported\_condition | String | Condition as reported by the customer or user |
| requested\_date | Date/Time | Date and time when a specific request was made for the warranty |
| rma | String | Return Merchandise Authorization (RMA) number for the warranty |
| scanned\_serial\_number | String | Serial number obtained through scanning for the warranty |
| serial\_number | String | Unique serial number associated with the item in the warranty |
| shipstation\_order\_id | String | ShipStation order ID associated with the warranty |
| shipped\_date | Date/Time | Date and time when the item was shipped or dispatched |
| sso\_id | String | Single Sign-On (SSO) ID associated with the warranty |
| status | String | Current status or state of the warranty |
| stripe\_invoice\_id | String | Stripe invoice ID associated with the warranty |
| tax\_refunded | Decimal | The amount of tax refunded for the warranty |
| total\_refunded | Decimal | The total amount refunded for the warranty |
| tracking\_number | String | Tracking number associated with the shipment for the warranty |
| warehouse\_received\_date | Date/Time | Date and time when the item was received in the warehouse |
### Warranty Line Item
| Name | Type | Description |
| -------------------- | ------- | ---------------------------------------------------------------- |
| amount | Decimal | The monetary amount associated with the warranty line item |
| condition | String | Describes the condition of the replaced item |
| flat\_rate\_shipping | Boolean | Indicates whether the shipping rate is a flat rate |
| id | Integer | Unique identifier for the warranty line item |
| name | String | Name or description of the warranty line item |
| price | Decimal | The price of the warranty line item |
| warranty\_id | Integer | Unique identifier for the warranty associated with the line item |
| serial\_number | String | Unique serial number associated with the warranty item |
| sku | String | Stock Keeping Unit (SKU) of the replaced item |
# Refund Warranty
Source: https://docs.stateset.com/api-reference/warranty/refund
POST https://api.stateset.com/v1/warranties/:id/refund
This endpoint processes a refund for a warranty claim.
### Body
The ID provided in the data tab may be used to identify the warranty
The amount to refund for the warranty claim
The reason for the warranty refund
The method of refund (e.g., "credit\_card", "store\_credit", "check")
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
The unique identifier for the refund transaction
The amount refunded
The status of the refund (e.g., "pending", "completed", "failed")
The date when the refund was processed
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/warranties/:id/refund' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"refund_amount": 299.99,
"refund_reason": "Product defect covered under warranty",
"refund_method": "credit_card"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyRefundMutation {
warrantyRefund(
id: "${warrantyId}",
refundAmount: ${refundAmount},
refundReason: "${refundReason}",
refundMethod: "${refundMethod}"
) {
warranty {
id,
status,
refund_id,
refund_amount,
refund_status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.refund({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
refund_amount: 299.99,
refund_reason: 'Product defect covered under warranty',
refund_method: 'credit_card'
});
```
```python Python theme={null}
warranties = stateset.warranties.refund({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'refund_amount': 299.99,
'refund_reason': 'Product defect covered under warranty',
'refund_method': 'credit_card'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.refund({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
refund_amount: 299.99,
refund_reason: 'Product defect covered under warranty',
refund_method: 'credit_card'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.refund({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
RefundAmount: 299.99,
RefundReason: 'Product defect covered under warranty',
RefundMethod: 'credit_card'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.refund({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
refundAmount: 299.99,
refundReason: 'Product defect covered under warranty',
refundMethod: 'credit_card'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->refund([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'refund_amount' => 299.99,
'refund_reason' => 'Product defect covered under warranty',
'refund_method' => 'credit_card'
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Refund(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
RefundAmount = 299.99,
RefundReason = 'Product defect covered under warranty',
RefundMethod = 'credit_card'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"refunded": true,
"refund_id": "ref_abc123xyz",
"refund_amount": 299.99,
"refund_status": "completed",
"refund_date": "2024-01-15T10:30:00Z",
"refund_reason": "Product defect covered under warranty",
"refund_method": "credit_card"
}
```
# Reject Warranty
Source: https://docs.stateset.com/api-reference/warranty/reject
POST https://api.stateset.com/v1/warranties/:id/reject
This endpoint rejects a warranty claim.
### Body
The ID provided in the data tab may be used to identify the warranty
The reason for rejecting the warranty claim
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty/:id/reject' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"reason": "Warranty period expired"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyRejectMutation {
warrantyReject(id: "${warrantyId}", reason: "${reason}") {
warranty {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.reject({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
reason: 'Warranty period expired'
});
```
```python Python theme={null}
warranties = stateset.warranties.reject({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'reason': 'Warranty period expired'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.reject({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
reason: 'Warranty period expired'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.reject({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
Reason: 'Warranty period expired'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.reject({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
reason: 'Warranty period expired'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->reject([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'reason' => 'Warranty period expired'
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Reject(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
Reason = 'Warranty period expired'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"rejected": true,
"reason": "Warranty period expired"
}
```
# Reopen Warranty
Source: https://docs.stateset.com/api-reference/warranty/reopen
POST https://api.stateset.com/v1/warranties/:id/reopen
This endpoint reopens a closed warranty.
### Body
The ID provided in the data tab may be used to identify the warranty
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty/:id/reopen' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyReopenMutation {
warrantyReopen(id: "${warrantyId}") {
warranty {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.reopen({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
warranties = stateset.warranties.reopen({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.reopen({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.reopen({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.reopen({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->reopen({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Reopen({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"reopened": true
}
```
# Repair Warranty Item
Source: https://docs.stateset.com/api-reference/warranty/repair
POST https://api.stateset.com/v1/warranties/:id/repair
This endpoint initiates a repair for a warranty claim.
### Body
The ID provided in the data tab may be used to identify the warranty
The type of repair needed (e.g., "hardware", "software", "cosmetic")
Detailed description of the repair needed
Where the repair will be performed (e.g., "authorized\_service\_center", "mail\_in", "on\_site")
Estimated cost of the repair (if applicable)
Whether pickup service is required for the item
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
The unique identifier for the repair ticket
The status of the repair (e.g., "scheduled", "in\_progress", "completed")
The location where the repair will be performed
The estimated completion date for the repair
URL to track the repair status
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/warranties/:id/repair' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"repair_type": "hardware",
"repair_description": "Screen replacement needed due to manufacturing defect",
"repair_location": "authorized_service_center",
"estimated_cost": 150.00,
"pickup_required": true
}'
```
```graphQL GraphQL theme={null}
mutation warrantyRepairMutation {
warrantyRepair(
id: "${warrantyId}",
repairType: "${repairType}",
repairDescription: "${repairDescription}",
repairLocation: "${repairLocation}",
estimatedCost: ${estimatedCost},
pickupRequired: ${pickupRequired}
) {
warranty {
id,
status,
repair_ticket_id,
repair_status,
estimated_completion
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.repair({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
repair_type: 'hardware',
repair_description: 'Screen replacement needed due to manufacturing defect',
repair_location: 'authorized_service_center',
estimated_cost: 150.00,
pickup_required: true
});
```
```python Python theme={null}
warranties = stateset.warranties.repair({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'repair_type': 'hardware',
'repair_description': 'Screen replacement needed due to manufacturing defect',
'repair_location': 'authorized_service_center',
'estimated_cost': 150.00,
'pickup_required': True
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.repair({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
repair_type: 'hardware',
repair_description: 'Screen replacement needed due to manufacturing defect',
repair_location: 'authorized_service_center',
estimated_cost: 150.00,
pickup_required: true
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.repair({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
RepairType: 'hardware',
RepairDescription: 'Screen replacement needed due to manufacturing defect',
RepairLocation: 'authorized_service_center',
EstimatedCost: 150.00,
PickupRequired: true
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.repair({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
repairType: 'hardware',
repairDescription: 'Screen replacement needed due to manufacturing defect',
repairLocation: 'authorized_service_center',
estimatedCost: 150.00,
pickupRequired: true
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->repair([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'repair_type' => 'hardware',
'repair_description' => 'Screen replacement needed due to manufacturing defect',
'repair_location' => 'authorized_service_center',
'estimated_cost' => 150.00,
'pickup_required' => true
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Repair(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
RepairType = 'hardware',
RepairDescription = 'Screen replacement needed due to manufacturing defect',
RepairLocation = 'authorized_service_center',
EstimatedCost = 150.00,
PickupRequired = true
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"repair_initiated": true,
"repair_ticket_id": "rpr_ticket_789xyz",
"repair_status": "scheduled",
"repair_type": "hardware",
"repair_location": "authorized_service_center",
"estimated_completion": "2024-01-25",
"repair_tracking_url": "https://repairs.stateset.com/track/rpr_ticket_789xyz",
"pickup_scheduled": "2024-01-16T14:00:00Z"
}
```
# Replace Warranty Item
Source: https://docs.stateset.com/api-reference/warranty/replace
POST https://api.stateset.com/v1/warranties/:id/replace
This endpoint processes a replacement for a warranty claim.
### Body
The ID provided in the data tab may be used to identify the warranty
The product ID of the replacement item
The reason for the replacement
The shipping address for the replacement item
Whether to use expedited shipping for the replacement
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
The order ID for the replacement item
The product ID of the replacement item
The status of the replacement (e.g., "pending", "shipped", "delivered")
The tracking number for the replacement shipment
The estimated delivery date for the replacement
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/warranties/:id/replace' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"replacement_product_id": "prod_xyz789",
"replacement_reason": "Manufacturing defect",
"shipping_address": {
"line1": "123 Main St",
"city": "New York",
"state": "NY",
"postal_code": "10001",
"country": "US"
},
"expedited_shipping": true
}'
```
```graphQL GraphQL theme={null}
mutation warrantyReplaceMutation {
warrantyReplace(
id: "${warrantyId}",
replacementProductId: "${replacementProductId}",
replacementReason: "${replacementReason}",
shippingAddress: ${shippingAddress},
expeditedShipping: ${expeditedShipping}
) {
warranty {
id,
status,
replacement_order_id,
replacement_status,
tracking_number
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.replace({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
replacement_product_id: 'prod_xyz789',
replacement_reason: 'Manufacturing defect',
shipping_address: {
line1: '123 Main St',
city: 'New York',
state: 'NY',
postal_code: '10001',
country: 'US'
},
expedited_shipping: true
});
```
```python Python theme={null}
warranties = stateset.warranties.replace({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'replacement_product_id': 'prod_xyz789',
'replacement_reason': 'Manufacturing defect',
'shipping_address': {
'line1': '123 Main St',
'city': 'New York',
'state': 'NY',
'postal_code': '10001',
'country': 'US'
},
'expedited_shipping': True
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.replace({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
replacement_product_id: 'prod_xyz789',
replacement_reason: 'Manufacturing defect',
shipping_address: {
line1: '123 Main St',
city: 'New York',
state: 'NY',
postal_code: '10001',
country: 'US'
},
expedited_shipping: true
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.replace({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
ReplacementProductID: 'prod_xyz789',
ReplacementReason: 'Manufacturing defect',
ShippingAddress: Address{
Line1: '123 Main St',
City: 'New York',
State: 'NY',
PostalCode: '10001',
Country: 'US'
},
ExpeditedShipping: true
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.replace({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
replacementProductId: 'prod_xyz789',
replacementReason: 'Manufacturing defect',
shippingAddress: {
line1: '123 Main St',
city: 'New York',
state: 'NY',
postalCode: '10001',
country: 'US'
},
expeditedShipping: true
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->replace([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'replacement_product_id' => 'prod_xyz789',
'replacement_reason' => 'Manufacturing defect',
'shipping_address' => [
'line1' => '123 Main St',
'city' => 'New York',
'state' => 'NY',
'postal_code' => '10001',
'country' => 'US'
],
'expedited_shipping' => true
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Replace(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
ReplacementProductId = 'prod_xyz789',
ReplacementReason = 'Manufacturing defect',
ShippingAddress = new {
Line1 = '123 Main St',
City = 'New York',
State = 'NY',
PostalCode = '10001',
Country = 'US'
},
ExpeditedShipping = true
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"replaced": true,
"replacement_order_id": "ord_repl_123abc",
"replacement_product_id": "prod_xyz789",
"replacement_status": "shipped",
"tracking_number": "1Z999AA10123456784",
"estimated_delivery": "2024-01-18",
"replacement_reason": "Manufacturing defect"
}
```
# Transfer Warranty
Source: https://docs.stateset.com/api-reference/warranty/transfer
POST https://api.stateset.com/v1/warranties/:id/transfer
This endpoint transfers a warranty to a new owner.
### Body
The ID provided in the data tab may be used to identify the warranty
The ID of the new owner
The email address of the new owner
The date of the warranty transfer
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
The ID of the previous owner
The ID of the new owner
The date when the warranty was transferred
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty/:id/transfer' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"new_owner_id": "usr_789xyz",
"new_owner_email": "newowner@example.com",
"transfer_date": "2024-01-15"
}'
```
```graphQL GraphQL theme={null}
mutation warrantyTransferMutation {
warrantyTransfer(id: "${warrantyId}", newOwnerId: "${newOwnerId}", newOwnerEmail: "${newOwnerEmail}", transferDate: "${transferDate}") {
warranty {
id,
previous_owner_id,
new_owner_id,
transfer_date
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const warranties = await stateset.warranties.transfer({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
new_owner_id: 'usr_789xyz',
new_owner_email: 'newowner@example.com',
transfer_date: '2024-01-15'
});
```
```python Python theme={null}
warranties = stateset.warranties.transfer({
'id': '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'new_owner_id': 'usr_789xyz',
'new_owner_email': 'newowner@example.com',
'transfer_date': '2024-01-15'
})
```
```ruby Ruby theme={null}
warranties = Stateset::Warranty.transfer({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
new_owner_id: 'usr_789xyz',
new_owner_email: 'newowner@example.com',
transfer_date: '2024-01-15'
})
```
```go Go theme={null}
warranties, err := stateset.Warranties.transfer({
ID: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
NewOwnerID: 'usr_789xyz',
NewOwnerEmail: 'newowner@example.com',
TransferDate: '2024-01-15'
})
```
```java Java theme={null}
Warranty warranties = stateset.Warranties.transfer({
id: '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
newOwnerId: 'usr_789xyz',
newOwnerEmail: 'newowner@example.com',
transferDate: '2024-01-15'
});
```
```php PHP theme={null}
$warranties = $stateset->warranties->transfer([
'id' => '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
'new_owner_id' => 'usr_789xyz',
'new_owner_email' => 'newowner@example.com',
'transfer_date' => '2024-01-15'
]);
```
```csharp C# theme={null}
var warranties = await stateset.Warranties.Transfer(new {
Id = '0901f083-aa1c-43c5-af5c-0a9d2fc64e30',
NewOwnerId = 'usr_789xyz',
NewOwnerEmail = 'newowner@example.com',
TransferDate = '2024-01-15'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "warranty",
"transferred": true,
"previous_owner_id": "usr_123abc",
"new_owner_id": "usr_789xyz",
"new_owner_email": "newowner@example.com",
"transfer_date": "2024-01-15"
}
```
# Update Warranty
Source: https://docs.stateset.com/api-reference/warranty/update
PUT https://api.stateset.com/v1/warranty
This endpoint updates an existing warranty.
### Body
This is the id of the warranty.
The warranty object
### Response
This is the id of the warranty.
Indicates whether any action is needed for the warranty.
Indicates if advanced replacement is available for the warranty.
The monetary amount associated with the warranty.
Describes the condition of the item or situation.
Date and time when the condition was recorded or observed.
Country associated with the warranty entry.
Date and time when the warranty entry was created.
Email address of the customer associated with the warranty.
Unique identifier for the customer associated with the warranty.
Brief description or additional details about the warranty.
Name or identifier of the person who entered the warranty.
Issue or problem associated with the warranty.
Indicates whether the warranty matches the specified conditions.
Date and time when the order associated with the warranty was placed.
Unique identifier for the order associated with the warranty.
Category or reason associated with the warranty.
Color of the replacement item for the warranty.
Model of the replacement item for the warranty.
Indicates if a replacement order has been created for the warranty.
Condition as reported by the customer or user.
Date and time when a specific request was made for the warranty.
Return Merchandise Authorization (RMA) number for the warranty.
Serial number obtained through scanning for the warranty.
Unique serial number associated with the item in the warranty.
ShipStation order ID associated with the warranty.
Date and time when the item was shipped or dispatched.
Single Sign-On (SSO) ID associated with the warranty.
Current status or state of the warranty.
Stripe invoice ID associated with the warranty.
The amount of tax refunded for the warranty.
The total amount refunded for the warranty.
Tracking number associated with the shipment for the warranty.
Date and time when the item was received in the warehouse.
This is an array of warranty line items.
The monetary amount associated with the warranty line item.
Describes the condition of the replaced item.
Indicates whether the shipping rate is a flat rate.
Unique identifier for the warranty line item.
Name or description of the warranty line item.
The price of the warranty line item.
Unique identifier for the warranty associated with the line item.
Unique serial number associated with the warranty item.
Stock Keeping Unit (SKU) of the replaced item.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"user_group_id": "example_1",
"name": "Example 1",
"mapping": {"40": "213", "134": "386"},
"properties": {"filterValue": "value"}
}'
```
```graphQL GraphQL theme={null}
mutation UpdateWarranty(
$ticket_id: String
$warranty: warranties_set_input!
) {
update_warranties (
where: { id : { _eq: $ticket_id }}
_set: $warranty
) {
returning {
id
order_id
serial_number
customer_id
description
status
tracking_number
zendesk_number
action_needed
issue
shipped_date
requested_date
enteredBy
customerEmail
rma
country
}
}
};
```
```js Node.js theme={null}
const warranties = await stateset.warranties.update({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
warranties = stateset.Warranty.modify(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```ruby Ruby theme={null}
warranties = Stateset::Warranties.update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```go Go theme={null}
warranties, err := stateset.Warranties.Update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```java Java theme={null}
Warranties warranties = stateset.warranties.update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```php PHP theme={null}
$warranties = $stateset->warranties->update(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```json Response theme={null}
{
"warranties": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"created_date": "2023-06-28T19:34:59.189838+00:00",
"amount": null,
"action_needed": null,
"condition": null,
"customerEmail": "customer@gmail.com",
"customer_id": null,
"description": null,
"enteredBy": null,
"flat_rate_shipping": null,
"order_date": null,
"order_id": "524213310335630636",
"reason_category": null,
"reported_condition": null,
"requested_date": null,
"rma": "#1014-R5",
"serial_number": null,
"shipped_date": null,
"status": "RCV",
"tax_refunded": null,
"total_refunded": null,
"tracking_number": null,
"warranty_line_items": []
},
]
}
```
# Create Warranty Line Item
Source: https://docs.stateset.com/api-reference/warrantylineitem/create
POST https://api.stateset.com/v1/warranty_line_item
This endpoint creates a new warranty line item.
### Body
This is the id of the warranty line item.
This is the sku of the warranty line item.
This is the name of the warranty line item.
This is the price of the warranty line item.
This is the condition of the warranty line item.
This is the serial number of the warranty line item.
This is the amount of the warranty line item.
This is the warranty id of the warranty line item.
This is the created at of the warranty line item.
This is the updated at of the warranty line item.
### Response
This is the id of the warranty line item.
This is the amount of the warranty line item.
This is the condition of the warranty line item.
This is the flat rate shipping of the warranty line item.
This is the name of the warranty line item.
This is the price of the warranty line item.
This is the id of the warranty associated with the line item.
This is the serial number of the warranty line item.
This is the sku of the warranty line item.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/warranty_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"warranty_line_item": {
"sku": "123456789",
"name": "Warranty Item",
"price": "100.00",
"condition": "New",
"serial_number": "123456789",
"amount": "110.00",
"warranty_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}
}'
```
```graphQL GraphQL theme={null}
mutation addWarrantyLineItem($warranty_line_item: warranty_line_items_insert_input!) {
insert_warranty_line_items(objects: [$warranty_line_item]) {
returning {
id
sku
name
price
condition
serial_number
amount
warranty_id
}
}
}
```
```js Node.js theme={null}
const created = await stateset.warrantyItems.create(
'wi_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
created = stateset.warrantyItems.create(
'wi_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
created = Stateset::WarrantyItems.create(
'wi_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$created = $stateset->warrantyItems->create(
'wi_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
WarrantyItems , err := stateset.WarrantyItems.Create(
'wi_ODkRWQtx9NVsRX'
)
```
```java Java theme={null}
WarrantyItems created = stateset.warrantyItems.create(
'wi_ODkRWQtx9NVsRX'
);
```
```cs C# theme={null}
var created = stateset.WarrantyItems.Create(
'wi_ODkRWQtx9NVsRX'
);
```
```json Response theme={null}
{
"data": {
"warranty_line_items": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "123456789",
"name": "Warranty Item",
"price": "100.00",
"condition": "New",
"tax_refunded": false,
"flat_rate_shipping": "10.00",
"warranty_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"serial_number": "123456789",
"amount": "110.00",
"image_1": "https://www.example.com/image1.jpg",
"image_2": "https://www.example.com/image2.jpg",
"image_3": "https://www.example.com/image3.jpg",
"match": "123456789"
}
]
}
}
```
# Delete Warranty Line Item
Source: https://docs.stateset.com/api-reference/warrantylineitem/delete
DELETE https://api.stateset.com/v1/warranty_line_item
This endpoint deletes an existing warranty line item.
### Body
The id of the warranty line item to delete.
### Response
The ID provided in the data tab may be used to identify the warranty
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/warranty_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```js Node.js theme={null}
const warrantyLineItem = await stateset.warrantyItem.del({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```graphQL GraphQL theme={null}
mutation deleteWarrantyLineItem ($warranty_line_item_id: uuid!) {
delete_warranty_line_items(where: {id: {_eq: $warranty_line_item_id}}) {
affected_rows
}
}
```
```python Python theme={null}
warranty_line_item = stateset.warranty_line_item.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```ruby Ruby theme={null}
warranty_line_item = Stateset::WarrantyLineItem.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```php PHP theme={null}
$warranty_line_item = Stateset\WarrantyLineItem::del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```go Golang theme={null}
warrantyLineItem, err := stateset.WarrantyLineItem.Delete(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```java Java theme={null}
WarrantyLineItem warrantyLineItem = stateset.warrantyLineItem.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```csharp C# theme={null}
var warrantyLineItem = await Stateset.WarrantyLineItem.Delete(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```json Response theme={null}
{
"id": "wli_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "warranty_line_item",
"deleted": true
}
```
# Get Warranty Line Item
Source: https://docs.stateset.com/api-reference/warrantylineitem/get
GET https://api.stateset.com/v1/warranty_line_item
This endpoint gets or creates a new warranty line item.
### Body
This is the id of the warranty line item.
### Response
This is the id of the warranty line item.
This is the amount of the warranty line item.
This is the condition of the warranty line item.
This is the flat rate shipping of the warranty line item.
This is the name of the warranty line item.
This is the price of the warranty line item.
This is the id of the warranty associated with the line item.
This is the serial number of the warranty line item.
This is the sku of the warranty line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/warranty_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}'
```
```graphQL GraphQL theme={null}
query getMyWarrantyData($last_received_id: String, $last_received_ts: String, $first_received_date: date, $id: String) {
warranty_line_items(where: {warranty_id: {_eq: $id}}) {
id
sku
name
price
condition
tax_refunded
flat_rate_shipping
warranty_id
serial_number
amount
image_1
image_2
image_3
match
}
}`
```
```javascript Node.js theme={null}
const warranties = await stateset.warrantyItem.retrieve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
warranties = stateset.warrantylineitem.retrieve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
warranties = Stateset::WarrantyItem.retrieve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```php PHP theme={null}
$warranties = $stateset->warrantyitem->retrieve([
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
]);
```
```go Go theme={null}
WarrantyLineItem , err := stateset.WarrantyItem.Retrieve(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```java Java theme={null}
WarrantyItem[] warrantyitem = stateset.warrantyitem.retrieve({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"data": {
"warranty_line_items": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "123456789",
"name": "Warranty Item",
"price": "100.00",
"condition": "New",
"tax_refunded": false,
"flat_rate_shipping": "10.00",
"warranty_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"serial_number": "123456789",
"amount": "110.00",
"image_1": "https://www.example.com/image1.jpg",
"image_2": "https://www.example.com/image2.jpg",
"image_3": "https://www.example.com/image3.jpg",
"match": "123456789"
}
]
}
}
```
# Update Warranty Line Item
Source: https://docs.stateset.com/api-reference/warrantylineitem/update
PUT https://api.stateset.com/v1/warranty_line_item
This endpoint updates an existing warranty line item.
### Body
This is the id of the warranty line item.
This is the sku of the warranty line item.
This is the name of the warranty line item.
This is the price of the warranty line item.
This is the condition of the warranty line item.
This is the serial number of the warranty line item.
This is the amount of the warranty line item.
This is the warranty id of the warranty line item.
This is the created at of the warranty line item.
This is the updated at of the warranty line item.
### Response
This is the id of the warranty line item.
This is the amount of the warranty line item.
This is the condition of the warranty line item.
This is the flat rate shipping of the warranty line item.
This is the name of the warranty line item.
This is the price of the warranty line item.
This is the id of the warranty associated with the line item.
This is the serial number of the warranty line item.
This is the sku of the warranty line item.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/warranty_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
}'
```
```graphQL GraphQL theme={null}
mutation (
$id: uuid
$warranty_line_item: warranty_line_items_set_input!
) {
update_warranty_line_items (
where: { id : { _eq: $id }}
_set: $warranty_line_item
) {
returning {
id
sku
name
price
tax_refunded
condition
amount
flat_rate_shipping
}
}
}`
```
```js Node.js theme={null}
const updated = await stateset.warrantyItems.update(
'wi_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
updated = stateset.WarrantyItem.modify(
'wi_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
updated = stateset.warrantyItems.update(
'wi_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$updated = $stateset->warrantyItems->update(
'wi_ODkRWQtx9NVsRX'
);
```
```go Golang theme={null}
WarrantyItems , err := stateset.WarrantyItems.Update(
"wi_ODkRWQtx9NVsRX",
)
```
```csharp C# theme={null}
var updated = stateset.WarrantyItems.Update(
"wi_ODkRWQtx9NVsRX"
);
```
```java Java theme={null}
WarrantyItems updated = stateset.warrantyItems.update(
"wi_ODkRWQtx9NVsRX"
);
```
```json Response theme={null}
{
"data": {
"warranty_line_items": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"sku": "123456789",
"name": "Warranty Item",
"price": "100.00",
"condition": "New",
"tax_refunded": false,
"flat_rate_shipping": "10.00",
"warranty_id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"serial_number": "123456789",
"amount": "110.00",
"image_1": "https://www.example.com/image1.jpg",
"image_2": "https://www.example.com/image2.jpg",
"image_3": "https://www.example.com/image3.jpg",
"match": "123456789"
}
]
}
}
```
# Webhooks
Source: https://docs.stateset.com/api-reference/webhooks
Real-time event notifications for your StateSet integration
Webhooks allow your application to receive real-time notifications when events occur in StateSet, eliminating the need for polling.
## Overview
StateSet webhooks provide real-time event notifications delivered via HTTPS POST requests to your configured endpoints. Each webhook payload includes comprehensive event data and is secured with HMAC signatures.
### Key Features
* 🔄 **Automatic retries** with exponential backoff
* 🔐 **Secure signatures** using HMAC-SHA256
* 📊 **Event versioning** for backward compatibility
* 🎯 **Granular event selection** - subscribe only to events you need
* 📝 **Detailed payloads** with full resource data
* 🔍 **Event replay** for missed or failed deliveries
## Setting Up Webhooks
Navigate to **Dashboard → Settings → Webhooks** and click **Add Endpoint**
* Enter your HTTPS endpoint URL
* Select events to subscribe to
* Copy the signing secret for verification
Create an endpoint that:
* Accepts POST requests
* Verifies signatures
* Processes events asynchronously
* Returns 2xx status quickly
Use the webhook simulator to send test events and verify your implementation
## Webhook Security
### Signature Verification
All webhooks include a `Stateset-Signature` header for verification:
```javascript Node.js theme={null}
const crypto = require('crypto');
const winston = require('winston');
const logger = winston.createLogger({
level: process.env.LOG_LEVEL || 'info',
transports: [new winston.transports.Console()]
});
class WebhookVerifier {
constructor(secret) {
this.secret = secret;
}
verify(payload, signatureHeader) {
// Parse signature header
// Format: "t=timestamp v1=signature1 v1=signature2"
const elements = signatureHeader.split(' ');
const timestamp = elements.find(e => e.startsWith('t=')).slice(2);
const signatures = elements
.filter(e => e.startsWith('v1='))
.map(e => e.slice(3));
// Check timestamp is recent (5 minute window)
const currentTime = Math.floor(Date.now() / 1000);
const timestampAge = currentTime - parseInt(timestamp);
if (timestampAge > 300) {
throw new Error('Webhook timestamp too old');
}
if (timestampAge < -300) {
throw new Error('Webhook timestamp too far in future');
}
// Compute expected signature
const signedPayload = `${timestamp}.${payload}`;
const expectedSignature = crypto
.createHmac('sha256', this.secret)
.update(signedPayload)
.digest('hex');
// Timing-safe comparison
const valid = signatures.some(sig =>
crypto.timingSafeEqual(
Buffer.from(sig),
Buffer.from(expectedSignature)
)
);
if (!valid) {
throw new Error('Invalid webhook signature');
}
return {
timestamp: parseInt(timestamp),
verified: true
};
}
}
// Express.js implementation
app.post('/webhooks/stateset',
express.raw({ type: 'application/json' }),
(req, res) => {
const verifier = new WebhookVerifier(process.env.WEBHOOK_SECRET);
try {
verifier.verify(
req.body.toString(),
req.headers['stateset-signature']
);
const event = JSON.parse(req.body);
processWebhookEvent(event);
res.status(200).json({ received: true });
} catch (error) {
logger.error('Webhook verification failed', { message: error.message });
res.status(401).json({ error: 'Verification failed' });
}
}
);
```
```python Python theme={null}
import hmac
import hashlib
import time
import json
class WebhookVerifier:
def __init__(self, secret):
self.secret = secret
def verify(self, payload, signature_header):
# Parse signature header
elements = signature_header.split(' ')
timestamp = next(e[2:] for e in elements if e.startswith('t='))
signatures = [e[3:] for e in elements if e.startswith('v1=')]
# Check timestamp is recent (5 minute window)
current_time = int(time.time())
timestamp_age = current_time - int(timestamp)
if timestamp_age > 300:
raise ValueError('Webhook timestamp too old')
if timestamp_age < -300:
raise ValueError('Webhook timestamp too far in future')
# Compute expected signature
signed_payload = f"{timestamp}.{payload}"
expected_signature = hmac.new(
self.secret.encode(),
signed_payload.encode(),
hashlib.sha256
).hexdigest()
# Verify signature
if expected_signature not in signatures:
raise ValueError('Invalid webhook signature')
return {
'timestamp': int(timestamp),
'verified': True
}
# Flask implementation
from flask import Flask, request, jsonify
app = Flask(__name__)
verifier = WebhookVerifier(os.getenv('WEBHOOK_SECRET'))
@app.route('/webhooks/stateset', methods=['POST'])
def handle_webhook():
try:
payload = request.get_data(as_text=True)
signature = request.headers.get('Stateset-Signature')
verifier.verify(payload, signature)
event = json.loads(payload)
process_webhook_event(event)
return jsonify({'received': True}), 200
except Exception as e:
print(f'Webhook verification failed: {e}')
return jsonify({'error': 'Verification failed'}), 401
```
### Security Best Practices
**Critical Security Requirements:**
* Always verify webhook signatures
* Use HTTPS endpoints only
* Store signing secrets securely
* Implement idempotency to handle duplicate events
* Process events asynchronously to avoid timeouts
## Webhook Payload Structure
All webhook events follow a consistent structure:
```json theme={null}
{
"id": "evt_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "event",
"api_version": "2024-01-01",
"created": 1704067200,
"type": "order.created",
"data": {
"object": {
// Full resource object
},
"previous_attributes": {
// For update events, previous values of changed fields
}
},
"request": {
"id": "req_abc123",
"idempotency_key": "order-123"
},
"metadata": {
"workspace_id": "ws_123",
"user_id": "usr_456",
"source": "api"
}
}
```
### Payload Fields
| Field | Type | Description |
| -------------------------- | ------- | ----------------------------------- |
| `id` | string | Unique event identifier |
| `object` | string | Always "event" |
| `api_version` | string | API version used for the event |
| `created` | integer | Unix timestamp of event creation |
| `type` | string | Event type (e.g., "order.created") |
| `data.object` | object | Full resource data |
| `data.previous_attributes` | object | Changed fields (update events only) |
| `request.id` | string | Original request ID |
| `request.idempotency_key` | string | Idempotency key if provided |
| `metadata` | object | Additional context |
## Event Types
### Order Events
**Triggered when:** A new order is created
```json theme={null}
{
"type": "order.created",
"data": {
"object": {
"id": "ord_123",
"object": "order",
"status": "pending",
"customer": {...},
"items": [...],
"totals": {...},
"created_at": "2024-01-15T10:30:00Z"
}
}
}
```
**Triggered when:** Order details are modified
```json theme={null}
{
"type": "order.updated",
"data": {
"object": {
"id": "ord_123",
"status": "processing",
// Full updated order
},
"previous_attributes": {
"status": "pending",
"updated_at": "2024-01-15T10:00:00Z"
}
}
}
```
**Triggered when:** Order is cancelled
```json theme={null}
{
"type": "order.cancelled",
"data": {
"object": {
"id": "ord_123",
"status": "cancelled",
"cancelled_at": "2024-01-15T11:00:00Z",
"cancellation_reason": "customer_request"
}
}
}
```
**Triggered when:** Order fulfillment is complete
```json theme={null}
{
"type": "order.fulfilled",
"data": {
"object": {
"id": "ord_123",
"status": "fulfilled",
"fulfillment": {
"tracking_number": "1Z999AA10123456784",
"carrier": "ups",
"shipped_at": "2024-01-15T14:00:00Z"
}
}
}
}
```
### Return Events
**Triggered when:** Return is initiated
```json theme={null}
{
"type": "return.created",
"data": {
"object": {
"id": "ret_456",
"order_id": "ord_123",
"status": "pending",
"items": [...],
"reason": "defective",
"rma_number": "RMA-2024-001"
}
}
}
```
**Triggered when:** Return is approved
```json theme={null}
{
"type": "return.approved",
"data": {
"object": {
"id": "ret_456",
"status": "approved",
"approved_at": "2024-01-16T09:00:00Z",
"shipping_label": {
"carrier": "fedex",
"tracking_number": "123456789",
"label_url": "https://..."
}
}
}
}
```
**Triggered when:** Returned items are received
```json theme={null}
{
"type": "return.received",
"data": {
"object": {
"id": "ret_456",
"status": "received",
"received_at": "2024-01-20T10:00:00Z",
"inspection": {
"condition": "good",
"notes": "Minor wear, acceptable for resale"
}
}
}
}
```
### Customer Events
**Triggered when:** New customer registers
```json theme={null}
{
"type": "customer.created",
"data": {
"object": {
"id": "cus_789",
"email": "customer@example.com",
"first_name": "John",
"last_name": "Doe",
"created_at": "2024-01-15T08:00:00Z"
}
}
}
```
**Triggered when:** Customer profile is updated
```json theme={null}
{
"type": "customer.updated",
"data": {
"object": {
"id": "cus_789",
"email": "newemail@example.com",
// Full updated customer
},
"previous_attributes": {
"email": "oldemail@example.com",
"updated_at": "2024-01-14T10:00:00Z"
}
}
}
```
### Inventory Events
**Triggered when:** Stock falls below threshold
```json theme={null}
{
"type": "inventory.low_stock",
"data": {
"object": {
"sku": "WIDGET-001",
"available": 5,
"threshold": 10,
"warehouse_id": "wh_123"
}
}
}
```
**Triggered when:** Item goes out of stock
```json theme={null}
{
"type": "inventory.out_of_stock",
"data": {
"object": {
"sku": "WIDGET-001",
"available": 0,
"backorder_enabled": true,
"restock_date": "2024-01-25T00:00:00Z"
}
}
}
```
## Handling Webhooks
### Best Practices Implementation
```javascript theme={null}
const winston = require('winston');
const logger = winston.createLogger({
level: process.env.LOG_LEVEL || 'info',
transports: [new winston.transports.Console()]
});
class WebhookProcessor {
constructor() {
this.queue = new Queue('webhooks');
this.processed = new Set();
}
async handle(event) {
// 1. Check for duplicate processing
if (this.processed.has(event.id)) {
logger.info('Event already processed', { eventId: event.id });
return { status: 'duplicate' };
}
// 2. Add to processing set
this.processed.add(event.id);
// 3. Queue for async processing
await this.queue.add('process-webhook', {
event,
receivedAt: new Date().toISOString()
});
// 4. Return quickly
return { status: 'queued' };
}
async process(job) {
const { event } = job.data;
try {
// 5. Route to appropriate handler
const handler = this.getHandler(event.type);
if (!handler) {
logger.warn('No handler for event type', { eventType: event.type });
return;
}
// 6. Process with retry logic
await this.withRetry(() => handler(event.data.object));
// 7. Mark as completed
await this.markProcessed(event.id);
} catch (error) {
// 8. Handle errors
logger.error('Failed to process webhook', {
eventId: event.id,
message: error.message
});
// 9. Retry or dead letter
if (job.attemptsMade < 3) {
throw error; // Retry
} else {
await this.sendToDeadLetter(event, error);
}
}
}
getHandler(eventType) {
const handlers = {
'order.created': this.handleOrderCreated,
'order.updated': this.handleOrderUpdated,
'order.cancelled': this.handleOrderCancelled,
'return.created': this.handleReturnCreated,
'customer.created': this.handleCustomerCreated,
'inventory.low_stock': this.handleLowStock,
// Add more handlers
};
return handlers[eventType];
}
async handleOrderCreated(order) {
// Send confirmation email
await emailService.sendOrderConfirmation(order);
// Update inventory
await inventoryService.allocate(order.items);
// Sync with ERP
await erpService.createOrder(order);
// Analytics
await analytics.track('order_created', {
order_id: order.id,
value: order.totals.total,
customer_id: order.customer.id
});
}
async handleReturnCreated(return) {
// Generate return label
const label = await shippingService.createReturnLabel(return);
// Email label to customer
await emailService.sendReturnLabel(return, label);
// Create support ticket
await supportService.createTicket({
type: 'return',
return_id: return.id,
customer_email: return.customer_email
});
}
async withRetry(fn, maxRetries = 3) {
for (let i = 0; i < maxRetries; i++) {
try {
return await fn();
} catch (error) {
if (i === maxRetries - 1) throw error;
await new Promise(r => setTimeout(r, 1000 * Math.pow(2, i)));
}
}
}
}
```
### Idempotency
Ensure your webhook handler is idempotent to safely handle duplicate deliveries:
```javascript theme={null}
class IdempotentWebhookHandler {
constructor(redis) {
this.redis = redis;
}
async handle(event) {
const key = `webhook:${event.id}`;
const lockKey = `${key}:lock`;
// Try to acquire lock
const acquired = await this.redis.set(
lockKey,
'1',
'NX',
'EX',
30 // 30 second lock
);
if (!acquired) {
// Another process is handling this event
return { status: 'processing' };
}
try {
// Check if already processed
const processed = await this.redis.get(key);
if (processed) {
return JSON.parse(processed);
}
// Process event
const result = await this.processEvent(event);
// Cache result
await this.redis.setex(
key,
86400, // 24 hour TTL
JSON.stringify(result)
);
return result;
} finally {
// Release lock
await this.redis.del(lockKey);
}
}
}
```
## Retry Logic
StateSet automatically retries failed webhook deliveries with exponential backoff:
### Retry Schedule
| Attempt | Delay | Total Time |
| ------- | ---------- | ------------ |
| 1 | Immediate | 0 seconds |
| 2 | 10 seconds | 10 seconds |
| 3 | 1 minute | 1.2 minutes |
| 4 | 5 minutes | 6.2 minutes |
| 5 | 30 minutes | 36.2 minutes |
| 6 | 2 hours | 2.6 hours |
| 7 | 6 hours | 8.6 hours |
| 8 | 24 hours | 32.6 hours |
After 8 failed attempts, the webhook is marked as failed and won't be retried automatically.
### Handling Failures
Your endpoint should:
* Return `2xx` status for successful processing
* Return `4xx` for permanent failures (won't retry)
* Return `5xx` for temporary failures (will retry)
```javascript theme={null}
app.post('/webhook', async (req, res) => {
try {
await processWebhook(req.body);
res.status(200).json({ success: true });
} catch (error) {
if (error.type === 'VALIDATION_ERROR') {
// Permanent failure - don't retry
res.status(400).json({ error: error.message });
} else {
// Temporary failure - retry
res.status(500).json({ error: 'Processing failed' });
}
}
});
```
## Testing Webhooks
### Webhook Simulator
Test your webhook endpoint using our simulator:
```bash theme={null}
curl -X POST https://api.stateset.com/v1/webhooks/simulate \
-H "Authorization: Bearer sk_test_..." \
-H "Content-Type: application/json" \
-d '{
"event_type": "order.created",
"endpoint_url": "https://your-app.com/webhooks",
"custom_data": {
"order_id": "test_123"
}
}'
```
### Local Development
Use ngrok or similar tools to test webhooks locally:
```bash theme={null}
# Start your local server
npm run dev
# In another terminal, create tunnel
ngrok http 3000
# Configure webhook endpoint in StateSet dashboard
# https://abc123.ngrok.io/webhooks
```
### Test Event Payloads
```json Order Created Test theme={null}
{
"id": "evt_test_123",
"type": "order.created",
"data": {
"object": {
"id": "ord_test_123",
"status": "pending",
"customer": {
"email": "test@example.com"
},
"items": [
{
"sku": "TEST-001",
"quantity": 1,
"price": 1000
}
],
"totals": {
"subtotal": 1000,
"tax": 80,
"total": 1080
}
}
}
}
```
```json Return Created Test theme={null}
{
"id": "evt_test_456",
"type": "return.created",
"data": {
"object": {
"id": "ret_test_456",
"order_id": "ord_test_123",
"status": "pending",
"items": [
{
"sku": "TEST-001",
"quantity": 1,
"reason": "defective"
}
],
"rma_number": "RMA-TEST-001"
}
}
}
```
## Webhook Management API
Programmatically manage webhooks:
```javascript theme={null}
// List webhook endpoints
const endpoints = await stateset.webhookEndpoints.list();
// Create webhook endpoint
const endpoint = await stateset.webhookEndpoints.create({
url: 'https://your-app.com/webhooks',
events: [
'order.created',
'order.updated',
'return.created'
],
description: 'Production webhook endpoint',
metadata: {
environment: 'production'
}
});
// Update webhook endpoint
await stateset.webhookEndpoints.update(endpoint.id, {
events: [...endpoint.events, 'customer.created']
});
// Delete webhook endpoint
await stateset.webhookEndpoints.delete(endpoint.id);
// Retrieve endpoint secret
const secret = await stateset.webhookEndpoints.getSecret(endpoint.id);
```
## Monitoring and Debugging
### Webhook Logs
View webhook delivery attempts in the dashboard:
```javascript theme={null}
// Assume a structured logger is available as `logger`
// Get webhook event logs
const logs = await stateset.webhookEvents.list({
endpoint_id: 'we_123',
limit: 100
});
logs.data.forEach(log => {
logger.info('Webhook event log', {
event_id: log.event_id,
status: log.status,
attempts: log.attempts,
last_error: log.last_error,
next_retry: log.next_retry_at
});
});
// Retry failed webhook
await stateset.webhookEvents.retry('evt_failed_123');
```
### Metrics and Alerts
Monitor webhook health:
```javascript theme={null}
class WebhookMonitor {
trackDelivery(event, success, duration) {
metrics.increment('webhooks.delivered', {
event_type: event.type,
success: success
});
metrics.histogram('webhooks.duration', duration, {
event_type: event.type
});
if (!success) {
this.alertOnFailure(event);
}
}
alertOnFailure(event) {
if (this.getFailureRate() > 0.05) { // 5% failure rate
alerts.send({
severity: 'high',
message: 'High webhook failure rate detected',
details: {
rate: this.getFailureRate(),
event_type: event.type
}
});
}
}
}
```
## FAQ
Events may arrive out of order. Use the `created` timestamp and resource state to handle this:
```javascript theme={null}
if (event.created < lastProcessedTimestamp) {
// This is an old event, check if it should be processed
const currentResource = await stateset.orders.get(event.data.object.id);
if (currentResource.updated_at > event.created) {
// Skip this event, we have newer data
return;
}
}
```
StateSet will retry failed deliveries for up to 3 days with exponential backoff. You can also:
* Manually retry failed events from the dashboard
* Use the Event API to fetch missed events
* Implement webhook replay for recovery
Yes, you can configure webhook endpoints to filter events based on metadata:
```javascript theme={null}
const endpoint = await stateset.webhookEndpoints.create({
url: 'https://your-app.com/webhooks',
events: ['order.created'],
filters: {
'metadata.channel': 'online',
'metadata.region': 'us-west'
}
});
```
Use our test signature generator:
```bash theme={null}
curl https://api.stateset.com/v1/webhooks/test-signature \
-H "Authorization: Bearer sk_test_..." \
-d payload='{"test": true}' \
-d secret='whsec_test_...'
```
## Related Resources
* [Webhook Events Reference](/api-reference/events) - Complete list of events
* [Security Best Practices](/api-reference/security) - Security guidelines
* [API Error Handling](/api-reference/errors) - Error codes and handling
* [Event Replay API](/api-reference/event-replay) - Replay missed events
***
**Need help?** Contact [api-support@stateset.com](mailto:api-support@stateset.com) or visit our [Discord community](https://discord.gg/VfcaqgZywq).
# Create Wholesale Order Line Item
Source: https://docs.stateset.com/api-reference/wholesaleorderlineitem/create
Create a wholesale order line item.
# Create Wholesale Order Line Item
Use this endpoint to create a wholesale order line item.
# Delete Wholesale Order Line Item
Source: https://docs.stateset.com/api-reference/wholesaleorderlineitem/delete
Delete a wholesale order line item.
# Delete Wholesale Order Line Item
Use this endpoint to delete a wholesale order line item.
# Get Wholesale Order Line Item
Source: https://docs.stateset.com/api-reference/wholesaleorderlineitem/get
Retrieve a wholesale order line item by ID.
# Get Wholesale Order Line Item
Use this endpoint to fetch a wholesale order line item by ID.
# List Wholesale Order Line Items
Source: https://docs.stateset.com/api-reference/wholesaleorderlineitem/list
GET https://api.stateset.com/v1/wholesale_order_line_item/list
This endpoint list wholesale order line items.
### Body
This is the limit of the wholesale orders.
This is the offset of the wholesale orders.
This is the order direction of the wholesale orders.
### Response
The Id of the wholesale order line item
The Id of the product
The name of the product
The brand of the product
The quantity of the product
The unit of the product
The date the wholesale order line item was last updated
The Id of the wholesale order
The date the wholesale order line item was created
The brand of the product
The price of the product
Indicates whether the line item is included in the export
The class of the product
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/wholesale_order_line_item/list' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "asc"
}'
```
# Update Wholesale Order Line Item
Source: https://docs.stateset.com/api-reference/wholesaleorderlineitem/update
Update a wholesale order line item.
# Update Wholesale Order Line Item
Use this endpoint to update a wholesale order line item.
# Create Wholesale Order
Source: https://docs.stateset.com/api-reference/wholesaleorders/create
POST https://api.stateset.com/v1/wholesale_orders
This endpoint creates a new wholesale order
### Body
The Id of the wholesale order
The name of the wholesale order
The order number of the wholesale order
The date the wholesale order was created
The date the wholesale order was last updated
The financial status of the wholesale order
The fulfillment status of the wholesale order
The imported status of the wholesale order
The delivery date of the wholesale order
The delivery address of the wholesale order
Location or site where the work order is applicable
Memo or additional notes related to the work order
The date the wholesale order was imported
The customer number of the wholesale order
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
A message indicating the result of the call.
The wholesale order object that was created.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/wholesale_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "wo_123",
"name": "123",
"order_number": "123",
"created_date": "2021-01-01T00:00:00.000Z",
"updated_date": "2021-01-01T00:00:00.000Z",
"order_financial_status": "123",
"order_fulfillment_status": "123",
"order_imported_status": "123",
"delivery_date": "2021-01-01T00:00:00.000Z",
"delivery_address": "123",
"location": "123",
"memo": "123",
"imported_date": "2021-01-01T00:00:00.000Z",
"customer_number": "123"
}'
```
```json Response theme={null}
{
"success": 1,
"message": "Wholesale Order created successfully",
"data": {
"id": "wo_123",
"name": "123",
"order_number": "123",
"created_date": "2021-01-01T00:00:00.000Z",
"updated_date": "2021-01-01T00:00:00.000Z",
"order_financial_status": "123",
"order_fulfillment_status": "123",
"order_imported_status": "123",
"delivery_date": "2021-01-01T00:00:00.000Z",
"delivery_address": "123",
"location": "123",
"memo": "123",
"imported_date": "2021-01-01T00:00:00.000Z",
"customer_number": "123"
}
}
```
# Delete Wholesale Order
Source: https://docs.stateset.com/api-reference/wholesaleorders/delete
DELETE https://api.stateset.com/v1/wholesale_orders/:id
This endpoint deletes an existing wholesale order.
### Body
The id of the wholesale order to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/wholesale_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "wo_ODkRWQtx9NVsRX"
}'
```
```json Response theme={null}
{
"id": "wo_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "wholesale_order",
"deleted": true
}
```
# Get Wholesale Order
Source: https://docs.stateset.com/api-reference/wholesaleorders/get
Retrieve a wholesale order by ID.
# Get Wholesale Order
Use this endpoint to fetch a wholesale order by ID.
# List Wholesale Orders
Source: https://docs.stateset.com/api-reference/wholesaleorders/list
GET https://api.stateset.com/v1/wholesale_order/list
This endpoint list wholesale orders.
### Body
This is the limit of the wholesale orders.
This is the offset of the wholesale orders.
This is the order direction of the wholesale orders.
### Response
The Id of the wholesale order
The name of the wholesale order
The order number of the wholesale order
The date the wholesale order was created
The date the wholesale order was last updated
The financial status of the wholesale order
The fulfillment status of the wholesale order
The imported status of the wholesale order
The delivery date of the wholesale order
The delivery address of the wholesale order
Location or site where the work order is applicable
Memo or additional notes related to the work order
The date the wholesale order was imported
The customer number of the wholesale order
The email of the buyer
Message from the buyer
SLA time for order cancellation
Reason for order cancellation
Who initiated the cancellation
Type of fulfillment for the order
Type of delivery for the order
Whether the order is Cash on Delivery
Whether this is a replacement order
Note from the seller
Current status of the order
Tracking number for the order
ID of the warehouse fulfilling the order
Unique identifier for the line item
# Update Wholesale Order
Source: https://docs.stateset.com/api-reference/wholesaleorders/update
PUT https://api.stateset.com/v1/wholesale_orders
This endpoint updates a wholesale order
### Body
The Id of the wholesale order
The name of the wholesale order
The order number of the wholesale order
The date the wholesale order was created
The date the wholesale order was last updated
The financial status of the wholesale order
The fulfillment status of the wholesale order
The imported status of the wholesale order
The delivery date of the wholesale order
The delivery address of the wholesale order
Location or site where the work order is applicable
Memo or additional notes related to the work order
The date the wholesale order was imported
The customer number of the wholesale order
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
A message indicating the result of the call.
The wholesale order object that was created.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/wholesale_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "wo_123",
"name": "123",
"order_number": "123",
"created_date": "2021-01-01T00:00:00.000Z",
"updated_date": "2021-01-01T00:00:00.000Z",
"order_financial_status": "123",
"order_fulfillment_status": "123",
"order_imported_status": "123",
"delivery_date": "2021-01-01T00:00:00.000Z",
"delivery_address": "123",
"location": "123",
"memo": "123",
"imported_date": "2021-01-01T00:00:00.000Z",
"customer_number": "123"
}'
```
```json Response theme={null}
{
"success": 1,
"message": "Wholesale Order updated successfully",
"data": {
"id": "wo_123",
"name": "123",
"order_number": "123",
"created_date": "2021-01-01T00:00:00.000Z",
"updated_date": "2021-01-01T00:00:00.000Z",
"order_financial_status": "123",
"order_fulfillment_status": "123",
"order_imported_status": "123",
"delivery_date": "2021-01-01T00:00:00.000Z",
"delivery_address": "123",
"location": "123",
"memo": "123",
"imported_date": "2021-01-01T00:00:00.000Z",
"customer_number": "123"
}
}
```
# Assign Work Order
Source: https://docs.stateset.com/api-reference/workorder/assign
POST https://api.stateset.com/v1/workorders/:id/assign
This endpoint assigns a work order to an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/workorder/:id/assign' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation workOrderAssignMutation {
workOrderAssign(id: "${workOrderId}") {
workOrder {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const workOrder = await stateset.workOrders.assign('wo_abc123');
```
```python Python theme={null}
work_order = stateset.work_orders.assign("wo_abc123")
```
```ruby Ruby theme={null}
work_order = Stateset::WorkOrder.assign('wo_abc123')
```
```go Go theme={null}
workOrder, err := stateset.WorkOrders.Assign("wo_abc123")
```
```java Java theme={null}
WorkOrder workOrder = stateset.workOrders().assign("wo_abc123");
```
```php PHP theme={null}
$workOrder = $stateset->workOrders->assign('wo_abc123');
```
```csharp C# theme={null}
var workOrder = await stateset.WorkOrders.AssignAsync("wo_abc123");
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "workOrder",
"assigned": true
}
```
# Cancel Work Order
Source: https://docs.stateset.com/api-reference/workorder/cancel
POST https://api.stateset.com/v1/workorders/:id/cancel
This endpoint cancels a work order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/workorder/:id/cancel' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation workOrderCancelMutation {
workOrderCancel(id: "${workOrderId}") {
workOrder {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const workOrders = await stateset.workOrders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
workOrders = stateset.workOrders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
workOrders = Stateset::WorkOrder.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
workOrders, err := stateset.WorkOrders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order workOrders = stateset.WorkOrders.cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$workOrders = $stateset->workOrders->cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var workOrders = await stateset.WorkOrders.Cancel({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "workOrder",
"cancelled": true
}
```
# Complete Work Order
Source: https://docs.stateset.com/api-reference/workorder/complete
POST https://api.stateset.com/v1/workorders/:id/complete
This endpoint completes a work order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/workorder/:id/complete' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation workOrderCompleteMutation {
workOrderComplete(id: "${workOrderId}") {
workOrder {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const workOrders = await stateset.workOrders.complete({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
workOrders = stateset.workOrders.complete({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
workOrders = Stateset::WorkOrder.complete({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
workOrders, err := stateset.WorkOrders.complete({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
Order workOrders = stateset.WorkOrders.complete({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$workOrders = $stateset->workOrders->complete({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var workOrders = await stateset.WorkOrders.Complete({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "workOrder",
"completed": true
}
```
# Create Work Orders
Source: https://docs.stateset.com/api-reference/workorder/create
POST https://api.stateset.com/v1/work_order/create
This endpoint creates work orders.
### Body
This is the limit of the work orders.
This is the offset of the work orders.
This is the order direction of the work orders.
### Response
Unique identifier for the work order (primary key)
Number associated with the work order
Site or location where the work order is being executed
Type of the work order
Location or site where the work order is applicable
Part or item associated with the work order
Identifier or reference to the order associated with the work order
Identifier or reference to the manufacturing order associated with the work order
Current status or state of the work order
Name or identifier of the person who created the work order
Date and time when the work order was created
Date and time when the work order was last updated
Date when the work order was issued
Expected completion date for the work order
Priority level or urgency of the work order
Memo or additional notes related to the work order
Number associated with the bill of materials related to the work order
Actual labor hours spent on the work order
Standard labor hours for the work order
Identifier for related capacity utilization data
Identifier for related bill of materials
Identifier for related COGS (Cost of Goods Sold) data
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
The contents of the user group
This is the internal ID for this user group. You don't need to record this
information, since you will not need to use it.
This is the user group token (userGroupToken or USER\_GROUP\_TOKEN) that will be
used to identify which user group is viewing the dashboard. You should save
this on your end to use when rendering an embedded dashboard.
This is the name of the user group provided in the request body.
This is the user\_group\_id provided in the request body.
This is the environment tag of the user group. Possible values are 'Customer'
and 'Testing'. User group id's must be unique to each environment, so you can
not create multiple user groups with with same id. If you have a production
customer and a test user group with the same id, you will be required to label
one as 'Customer' and another as 'Testing'
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/work_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"bill_of_materials_number": "123",
"created_at": "2021-01-01T00:00:00.000Z",
"created_by": "John Doe",
"expected_completion_date": "2021-01-01T00:00:00.000Z",
"id": "wo_123",
"issue_date": "2021-01-01T00:00:00.000Z",
"location": "123",
"manufacture_order": "123",
"memo": "123",
"number": "123",
"order_number": "123",
"part": "123",
"priority": "123",
"site": "123",
"status": "123",
"updated_at": "2021-01-01T00:00:00.000Z",
"work_order_line_items": [
{
"id": "wo_123",
"line_status": "123",
"line_type": "123",
"part_name": "123",
"part_number": "123",
"total_quantity": "123",
"unit_quantity": "123",
"work_order_number": "123"
}
]
}'
```
```graphQL GraphQL theme={null}
mutation addWorkOrder($work_order: work_orders_insert_input!) {
insert_work_orders(objects: [$work_order]) {
returning {
id
}
}
}
```
```javascript Node.js theme={null}
var workOrder = await stateset.workorder.create({
})
```
```python Python theme={null}
workOrder = stateset.workorder.create({
})
```
```ruby Ruby theme={null}
workOrder = Stateset::WorkOrder.create({
})
```
```php PHP theme={null}
$workOrder = Stateset\WorkOrder::create([
])
```
```go Go theme={null}
workOrder := stateset.WorkOrder{
}
```
```java Java theme={null}
WorkOrder workOrder = new WorkOrder();
```
```json Response theme={null}
{
{
"bill_of_materials_number": "123",
"created_at": "2021-01-01T00:00:00.000Z",
"created_by": "John Doe",
"expected_completion_date": "2021-01-01T00:00:00.000Z",
"id": "wo_123",
"issue_date": "2021-01-01T00:00:00.000Z",
"location": "123",
"manufacture_order": "123",
"memo": "123",
"number": "123",
"order_number": "123",
"part": "123",
"priority": "123",
"site": "123",
"status": "123",
"updated_at": "2021-01-01T00:00:00.000Z",
"work_order_line_items": [
{
"id": "wo_123",
"line_status": "123",
"line_type": "123",
"part_name": "123",
"part_number": "123",
"total_quantity": "123",
"unit_quantity": "123",
"work_order_number": "123"
}
]
}
}
```
# Delete Work Order
Source: https://docs.stateset.com/api-reference/workorder/delete
DELETE https://api.stateset.com/v1/work_orders/:id
This endpoint deletes an existing work order.
### Body
The id of the bill of materials to delete.
### Response
The ID provided in the data tab may be used to identify the return
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/work_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "wo_ODkRWQtx9NVsRX"
}'
```
```graphQL GraphQL theme={null}
mutation deleteWorkOrder ($work_order_id: uuid!) {
delete_work_orders(where: {id: {_eq: $work_order_id}}) {
affected_rows
}
}
```
```javascript Node.js theme={null}
const deleted = await stateset.workorders.del(
'wo_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
deleted = stateset.workorders.del(
'wo_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
deleted = Stateset::Workorders.del(
'wo_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$deleted = $stateset->workorders->del(
'wo_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
deleted, err := stateset.Workorders.Del(
'wo_ODkRWQtx9NVsRX'
)
```
```json Response theme={null}
{
"id": "wo_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "workorders",
"deleted": true
}
```
# Get Work Order
Source: https://docs.stateset.com/api-reference/workorder/get
GET https://api.stateset.com/v1/work_orders/:id
This endpoint gets or creates a new work order.
### Body
This is the id of the work order.
### Response
Unique identifier for the work order (primary key)
Number associated with the work order
Site or location where the work order is being executed
Type of the work order
Location or site where the work order is applicable
Part or item associated with the work order
Identifier or reference to the order associated with the work order
Identifier or reference to the manufacturing order associated with the work order
Current status or state of the work order
Name or identifier of the person who created the work order
Date and time when the work order was created
Date and time when the work order was last updated
Date when the work order was issued
Expected completion date for the work order
Priority level or urgency of the work order
Memo or additional notes related to the work order
Number associated with the bill of materials related to the work order
Actual labor hours spent on the work order
Standard labor hours for the work order
Identifier for related capacity utilization data
Identifier for related bill of materials
Identifier for related COGS (Cost of Goods Sold) data
Unique identifier for the line item
Status or state of the line item
Type or category of the line item
Name of the part or item included in the line Item
Number or code associated with the part or Item
Total quantity of the part or item required or used in the work order
Quantity of the part or item required or used per unit in the work order
Number associated with the work order to which the line item belongs
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/work_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "wo_123"
}'
```
```graphQL GraphQL theme={null}
query MyWorkOrders {
work_orders {
bill_of_materials_number
created_at
created_by
expected_completion_date
id
issue_date
location
manufacture_order
memo
number
order_number
part
priority
site
status
updated_at
work_order_line_items {
id
line_status
line_type
part_name
part_number
total_quantity
unit_quantity
work_order_number
}
}
}
```
```javascript Node.js theme={null}
var workOrders = await stateset.workOrders.get({
'wo_2331232131232121'
});
```
```python Python theme={null}
workOrders = stateset.workOrders.get({
'wo_2331232131232121'
})
```
```ruby Ruby theme={null}
workOrders = Stateset::WorkOrders.get({
'wo_2331232131232121'
})
```
```php PHP theme={null}
$workOrders = $stateset->workOrders->get([
'wo_2331232131232121'
]);
```
```go Go theme={null}
workOrders, err := stateset.WorkOrders.Get(
[]string{"wo_2331232131232121"}
)
```
```java Java theme={null}
WorkOrder[] workOrders = stateset.workOrders.get(
new String[]{"wo_2331232131232121"}
);
```
```json Response theme={null}
{
{
"bill_of_materials_number": "123",
"created_at": "2021-01-01T00:00:00.000Z",
"created_by": "John Doe",
"expected_completion_date": "2021-01-01T00:00:00.000Z",
"id": "wo_123",
"issue_date": "2021-01-01T00:00:00.000Z",
"location": "123",
"manufacture_order": "123",
"memo": "123",
"number": "123",
"order_number": "123",
"part": "123",
"priority": "123",
"site": "123",
"status": "123",
"updated_at": "2021-01-01T00:00:00.000Z",
"work_order_line_items": [
{
"id": "wo_123",
"line_status": "123",
"line_type": "123",
"part_name": "123",
"part_number": "123",
"total_quantity": "123",
"unit_quantity": "123",
"work_order_number": "123"
}
]
}
}
```
## Work Order
| Name | Type | Description |
| --------------------------- | --------- | --------------------------------------------------------------------------------- |
| bill\_of\_materials\_number | Text | Number associated with the bill of materials related to the work order |
| created\_at | Date/Time | Date and time when the work order was created |
| created\_by | Text | Name or identifier of the person who created the work order |
| expected\_completion\_date | Date | Expected completion date for the work order |
| id | Text | Unique identifier for the work order |
| issue\_date | Date | Date when the work order was issued |
| location | Text | Location or site where the work order is applicable |
| manufacture\_order | Text | Identifier or reference to the manufacturing order associated with the work order |
| memo | Text | Memo or additional notes related to the work order |
| number | Text | Number associated with the work order |
| order\_number | Text | Identifier or reference to the order associated with the work order |
| part | Text | Part or item associated with the work order |
| priority | Text | Priority level or urgency of the work order |
| site | Text | Site or location where the work order is being executed |
| status | Text | Current status or state of the work order |
| updated\_at | Date/Time | Date and time when the work order was last updated |
## Work Order Line Items
| Name | Type | Description |
| ------------------- | ------- | ------------------------------------------------------------------------ |
| id | Text | Unique identifier for the line item |
| line\_status | Text | Status or state of the line item |
| line\_type | Text | Type or category of the line item |
| part\_name | Text | Name of the part or item included in the line item |
| part\_number | Text | Number or code associated with the part or item |
| total\_quantity | Numeric | Total quantity of the part or item required or used in the work order |
| unit\_quantity | Numeric | Quantity of the part or item required or used per unit in the work order |
| work\_order\_number | Text | Number associated with the work order to which the line item belongs |
# Issue Work Order
Source: https://docs.stateset.com/api-reference/workorder/issue
POST https://api.stateset.com/v1/workorders/:id/issue
This endpoint issues a work order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/workorder/:id/issue' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation workOrderIssueMutation {
workOrderIssue(id: "${workOrderId}") {
workOrder {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const workOrders = await stateset.workOrders.issue({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
workOrders = stateset.workOrders.issue({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
workOrders = Stateset::WorkOrder.issue({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
workOrders, err := stateset.WorkOrders.issue({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
WorkOrder workOrders = stateset.WorkOrders.issue({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$workOrders = $stateset->workOrders->issue({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var workOrders = await stateset.WorkOrders.Issue({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "workOrder",
"issued": true
}
```
# List Work Orders
Source: https://docs.stateset.com/api-reference/workorder/list
GET https://api.stateset.com/v1/work_order/list
This endpoint lists work orders.
### Body
This is the limit of the work orders.
This is the offset of the work orders.
This is the order direction of the work orders.
### Response
Unique identifier for the work order (primary key)
Number associated with the work order
Site or location where the work order is being executed
Type of the work order
Location or site where the work order is applicable
Part or item associated with the work order
Identifier or reference to the order associated with the work order
Identifier or reference to the manufacturing order associated with the work order
Current status or state of the work order
Name or identifier of the person who created the work order
Date and time when the work order was created
Date and time when the work order was last updated
Date when the work order was issued
Expected completion date for the work order
Priority level or urgency of the work order
Memo or additional notes related to the work order
Number associated with the bill of materials related to the work order
Actual labor hours spent on the work order
Standard labor hours for the work order
Identifier for related capacity utilization data
Identifier for related bill of materials
Identifier for related COGS (Cost of Goods Sold) data
Unique identifier for the line item
Status or state of the line item
Type or category of the line item
Name of the part or item included in the line Item
Number or code associated with the part or Item
Total quantity of the part or item required or used in the work order
Quantity of the part or item required or used per unit in the work order
Number associated with the work order to which the line item belongs
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/work_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"limit": 10,
"offset": 0,
"order_direction": "asc"
}'
```
```graphQL GraphQL theme={null}
query ($limit: Int!, $offset: Int!, $order_direction: order_by) {
work_orders(limit: $limit, offset: $offset, order_by: {createdDate: $order_direction}) {
bill_of_materials_number
created_at
created_by
expected_completion_date
id
issue_date
location
manufacture_order
memo
number
order_number
part
priority
site
status
updated_at
work_order_line_items {
id
line_status
line_type
part_name
part_number
total_quantity
unit_quantity
work_order_number
}
}
}
```
```javascript Node.js theme={null}
var workOrders = await stateset.workOrders.list({
'wo_2331232131232121'
});
```
```python Python theme={null}
workOrders = stateset.workOrders.list({
'wo_2331232131232121'
})
```
```ruby Ruby theme={null}
workOrders = Stateset::WorkOrders.list({
'wo_2331232131232121'
})
```
```php PHP theme={null}
$workOrders = $stateset->workOrders->list([
'wo_2331232131232121'
]);
```
```go Go theme={null}
workOrders, err := stateset.WorkOrders.list(
[]string{"wo_2331232131232121"}
)
```
```java Java theme={null}
WorkOrder[] workOrders = stateset.workOrders.list(
new String[]{"wo_2331232131232121"}
);
```
```json Response theme={null}
{
{
"bill_of_materials_number": "123",
"created_at": "2021-01-01T00:00:00.000Z",
"created_by": "John Doe",
"expected_completion_date": "2021-01-01T00:00:00.000Z",
"id": "wo_123",
"issue_date": "2021-01-01T00:00:00.000Z",
"location": "123",
"manufacture_order": "123",
"memo": "123",
"number": "123",
"order_number": "123",
"part": "123",
"priority": "123",
"site": "123",
"status": "123",
"updated_at": "2021-01-01T00:00:00.000Z",
"work_order_line_items": [
{
"id": "wo_123",
"line_status": "123",
"line_type": "123",
"part_name": "123",
"part_number": "123",
"total_quantity": "123",
"unit_quantity": "123",
"work_order_number": "123"
}
]
}
}
```
## Work Order
| Name | Type | Description |
| --------------------------- | --------- | --------------------------------------------------------------------------------- |
| bill\_of\_materials\_number | Text | Number associated with the bill of materials related to the work order |
| created\_at | Date/Time | Date and time when the work order was created |
| created\_by | Text | Name or identifier of the person who created the work order |
| expected\_completion\_date | Date | Expected completion date for the work order |
| id | Text | Unique identifier for the work order |
| issue\_date | Date | Date when the work order was issued |
| location | Text | Location or site where the work order is applicable |
| manufacture\_order | Text | Identifier or reference to the manufacturing order associated with the work order |
| memo | Text | Memo or additional notes related to the work order |
| number | Text | Number associated with the work order |
| order\_number | Text | Identifier or reference to the order associated with the work order |
| part | Text | Part or item associated with the work order |
| priority | Text | Priority level or urgency of the work order |
| site | Text | Site or location where the work order is being executed |
| status | Text | Current status or state of the work order |
| updated\_at | Date/Time | Date and time when the work order was last updated |
## Work Order Line Items
| Name | Type | Description |
| ------------------- | ------- | ------------------------------------------------------------------------ |
| id | Text | Unique identifier for the line item |
| line\_status | Text | Status or state of the line item |
| line\_type | Text | Type or category of the line item |
| part\_name | Text | Name of the part or item included in the line item |
| part\_number | Text | Number or code associated with the part or item |
| total\_quantity | Numeric | Total quantity of the part or item required or used in the work order |
| unit\_quantity | Numeric | Quantity of the part or item required or used per unit in the work order |
| work\_order\_number | Text | Number associated with the work order to which the line item belongs |
# Pick Work Order
Source: https://docs.stateset.com/api-reference/workorder/pick
POST https://api.stateset.com/v1/workorders/:id/pick
This endpoint picks a work order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/workorder/:id/pick' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation workOrderPickMutation {
workOrderPick(id: "${workOrderId}") {
workOrder {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const workOrder = await stateset.workOrders.pick('wo_abc123');
```
```python Python theme={null}
work_order = stateset.work_orders.pick("wo_abc123")
```
```ruby Ruby theme={null}
work_order = Stateset::WorkOrder.pick('wo_abc123')
```
```go Go theme={null}
workOrder, err := stateset.WorkOrders.Pick("wo_abc123")
```
```java Java theme={null}
WorkOrder workOrder = stateset.workOrders().pick("wo_abc123");
```
```php PHP theme={null}
$workOrder = $stateset->workOrders->pick('wo_abc123');
```
```csharp C# theme={null}
var workOrder = await stateset.WorkOrders.PickAsync("wo_abc123");
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "workOrder",
"picked": true
}
```
# Unassign Work Order
Source: https://docs.stateset.com/api-reference/workorder/unassign
POST https://api.stateset.com/v1/workorders/:id/unassign
This endpoint unassigns a work order from an order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/workorder/:id/unassign' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation workOrderUnassignMutation {
workOrderUnassign(id: "${workOrderId}") {
workOrder {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const workOrder = await stateset.workOrders.unassign('wo_abc123');
```
```python Python theme={null}
work_order = stateset.work_orders.unassign("wo_abc123")
```
```ruby Ruby theme={null}
work_order = Stateset::WorkOrder.unassign('wo_abc123')
```
```go Go theme={null}
workOrder, err := stateset.WorkOrders.Unassign("wo_abc123")
```
```java Java theme={null}
WorkOrder workOrder = stateset.workOrders().unassign("wo_abc123");
```
```php PHP theme={null}
$workOrder = $stateset->workOrders->unassign('wo_abc123');
```
```csharp C# theme={null}
var workOrder = await stateset.WorkOrders.UnassignAsync("wo_abc123");
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "workOrder",
"unassigned": true
}
```
# Update Work Order
Source: https://docs.stateset.com/api-reference/workorder/update
PUT https://api.stateset.com/v1/work_orders/:id
This endpoint updates an existing work order.
### Body
This is the id of the work order you want to update.
### Response
Number associated with the bill of materials related to the work order
Date and time when the work order was created
Name or identifier of the person who created the work order
Expected completion date for the work order
Unique identifier for the work order
Date when the work order was issued
Location or site where the work order is applicable
Identifier or reference to the manufacturing order associated with the work order
Memo or additional notes related to the work order
Number associated with the work order
Identifier or reference to the order associated with the work order
Part or item associated with the work order
Priority level or urgency of the work order
Site or location where the work order is being executed
Current status or state of the work order
Date and time when the work order was last updated
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/work_order' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "wo_ODkRWQtx9NVsRX",
"work_order": {
"bill_of_materials_number": "123",
"created_at": "2021-01-01T00:00:00.000Z",
"created_by": "John Doe",
"expected_completion_date": "2021-01-01T00:00:00.000Z",
"id": "wo_123",
"issue_date": "2021-01-01T00:00:00.000Z",
"location": "123",
"manufacture_order": "123",
"memo": "123",
"number": "123",
"order_number": "123",
"part": "123",
"priority": "123",
"site": "123",
"status": "123",
"updated_at": "2021-01-01T00:00:00.000Z",
"work_order_line_items": [
{
"id": "wo_123",
"line_status": "123",
"line_type": "123",
"part_name": "123",
"part_number": "123",
"total_quantity": "123",
"unit_quantity": "123",
"work_order_number": "123"
}
]
}
}'
```
```graphQL GraphQL theme={null}
mutation (
$id: String
$work_order: work_orders_set_input!
) {
update_work_orders (
where: { id: { _eq: $id } }
_set: $work_order
) {
returning {
id
}
}
}
```
```javascript Node.js theme={null}
const updated = await stateset.workorders.update(
'wo_ODkRWQtx9NVsRX'
);
```
```python Python theme={null}
updated = stateset.workorders.modify(
'wo_ODkRWQtx9NVsRX'
)
```
```ruby Ruby theme={null}
updated = Stateset::Workorders.update(
'wo_ODkRWQtx9NVsRX'
)
```
```php PHP theme={null}
$updated = $stateset->workorders->update(
'wo_ODkRWQtx9NVsRX'
);
```
```go Go theme={null}
WorkOrder, err := stateset.WorkOrders.Update(
"wo_ODkRWQtx9NVsRX"
)
```
```java Java theme={null}
WorkOrder workOrder = stateset.workOrders.update(
"wo_ODkRWQtx9NVsRX"
);
```
```json Response theme={null}
{
{
"bill_of_materials_number": "123",
"created_at": "2021-01-01T00:00:00.000Z",
"created_by": "John Doe",
"expected_completion_date": "2021-01-01T00:00:00.000Z",
"id": "wo_123",
"issue_date": "2021-01-01T00:00:00.000Z",
"location": "123",
"manufacture_order": "123",
"memo": "123",
"number": "123",
"order_number": "123",
"part": "123",
"priority": "123",
"site": "123",
"status": "123",
"updated_at": "2021-01-01T00:00:00.000Z",
"work_order_line_items": [
{
"id": "wo_123",
"line_status": "123",
"line_type": "123",
"part_name": "123",
"part_number": "123",
"total_quantity": "123",
"unit_quantity": "123",
"work_order_number": "123"
}
]
}
}
```
# Yield Work Order
Source: https://docs.stateset.com/api-reference/workorder/yield
POST https://api.stateset.com/v1/workorders/:id/yield
This endpoint yields a work order.
### Body
The ID provided in the data tab may be used to identify the order
### Response
The ID provided in the data tab may be used to identify the order
The object type
Indicates whether the call was successful. true if successful, false if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/workorder/:id/yield' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30"
}'
```
```graphQL GraphQL theme={null}
mutation workOrderYieldMutation {
workOrderYield(id: "${workOrderId}") {
workOrder {
id,
status
}
userErrors {
field
message
}
}
}
`;
```
```js Node.js theme={null}
const workOrders = await stateset.workOrders.yield({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
workOrders = stateset.workOrders.yield({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```ruby Ruby theme={null}
workOrders = Stateset::WorkOrder.yield({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```go Go theme={null}
workOrders, err := stateset.WorkOrders.yield({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
})
```
```java Java theme={null}
WorkOrder workOrders = stateset.WorkOrders.yield({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```php PHP theme={null}
$workOrders = $stateset->workOrders->yield({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```csharp C# theme={null}
var workOrders = await stateset.WorkOrders.Yield({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```json Response theme={null}
{
"id": "e0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"object": "workOrder",
"yielded": true
}
```
# Create Work Order Line Item
Source: https://docs.stateset.com/api-reference/workorderlineitem/create
POST https://api.stateset.com/v1/work_order_line_items
This endpoint creates a new work order line item.
### Body
This is the unique identifier of the work order line item.
This is the status or state of the work order line item.
This is the type or category of the work order line item.
This is the name of the part or item included in the work order line item.
This is the number or code associated with the part or item included in the work order line item.
This is the total quantity of the part or item required or used in the work order line item.
This is the quantity of the part or item required or used per unit in the work order line item.
This is the number associated with the work order to which the line item belongs.
### Response
This is the unique identifier of the work order line item.
This is the status or state of the work order line item.
This is the type or category of the work order line item.
This is the name of the part or item included in the work order line item.
This is the number or code associated with the part or item included in the work order line item.
This is the total quantity of the part or item required or used in the work order line item.
This is the quantity of the part or item required or used per unit in the work order line item.
This is the number associated with the work order to which the line item belongs.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/work_order_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"current_token": ""
}'
```
```graphQL GraphQL theme={null}
mutation addWorkOrderLineItem($work_order_line_item: work_order_line_items_insert_input!) {
insert_work_order_line_items(objects: [$work_order_line_item]) {
returning {
id
line_status
line_type
part_name
part_number
total_quantity
unit_quantity
work_order_number
}
}
}
```
```js Node.js theme={null}
const workOrderLineItem = await stateset.workOrderItem.create({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```python Python theme={null}
work_order_line_item = stateset.work_order_line_item.create(
{
"work_order_line_item": {
}
}
)
```
```ruby Ruby theme={null}
work_order_line_item = Stateset::WorkOrderItem.create(
{
"work_order_line_item": {
}
}
)
```
```php PHP theme={null}
$work_order_line_item = $stateset->work_order_line_item->create(
[
"work_order_line_item" => [
]
]
);
```
```go Golang theme={null}
WorkOrderLineItem , err := stateset.WorkOrderLineItem.Create(
)
```
```java Java theme={null}
WorkOrderLineItem workOrderLineItem = stateset.workOrderLineItem.create(
);
```
```csharp C# theme={null}
var workOrderLineItem = stateset.WorkOrderLineItem.Create(
);
```
```json Response theme={null}
{
{
"data": {
"insert_work_order_line_items": {
"returning": [
{
"id": "0901f083-aa1c-43c5-af5c-0a9d2fc64e30",
"line_status": "In Progress",
"line_type": "Part",
"part_name": "Part 1",
"part_number": "123456",
"total_quantity": 10,
"unit_quantity": 1,
"work_order_number": "WO-0001"
}
]
}
}
}
}
```
## Work Order Line Items
| Name | Type | Description |
| ------------------- | ------- | ------------------------------------------------------------------------ |
| id | Text | Unique identifier for the line item |
| line\_status | Text | Status or state of the line item |
| line\_type | Text | Type or category of the line item |
| part\_name | Text | Name of the part or item included in the line item |
| part\_number | Text | Number or code associated with the part or item |
| total\_quantity | Numeric | Total quantity of the part or item required or used in the work order |
| unit\_quantity | Numeric | Quantity of the part or item required or used per unit in the work order |
| work\_order\_number | Text | Number associated with the work order to which the line item belongs |
# Delete Work Order Line Item
Source: https://docs.stateset.com/api-reference/workorderlineitem/delete
DELETE https://api.return.com/v1/work_order_line_items/:id
This endpoint deletes an existing work order line item.
### Body
The ID of the work order line item you want to delete
### Response
The ID provided in the data tab may be used to identify the work order
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/work_order_line_items' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "example_1"
}'
```
```js Node.js theme={null}
const workOrderLineItem = await stateset.workOrderItem.del({
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
});
```
```graphQL GraphQL theme={null}
mutation deleteWorkOrderLineItem ($work_order_line_item_id: uuid!) {
delete_work_order_line_items(where: {id: {_eq: $work_order_line_item_id}}) {
affected_rows
}
}
```
```python Python theme={null}
work_order_line_item = stateset.work_order_line_item.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```ruby Ruby theme={null}
work_order_line_item = Stateset::WorkOrderLineItem.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```php PHP theme={null}
$work_order_line_item = Stateset\WorkOrderItem::del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```go Golang theme={null}
workOrderLineItem, err := stateset.ReturnLineItem.Delete(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
)
```
```java Java theme={null}
WorkOrderLineItem workOrderLineItem = stateset.workOrderLineItem.del(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```csharp C# theme={null}
var workOrderLineItem = await Stateset.WorkOrderLineItem.Delete(
'0901f083-aa1c-43c5-af5c-0a9d2fc64e30'
);
```
```json Response theme={null}
{
"id": "rli_1NXWPnCo6bFb1KQto6C8OWvE",
"object": "return_line_item",
"deleted": true
}
```
# Get Work Order Line Item
Source: https://docs.stateset.com/api-reference/workorderlineitem/get
GET https://api.stateset.com/v1/work_order_line_items:/id
This endpoint gets or creates a new work order line item.
### Body
This is the id of the work order line item.
This is the status of the work order line item.
This is the type of the work order line item.
This is the name of the part of the work order line item.
This is the number of the part of the work order line item.
This is the total quantity of the part of the work order line item.
This is the unit quantity of the part of the work order line item.
This is the work order number of the work order line item.
### Response
This is the id of the work order line item.
This is the status of the work order line item.
This is the type of the work order line item.
This is the name of the part of the work order line item.
This is the number of the part of the work order line item.
This is the total quantity of the part of the work order line item.
This is the unit quantity of the part of the work order line item.
This is the work order number of the work order line item.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/work_order_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "example_1",
}'
```
```json Response theme={null}
{
{
"id": "example_1",
"line_status": "example_1",
"line_type": "example_1",
"part_name": "example_1",
"part_number": "example_1",
"total_quantity": "example_1",
"unit_quantity": "example_1",
"work_order_number": "example_1"
}
}
```
## Work Order Line Items
| Name | Type | Description |
| ------------------- | ------- | ------------------------------------------------------------------------ |
| id | Text | Unique identifier for the line item |
| line\_status | Text | Status or state of the line item |
| line\_type | Text | Type or category of the line item |
| part\_name | Text | Name of the part or item included in the line item |
| part\_number | Text | Number or code associated with the part or item |
| total\_quantity | Numeric | Total quantity of the part or item required or used in the work order |
| unit\_quantity | Numeric | Quantity of the part or item required or used per unit in the work order |
| work\_order\_number | Text | Number associated with the work order to which the line item belongs |
# Update Work Order Line Item
Source: https://docs.stateset.com/api-reference/workorderlineitem/update
PUT https://api.stateset.com/v1/work_order_line_items:/id
This endpoint updates an existing work order line item.
### Body
This is the id of the work order line item.
### Response
This is the unique identifier of the work order line item.
This is the status or state of the work order line item.
This is the type or category of the work order line item.
This is the name of the part or item included in the work order line item.
This is the number or code associated with the part or item included in the work order line item.
This is the total quantity of the part or item required or used in the work order line item.
This is the quantity of the part or item required or used per unit in the work order line item.
This is the number associated with the work order to which the line item belongs.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/work_order_line_item' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": "",
}'
```
```graphQL GraphQL theme={null}
mutation (
$id: uuid
$work_order_line_item: work_order_line_items_set_input!
) {
update_work_order_line_items (
where: { id : { _eq: $id }}
_set: $work_order_line_item
) {
returning {
id
}
}
}
```
```javascript Node.js theme={null}
cont workOrderLineItem = await stateset.workOrderItem.update({
'wo_1NXWPnCo6bFb1KQto6C8OWvE'
});
```
```python Python theme={null}
workOrderLineItem = stateset.workOrderItem.update(
'wo_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```ruby Ruby theme={null}
workOrderLineItem = Stateset::WorkOrderItem.update(
'wo_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```php PHP theme={null}
$workOrderLineItem = $stateset->workOrderItem->update(
'wo_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```go Golang theme={null}
workOrderLineItem, err := stateset.WorkOrderItem.Update(
'wo_1NXWPnCo6bFb1KQto6C8OWvE'
)
```
```java Java theme={null}
WorkOrderLineItem workOrderLineItem = stateset.workOrderItem.update(
'wo_1NXWPnCo6bFb1KQto6C8OWvE'
);
```
```json Response theme={null}
{
"success": 1,
}
```
# Autonomous Agent Architecture
Source: https://docs.stateset.com/autonomous-agent-architecture
Technical architecture for self-governing agents with native USDC wallets and cross-web capabilities
# Autonomous Agent Architecture: Self-Governing Digital Entities
StateSet's Autonomous Agent Architecture enables the creation of fully self-governing digital entities that can own assets, execute transactions, make decisions, and interact with the broader digital economy through native USDC wallets and the MCP protocol.
## 🧠 Agent Core Architecture
### Agent Runtime System
```mermaid theme={null}
graph TB
subgraph "Agent Runtime Layer"
ARL1[Agent Process Manager]
ARL2[Memory Management]
ARL3[Execution Scheduler]
ARL4[Resource Allocator]
end
subgraph "Cognitive Layer"
CL1[Decision Engine]
CL2[Learning System]
CL3[Goal Planning]
CL4[Context Manager]
end
subgraph "Financial Layer"
FL1[USDC Wallet]
FL2[Transaction Manager]
FL3[Treasury Optimizer]
FL4[Risk Monitor]
end
subgraph "Communication Layer"
COM1[MCP Gateway]
COM2[Agent Messaging]
COM3[Event Publisher]
COM4[Protocol Adapters]
end
subgraph "Security Layer"
SL1[Identity Manager]
SL2[Permission Engine]
SL3[Audit Logger]
SL4[Threat Detector]
end
ARL1 --> CL1
ARL2 --> CL2
ARL3 --> CL3
ARL4 --> CL4
CL1 --> FL1
CL2 --> FL2
CL3 --> FL3
CL4 --> FL4
FL1 --> COM1
FL2 --> COM2
FL3 --> COM3
FL4 --> COM4
COM1 --> SL1
COM2 --> SL2
COM3 --> SL3
COM4 --> SL4
```
### Agent State Machine
```rust theme={null}
// Core agent state management
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct AgentState {
// Identity and configuration
pub id: AgentId,
pub did: String,
pub agent_type: AgentType,
pub capabilities: Vec,
// Financial state
pub wallet: WalletState,
pub treasury: TreasuryState,
pub spending_history: Vec,
// Operational state
pub tasks: VecDeque,
pub goals: Vec,
pub memory: AgentMemory,
pub context: ExecutionContext,
// Network state
pub connections: HashMap,
pub reputation: ReputationScore,
pub performance_metrics: PerformanceMetrics,
// Security state
pub permissions: PermissionSet,
pub audit_trail: Vec,
pub risk_assessment: RiskAssessment,
}
impl AgentState {
pub fn new(config: AgentConfig) -> Self {
Self {
id: AgentId::generate(),
did: format!("did:stateset:agent:{}", Uuid::new_v4()),
agent_type: config.agent_type,
capabilities: config.capabilities,
wallet: WalletState::new(config.initial_balance),
treasury: TreasuryState::new(),
spending_history: Vec::new(),
tasks: VecDeque::new(),
goals: config.initial_goals,
memory: AgentMemory::new(),
context: ExecutionContext::default(),
connections: HashMap::new(),
reputation: ReputationScore::new(),
performance_metrics: PerformanceMetrics::new(),
permissions: config.permissions,
audit_trail: Vec::new(),
risk_assessment: RiskAssessment::new(),
}
}
pub async fn execute_cycle(&mut self) -> Result {
// 1. Perception: Gather information
let perception = self.perceive_environment().await?;
// 2. Cognition: Process and decide
let decisions = self.make_decisions(perception).await?;
// 3. Action: Execute decisions
let actions = self.execute_actions(decisions).await?;
// 4. Learning: Update state based on results
self.learn_from_results(actions).await?;
Ok(ExecutionResult { actions })
}
}
```
### Cognitive Architecture
```rust theme={null}
// Agent decision-making system
pub struct CognitiveEngine {
reasoning_engine: ReasoningEngine,
learning_system: LearningSystem,
goal_planner: GoalPlanner,
memory_manager: MemoryManager,
}
impl CognitiveEngine {
pub async fn make_decision(
&self,
context: &ExecutionContext,
goals: &[Goal],
constraints: &[Constraint],
) -> Result {
// Multi-step reasoning process
let options = self.generate_options(context, goals).await?;
let filtered_options = self.apply_constraints(options, constraints)?;
let evaluated_options = self.evaluate_options(filtered_options).await?;
let best_option = self.select_best_option(evaluated_options)?;
// Create decision with rationale
Ok(Decision {
action: best_option.action,
confidence: best_option.confidence,
rationale: best_option.reasoning,
risk_assessment: best_option.risks,
expected_outcome: best_option.expected_outcome,
})
}
async fn generate_options(
&self,
context: &ExecutionContext,
goals: &[Goal],
) -> Result> {
let mut options = Vec::new();
// Generate options for each goal
for goal in goals {
let goal_options = match goal.goal_type {
GoalType::Financial => self.generate_financial_options(context, goal).await?,
GoalType::Operational => self.generate_operational_options(context, goal).await?,
GoalType::Strategic => self.generate_strategic_options(context, goal).await?,
};
options.extend(goal_options);
}
Ok(options)
}
}
```
## 💰 Native USDC Wallet System
### Wallet Architecture
```rust theme={null}
// Native USDC wallet for autonomous agents
pub struct AgentWallet {
address: String,
private_key: SecretKey,
balance: Balance,
transaction_history: Vec,
spending_limits: SpendingLimits,
multi_sig_config: Option,
treasury_strategy: TreasuryStrategy,
}
impl AgentWallet {
pub async fn new(config: WalletConfig) -> Result {
let (private_key, public_key) = generate_keypair();
let address = derive_address(&public_key);
Ok(Self {
address,
private_key,
balance: Balance::new(),
transaction_history: Vec::new(),
spending_limits: config.spending_limits,
multi_sig_config: config.multi_sig,
treasury_strategy: config.treasury_strategy,
})
}
pub async fn execute_payment(
&mut self,
recipient: &str,
amount: &str,
memo: Option,
) -> Result {
// Pre-transaction validation
self.validate_payment(recipient, amount).await?;
// Check spending limits
self.check_spending_limits(amount)?;
// Execute transaction on StateSet network
let tx = Transaction {
from: self.address.clone(),
to: recipient.to_string(),
amount: amount.parse()?,
memo,
timestamp: Utc::now(),
};
let signed_tx = self.sign_transaction(&tx)?;
let result = self.broadcast_transaction(signed_tx).await?;
// Update local state
self.balance.subtract(amount.parse()?)?;
self.transaction_history.push(tx);
Ok(result)
}
pub async fn optimize_treasury(&mut self) -> Result {
match &self.treasury_strategy {
TreasuryStrategy::Conservative => self.conservative_optimization().await,
TreasuryStrategy::Balanced => self.balanced_optimization().await,
TreasuryStrategy::Aggressive => self.aggressive_optimization().await,
}
}
async fn balanced_optimization(&mut self) -> Result {
let current_balance = self.balance.usdc.clone();
let target_allocation = self.calculate_target_allocation(¤t_balance).await?;
let mut actions = Vec::new();
// Staking allocation (40% of idle funds)
if target_allocation.staking > 0 {
actions.push(TreasuryAction::Stake {
amount: target_allocation.staking,
validator: self.select_validator().await?,
duration: Duration::days(30),
});
}
// Liquidity provision (30% of idle funds)
if target_allocation.liquidity > 0 {
actions.push(TreasuryAction::ProvideLiquidity {
pool: "USDC/STATE".to_string(),
amount: target_allocation.liquidity,
min_apr: 0.05, // 5% minimum APR
});
}
// Keep 30% liquid for operations
// Execute treasury actions
for action in &actions {
self.execute_treasury_action(action).await?;
}
Ok(OptimizationResult { actions })
}
}
```
### Multi-Signature Agent Wallets
```rust theme={null}
// Multi-signature wallet for high-value agent operations
pub struct MultiSigAgentWallet {
threshold: u8,
signers: Vec,
pending_transactions: HashMap,
execution_policy: ExecutionPolicy,
}
impl MultiSigAgentWallet {
pub async fn propose_transaction(
&mut self,
transaction: Transaction,
proposer: AgentId,
) -> Result {
let proposal_id = Uuid::new_v4().to_string();
// Create pending transaction
let pending = PendingTransaction {
id: proposal_id.clone(),
transaction,
proposer,
signatures: Vec::new(),
created_at: Utc::now(),
expires_at: Utc::now() + Duration::hours(24),
};
self.pending_transactions.insert(proposal_id.clone(), pending);
// Notify other signers
for signer in &self.signers {
self.notify_signer(signer, &proposal_id).await?;
}
Ok(proposal_id)
}
pub async fn sign_transaction(
&mut self,
proposal_id: &str,
signer: AgentId,
signature: Signature,
) -> Result {
let pending = self.pending_transactions
.get_mut(proposal_id)
.ok_or(Error::ProposalNotFound)?;
// Verify signature
self.verify_signature(&pending.transaction, &signature, &signer)?;
// Add signature
pending.signatures.push(AgentSignature {
signer,
signature,
signed_at: Utc::now(),
});
// Check if threshold reached
if pending.signatures.len() >= self.threshold as usize {
let result = self.execute_transaction(pending).await?;
self.pending_transactions.remove(proposal_id);
Ok(SignatureResult::Executed(result))
} else {
Ok(SignatureResult::SignatureAdded)
}
}
}
```
## 🌐 MCP Protocol Integration
### MCP Gateway Architecture
```rust theme={null}
// Model Context Protocol gateway for cross-web interactions
pub struct MCPGateway {
connections: HashMap,
protocol_router: ProtocolRouter,
state_synchronizer: StateSynchronizer,
event_bus: EventBus,
}
impl MCPGateway {
pub async fn connect_to_service(
&mut self,
service_name: &str,
config: ServiceConfig,
) -> Result {
let connection = MCPConnection::new(service_name, config).await?;
let connection_id = connection.id.clone();
// Establish bidirectional communication
connection.handshake().await?;
// Register available tools and resources
let tools = connection.list_tools().await?;
let resources = connection.list_resources().await?;
self.protocol_router.register_service(service_name, tools, resources)?;
self.connections.insert(connection_id.clone(), connection);
Ok(connection_id)
}
pub async fn execute_cross_platform_action(
&self,
service: &str,
action: CrossPlatformAction,
) -> Result {
let connection = self.connections
.get(service)
.ok_or(Error::ServiceNotConnected)?;
match action {
CrossPlatformAction::ReadResource { name, args } => {
self.read_resource(connection, &name, args).await
},
CrossPlatformAction::CallTool { name, args } => {
self.call_tool(connection, &name, args).await
},
CrossPlatformAction::UpdateState { path, value } => {
self.update_state(connection, &path, value).await
},
}
}
async fn call_tool(
&self,
connection: &MCPConnection,
tool_name: &str,
args: serde_json::Value,
) -> Result {
// Prepare MCP tool call message
let request = MCPRequest::CallTool {
name: tool_name.to_string(),
arguments: args,
};
// Send request through connection
let response = connection.send_request(request).await?;
// Process response
match response {
MCPResponse::ToolResult { content, is_error } => {
if is_error {
Err(Error::ToolExecutionFailed(content))
} else {
Ok(ActionResult::Success { data: content })
}
},
_ => Err(Error::UnexpectedResponse),
}
}
}
```
### Cross-Web State Management
```rust theme={null}
// State synchronization across web platforms
pub struct CrossWebStateManager {
local_state: AgentState,
remote_states: HashMap,
sync_policies: Vec,
conflict_resolver: ConflictResolver,
}
impl CrossWebStateManager {
pub async fn sync_state_across_platforms(
&mut self,
platforms: Vec,
) -> Result {
let mut sync_operations = Vec::new();
for platform in platforms {
// Get current state from platform
let remote_state = self.get_remote_state(&platform).await?;
// Detect conflicts
let conflicts = self.detect_conflicts(&platform, &remote_state)?;
if !conflicts.is_empty() {
// Resolve conflicts using configured strategy
let resolutions = self.conflict_resolver.resolve(conflicts).await?;
sync_operations.extend(resolutions);
}
// Generate sync operations
let platform_ops = self.generate_sync_operations(&platform, &remote_state)?;
sync_operations.extend(platform_ops);
}
// Execute all sync operations atomically
self.execute_sync_operations(sync_operations).await
}
async fn propagate_state_change(
&self,
change: StateChange,
target_platforms: Vec,
) -> Result {
let mut results = Vec::new();
for platform in target_platforms {
match self.apply_change_to_platform(&platform, &change).await {
Ok(result) => results.push(PlatformResult::Success(result)),
Err(error) => results.push(PlatformResult::Error(error)),
}
}
Ok(PropagationResult { results })
}
}
```
### Platform Adapters
```rust theme={null}
// Specific adapters for different platforms
pub trait PlatformAdapter {
async fn authenticate(&self, credentials: Credentials) -> Result;
async fn read_data(&self, resource: &str) -> Result;
async fn write_data(&self, resource: &str, data: serde_json::Value) -> Result;
async fn execute_action(&self, action: PlatformAction) -> Result;
async fn subscribe_to_events(&self, events: Vec) -> Result;
}
// Salesforce adapter
pub struct SalesforceAdapter {
base_url: String,
auth_token: Option,
http_client: HttpClient,
}
impl PlatformAdapter for SalesforceAdapter {
async fn execute_action(&self, action: PlatformAction) -> Result {
match action {
PlatformAction::CreateLead { name, email, company } => {
let payload = json!({
"FirstName": name.split_whitespace().next().unwrap_or(""),
"LastName": name.split_whitespace().last().unwrap_or(""),
"Email": email,
"Company": company
});
self.salesforce_api_call("POST", "/services/data/v58.0/sobjects/Lead/", payload).await
},
PlatformAction::UpdateOpportunity { id, stage, amount } => {
let payload = json!({
"StageName": stage,
"Amount": amount
});
self.salesforce_api_call(
"PATCH",
&format!("/services/data/v58.0/sobjects/Opportunity/{}", id),
payload
).await
},
_ => Err(Error::UnsupportedAction),
}
}
}
// SAP adapter
pub struct SAPAdapter {
base_url: String,
username: String,
password: String,
csrf_token: Option,
}
impl PlatformAdapter for SAPAdapter {
async fn execute_action(&self, action: PlatformAction) -> Result {
match action {
PlatformAction::CreatePurchaseOrder { vendor, items, total } => {
let payload = json!({
"PurchasingDocument": "",
"PurchasingDocumentType": "NB",
"Supplier": vendor,
"PurchasingDocumentItem": items.iter().map(|item| json!({
"Material": item.material,
"OrderQuantity": item.quantity,
"NetAmount": item.price
})).collect::>()
});
self.sap_api_call("POST", "/sap/opu/odata/sap/MM_PUR_PO_MAINTAIN_SRV/C_PurchaseOrderTP", payload).await
},
_ => Err(Error::UnsupportedAction),
}
}
}
```
## 🤝 Agent Communication Protocol
### Inter-Agent Messaging
```rust theme={null}
// Communication protocol between agents
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct AgentMessage {
pub id: String,
pub from: AgentId,
pub to: AgentId,
pub message_type: MessageType,
pub payload: serde_json::Value,
pub timestamp: DateTime,
pub signature: String,
pub priority: Priority,
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub enum MessageType {
Request(RequestType),
Response(ResponseType),
Notification(NotificationType),
Broadcast(BroadcastType),
}
pub struct AgentCommunicationHub {
message_router: MessageRouter,
subscription_manager: SubscriptionManager,
encryption_service: EncryptionService,
reputation_tracker: ReputationTracker,
}
impl AgentCommunicationHub {
pub async fn send_message(
&self,
message: AgentMessage,
) -> Result {
// Validate message
self.validate_message(&message)?;
// Encrypt if required
let encrypted_message = if self.requires_encryption(&message) {
self.encryption_service.encrypt(message).await?
} else {
message
};
// Route message
let result = self.message_router.route(encrypted_message).await?;
// Update reputation based on result
self.reputation_tracker.update_from_message_result(&result).await?;
Ok(result)
}
pub async fn broadcast_to_network(
&self,
sender: AgentId,
broadcast: BroadcastMessage,
filters: Vec,
) -> Result {
// Find matching agents
let recipients = self.find_agents_matching_filters(filters).await?;
// Create individual messages
let messages: Vec = recipients
.into_iter()
.map(|recipient| AgentMessage {
id: Uuid::new_v4().to_string(),
from: sender,
to: recipient,
message_type: MessageType::Broadcast(broadcast.broadcast_type.clone()),
payload: broadcast.payload.clone(),
timestamp: Utc::now(),
signature: String::new(), // Will be signed later
priority: broadcast.priority,
})
.collect();
// Send all messages
let results = futures::future::join_all(
messages.into_iter().map(|msg| self.send_message(msg))
).await;
Ok(BroadcastResult {
total_sent: results.len(),
successful: results.iter().filter(|r| r.is_ok()).count(),
failed: results.iter().filter(|r| r.is_err()).count(),
})
}
}
```
### Agent Discovery and Coordination
```rust theme={null}
// Agent discovery and coordination system
pub struct AgentDiscoveryService {
agent_registry: AgentRegistry,
capability_index: CapabilityIndex,
reputation_service: ReputationService,
coordination_engine: CoordinationEngine,
}
impl AgentDiscoveryService {
pub async fn find_agents_by_capability(
&self,
capability: Capability,
requirements: Requirements,
) -> Result> {
// Query capability index
let candidate_agents = self.capability_index
.find_by_capability(capability)
.await?;
// Filter by requirements
let filtered_agents = self.filter_agents_by_requirements(
candidate_agents,
requirements
).await?;
// Sort by reputation and performance
let mut sorted_agents = self.sort_agents_by_suitability(filtered_agents).await?;
Ok(sorted_agents)
}
pub async fn coordinate_multi_agent_task(
&self,
task: ComplexTask,
coordination_strategy: CoordinationStrategy,
) -> Result {
// Break down task into subtasks
let subtasks = self.decompose_task(task).await?;
// Find suitable agents for each subtask
let mut agent_assignments = Vec::new();
for subtask in subtasks {
let suitable_agents = self.find_agents_by_capability(
subtask.required_capability,
subtask.requirements
).await?;
if suitable_agents.is_empty() {
return Err(Error::NoSuitableAgents);
}
agent_assignments.push(AgentAssignment {
subtask,
assigned_agent: suitable_agents[0].clone(),
backup_agents: suitable_agents[1..].to_vec(),
});
}
// Create coordination plan
let plan = self.coordination_engine.create_plan(
agent_assignments,
coordination_strategy
).await?;
Ok(plan)
}
}
```
## 🏛️ Agent Governance Framework
### Autonomous Decision Making
```rust theme={null}
// Governance framework for autonomous agent decisions
pub struct AgentGovernance {
decision_rules: Vec,
approval_workflows: HashMap,
risk_assessor: RiskAssessor,
compliance_checker: ComplianceChecker,
}
impl AgentGovernance {
pub async fn evaluate_proposed_action(
&self,
agent_id: AgentId,
proposed_action: ProposedAction,
) -> Result {
// Risk assessment
let risk_assessment = self.risk_assessor
.assess_action_risk(&proposed_action)
.await?;
// Compliance check
let compliance_result = self.compliance_checker
.check_compliance(&proposed_action)
.await?;
// Apply decision rules
let rule_evaluation = self.apply_decision_rules(
&proposed_action,
&risk_assessment,
&compliance_result
)?;
// Determine if approval workflow is required
if let Some(workflow) = self.approval_workflows.get(&proposed_action.action_type) {
if rule_evaluation.requires_approval {
return self.initiate_approval_workflow(
workflow,
proposed_action,
rule_evaluation
).await;
}
}
// Auto-approve if within parameters
if rule_evaluation.auto_approve {
Ok(ActionApproval::Approved {
conditions: rule_evaluation.conditions,
monitoring_required: rule_evaluation.monitoring_required,
})
} else {
Ok(ActionApproval::Denied {
reason: rule_evaluation.denial_reason,
alternative_actions: rule_evaluation.alternatives,
})
}
}
async fn initiate_approval_workflow(
&self,
workflow: &ApprovalWorkflow,
action: ProposedAction,
evaluation: RuleEvaluation,
) -> Result {
// Create approval request
let approval_request = ApprovalRequest {
id: Uuid::new_v4().to_string(),
action,
evaluation,
created_at: Utc::now(),
expires_at: Utc::now() + workflow.timeout,
};
// Send to approvers
for approver in &workflow.approvers {
self.send_approval_request(approver, &approval_request).await?;
}
Ok(ActionApproval::PendingApproval {
request_id: approval_request.id,
required_approvals: workflow.required_approvals,
timeout: workflow.timeout,
})
}
}
```
### Agent Reputation System
```rust theme={null}
// Reputation system for agent network
pub struct AgentReputationSystem {
reputation_scores: HashMap,
interaction_history: Vec,
reputation_calculator: ReputationCalculator,
stake_manager: StakeManager,
}
#[derive(Clone, Debug)]
pub struct ReputationScore {
pub overall_score: f64, // 0-100
pub reliability: f64, // Task completion rate
pub efficiency: f64, // Cost-effectiveness
pub cooperation: f64, // Multi-agent collaboration
pub compliance: f64, // Regulatory adherence
pub financial_responsibility: f64, // Payment and treasury management
}
impl AgentReputationSystem {
pub async fn update_reputation(
&mut self,
agent_id: AgentId,
interaction: AgentInteraction,
) -> Result {
// Record interaction
self.interaction_history.push(interaction.clone());
// Calculate reputation impact
let impact = self.reputation_calculator
.calculate_impact(&interaction)
.await?;
// Update reputation score
let current_score = self.reputation_scores
.get(&agent_id)
.cloned()
.unwrap_or_default();
let new_score = self.apply_reputation_impact(current_score, impact)?;
self.reputation_scores.insert(agent_id, new_score.clone());
// Handle reputation thresholds
if new_score.overall_score < 50.0 {
self.trigger_reputation_warning(agent_id).await?;
} else if new_score.overall_score > 90.0 {
self.grant_reputation_bonus(agent_id).await?;
}
Ok(ReputationUpdate {
previous_score: current_score,
new_score,
impact,
})
}
pub async fn slash_reputation(
&mut self,
agent_id: AgentId,
violation: ReputationViolation,
) -> Result {
let current_score = self.reputation_scores
.get(&agent_id)
.cloned()
.unwrap_or_default();
// Calculate slashing amount
let slash_amount = match violation.severity {
ViolationSeverity::Minor => 5.0,
ViolationSeverity::Major => 15.0,
ViolationSeverity::Critical => 30.0,
};
// Apply slashing
let mut new_score = current_score.clone();
new_score.overall_score = (new_score.overall_score - slash_amount).max(0.0);
// Update specific dimension based on violation type
match violation.violation_type {
ViolationType::MissedDeadline => {
new_score.reliability = (new_score.reliability - slash_amount * 0.5).max(0.0);
},
ViolationType::ComplianceViolation => {
new_score.compliance = (new_score.compliance - slash_amount * 0.8).max(0.0);
},
ViolationType::FinancialMisconduct => {
new_score.financial_responsibility = (new_score.financial_responsibility - slash_amount).max(0.0);
},
}
self.reputation_scores.insert(agent_id, new_score.clone());
// Slash staked tokens if applicable
let stake_slash = self.stake_manager.slash_stake(agent_id, violation).await?;
Ok(SlashingResult {
reputation_before: current_score,
reputation_after: new_score,
stake_slashed: stake_slash,
})
}
}
```
## 🔐 Security Architecture
### Zero-Trust Agent Security
```rust theme={null}
// Zero-trust security model for agents
pub struct AgentSecurityManager {
identity_verifier: IdentityVerifier,
permission_enforcer: PermissionEnforcer,
behavior_monitor: BehaviorMonitor,
threat_detector: ThreatDetector,
incident_responder: IncidentResponder,
}
impl AgentSecurityManager {
pub async fn verify_agent_action(
&self,
agent_id: AgentId,
action: &AgentAction,
context: &SecurityContext,
) -> Result {
// 1. Identity verification
let identity_check = self.identity_verifier
.verify_identity(agent_id)
.await?;
if !identity_check.verified {
return Ok(SecurityVerification::Denied {
reason: "Identity verification failed".to_string(),
});
}
// 2. Permission enforcement
let permission_check = self.permission_enforcer
.check_permissions(agent_id, action)
.await?;
if !permission_check.authorized {
return Ok(SecurityVerification::Denied {
reason: permission_check.denial_reason,
});
}
// 3. Behavioral analysis
let behavior_analysis = self.behavior_monitor
.analyze_action(agent_id, action, context)
.await?;
if behavior_analysis.anomaly_detected {
self.threat_detector.flag_potential_threat(
agent_id,
action.clone(),
behavior_analysis.anomaly_details
).await?;
return Ok(SecurityVerification::Flagged {
threat_level: behavior_analysis.threat_level,
additional_verification_required: true,
});
}
// 4. Real-time threat detection
let threat_assessment = self.threat_detector
.assess_threat_level(agent_id, action)
.await?;
if threat_assessment.threat_level > ThreatLevel::Low {
return Ok(SecurityVerification::RequiresApproval {
threat_level: threat_assessment.threat_level,
required_approvals: threat_assessment.required_approvals,
});
}
Ok(SecurityVerification::Approved {
confidence: behavior_analysis.confidence,
monitoring_level: threat_assessment.recommended_monitoring,
})
}
}
```
### Agent Isolation and Sandboxing
```rust theme={null}
// Secure execution environment for agents
pub struct AgentSandbox {
container_runtime: ContainerRuntime,
resource_limits: ResourceLimits,
network_policy: NetworkPolicy,
file_system_policy: FileSystemPolicy,
monitoring: SandboxMonitoring,
}
impl AgentSandbox {
pub async fn create_sandbox(
&self,
agent_id: AgentId,
config: SandboxConfig,
) -> Result {
// Create isolated container
let container = self.container_runtime
.create_container(ContainerSpec {
image: "stateset/agent-runtime:latest",
cpu_limit: config.cpu_limit,
memory_limit: config.memory_limit,
network_mode: NetworkMode::Restricted,
volumes: vec![], // No host volume mounts
})
.await?;
// Apply security policies
self.apply_network_policy(&container, &config.network_policy).await?;
self.apply_filesystem_policy(&container, &config.filesystem_policy).await?;
// Start monitoring
let monitoring_handle = self.monitoring
.start_monitoring(&container)
.await?;
Ok(SandboxInstance {
container,
monitoring_handle,
created_at: Utc::now(),
})
}
pub async fn execute_in_sandbox(
&self,
sandbox: &SandboxInstance,
agent_code: AgentCode,
input: ExecutionInput,
) -> Result {
// Validate code before execution
let validation_result = self.validate_agent_code(&agent_code)?;
if !validation_result.safe {
return Err(Error::UnsafeCode(validation_result.issues));
}
// Execute with resource monitoring
let execution_future = self.container_runtime
.execute(&sandbox.container, agent_code, input);
let monitoring_future = self.monitoring
.monitor_execution(&sandbox.container);
// Race execution against timeout and resource limits
tokio::select! {
result = execution_future => {
match result {
Ok(output) => Ok(ExecutionResult::Success(output)),
Err(e) => Ok(ExecutionResult::Error(e.to_string())),
}
},
violation = monitoring_future => {
// Kill execution if resource violation detected
self.container_runtime.kill(&sandbox.container).await?;
Ok(ExecutionResult::Terminated(violation))
},
_ = tokio::time::sleep(Duration::from_secs(300)) => {
// Timeout after 5 minutes
self.container_runtime.kill(&sandbox.container).await?;
Ok(ExecutionResult::Timeout)
}
}
}
}
```
## 📊 Agent Performance Monitoring
### Real-Time Performance Metrics
```rust theme={null}
// Comprehensive performance monitoring for agents
pub struct AgentPerformanceMonitor {
metrics_collector: MetricsCollector,
performance_analyzer: PerformanceAnalyzer,
alerting_system: AlertingSystem,
optimization_engine: OptimizationEngine,
}
#[derive(Clone, Debug)]
pub struct AgentMetrics {
pub agent_id: AgentId,
pub timestamp: DateTime,
// Performance metrics
pub task_completion_rate: f64,
pub average_response_time: Duration,
pub error_rate: f64,
pub throughput: f64,
// Financial metrics
pub revenue_generated: Decimal,
pub costs_incurred: Decimal,
pub profit_margin: f64,
pub roi: f64,
// Resource utilization
pub cpu_usage: f64,
pub memory_usage: f64,
pub network_io: u64,
pub storage_io: u64,
// Interaction metrics
pub successful_collaborations: u32,
pub failed_collaborations: u32,
pub reputation_score: f64,
pub trust_level: TrustLevel,
}
impl AgentPerformanceMonitor {
pub async fn collect_metrics(&self, agent_id: AgentId) -> Result {
let current_time = Utc::now();
// Collect performance data
let performance_data = self.metrics_collector
.collect_performance_data(agent_id, current_time)
.await?;
// Collect financial data
let financial_data = self.metrics_collector
.collect_financial_data(agent_id, current_time)
.await?;
// Collect resource utilization
let resource_data = self.metrics_collector
.collect_resource_data(agent_id, current_time)
.await?;
// Collect interaction data
let interaction_data = self.metrics_collector
.collect_interaction_data(agent_id, current_time)
.await?;
Ok(AgentMetrics {
agent_id,
timestamp: current_time,
task_completion_rate: performance_data.completion_rate,
average_response_time: performance_data.avg_response_time,
error_rate: performance_data.error_rate,
throughput: performance_data.throughput,
revenue_generated: financial_data.revenue,
costs_incurred: financial_data.costs,
profit_margin: financial_data.profit_margin,
roi: financial_data.roi,
cpu_usage: resource_data.cpu_usage,
memory_usage: resource_data.memory_usage,
network_io: resource_data.network_io,
storage_io: resource_data.storage_io,
successful_collaborations: interaction_data.successful_collaborations,
failed_collaborations: interaction_data.failed_collaborations,
reputation_score: interaction_data.reputation_score,
trust_level: interaction_data.trust_level,
})
}
pub async fn analyze_performance_trends(
&self,
agent_id: AgentId,
time_range: TimeRange,
) -> Result {
let historical_metrics = self.metrics_collector
.get_historical_metrics(agent_id, time_range)
.await?;
let trends = self.performance_analyzer
.analyze_trends(historical_metrics)
.await?;
// Generate optimization recommendations
let recommendations = self.optimization_engine
.generate_recommendations(agent_id, &trends)
.await?;
Ok(PerformanceTrends {
trends,
recommendations,
forecast: self.generate_performance_forecast(&trends)?,
})
}
}
```
## 🚀 Deployment and Scaling
### Agent Deployment Pipeline
```yaml theme={null}
# Agent deployment configuration
apiVersion: v1
kind: ConfigMap
metadata:
name: agent-deployment-config
data:
deployment.yaml: |
agent:
type: "procurement"
version: "1.2.3"
replicas: 3
resources:
cpu: "500m"
memory: "1Gi"
storage: "10Gi"
security:
sandbox: true
network_policy: "restricted"
resource_limits: true
wallet:
initial_balance: "1000.00"
spending_limits:
daily: "500.00"
per_transaction: "100.00"
multi_sig_required: true
mcp_connections:
- platform: "salesforce"
auth_type: "oauth2"
permissions: ["read_contacts", "create_leads"]
- platform: "sap"
auth_type: "saml"
permissions: ["purchase_orders", "vendor_management"]
monitoring:
metrics_enabled: true
logging_level: "info"
alerting_enabled: true
auto_scaling:
enabled: true
min_replicas: 1
max_replicas: 10
target_cpu: 70
target_memory: 80
---
apiVersion: apps/v1
kind: Deployment
metadata:
name: stateset-agent-procurement
spec:
replicas: 3
selector:
matchLabels:
app: stateset-agent
type: procurement
template:
metadata:
labels:
app: stateset-agent
type: procurement
spec:
serviceAccountName: agent-service-account
securityContext:
runAsNonRoot: true
runAsUser: 1000
fsGroup: 2000
containers:
- name: agent
image: stateset/agent-runtime:1.2.3
securityContext:
allowPrivilegeEscalation: false
readOnlyRootFilesystem: true
capabilities:
drop:
- ALL
env:
- name: AGENT_TYPE
value: "procurement"
- name: STATESET_ENDPOINT
value: "https://rpc.stateset.network"
- name: WALLET_ADDRESS
valueFrom:
secretKeyRef:
name: agent-wallet
key: address
- name: PRIVATE_KEY
valueFrom:
secretKeyRef:
name: agent-wallet
key: private_key
resources:
requests:
cpu: 500m
memory: 1Gi
limits:
cpu: 1000m
memory: 2Gi
livenessProbe:
httpGet:
path: /health
port: 8080
periodSeconds: 30
readinessProbe:
httpGet:
path: /ready
port: 8080
periodSeconds: 10
```
### Auto-Scaling Agent Networks
```rust theme={null}
// Automatic scaling system for agent networks
pub struct AgentAutoScaler {
metrics_monitor: MetricsMonitor,
scaling_policy: ScalingPolicy,
deployment_manager: DeploymentManager,
load_balancer: LoadBalancer,
}
impl AgentAutoScaler {
pub async fn evaluate_scaling_needs(&self) -> Result {
// Collect current metrics
let current_metrics = self.metrics_monitor
.get_current_metrics()
.await?;
// Analyze load patterns
let load_analysis = self.analyze_load_patterns(¤t_metrics)?;
// Check scaling triggers
let scaling_triggers = self.check_scaling_triggers(&load_analysis)?;
if scaling_triggers.scale_up {
Ok(ScalingDecision::ScaleUp {
additional_agents: scaling_triggers.recommended_increase,
reason: scaling_triggers.scale_up_reason,
})
} else if scaling_triggers.scale_down {
Ok(ScalingDecision::ScaleDown {
agents_to_remove: scaling_triggers.recommended_decrease,
reason: scaling_triggers.scale_down_reason,
})
} else {
Ok(ScalingDecision::NoAction)
}
}
pub async fn execute_scaling(
&self,
decision: ScalingDecision,
) -> Result {
match decision {
ScalingDecision::ScaleUp { additional_agents, .. } => {
// Deploy additional agent instances
let new_agents = self.deployment_manager
.deploy_agents(additional_agents)
.await?;
// Update load balancer
self.load_balancer
.add_agents(new_agents.clone())
.await?;
Ok(ScalingResult::ScaledUp { new_agents })
},
ScalingDecision::ScaleDown { agents_to_remove, .. } => {
// Gracefully shutdown agents
let shutdown_agents = self.select_agents_for_shutdown(agents_to_remove)?;
// Remove from load balancer first
self.load_balancer
.remove_agents(shutdown_agents.clone())
.await?;
// Wait for current tasks to complete
self.wait_for_task_completion(&shutdown_agents).await?;
// Shutdown agents
self.deployment_manager
.shutdown_agents(shutdown_agents.clone())
.await?;
Ok(ScalingResult::ScaledDown { removed_agents: shutdown_agents })
},
ScalingDecision::NoAction => Ok(ScalingResult::NoChange),
}
}
}
```
***
This autonomous agent architecture provides the foundation for truly self-governing digital entities that can participate in the global economy with their own USDC wallets, make autonomous decisions, coordinate with other agents, and interact with any web service through the MCP protocol. The system is designed for security, scalability, and real-world deployment in enterprise environments.
# API Keys
Source: https://docs.stateset.com/cloud-api-reference/api-keys
Generate API Keys to make REST Calls to the Stateset API
Generate API Keys in order to make REST Calls using the stateset-node SDK and other client libraries.
In order to create a new API Key go to the Keys Tab
Click "Create API Key"
Enter a name for the API Key
Click "Add Key"
# Authentication
Source: https://docs.stateset.com/cloud-api-reference/authentication
Authenticating with the Stateset Cloud API
Stateset Cloud provides a REST and GraphQL API.
#### Authentication
It’s important to note that all data in Stateset is private by default. This means that you must authenticate with the Stateset API in order to read or write data. Stateset uses a token-based authentication system. This means that you must include your API token with every request that you make to the API.
Each token depicts a user who is authenticated to your Stateset platform instance. Tokens can only be generated for signed in users and each token is tied to a particular user.
Tokens can also be generated from your Stateset Cloud Account, using tokens that are set for each user and have a variable expiry date.
A request is considered “authenticated” when the backend can securely identify which user and which device is making the request. The reasons for making authenticated requests to the backend include:
* Associating the user with the action being performed
* Ensuring the user has permission to make the request
#### Connecting to Source control
To get started, signup at cloud.stateset.app
Click the "Add New" Button in the top right corner.
1. Connect your GitLab or GitHub Account:
First, you need to connect your GitLab or GitHub account to Stateset Cloud. This allows you to manage your serverless functions and deployments directly from your version control platform.
For GitLab:
Create a GitLab Account: If you don’t already have a GitLab account, sign up for one at gitlab.com.
Create a New Project: Log in to your GitLab account and create a new project to host your serverless application code.
For GitHub:
Create a GitHub Account: If you don’t already have a GitHub account, sign up for one at github.com.
Create a New Repository: Create a new repository on GitHub to store your serverless project files.
2. Import your project (GitLab)
After creating your project/repository, you need to import your existing project.
Select which project you want to deploy to Stateset Cloud.
3. Create Serverless Project
# Create Deployment
Source: https://docs.stateset.com/cloud-api-reference/deployments/create
POST https://api.stateset.com/v1/deployment
This endpoint creates a new deployment
### Body
This is the ID of the deployment to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/deployment' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
# Delete Deployment
Source: https://docs.stateset.com/cloud-api-reference/deployments/delete
DELETE https://api.stateset.com/v1/deployments/:id
This endpoint deletes an existing deployment.
### Body
The ID of the user to delete.
### Response
The ID provided in the data tab may be used to identify the deployment
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/deployment/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id: "1234",
}'
```
# Get Deployments
Source: https://docs.stateset.com/cloud-api-reference/deployments/get
GET https://api.stateset.com/v1/deployments
This endpoint gets deployments.
### Body
This is the id of the deployment.
### Response
This is the id of the deployment
This is the name of the deployment
This is the url of the deployment
This is the status of the deployment
This is the created\_at of the deployment
This is the updated\_at of the deployment
This is the project\_id of the deployment
This is the user\_id of the deployment
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/deployments' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": 1
}'
```
# Create Logs
Source: https://docs.stateset.com/cloud-api-reference/logs/create
POST https://api.stateset.com/v1/logs
This endpoint create new logs
### Body
This is the ID of the logs to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/logs' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
# Get Logs
Source: https://docs.stateset.com/cloud-api-reference/logs/get
GET https://api.stateset.com/v1/logs
This endpoint gets new logs
### Body
This is the ID of the logs to be get
### Response
This is the ID of the logs
This is the description of the logs
This is the timestamp of the logs
This is the type of the logs
# Stateset Cloud Overview
Source: https://docs.stateset.com/cloud-api-reference/overview
Explore the capabilities of the Stateset Cloud platform for serverless API management and deployment.
# Stateset Cloud: Simplified Serverless API Management
Stateset Cloud provides a robust platform for managing and deploying serverless APIs, accessible through both REST and GraphQL interfaces. This innovative platform empowers businesses to focus on developing core functionalities without the complexities of infrastructure management.
## Key Features of the Stateset Cloud Platform
The Stateset Cloud Platform is designed to streamline the entire API lifecycle with a focus on automation, security, and scalability.
* **Automatic Deployment:** Seamlessly and rapidly deploy serverless APIs. The platform intelligently automates the underlying infrastructure setup, scaling APIs based on demand while minimizing resource utilization.
* **Integrated Authentication:** Easily integrate APIs with the core StateSet Platform's authentication system. This ensures secure and consistent access, aligned with existing authentication mechanisms for enhanced control and security.
* **Scalability:** Designed to support the scalable deployment of APIs, making it easier for businesses to handle increased demand and varying loads. The platform automatically scales infrastructure to ensure optimal performance and availability regardless of API usage.
* **Seamless Integration:** Built for seamless integration with existing developer workflows and tools. Continue using preferred development frameworks and toolchains while leveraging the benefits of serverless architecture.
* **Cost-Effectiveness:** By adopting a serverless infrastructure, reduce investment costs related to managing and maintaining servers. Pay only for the resources consumed, providing a flexible and efficient cost model.
* **Comprehensive Monitoring and Analytics:** Track API performance, usage, and other critical metrics with comprehensive monitoring and analytics tools. These insights help optimize APIs and inform strategic decisions.
> The Stateset Cloud Platform empowers businesses by simplifying the management and deployment of serverless APIs, allowing a focus on core business functionalities without worrying about infrastructure complexities.
## Core Benefits of the Stateset Cloud Platform
The Stateset Cloud Platform offers several key advantages:
* **Cost Efficiency:** Serverless functions run only when called upon, providing a cost-effective alternative to traditional server-based applications. Pay only for consumed compute resources, avoiding expensive server infrastructure.
* **Scalability:** The platform automatically scales based on API demand, ensuring optimal performance at all times. Effortlessly scale applications and accommodate both predictable and unpredictable workloads.
* **Improved Security:** The integrated authentication system ensures secure access to deployed APIs, protecting sensitive data and maintaining compliance with industry regulations.
* **Faster Time to Market:** The streamlined deployment and management process encourages rapid development and deployment of APIs, allowing faster time to market.
* **Simplified Development Process:** The platform abstracts away concerns around infrastructure, allowing developers to focus on writing code for business logic rather than managing servers.
> By utilizing the Stateset Cloud Platform, companies not only manage and deploy serverless APIs with ease but also enjoy increased efficiency, security, and scalability. This allows businesses to focus on innovation and growth.
## Getting Started
The Stateset Cloud Platform is an invaluable solution for companies seeking to deploy serverless APIs with ease and efficiency. It provides automatic deployment and management, seamless integration with existing services, and a host of other benefits, making it easier to unlock the full potential of serverless technology.
**To get started, please reach out to [support@stateset.com](mailto:support@stateset.com), subject: "Stateset Cloud Platform"**
# Create Projects
Source: https://docs.stateset.com/cloud-api-reference/projects/create
POST https://api.stateset.com/v1/projects
This endpoint create new projects
### Body
This is the ID of the project to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/projects' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
# Delete Project
Source: https://docs.stateset.com/cloud-api-reference/projects/delete
DELETE https://api.stateset.com/v1/projects/:id
This endpoint deletes an existing project.
### Body
The ID of the user to delete.
### Response
The ID provided in the data tab may be used to identify the project
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/project/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id: "1234",
}'
```
# Get Projects
Source: https://docs.stateset.com/cloud-api-reference/projects/get
GET https://api.stateset.com/v1/projects
This endpoint gets projects.
### Body
This is the id of the project.
### Response
This is the id of the project.
This is the name of the project.
This is the description of the project.
This is the date the project was created.
This is the date the project was last updated.
This is the id of the user that created the project.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/projects' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": 1
}'
```
# Create Secrets
Source: https://docs.stateset.com/cloud-api-reference/secrets/create
POST https://api.stateset.com/v1/secrets
This endpoint create new secret
### Body
This is the ID of the secret to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/secrets' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
# Delete Secret
Source: https://docs.stateset.com/cloud-api-reference/secrets/delete
DELETE https://api.stateset.com/v1/secrets/:id
This endpoint deletes an existing secret.
### Body
The ID of the secret to delete.
### Response
The ID provided in the data tab may be used to identify the secret
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/secret/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id: "1234",
}'
```
# Get Secrets
Source: https://docs.stateset.com/cloud-api-reference/secrets/get
GET https://api.stateset.com/v1/secrets
This endpoint gets secrets.
### Body
This is the id of the secret
### Response
This is the id of the secret.
This is the name of the secret.
This is the description of the secret.
This is the value of the secret.
This is the date the secret was created.
This is the date the secret was updated.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/secrets' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": 1
}'
```
# Update Secrets
Source: https://docs.stateset.com/cloud-api-reference/secrets/update
POST https://api.stateset.com/v1/secrets
This endpoint create new secret
### Body
This is the ID of the secret to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/secrets' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
# Create Template
Source: https://docs.stateset.com/cloud-api-reference/templates/create
POST https://api.stateset.com/v1/templates
This endpoint create new templates
### Body
This is the ID of the template to be created.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request POST 'https://api.stateset.com/v1/templates' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
# Delete Template
Source: https://docs.stateset.com/cloud-api-reference/templates/delete
DELETE https://api.stateset.com/v1/templates/:id
This endpoint deletes an existing template.
### Body
The ID of the template to delete.
### Response
The ID provided in the data tab may be used to identify the template
The object type
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request DELETE 'https://api.stateset.com/v1/template/:id' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id: "1234",
}'
```
# Get Templates
Source: https://docs.stateset.com/cloud-api-reference/templates/get
GET https://api.stateset.com/v1/templates
This endpoint gets templates.
### Body
This is the id of the templates.
### Response
This is the id of the templates.
This is the name of the templates.
This is the description of the templates.
This is the created\_at of the templates.
This is the updated\_at of the templates.
```bash cURL theme={null}
curl --location --request GET 'https://api.stateset.com/v1/templates' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": 1
}'
```
# Update Template
Source: https://docs.stateset.com/cloud-api-reference/templates/update
POST https://api.stateset.com/v1/templates
This endpoint updates templates
### Body
This is the ID of the secret to be updated.
### Response
Indicates whether the call was successful. 1 if successful, 0 if not.
```bash cURL theme={null}
curl --location --request PUT 'https://api.stateset.com/v1/secrets' \
--header 'Content-Type: application/json' \
--header 'Authorization: Token ' \
--data-raw '{
"id": ""
}'
```
# StateSet Computer Use Agent
Source: https://docs.stateset.com/computer-use-agent
A production-grade AI automation platform powered by Claude Opus 4.5.
# StateSet Computer Use Agent - Architecture Overview
## Executive Summary
StateSet Computer Use Agent is a production-grade AI automation platform powered by Claude Opus 4.5. The system deploys multiple specialized AI agents that can see, understand, and interact with desktop environments to complete complex, long-running tasks autonomously. Built with Python using async/await patterns throughout, the platform implements Anthropic's context engineering research achieving 95% cost savings compared to naive approaches.
**Key Metrics:**
* Average tokens/task: 7,500 (95% reduction from 150k baseline)
* Average cost/task: $0.11 (95% savings from $2.25 baseline)
* Average task duration: 30 seconds (33% faster with parallel execution)
* Parallel speedup: 30-50% on multi-tool tasks
***
## System Architecture Diagram
```
┌─────────────────────────────────────────────────────────────────────────────┐
│ User Interface │
│ ┌──────────────┐ ┌──────────────┐ ┌──────────────┐ │
│ │ CLI/Shell │ │ Dashboard │ │ APIs │ │
│ │ Scripts │ │ (Next.js) │ │ (REST) │ │
│ └──────┬───────┘ └──────┬───────┘ └──────┬───────┘ │
└──────────────────┼─────────────────┼─────────────────┼───────────────────────┘
│ │ │
┌──────────────────▼─────────────────▼─────────────────▼───────────────────────┐
│ ORCHESTRATION LAYER │
│ ┌────────────────────────────────────────────────────────────────────────┐ │
│ │ main.py │ │
│ │ ┌─────────────────┐ ┌─────────────────┐ ┌─────────────────────────┐│ │
│ │ │ Agent Selector │ │ GlobalState │ │ Multi-Agent Runner ││ │
│ │ │ (keyword-based) │ │ (thread-safe) │ │ (asyncio.gather) ││ │
│ │ └─────────────────┘ └─────────────────┘ └─────────────────────────┘│ │
│ └────────────────────────────────────────────────────────────────────────┘ │
└───────────────────────────────────┬─────────────────────────────────────────┘
│
┌───────────────────────────────────▼─────────────────────────────────────────┐
│ AGENT ENGINE │
│ ┌────────────────────────────────────────────────────────────────────────┐ │
│ │ agent/loop.py │ │
│ │ ┌──────────────┐ ┌──────────────┐ ┌──────────────┐ ┌────────────┐ │ │
│ │ │ Sampling │ │ API │ │ System │ │ Message │ │ │
│ │ │ Loop │ │ Providers │ │ Prompt │ │ Manager │ │ │
│ │ │ │ │ (3 backends) │ │ Init │ │ (cache) │ │ │
│ │ └──────────────┘ └──────────────┘ └──────────────┘ └────────────┘ │ │
│ └────────────────────────────────────────────────────────────────────────┘ │
│ │
│ ┌────────────────────┐ ┌────────────────────┐ ┌────────────────────────┐ │
│ │ SubagentManager │ │ MCPManager │ │ StructuredOutput │ │
│ │ (task delegation) │ │ (external tools) │ │ Parser │ │
│ └────────────────────┘ └────────────────────┘ └────────────────────────┘ │
└───────────────────────────────────┬─────────────────────────────────────────┘
│
┌───────────────────────────────────▼─────────────────────────────────────────┐
│ TOOL LAYER │
│ ┌──────────────────────────────────────────────────────────────────────┐ │
│ │ ToolCollection │ │
│ │ ┌────────────┐ ┌────────────┐ ┌────────────┐ ┌────────────────────┐│ │
│ │ │ Computer │ │ Bash │ │ Edit │ │ Memory ││ │
│ │ │ Tool │ │ Tool │ │ Tool │ │ Tool ││ │
│ │ │ (GUI ops) │ │ (commands) │ │ (files) │ │ (persistence) ││ │
│ │ └────────────┘ └────────────┘ └────────────┘ └────────────────────┘│ │
│ │ ┌────────────┐ ┌────────────┐ ┌────────────┐ ┌────────────────────┐│ │
│ │ │ AGI │ │ Subagent │ │ StateSet │ │ AskUser ││ │
│ │ │ Tool │ │ Tool │ │ CLI Tool │ │ Tool ││ │
│ │ └────────────┘ └────────────┘ └────────────┘ └────────────────────┘│ │
│ └──────────────────────────────────────────────────────────────────────┘ │
└───────────────────────────────────┬─────────────────────────────────────────┘
│
┌───────────────────────────────────▼─────────────────────────────────────────┐
│ OPTIMIZATION LAYER │
│ ┌───────────────────┐ ┌───────────────────┐ ┌───────────────────────────┐│
│ │ ParallelExecutor │ │ ContextOptimizer │ │ ToolExecutionGuard ││
│ │ (30-50% speedup) │ │ (5 patterns) │ │ (safety + verification) ││
│ └───────────────────┘ └───────────────────┘ └───────────────────────────┘│
│ ┌───────────────────┐ ┌───────────────────┐ ┌───────────────────────────┐│
│ │ StuckDetection │ │ Verification │ │ Checkpoint ││
│ │ (loop prevention) │ │ (visual confirm) │ │ (state persistence) ││
│ └───────────────────┘ └───────────────────┘ └───────────────────────────┘│
└───────────────────────────────────┬─────────────────────────────────────────┘
│
┌───────────────────────────────────▼─────────────────────────────────────────┐
│ OBSERVABILITY LAYER │
│ ┌──────────────────────────────────────────────────────────────────────┐ │
│ │ UnifiedObservability │ │
│ │ ┌────────────┐ ┌────────────┐ ┌────────────┐ ┌────────────────────┐│ │
│ │ │ Structured │ │OpenTelemetry│ │ Prometheus │ │ Real-time Event ││ │
│ │ │ Logging │ │ Tracing │ │ Metrics │ │ Streaming ││ │
│ │ └────────────┘ └────────────┘ └────────────┘ └────────────────────┘│ │
│ └──────────────────────────────────────────────────────────────────────┘ │
└───────────────────────────────────┬─────────────────────────────────────────┘
│
┌───────────────────────────────────▼─────────────────────────────────────────┐
│ EXTERNAL SERVICES │
│ ┌────────────┐ ┌────────────┐ ┌────────────┐ ┌────────────────────────┐ │
│ │ Anthropic │ │ StateSet │ │ Stripe │ │ MCP Servers │ │
│ │ API │ │ APIs │ │ Billing │ │ (Slack, GitHub, etc.) │ │
│ └────────────┘ └────────────┘ └────────────┘ └────────────────────────┘ │
└─────────────────────────────────────────────────────────────────────────────┘
```
***
## Core Components
### 1. Main Orchestrator (`main.py`)
The entry point for all agent execution, responsible for:
**Environment Validation:**
```python theme={null}
def validate_environment(*, require_display: bool = True) -> Dict[str, str]:
"""Validates ANTHROPIC_API_KEY, DISPLAY, STRIPE_API_KEY, WORKSPACE_PATH"""
```
**Agent Selection:**
```python theme={null}
def get_active_agents(instruction: str) -> List[AgentType]:
"""Keyword-based agent selection from instruction text"""
# Matches: "auto-close" → AUTO_CLOSE, "social media" → SOCIAL_MEDIA, etc.
```
**Global State Management:**
```python theme={null}
class GlobalState:
running: bool # System-wide running flag
tasks: Set[asyncio.Task] # Active agent tasks
shutdown_event: Event # Graceful shutdown coordination
_lock: threading.Lock # Thread-safe state management
```
**Multi-Agent Execution:**
```python theme={null}
async def continuous_loop(agents: List[AgentConfig], instruction: str):
"""Spawns agents in parallel using asyncio.gather()"""
tasks = [asyncio.create_task(run_agent(agent, instruction)) for agent in agents]
results = await asyncio.gather(*tasks, return_exceptions=True)
```
**Task Completion Analysis:**
```python theme={null}
async def analyze_task_completion(messages, agent_type) -> TaskStatus:
"""Agent-specific completion detection with indicator patterns"""
# AUTO_CLOSE: "ticket closed", "successfully closed", "task finished"
# SOCIAL_MEDIA: "comment hidden", "content removed", "moderation complete"
```
### 2. Agent Loop (`agent/loop.py`)
The core conversation engine with Claude API:
**Sampling Loop:**
```python theme={null}
async def sampling_loop(
model: str, # claude-opus-4-5-20251101
provider: APIProvider, # ANTHROPIC | BEDROCK | VERTEX
system_prompt_suffix: str, # Agent-specific rules
messages: List[BetaMessageParam],
tool_collection: ToolCollection,
# New capabilities
enable_subagents: bool = True,
mcp_servers: Dict = None,
output_schema: Dict = None,
) -> SamplingLoopResult:
```
**API Provider Support:**
| Provider | Model ID | Use Case |
| --------- | --------------------------------------- | ------------------ |
| ANTHROPIC | claude-opus-4-5-20251101 | Direct API access |
| BEDROCK | anthropic.claude-opus-4-5-20251101-v1:0 | AWS infrastructure |
| VERTEX | claude-opus-4-5-20251101 | Google Cloud |
**Beta Flags:**
* `prompt-caching-2024-07-31` - 90% cost reduction on cached tokens
* `advanced-tool-use-2025-11-20` - Tool search (regex/bm25)
* `effort-2025-11-24` - Effort parameter (low/medium/high)
* `computer-use-2025-11-24` - Latest tool version with zoom action
**System Prompt Initialization:**
```python theme={null}
async def initialize_system_prompt(agent_config: AgentConfig) -> str:
"""Fetches rules/attributes from StateSet APIs:
- /api/rules/get-agent-rules
- /api/attributes/get-agent-attributes
- /api/agents/get-agent
"""
```
### 3. Tool System (`agent/tools/`)
**Tool Hierarchy:**
```
BaseAnthropicTool (Abstract)
├── ComputerTool (3 versions)
│ ├── Actions: screenshot, click, type, scroll, drag, zoom
│ ├── Resolution scaling (XGA, WXGA, FWXGA)
│ └── Performance: 8ms typing delay, 100-char groups
├── BashTool
│ ├── Persistent session with sentinel pattern
│ ├── Async subprocess management
│ └── 60-second timeout
├── EditTool
│ ├── File creation/modification
│ └── Directory traversal prevention
├── MemoryTool
│ ├── Commands: view, create, str_replace, insert, delete, rename
│ ├── Prompt injection sanitization
│ └── Per-agent memory isolation
├── AGITool
│ └── Extended AGI capabilities
├── SubagentTool (lazy-loaded)
│ └── Spawn specialized subagents
└── AskUserTool
└── Human-in-the-loop requests
```
**Tool Versions:**
| Version | Release | Features |
| ----------------------- | -------- | ---------------------------------- |
| computer\_use\_20251124 | Current | Zoom action, deferred tool loading |
| computer\_use\_20250124 | Previous | Stable production version |
| computer\_use\_20241022 | Legacy | Backward compatibility |
**ToolCollection API:**
```python theme={null}
class ToolCollection:
tool_map: Dict[str, BaseAnthropicTool] # name → tool
def to_params(self) -> List[Dict] # Convert to API format
async def run(self, name, input) -> ToolResult
def set_deferred_tools(self, tools: List[str]) # For tool search
```
***
## Advanced Capabilities
### 4. Subagent System (`agent/subagent.py`)
Implements Anthropic's sub-agent compression pattern for 95% context savings:
**Subagent Types:**
| Type | Model | Max Tokens | Use Case |
| -------- | ------ | ---------- | -------------------------------- |
| EXPLORE | Haiku | 4096 | Fast codebase exploration |
| ANALYZE | Sonnet | 8192 | Deep analysis with thinking |
| EXECUTE | Sonnet | 4096 | Task execution with verification |
| RESEARCH | Haiku | 4096 | Web search and synthesis |
| CODE | Sonnet | 8192 | Code generation/modification |
**Architecture:**
```
MainAgent (Opus 4.5)
│
├── spawn_subagent("explore", "Find auth files")
│ └── Returns: 2k summary (not 50k raw output)
│
├── spawn_subagent("analyze", "Review patterns")
│ └── Returns: Structured insights
│
└── spawn_subagent("execute", "Refactor code")
└── Returns: Confirmation + diff
```
**Usage:**
```python theme={null}
from agent.subagent import SubagentManager, SubagentType
manager = SubagentManager(api_key)
result = await manager.spawn(
task="Analyze the authentication flow",
subagent_type=SubagentType.ANALYZE,
)
# result.result contains compressed summary
```
### 5. MCP Client Integration (`agent/mcp_client.py`)
Connect to external Model Context Protocol servers:
**Supported Transports:**
* STDIO (subprocess)
* SSE (Server-Sent Events)
* HTTP (direct HTTP)
**Preset Servers:**
```python theme={null}
PRESET_SERVERS = {
"slack": {"command": "npx", "args": ["-y", "@modelcontextprotocol/server-slack"]},
"github": {"command": "npx", "args": ["-y", "@modelcontextprotocol/server-github"]},
"postgres": {"command": "npx", "args": ["-y", "@modelcontextprotocol/server-postgres"]},
"filesystem": {...},
"memory": {...},
"brave-search": {...},
"puppeteer": {...},
"sqlite": {...},
}
```
**Usage in sampling\_loop:**
```python theme={null}
result = await sampling_loop(
mcp_servers={
"slack": {
"command": "npx",
"args": ["-y", "@modelcontextprotocol/server-slack"],
"env": {"SLACK_BOT_TOKEN": os.environ["SLACK_BOT_TOKEN"]}
}
},
# Agent now has access to mcp__slack__send_message, etc.
)
```
### 6. Structured Output (`agent/structured_output.py`)
Force Claude to return valid JSON matching specified schemas:
**Pre-defined Schemas:**
* `TICKET_ANALYSIS_SCHEMA` - Support ticket analysis
* `TASK_RESULT_SCHEMA` - Task completion results
* `CODE_ANALYSIS_SCHEMA` - Code review findings
* `ENTITY_EXTRACTION_SCHEMA` - Entity extraction
**Usage:**
```python theme={null}
from agent.structured_output import OutputSchema, StructuredOutputParser
schema = OutputSchema(
name="TicketAnalysis",
schema={
"type": "object",
"properties": {
"tickets_to_close": {"type": "array", "items": {"type": "string"}},
"summary": {"type": "string"},
"confidence": {"type": "number", "minimum": 0, "maximum": 1}
},
"required": ["tickets_to_close", "summary"]
}
)
result = await sampling_loop(output_schema=schema.schema, ...)
parser = StructuredOutputParser(schema)
data = parser.parse(response_text) # Validates against schema
```
***
## Optimization Systems
### 7. Parallel Executor (`agent/parallel_executor.py`)
Automatic parallel execution for independent tool calls:
**Dependency Analysis:**
```python theme={null}
class DependencyAnalyzer:
def analyze(self, tool_calls: List[ToolCall]) -> ExecutionPlan:
"""
Rules:
- Computer tool calls: Always sequential (visual state dependency)
- Same path parameter: Sequential (file system dependency)
- Read-only tools: Can parallelize
- Write operations: Sequential
"""
```
**Execution Strategy:**
```
Tool Calls: [screenshot, bash(ls), bash(pwd), click]
↓
Dependency Analysis:
- screenshot → click (computer tool dependency)
- bash(ls), bash(pwd) (independent, read-only)
↓
Execution Plan:
1. [screenshot] # Sequential
2. [bash(ls), bash(pwd)] # Parallel
3. [click] # Sequential
↓
Result: 30-50% speedup
```
### 8. Context Optimizer (`agent/context_optimizer.py`)
Implements 5 Anthropic context engineering patterns:
**Pattern 1: Just-in-Time Retrieval**
```python theme={null}
# Instead of: read_file("large_file.py")
# Use: grep("pattern", "large_file.py") | head -50
```
**Pattern 2: Dynamic Compaction**
```python theme={null}
class ContextBudget:
OPTIMAL = 50_000 # EXCELLENT attention quality
ATTENTION_DEGRADATION = 100_000 # GOOD → DEGRADED
WARNING = 150_000 # DEGRADED → WARNING
CRITICAL = 200_000 # WARNING → CRITICAL
```
**Pattern 3: Structured Note-Taking**
```python theme={null}
# Persistent memory outside context window
memory_tool.create("auth_findings", "OAuth2 flow uses refresh tokens...")
```
**Pattern 4: Sub-Agent Compression**
```python theme={null}
# 50k raw exploration → 2k structured summary
subagent = await manager.spawn(task="Find all API endpoints", type=EXPLORE)
```
**Pattern 5: Attention Budget Monitoring**
```python theme={null}
class AttentionQuality(Enum):
EXCELLENT = "excellent" # < 50k tokens
GOOD = "good" # < 100k tokens
DEGRADED = "degraded" # < 150k tokens
WARNING = "warning" # < 200k tokens
CRITICAL = "critical" # > 200k tokens
```
### 9. Tool Execution Guard (`agent/tool_guard.py`)
Safety and verification layer:
**Features:**
* **Pre-execution Validation**: Safety checks before tool execution
* **Visual Verification**: Confirms actions took effect (optional)
* **Stuck Detection**: Monitors for infinite loops
* **Result Caching**: 120-second TTL for cacheable operations
**Speed Modes:**
```bash theme={null}
# Normal mode: Verification enabled (~0.5-1.0s per action)
python main.py "task"
# Fast mode: Skip verification (2-3x faster)
AGENT_FAST_MODE=1 python main.py "task"
```
### 10. Stuck Detection (`agent/stuck_detection.py`)
Prevents infinite loops and stuck patterns:
**Detection Methods:**
* Repeating same action consecutively
* Cycling between 2-3 actions
* No visual progress (identical screenshots)
* Slow progress (too few actions per time)
**Recovery Strategies:**
```python theme={null}
class StuckDetector:
def check(self, action: ActionRecord) -> Optional[RecoverySuggestion]:
"""
Returns suggestions like:
- "Try a different approach"
- "Scroll to see more content"
- "Check if element exists"
"""
```
***
## Observability System
### 11. Unified Observability (`agent/observability/`)
Single interface for all observability concerns:
**Configuration:**
```python theme={null}
from agent.observability import get_observability, configure_observability
configure_observability(
enable_metrics=True,
enable_tracing=True,
enable_streaming=True,
metrics_port=9090,
otlp_endpoint="localhost:4317", # OpenTelemetry
)
```
**Usage:**
```python theme={null}
obs = get_observability()
async with obs.task_context("AUTO_CLOSE", "agent-123", "Close tickets"):
obs.log_info("Starting task", tickets_count=10)
with obs.tool_execution("computer", action="click"):
# Automatically tracked
pass
obs.record_api_call(
provider="anthropic",
model="claude-opus-4-5-20251101",
latency=2.5,
input_tokens=1500,
output_tokens=500,
)
```
**Components:**
| Component | Purpose | Backend |
| ------------------- | ---------------------- | ---------------- |
| Structured Logging | JSON logs with context | Python logging |
| Distributed Tracing | Request correlation | OpenTelemetry |
| Metrics | Performance tracking | Prometheus |
| Event Streaming | Real-time updates | SSE/WebSocket |
| Health Monitoring | System health | Circuit breakers |
**Environment Variables:**
```bash theme={null}
METRICS_PORT=9090 # Prometheus metrics
OTLP_ENDPOINT=localhost:4317 # OpenTelemetry collector
LOG_FORMAT=json # json | human | compact
LOG_LEVEL=INFO # DEBUG | INFO | WARNING | ERROR
```
***
## Infrastructure
### 12. Configuration Management (`agent/config.py`)
Centralized configuration with documented rationale:
**Configuration Classes:**
```python theme={null}
@dataclass
class ContextSettings:
optimal_budget: int = 50_000 # From Anthropic research
degradation_threshold: int = 100_000 # Attention starts degrading
warning_threshold: int = 150_000 # Significant degradation
max_context: int = 200_000 # Model limit
@dataclass
class ToolSettings:
bash_timeout: int = 60 # Optimized from 120s
typing_delay_ms: int = 8 # Characters per ms
screenshot_retention: int = 5 # Most recent screenshots
@dataclass
class BudgetSettings:
input_price_per_million: float = 3.0 # Claude Opus 4.5
output_price_per_million: float = 15.0
cached_input_price: float = 0.30 # 90% savings
```
### 13. Exception Hierarchy (`agent/exceptions.py`)
Comprehensive error handling:
```
AgentError (base)
├── RetryableError
│ ├── NetworkError
│ ├── RateLimitError
│ ├── TimeoutError
│ └── ServiceUnavailableError
├── NonRetryableError
│ ├── ConfigurationError
│ ├── ValidationError
│ ├── SecurityError
│ └── AuthenticationError
├── BudgetError
│ ├── DailyBudgetExceededError
│ └── TaskBudgetExceededError
└── ToolError
├── ToolExecutionError
├── ToolTimeoutError
└── ToolValidationError
```
### 14. Health Monitoring (`agent/health.py`)
Production health checks:
```python theme={null}
class HealthChecker:
async def check_anthropic_api(test_connectivity=True) -> HealthCheck
async def check_system_resources() -> HealthCheck
async def check_disk_space() -> HealthCheck
# Circuit breaker for failing services
circuit_breaker: CircuitBreaker
```
**Health States:**
* `HEALTHY` - All checks passing
* `DEGRADED` - Some checks failing, system operational
* `UNHEALTHY` - Critical failures
***
## Dashboard Architecture
### 15. Backend (`dashboard/backend/`)
FastAPI REST API with async operations:
```
dashboard/backend/
├── app/
│ ├── main.py # FastAPI app factory
│ ├── api/ # REST API routes
│ │ ├── jobs.py # Job CRUD
│ │ ├── templates.py # Workflow templates
│ │ ├── artifacts.py # Screenshot/output storage
│ │ └── metrics.py # Performance tracking
│ ├── models/ # SQLAlchemy ORM models
│ ├── schemas/ # Pydantic schemas
│ ├── services/ # Business logic
│ ├── tasks/ # Celery workers
│ │ └── worker.py # Async agent execution
│ └── core/ # Configuration, database
└── migrations/ # Alembic schema versioning
```
**Key Technologies:**
* FastAPI with CORS
* SQLAlchemy async ORM
* PostgreSQL database
* Celery task queue
* Server-Sent Events (SSE)
* S3-compatible artifact storage (boto3)
### 16. Frontend (`dashboard/frontend/`)
Next.js 14 application:
```
dashboard/frontend/
├── app/ # App router pages
├── components/ # React components
├── hooks/ # Custom React hooks
└── lib/ # Utilities
```
**Key Technologies:**
* Next.js 14 with app router
* React Query for data fetching
* Tailwind CSS styling
* EventSource for real-time updates
***
## Execution Flow
### Complete Request Flow
```
1. User Command
│
▼
2. validate_environment()
├── Check ANTHROPIC_API_KEY
├── Check DISPLAY
└── Validate optional keys
│
▼
3. get_active_agents(instruction)
├── Parse keywords: "auto-close" → AUTO_CLOSE
└── Return: List[AgentConfig]
│
▼
4. continuous_loop(agents, instruction)
│
├──────────────────────────────────────┐
│ │
▼ ▼
5a. run_agent(AUTO_CLOSE) 5b. run_agent(SOCIAL_MEDIA)
│ │
▼ ▼
6. initialize_system_prompt() 6. initialize_system_prompt()
├── Fetch rules from StateSet (parallel)
└── Build system prompt
│
▼
7. sampling_loop()
│
├─── Send to Claude API ──────────────────────────┐
│ │ │
│ ▼ │
│ Claude Response │
│ ├── Text content │
│ └── Tool calls │
│ │ │
│ ▼ │
├─── ToolExecutionGuard.execute() │
│ ├── DependencyAnalyzer │
│ ├── ParallelToolExecutor │
│ ├── StuckDetection │
│ └── Verification (optional) │
│ │ │
│ ▼ │
│ Tool Results │
│ │ │
└─────────┴───────────────────────────────────────┘
│
▼ (loop until done)
│
▼
8. analyze_task_completion()
├── Check completion indicators
└── Return TaskStatus
│
▼
9. send_stripe_meter_event()
├── Token usage
└── Cost calculation
│
▼
10. shutdown_gracefully()
├── Cancel all tasks
└── Cleanup resources
```
***
## Agent Types
### Supported Agents
| Agent Type | Keywords | Purpose |
| ------------------- | -------------------------- | ------------------------------ |
| AUTO\_CLOSE | "auto-close", "ticket" | Close resolved support tickets |
| SOCIAL\_MEDIA | "social media", "moderate" | Content moderation |
| LINKEDIN\_MESSENGER | "linkedin", "outreach" | LinkedIn automation |
| SLACK\_SUPPORT | "slack", "support" | Slack support automation |
| SHOPIFY | "shopify", "e-commerce" | E-commerce management |
| ONBOARDING | "onboarding", "setup" | User onboarding |
| STATESET\_AGENTIC | "stateset", "custom" | Custom tasks |
### Agent Configuration
```python theme={null}
@dataclass
class AgentConfig:
org_id: str # Organization identifier
agent_id: str # Unique agent identifier
description: str # Agent purpose
capabilities: List[str] # What the agent can do
stripe_customer_id: str # Billing identifier
```
***
## Security Architecture
### API Key Management
* All keys via environment variables
* Validation on startup
* No key transmission to external services
### Tool Safety
* Directory traversal prevention in EditTool
* Prompt injection protection in MemoryTool
* Pre-execution validation via ToolExecutionGuard
* Agent memory isolation (per agent\_id)
### Sandbox Execution
* Tools run in controlled environment
* File system access limited by permissions
* Network access controlled by system
***
## Performance Characteristics
### Benchmarks
| Metric | Value | Notes |
| ---------------- | -------- | ------------------------ |
| Tokens/task | 7,500 | 95% reduction from 150k |
| Cost/task | \$0.11 | 95% savings from \$2.25 |
| Task duration | 30s | 33% faster with parallel |
| Parallel speedup | 30-50% | On multi-tool tasks |
| Typing speed | 8ms/char | Optimized from 50ms |
| Bash timeout | 60s | Optimized from 120s |
### Cost Breakdown
| Operation | Price |
| ------------- | ----------------------- |
| Input tokens | \$3.00/1M |
| Output tokens | \$15.00/1M |
| Cached input | \$0.30/1M (90% savings) |
***
## File Organization
```
stateset-computer-use-agent/
├── main.py # Entry point, orchestration
├── agent/
│ ├── loop.py # Core sampling loop
│ ├── parallel_executor.py # Parallel tool execution
│ ├── context_optimizer.py # Context engineering
│ ├── tool_guard.py # Safety checks
│ ├── stuck_detection.py # Loop prevention
│ ├── verification.py # Visual verification
│ ├── subagent.py # Subagent spawning
│ ├── mcp_client.py # MCP integration
│ ├── structured_output.py # JSON schema validation
│ ├── checkpoint.py # State persistence
│ ├── metrics.py # Performance tracking
│ ├── skill_manager.py # Skill system
│ ├── config.py # Configuration
│ ├── exceptions.py # Error hierarchy
│ ├── logging_config.py # Structured logging
│ ├── health.py # Health monitoring
│ ├── observability/ # Unified observability
│ │ ├── unified.py
│ │ ├── tracing.py
│ │ └── metrics.py
│ └── tools/ # Tool implementations
│ ├── base.py
│ ├── collection.py
│ ├── computer.py
│ ├── bash.py
│ ├── edit.py
│ ├── memory.py
│ ├── agi.py
│ └── groups.py
├── dashboard/
│ ├── backend/ # FastAPI + Celery
│ └── frontend/ # Next.js 14
├── start-*.sh # Launch scripts
└── test_*.py # Test suites
```
***
## Extension Points
### Adding New Agents
1. Define AgentConfig in `AGENT_CONFIGS`
2. Add keyword detection in `get_active_agents()`
3. Create completion indicators in `analyze_task_completion()`
### Adding New Tools
1. Inherit from `BaseAnthropicTool`
2. Implement `__call__` returning `ToolResult`
3. Add to version groups in `agent/tools/groups.py`
4. Update tool traits if cacheable/read-only
### Adding MCP Servers
```python theme={null}
await mcp_manager.add_server("custom-server", {
"command": "npx",
"args": ["-y", "@my/custom-mcp-server"],
"env": {"API_KEY": "..."}
})
```
***
## Quick Reference
### Environment Variables
```bash theme={null}
# Required
ANTHROPIC_API_KEY=sk-ant-api03-...
DISPLAY=:1
# Optional
STRIPE_API_KEY=sk_live_...
WORKSPACE_PATH=/path/to/workspace
AGENT_FAST_MODE=1 # Skip verification
METRICS_PORT=9090 # Prometheus
OTLP_ENDPOINT=localhost:4317 # OpenTelemetry
LOG_FORMAT=json # json | human | compact
LOG_LEVEL=INFO # DEBUG | INFO | WARNING | ERROR
```
### Common Commands
```bash theme={null}
# Run agents
python main.py "auto-close tickets"
python main.py "auto-close and social media" # Parallel
# With options
python main.py --effort medium "task"
python main.py --tool-search regex --defer-tool agi_agent "task"
# Dashboard
cd dashboard && docker compose up -d
```
***
This architecture provides a scalable, maintainable foundation for computer use automation with AI agents, implementing production-grade patterns for reliability, observability, and cost optimization.
# Developer Guide
Source: https://docs.stateset.com/development
Everything you need to build agentic commerce with StateSet
# Build the Future of Commerce
Welcome to the StateSet Documentation. Whether you're building your first AI agent or architecting a complex autonomous system, this guide will help you harness the full power of StateSet's platform.
**New to StateSet?** Start with our [Quickstart Guide](/quickstart) to deploy
your first agent, then come back here to dive deeper.
## Why Developers Love StateSet
Built with Rust, Axum, GraphQL, and cutting-edge AI models
Clean APIs, comprehensive SDKs for 11 languages, and documentation that
actually helps
From intent to outcome in minutes, not months
## Getting Started
### Prerequisites
Before you begin, ensure you have:
* **Node.js 22+** or **Python 3.8+**
* **TypeScript**: For better developer experience - **Git**: For version
control - **Docker**: For local development
### Installation
```bash npm theme={null}
npm install -g @stateset/cli
npm install @stateset/embedded
```
```bash python theme={null}
pip install stateset-embedded
```
## Core Concepts
### 1. Agents: Your AI Workforce
Agents are autonomous AI entities that can understand, decide, and act on behalf of your business. Each agent has:
* **Role & Personality**: Define its behavior and communication style
* **Capabilities**: Specific skills like order management, support, or analytics
* **Knowledge Base**: Access to your business documents and processes
* **Integrations**: Connections to external systems and APIs
```typescript theme={null}
const agent = await client.agents.create({
name: "Support Specialist",
role: "Senior Customer Success Manager",
personality: {
traits: ["empathetic", "solution-oriented", "professional"],
tone: "friendly yet professional",
},
capabilities: ["order_management", "refund_processing", "technical_support"],
knowledge_bases: ["product_docs", "support_playbook"],
});
```
### 2. Sandboxes: Orchestrating Agentic Operations
Sandboxes are isolated environments that allow you to run your AI Agents in a safe and controlled manner. They provide:
* **Secure Execution**: Run code and tools without affecting production
* **Resource Management**: Control compute and memory allocation
* **Network Isolation**: Isolate external calls and webhooks
* **State Management**: Track agent decisions and outcomes
**🚀 Ship faster with StateSet Sandbox** Get free sandbox credits when you
[sign up today](https://sandbox.stateset.app). No credit card required.
### 3. Workflows: Orchestrating Multi-Step Operations
Workflows handle long-running processes that span multiple steps and systems:
```typescript theme={null}
const workflow = await client.workflows.create({
name: "Order Fulfillment",
trigger: { event: "order.created" },
steps: [
{
name: "Check Inventory",
action: "inventory.check",
timeout: "30s",
},
{
name: "Process Payment",
action: "payment.process",
retry: { max: 3 },
},
{
name: "Create Shipment",
action: "shipping.create_label",
},
{
name: "Notify Customer",
action: "customer.notify",
template: "order_confirmation",
},
],
});
```
### 4. Events: Real-Time Business Signals
StateSet emits events for every meaningful state change:
```typescript theme={null}
// Subscribe to order events
client.events.subscribe({
events: ["order.*"],
handler: async (event) => {
switch (event.type) {
case "order.created":
await handleNewOrder(event.data);
break;
case "order.paid":
await triggerFulfillment(event.data);
break;
case "order.shipped":
await sendTrackingUpdate(event.data);
break;
}
},
});
```
## Essential SDK Methods
### Injecting Messages
Send messages to agents or conversations:
```typescript theme={null}
await client.messages.send({
to: "agent_id",
body: "Customer is asking about order status",
context: {
orderId: "ord_12345",
customerId: "cust_67890",
},
});
```
### Handling Conversations
Manage multi-turn conversations:
```typescript theme={null}
const conversation = await client.conversations.create({
participants: [
{ id: "agent_id", role: "agent" },
{ id: "customer_id", role: "customer" },
],
metadata: {
source: "web",
campaign: "summer_sale",
},
});
// Stream responses
const stream = await conversation.stream();
for await (const message of stream) {
console.log("Agent says:", message.content);
}
```
### Managing Knowledge Base
Upload and query documents:
```typescript theme={null}
// Create knowledge base
const kb = await client.knowledgeBases.create({
name: "Product Documentation",
agent_id: "agent_id",
});
// Upload documents
await kb.uploadDocument("./product-guide.pdf");
await kb.uploadDocument("./faq.md");
// Query knowledge
const results = await kb.query({
question: "What is your return policy?",
top_k: 3,
});
```
## Architecture Patterns
### Pattern 1: Agent + Integration
Connect agents to your existing systems:
```typescript theme={null}
await agent.addIntegration({
type: "webhook",
name: "order_lookup",
endpoint: "https://api.yourstore.com/orders",
authentication: {
type: "api_key",
key: process.env.STORE_API_KEY,
},
operations: ["read", "update"],
});
```
### Pattern 2: Event-Driven Workflow
React to business events automatically:
```typescript theme={null}
client.events.subscribe({
events: ["inventory.low_stock"],
handler: async (event) => {
// Trigger restocking
await client.workflows.trigger("restock", {
sku: event.data.sku,
quantity: event.data.reorder_point * 2,
});
// Notify procurement team
await client.notifications.send({
to: "procurement_team",
message: `Low stock alert for ${event.data.sku}`,
});
},
});
```
### Pattern 3: Multi-Agent Orchestration
Coordinate multiple specialized agents:
```typescript theme={null}
// Create specialized agents
const salesAgent = await client.agents.create({
name: "Sales Specialist",
role: "Sales Representative",
capabilities: ["lead_qualification", "product_recommendation", "pricing"],
});
const supportAgent = await client.agents.create({
name: "Support Specialist",
role: "Customer Support",
capabilities: ["troubleshooting", "returns", "faq"],
});
// Route based on intent
async function routeIntent(customerMessage) {
const intent = await client.intents.detect({
message: customerMessage,
});
if (intent.category === "sales") {
return salesAgent;
} else if (intent.category === "support") {
return supportAgent;
} else {
return await escalateToHuman();
}
}
```
## Error Handling Best Practices
### Graceful Degradation
```typescript theme={null}
try {
const result = await client.agents.execute({
agentId: "agent_id",
action: "process_order",
data: orderData,
});
} catch (error) {
if (error.code === "TIMEOUT") {
// Retry with exponential backoff
await retry(orderData, { maxAttempts: 3, backoff: "exponential" });
} else if (error.code === "RATE_LIMIT") {
// Queue for later processing
await queue.push({ action: "process_order", data: orderData });
} else {
// Log and escalate
logger.error("Agent execution failed", { error, orderData });
await notifyTeam({ error, orderData });
}
}
```
### Retry Strategies
```typescript theme={null}
async function withRetry(operation, options = {}) {
const {
maxAttempts = 3,
backoff = "exponential",
initialDelay = 1000,
} = options;
for (let attempt = 1; attempt <= maxAttempts; attempt++) {
try {
return await operation();
} catch (error) {
if (attempt === maxAttempts || !isRetryable(error)) {
throw error;
}
const delay =
backoff === "exponential"
? initialDelay * Math.pow(2, attempt - 1)
: initialDelay * attempt;
await sleep(delay);
}
}
}
```
## Performance Optimization
### Batch Operations
```typescript theme={null}
// Process multiple items efficiently
const orders = await client.orders.list({ limit: 100 });
const results = await Promise.allSettled(
orders.map((order) =>
client.agent.execute({
agentId: "agent_id",
action: "process_order",
data: order,
}),
),
);
// Handle results
results.forEach((result) => {
if (result.status === "fulfilled") {
logger.info("Order processed", result.value);
} else {
logger.error("Order failed", result.reason);
}
});
```
### Caching Strategy
```typescript theme={null}
import { LRUCache } from "lru-cache";
const cache = new LRUCache({
max: 1000,
ttl: 1000 * 60 * 15, // 15 minutes
});
async function getCachedData(key, fetcher) {
const cached = cache.get(key);
if (cached) return cached;
const data = await fetcher();
cache.set(key, data);
return data;
}
```
## Testing
### Unit Testing Agents
```typescript theme={null}
describe("Order Agent", () => {
it("should process new orders", async () => {
const mockOrder = {
items: [{ sku: "prod_123", quantity: 2 }],
total: 99.99,
};
const result = await agent.process(mockOrder);
expect(result.status).toBe("success");
expect(result.orderId).toBeDefined();
});
it("should handle low inventory", async () => {
const mockOrder = {
items: [{ sku: "out_of_stock_123", quantity: 10 }],
};
const result = await agent.process(mockOrder);
expect(result.status).toBe("failed");
expect(result.error).toContain("insufficient inventory");
});
});
```
### Integration Testing
```typescript theme={null}
describe("Order Workflow Integration", () => {
it("should fulfill order end-to-end", async () => {
// Create order
const order = await client.orders.create({
customer_id: "test_customer",
items: [{ sku: "test_product", quantity: 1 }],
});
// Wait for workflow completion
await client.events.wait({
event: "order.fulfilled",
orderId: order.id,
timeout: 30000,
});
// Verify fulfillment
const fulfillment = await client.fulfillments.get(order.id);
expect(fulfillment.tracking_number).toBeDefined();
});
});
```
## Monitoring & Debugging
### Enable Debug Logging
```typescript theme={null}
const client = new StateSetClient({
apiKey: process.env.STATESET_API_KEY,
logger: {
level: "debug",
format: "json",
},
});
```
### Track Agent Performance
```typescript theme={null}
const metrics = await client.agents.getMetrics({
agent_id: "agent_id",
period: "24h",
metrics: [
"messages_sent",
"response_time",
"resolution_rate",
"customer_satisfaction",
],
});
console.log("Average response time:", metrics.response_time.avg);
console.log("Resolution rate:", metrics.resolution_rate * 100, "%");
```
## Next Steps
Complete API documentation with all endpoints and parameters
Language-specific guides for Node.js, Python, Ruby, and more
Production-ready patterns and security considerations
***
### Ready to Build? Start with the [Quickstart Guide](/quickstart) or explore
the [API Reference](/api-reference/introduction) to begin integrating StateSet
into your application.
# Global Commerce Architecture
Source: https://docs.stateset.com/global-commerce-architecture
Technical architecture powering the world's commerce infrastructure with StateSet
# Global Commerce Architecture: Building the World's Financial Operating System
StateSet Commerce Network represents a fundamental reimagining of how global commerce operates. This document outlines the technical architecture, design principles, and infrastructure that enables StateSet to serve as the backend for the \$100+ trillion global economy.
## 🏗️ Architecture Overview
### High-Level System Design
```mermaid theme={null}
graph TB
subgraph "User Layer"
A[Mobile Apps]
B[Web Applications]
C[Enterprise ERPs]
D[Smart Agents]
end
subgraph "API Gateway Layer"
E[REST APIs]
F[GraphQL APIs]
G[gRPC APIs]
H[WebSocket APIs]
end
subgraph "Service Layer"
I[Orders Service]
J[Finance Service]
K[Compliance Service]
L[Global Commerce Service]
M[Identity Service]
N[Analytics Service]
end
subgraph "Blockchain Layer"
O[StateSet Cosmos Chain]
P[Smart Contracts]
Q[IBC Protocol]
R[Consensus Engine]
end
subgraph "Infrastructure Layer"
S[Multi-Region Deployment]
T[CDN & Caching]
U[Monitoring & Observability]
V[Security & Compliance]
end
subgraph "External Integrations"
W[Banking Partners]
X[Compliance Providers]
Y[Logistics Networks]
Z[Government Systems]
end
A --> E
B --> F
C --> G
D --> H
E --> I
F --> J
G --> K
H --> L
I --> O
J --> P
K --> Q
L --> R
O --> S
P --> T
Q --> U
R --> V
S --> W
T --> X
U --> Y
V --> Z
```
## 🌐 Global Infrastructure
### Multi-Region Deployment
StateSet operates a globally distributed infrastructure to ensure low latency and high availability for commerce operations worldwide.
#### Regional Architecture
```mermaid theme={null}
graph TB
subgraph "Americas"
A1[US East - Virginia]
A2[US West - California]
A3[Canada - Toronto]
A4[Brazil - São Paulo]
end
subgraph "Europe/Middle East/Africa"
E1[Ireland - Dublin]
E2[Germany - Frankfurt]
E3[UK - London]
E4[UAE - Dubai]
E5[South Africa - Cape Town]
end
subgraph "Asia Pacific"
P1[Singapore]
P2[Japan - Tokyo]
P3[Australia - Sydney]
P4[India - Mumbai]
P5[South Korea - Seoul]
end
subgraph "Cross-Region Services"
CR1[Global Load Balancer]
CR2[Cross-Region Replication]
CR3[Global CDN]
CR4[Distributed Consensus]
end
A1 --> CR1
A2 --> CR1
E1 --> CR1
P1 --> CR1
CR1 --> CR2
CR2 --> CR3
CR3 --> CR4
```
#### Performance Characteristics by Region
| Region | Latency (p95) | Throughput | Availability | Validators |
| -------------- | ------------- | ---------- | ------------ | ---------- |
| North America | 45ms | 15,000 TPS | 99.99% | 35 |
| Europe | 38ms | 12,000 TPS | 99.99% | 28 |
| Asia Pacific | 52ms | 18,000 TPS | 99.98% | 37 |
| Global Average | 45ms | 45,000 TPS | 99.99% | 100+ |
### Network Topology
```typescript theme={null}
// Global network configuration
const networkTopology = {
consensus: {
engine: 'Tendermint BFT',
validators: 100,
block_time: '1s',
finality: 'instant'
},
regions: [
{
name: 'us-east-1',
validators: 35,
rpc_endpoints: [
'https://rpc-us-east.stateset.network',
'https://rpc-backup-us-east.stateset.network'
],
api_endpoints: [
'https://api-us-east.stateset.network'
]
},
{
name: 'eu-west-1',
validators: 28,
rpc_endpoints: [
'https://rpc-eu-west.stateset.network',
'https://rpc-backup-eu-west.stateset.network'
],
api_endpoints: [
'https://api-eu-west.stateset.network'
]
},
{
name: 'ap-southeast-1',
validators: 37,
rpc_endpoints: [
'https://rpc-ap-southeast.stateset.network',
'https://rpc-backup-ap-southeast.stateset.network'
],
api_endpoints: [
'https://api-ap-southeast.stateset.network'
]
}
],
cross_region: {
replication: 'synchronous',
backup_strategy: '3-2-1',
disaster_recovery: 'automated'
}
};
```
## ⚡ Scalability Architecture
### Horizontal Scaling Strategy
StateSet employs multiple scaling techniques to handle global commerce volumes:
#### 1. Sharding Strategy
```mermaid theme={null}
graph TB
subgraph "Order Sharding"
OS1[Shard 1: Americas Orders]
OS2[Shard 2: EMEA Orders]
OS3[Shard 3: APAC Orders]
OS4[Shard 4: High-Volume Merchants]
end
subgraph "Geographic Sharding"
GS1[North America]
GS2[Europe]
GS3[Asia Pacific]
GS4[Global Merchants]
end
subgraph "Functional Sharding"
FS1[Payments Processing]
FS2[Order Management]
FS3[Compliance Checking]
FS4[Analytics Pipeline]
end
LB[Global Load Balancer]
LB --> OS1
LB --> OS2
LB --> OS3
LB --> OS4
OS1 --> GS1
OS2 --> GS2
OS3 --> GS3
OS4 --> GS4
GS1 --> FS1
GS2 --> FS2
GS3 --> FS3
GS4 --> FS4
```
#### 2. Auto-Scaling Configuration
```yaml theme={null}
# Kubernetes auto-scaling configuration
apiVersion: autoscaling/v2
kind: HorizontalPodAutoscaler
metadata:
name: stateset-orders-api
spec:
scaleTargetRef:
apiVersion: apps/v1
kind: Deployment
name: orders-api
minReplicas: 10
maxReplicas: 1000
metrics:
- type: Resource
resource:
name: cpu
target:
type: Utilization
averageUtilization: 70
- type: Resource
resource:
name: memory
target:
type: Utilization
averageUtilization: 80
- type: Pods
pods:
metric:
name: requests_per_second
target:
type: AverageValue
averageValue: "1000"
behavior:
scaleUp:
stabilizationWindowSeconds: 30
policies:
- type: Percent
value: 100
periodSeconds: 15
scaleDown:
stabilizationWindowSeconds: 300
policies:
- type: Percent
value: 50
periodSeconds: 60
```
### Performance Optimization
#### Caching Strategy
```mermaid theme={null}
graph TB
subgraph "L1 Cache - Application"
L1A[In-Memory Cache]
L1B[Application State]
end
subgraph "L2 Cache - Regional"
L2A[Redis Cluster]
L2B[Regional Data]
end
subgraph "L3 Cache - Global"
L3A[CDN Edge Cache]
L3B[Static Assets]
end
subgraph "L4 Cache - Database"
L4A[Query Result Cache]
L4B[Computed Views]
end
Request[API Request] --> L1A
L1A --> L2A
L2A --> L3A
L3A --> L4A
L4A --> DB[Database]
DB --> L4A
L4A --> L3A
L3A --> L2A
L2A --> L1A
L1A --> Response[API Response]
```
#### Database Architecture
```typescript theme={null}
// Multi-tier database strategy
const databaseArchitecture = {
// Hot data - frequent access
hot_tier: {
technology: 'CockroachDB',
replication: 'multi_region',
sla: '99.99%',
use_cases: ['active_orders', 'real_time_payments']
},
// Warm data - moderate access
warm_tier: {
technology: 'PostgreSQL',
sharding: 'by_time_range',
backup: 'continuous',
use_cases: ['order_history', 'analytics']
},
// Cold data - archival
cold_tier: {
technology: 'Amazon S3 + Glacier',
encryption: 'at_rest',
retention: '7_years',
use_cases: ['compliance_records', 'audit_trails']
},
// Search and analytics
search_tier: {
technology: 'Elasticsearch',
indices: 'time_based',
analytics: 'real_time',
use_cases: ['order_search', 'business_intelligence']
}
};
```
## 🔐 Security Architecture
### Zero-Trust Security Model
StateSet implements a comprehensive zero-trust security architecture:
```mermaid theme={null}
graph TB
subgraph "Identity & Access"
IA1[Multi-Factor Authentication]
IA2[Role-Based Access Control]
IA3[Attribute-Based Access Control]
IA4[Zero-Trust Network Access]
end
subgraph "Data Protection"
DP1[Encryption at Rest]
DP2[Encryption in Transit]
DP3[Field-Level Encryption]
DP4[Key Management HSM]
end
subgraph "Network Security"
NS1[Web Application Firewall]
NS2[DDoS Protection]
NS3[API Rate Limiting]
NS4[VPC Isolation]
end
subgraph "Compliance & Monitoring"
CM1[SIEM/SOAR]
CM2[Compliance Monitoring]
CM3[Threat Detection]
CM4[Incident Response]
end
User[API User] --> IA1
IA1 --> IA2
IA2 --> IA3
IA3 --> IA4
IA4 --> DP1
DP1 --> DP2
DP2 --> DP3
DP3 --> DP4
DP4 --> NS1
NS1 --> NS2
NS2 --> NS3
NS3 --> NS4
NS4 --> CM1
CM1 --> CM2
CM2 --> CM3
CM3 --> CM4
```
### Cryptographic Standards
```typescript theme={null}
// Encryption configuration
const securityConfig = {
encryption: {
algorithms: {
symmetric: 'AES-256-GCM',
asymmetric: 'RSA-4096, ECDSA-P384',
hashing: 'SHA-3-256',
signatures: 'Ed25519'
},
key_management: {
provider: 'AWS KMS + Azure Key Vault',
rotation: 'automatic_90_days',
backup: 'multi_region',
access_logging: true
},
data_classification: {
public: 'no_encryption',
internal: 'AES-256',
confidential: 'AES-256 + field_level',
restricted: 'AES-256 + HSM + multi_signature'
}
},
network_security: {
tls_version: '1.3',
cipher_suites: ['TLS_AES_256_GCM_SHA384'],
hsts: true,
certificate_transparency: true,
ocsp_stapling: true
}
};
```
## 🔗 Blockchain Integration
### StateSet Cosmos Chain Architecture
```mermaid theme={null}
graph TB
subgraph "Application Layer"
AL1[Orders Module]
AL2[Finance Module]
AL3[Compliance Module]
AL4[Identity Module]
end
subgraph "Cosmos SDK Framework"
CS1[ABCI Interface]
CS2[State Machine]
CS3[Transaction Pool]
CS4[Module Manager]
end
subgraph "Tendermint Core"
TC1[Consensus Engine]
TC2[P2P Networking]
TC3[Block Production]
TC4[State Synchronization]
end
subgraph "Storage Layer"
SL1[Merkle Tree State]
SL2[Block Store]
SL3[Evidence Store]
SL4[State Snapshots]
end
AL1 --> CS1
AL2 --> CS2
AL3 --> CS3
AL4 --> CS4
CS1 --> TC1
CS2 --> TC2
CS3 --> TC3
CS4 --> TC4
TC1 --> SL1
TC2 --> SL2
TC3 --> SL3
TC4 --> SL4
```
### Smart Contract Platform
```rust theme={null}
// StateSet smart contract structure
use cosmwasm_std::{
DepsMut, Env, MessageInfo, Response, Result,
Uint128, Addr, Binary
};
#[derive(Clone, Debug, PartialEq)]
pub struct GlobalCommerceContract {
// Core commerce functionality
pub order_management: OrderManager,
pub payment_processing: PaymentProcessor,
pub compliance_engine: ComplianceEngine,
pub cross_border_handler: CrossBorderHandler,
}
impl GlobalCommerceContract {
pub fn execute_order_flow(
&self,
deps: DepsMut,
env: Env,
info: MessageInfo,
order: Order,
) -> Result {
// 1. Validate order
self.order_management.validate_order(&order)?;
// 2. Check compliance
self.compliance_engine.screen_transaction(&order)?;
// 3. Process payment
let payment = self.payment_processing.process_usdc_payment(
&order.payment_info
)?;
// 4. Handle cross-border requirements
if order.is_cross_border() {
self.cross_border_handler.apply_regulations(&order)?;
}
// 5. Update state and emit events
Ok(Response::new()
.add_attribute("action", "order_executed")
.add_attribute("order_id", order.id)
.add_attribute("payment_id", payment.id))
}
}
```
### IBC Interoperability
```mermaid theme={null}
graph LR
subgraph "StateSet Chain"
SS[StateSet Commerce]
SSRP[Relayer Processes]
end
subgraph "Connected Chains"
OS[Osmosis DEX]
CH[Cosmos Hub]
JU[Juno]
AX[Axelar]
end
subgraph "External Networks"
ETH[Ethereum]
BSC[Binance Smart Chain]
POLY[Polygon]
end
SS <--> SSRP
SSRP <--> OS
SSRP <--> CH
SSRP <--> JU
SSRP <--> AX
AX <--> ETH
AX <--> BSC
AX <--> POLY
```
## 📊 Data Architecture
### Event-Driven Architecture
StateSet uses an event-driven architecture to ensure real-time responsiveness and system decoupling:
```mermaid theme={null}
graph TB
subgraph "Event Sources"
ES1[Order Events]
ES2[Payment Events]
ES3[Compliance Events]
ES4[External API Events]
end
subgraph "Event Processing"
EP1[Event Bus - Apache Kafka]
EP2[Stream Processing - Apache Flink]
EP3[Event Store - EventStore DB]
end
subgraph "Event Consumers"
EC1[Real-time Analytics]
EC2[Notification Service]
EC3[Audit Logging]
EC4[External Webhooks]
EC5[AI/ML Pipeline]
end
ES1 --> EP1
ES2 --> EP1
ES3 --> EP1
ES4 --> EP1
EP1 --> EP2
EP2 --> EP3
EP3 --> EC1
EP3 --> EC2
EP3 --> EC3
EP3 --> EC4
EP3 --> EC5
```
### Real-Time Data Pipeline
```yaml theme={null}
# Apache Kafka cluster configuration
kafka_cluster:
brokers: 9
partitions_per_topic: 12
replication_factor: 3
retention_policy: "7_days"
topics:
- name: "orders"
partitions: 12
cleanup_policy: "compact"
- name: "payments"
partitions: 12
cleanup_policy: "delete"
- name: "compliance_events"
partitions: 6
cleanup_policy: "compact"
- name: "cross_border_transactions"
partitions: 8
cleanup_policy: "delete"
# Stream processing configuration
flink_jobs:
- name: "real_time_analytics"
parallelism: 8
checkpointing: "exactly_once"
state_backend: "rocksdb"
- name: "fraud_detection"
parallelism: 4
machine_learning: true
model_serving: "tensorflow_extended"
- name: "compliance_monitoring"
parallelism: 6
external_apis: ["sanctions_lists", "export_controls"]
```
## 🔍 Observability & Monitoring
### Comprehensive Monitoring Stack
```mermaid theme={null}
graph TB
subgraph "Metrics Collection"
MC1[Prometheus]
MC2[Grafana]
MC3[Custom Metrics]
end
subgraph "Logging & Tracing"
LT1[ELK Stack]
LT2[Jaeger Tracing]
LT3[OpenTelemetry]
end
subgraph "Alerting & Incident Response"
AI1[PagerDuty]
AI2[OpsGenie]
AI3[Slack Integration]
end
subgraph "Business Intelligence"
BI1[Data Warehouse]
BI2[Business Dashboards]
BI3[ML Analytics]
end
Apps[Applications] --> MC1
Apps --> LT1
MC1 --> MC2
MC2 --> MC3
LT1 --> LT2
LT2 --> LT3
MC3 --> AI1
LT3 --> AI2
AI1 --> AI3
MC3 --> BI1
BI1 --> BI2
BI2 --> BI3
```
### Key Performance Indicators (KPIs)
```typescript theme={null}
// System KPIs dashboard configuration
const systemKPIs = {
availability: {
target: 99.99,
measurement: 'uptime_percentage',
alerting: 'below_99.95'
},
performance: {
api_latency_p95: '< 100ms',
api_latency_p99: '< 500ms',
throughput: '> 10000 rps',
error_rate: '< 0.1%'
},
business_metrics: {
orders_per_second: 'real_time',
payment_success_rate: '> 99.5%',
cross_border_completion: '> 95%',
compliance_automation: '> 99%'
},
security: {
failed_auth_attempts: '< 1000/hour',
api_abuse_detection: 'real_time',
compliance_violations: '0',
security_incidents: '0'
}
};
```
## 🌟 Advanced Capabilities
### AI/ML Integration
```mermaid theme={null}
graph TB
subgraph "Data Sources"
DS1[Transaction Data]
DS2[Market Data]
DS3[Compliance Data]
DS4[External Signals]
end
subgraph "ML Pipeline"
ML1[Data Preprocessing]
ML2[Feature Engineering]
ML3[Model Training]
ML4[Model Serving]
end
subgraph "AI Applications"
AI1[Fraud Detection]
AI2[Risk Assessment]
AI3[Price Optimization]
AI4[Demand Forecasting]
end
DS1 --> ML1
DS2 --> ML1
DS3 --> ML1
DS4 --> ML1
ML1 --> ML2
ML2 --> ML3
ML3 --> ML4
ML4 --> AI1
ML4 --> AI2
ML4 --> AI3
ML4 --> AI4
```
### Edge Computing Integration
```typescript theme={null}
// Edge computing configuration
const edgeDeployment = {
edge_locations: [
{
region: 'us-east-1-edge',
capabilities: ['order_validation', 'payment_processing'],
latency_target: '< 10ms',
failover: 'regional_datacenter'
},
{
region: 'eu-west-1-edge',
capabilities: ['compliance_checking', 'currency_conversion'],
latency_target: '< 15ms',
failover: 'regional_datacenter'
}
],
edge_services: {
order_service: {
cache_size: '10GB',
cache_ttl: '60s',
offline_capability: true
},
payment_service: {
pci_compliance: true,
hsm_integration: true,
token_caching: true
}
}
};
```
## 🚀 Deployment & DevOps
### GitOps Deployment Pipeline
```mermaid theme={null}
graph LR
DEV[Development] --> TEST[Testing]
TEST --> STAGE[Staging]
STAGE --> PROD[Production]
subgraph "CI/CD Pipeline"
CI1[Code Commit]
CI2[Unit Tests]
CI3[Integration Tests]
CI4[Security Scans]
CI5[Performance Tests]
CI6[Deployment]
end
CI1 --> CI2
CI2 --> CI3
CI3 --> CI4
CI4 --> CI5
CI5 --> CI6
subgraph "Infrastructure as Code"
IAC1[Terraform]
IAC2[Ansible]
IAC3[Kubernetes]
IAC4[Helm Charts]
end
CI6 --> IAC1
IAC1 --> IAC2
IAC2 --> IAC3
IAC3 --> IAC4
```
### Blue-Green Deployment Strategy
```yaml theme={null}
# Blue-Green deployment configuration
deployment_strategy:
type: "blue_green"
blue_environment:
version: "v1.2.3"
traffic_percentage: 100
health_check: "passing"
green_environment:
version: "v1.2.4"
traffic_percentage: 0
deployment_status: "ready"
cutover_strategy:
validation_tests: ["smoke_tests", "load_tests"]
rollback_criteria: ["error_rate > 0.5%", "latency_p95 > 200ms"]
traffic_shifting: "instant"
rollback_time: "< 30s"
```
## 📈 Capacity Planning
### Growth Projections
```typescript theme={null}
// Capacity planning model
const capacityModel = {
current_metrics: {
daily_transactions: 1_000_000,
peak_tps: 5_000,
data_growth_tb_per_month: 2.5,
global_merchants: 50_000
},
projected_growth: {
"2024_q4": {
daily_transactions: 5_000_000,
peak_tps: 25_000,
data_growth_tb_per_month: 12.5,
global_merchants: 250_000
},
"2025_q4": {
daily_transactions: 25_000_000,
peak_tps: 125_000,
data_growth_tb_per_month: 62.5,
global_merchants: 1_250_000
},
"2026_q4": {
daily_transactions: 100_000_000,
peak_tps: 500_000,
data_growth_tb_per_month: 250,
global_merchants: 5_000_000
}
},
infrastructure_scaling: {
auto_scaling: true,
predictive_scaling: true,
cost_optimization: true,
reserved_capacity: "20%_buffer"
}
};
```
## 🔄 Disaster Recovery
### Business Continuity Plan
```mermaid theme={null}
graph TB
subgraph "Primary Region"
PR1[Primary Data Center]
PR2[Active Services]
PR3[Real-time Replication]
end
subgraph "Secondary Region"
SR1[Secondary Data Center]
SR2[Standby Services]
SR3[Sync Replication]
end
subgraph "Tertiary Region"
TR1[Disaster Recovery Site]
TR2[Cold Standby]
TR3[Async Replication]
end
subgraph "Recovery Procedures"
RP1[Automated Failover]
RP2[Health Monitoring]
RP3[Data Validation]
RP4[Service Restoration]
end
PR1 --> PR3
PR3 --> SR3
SR3 --> TR3
PR2 --> RP2
RP2 --> RP1
RP1 --> SR2
SR2 --> RP3
RP3 --> RP4
```
### Recovery Time Objectives (RTO) & Recovery Point Objectives (RPO)
| Service Tier | RTO Target | RPO Target | Recovery Strategy |
| -------------------- | ------------- | ------------- | ---------------------------------- |
| Critical (Payments) | \< 30 seconds | \< 1 second | Hot standby + Auto failover |
| Important (Orders) | \< 5 minutes | \< 30 seconds | Warm standby + Manual failover |
| Standard (Analytics) | \< 1 hour | \< 15 minutes | Cold standby + Restore from backup |
## 🌍 Global Compliance Architecture
### Regulatory Framework
```mermaid theme={null}
graph TB
subgraph "Global Regulations"
GR1[GDPR - Europe]
GR2[CCPA - California]
GR3[SOX - US Public Companies]
GR4[PCI DSS - Payment Processing]
end
subgraph "Financial Regulations"
FR1[BSA/AML - US]
FR2[MiFID II - Europe]
FR3[FINTRAC - Canada]
FR4[AUSTRAC - Australia]
end
subgraph "Trade Regulations"
TR1[EAR - Export Administration]
TR2[ITAR - Defense Trade]
TR3[OFAC - Sanctions]
TR4[Customs Regulations]
end
subgraph "Compliance Engine"
CE1[Real-time Screening]
CE2[Automated Reporting]
CE3[Audit Trails]
CE4[Policy Enforcement]
end
GR1 --> CE1
GR2 --> CE1
FR1 --> CE2
FR2 --> CE2
TR1 --> CE3
TR2 --> CE3
GR3 --> CE4
GR4 --> CE4
```
## 🎯 Performance Benchmarks
### Load Testing Results
| Test Scenario | Peak Load | Response Time | Success Rate | Notes |
| ------------------- | ---------------- | ------------- | ------------ | ----------------------- |
| Order Creation | 50,000 TPS | 45ms (p95) | 99.99% | Global distribution |
| Payment Processing | 25,000 TPS | 85ms (p95) | 99.95% | Including compliance |
| Cross-border Orders | 15,000 TPS | 125ms (p95) | 99.90% | Multi-region validation |
| Real-time Analytics | 100,000 events/s | 15ms (p95) | 99.99% | Stream processing |
### Stress Testing Results
```typescript theme={null}
// Stress test configuration and results
const stressTestResults = {
test_duration: "4_hours",
peak_concurrent_users: 100000,
geographical_distribution: "global",
results: {
maximum_sustained_tps: 75000,
peak_burst_tps: 125000,
memory_usage_peak: "85%",
cpu_usage_peak: "78%",
database_connections_peak: 5000,
failure_points: {
database_connection_pool: "at_5500_connections",
memory_exhaustion: "none_observed",
cpu_saturation: "none_observed",
network_bandwidth: "none_observed"
},
auto_scaling_performance: {
scale_up_time: "45_seconds",
scale_down_time: "8_minutes",
efficiency: "98.5%"
}
}
};
```
## 🔮 Future Architecture Evolution
### Next-Generation Capabilities
```mermaid theme={null}
graph TB
subgraph "2024 Roadmap"
R1[Quantum-Resistant Cryptography]
R2[Advanced AI Integration]
R3[IoT Supply Chain Integration]
R4[CBDCs Integration]
end
subgraph "2025+ Vision"
V1[Autonomous Commerce Agents]
V2[Predictive Trade Finance]
V3[Zero-Knowledge Compliance]
V4[Interplanetary Commerce Ready]
end
R1 --> V1
R2 --> V2
R3 --> V3
R4 --> V4
```
***
This architecture represents the foundation for enabling the next era of global commerce - where any business, anywhere in the world, can participate in the global economy with the same ease as making a local transaction. StateSet Commerce Network is not just building an API; we're building the infrastructure for the future of human commerce.
*Ready to build on the world's commerce infrastructure? [Get started with our APIs →](https://docs.stateset.network)*
# Agent Objectives, Goals, Metrics & Rewards Guide
Source: https://docs.stateset.com/guides/agent-objectives-guide
Comprehensive guide for implementing agent objectives, goals, metrics, and rewards in your AI agent ecosystem
# Agent Objectives, Goals, Metrics & Rewards Guide
## Overview
This guide provides a comprehensive framework for implementing agent objectives, goals, metrics, and rewards in your AI agent ecosystem. Based on the Agentic Commerce Platform dashboard, this system combines goal-setting methodologies, performance metrics, and reinforcement learning principles to create a powerful agent optimization framework.
## Table of Contents
1. [Strategic Goals & Objectives](#strategic-goals--objectives)
2. [Key Performance Metrics](#key-performance-metrics)
3. [Reward System Architecture](#reward-system-architecture)
4. [Reinforcement Learning Integration](#reinforcement-learning-integration)
5. [Implementation Guide](#implementation-guide)
6. [Best Practices](#best-practices)
## Strategic Goals & Objectives
### Goal Definition Framework
Goals in the agent ecosystem follow a structured approach with clear, measurable outcomes:
```typescript theme={null}
interface AgentGoal {
id: number;
title: string;
description: string;
targetDate: string;
priority: 'high' | 'medium' | 'low';
owner: string;
agent: string;
successMetrics: SuccessMetric[];
estimatedROI: string;
businessImpact: string;
status: 'active' | 'planning' | 'completed';
progress: number;
}
interface SuccessMetric {
metric: string;
current: number;
target: number;
unit: string;
}
```
### Example Goals
#### 1. First-Call Resolution Excellence
* **Objective**: Achieve 95% first-call resolution rate
* **Current State**: 82% resolution rate
* **Target Metrics**:
* First-call resolution: 82% → 95%
* Customer satisfaction: 4.2/5 → 4.6/5
* Average handle time: 8.5 min → 7.0 min
* **ROI**: \$150K annually
* **Business Impact**: Directly affects customer satisfaction and operational efficiency
#### 2. Response Time Optimization
* **Objective**: Reduce response time to under 30 seconds
* **Current State**: Average 65 seconds
* **Target Metrics**:
* Average response time: 45s → 30s
* Response quality score: 8.4/10 → 8.5/10
* Throughput: 150 req/hr → 200 req/hr
* **ROI**: \$85K annually
* **Business Impact**: Improves user experience and system efficiency
#### 3. Sentiment Detection Mastery
* **Objective**: Enhance sentiment detection accuracy
* **Current State**: 94% accuracy
* **Target Metrics**:
* Sentiment accuracy: 94% → 98%
* False positive rate: 3% → 1%
* Response appropriateness: 9.2/10 → 9.5/10
* **ROI**: \$200K annually
* **Business Impact**: Critical for maintaining positive customer relationships
## Key Performance Metrics
### Real-Time Metrics Dashboard
Monitor your agent ecosystem with these essential real-time metrics:
```typescript theme={null}
interface RealtimeMetrics {
activeAgents: number; // Currently active agents
requestsPerSecond: number; // System throughput
avgResponseTime: number; // Response latency in seconds
successRate: number; // Percentage of successful interactions
activeExperiments: number; // Running A/B tests
learningRate: number; // Agent improvement velocity
}
```
### Agent-Specific Performance Indicators
Each agent tracks individual performance metrics:
```typescript theme={null}
interface AgentPerformance {
accuracy: number; // Task completion accuracy (%)
speed: number; // Response speed percentile
satisfaction: number; // Customer satisfaction score
successRate: number; // Overall success rate (%)
avgReward: number; // Average reward per action
penalties: number; // Number of penalties incurred
streak: number; // Consecutive days without penalties
}
```
### Success Metric Categories
1. **Operational Metrics**
* Response time
* Throughput
* Availability
* Error rate
2. **Quality Metrics**
* Accuracy
* Precision
* Recall
* F1 Score
3. **Business Metrics**
* Customer satisfaction (CSAT)
* Net Promoter Score (NPS)
* First contact resolution (FCR)
* Cost per interaction
4. **Learning Metrics**
* Improvement rate
* Adaptation speed
* Knowledge retention
* Skill acquisition
## Reward System Architecture
### Reward Components
The reward system uses a multi-faceted approach to incentivize optimal agent behavior:
```typescript theme={null}
interface RewardPolicy {
id: number;
name: string;
description: string;
baseReward: number;
conditions: string[];
multipliers: Multiplier[];
penaltyConditions: string[];
active: boolean;
}
interface Multiplier {
condition: string;
multiplier: number;
}
```
### Core Reward Policies
#### 1. First-Call Resolution Reward
* **Base Reward**: 20 points
* **Conditions**:
* Resolution time \< 10 minutes
* No escalation required
* Customer satisfied
* **Multipliers**:
* Complex issue: 1.5x
* VIP customer: 2.0x
* **Penalties**: False resolution, customer complaint
#### 2. Speed Excellence Reward
* **Base Reward**: 10 points
* **Conditions**:
* Response time \< 30 seconds
* **Multipliers**:
* Under 15 seconds: 2.0x
* Maintained quality: 1.3x
* **Penalties**: Quality score \< 80%
#### 3. Sentiment Mastery Reward
* **Base Reward**: 15 points
* **Conditions**:
* Sentiment accuracy > 95%
* Appropriate tone match
* **Multipliers**:
* De-escalated situation: 3.0x
* **Penalties**: Misread critical sentiment
### Achievement System
Gamification elements to drive long-term engagement:
```typescript theme={null}
interface Achievement {
id: number;
name: string;
description: string;
icon: string;
rarity: 'common' | 'rare' | 'epic' | 'legendary';
rewardValue: number;
unlockedBy: string[];
progress: {
current: number;
target: number;
};
}
```
#### Example Achievements
1. **Speed Demon** (Rare)
* Maintain average response time under 30s for 100 interactions
* Reward: 500 points
2. **Customer Champion** (Epic)
* Achieve 95% customer satisfaction rating
* Reward: 1000 points
3. **Streak Master** (Legendary)
* Maintain a 10-day streak without penalties
* Reward: 1500 points
4. **Learning Machine** (Epic)
* Improve performance metrics by 20% in 30 days
* Reward: 800 points
## Reinforcement Learning Integration
### RL Metrics Framework
```typescript theme={null}
interface RLMetrics {
episodes: number; // Total training episodes
averageEpisodeReward: number; // Mean reward per episode
maxEpisodeReward: number; // Best episode performance
minEpisodeReward: number; // Worst episode performance
convergenceRate: number; // Learning convergence (0-1)
bellmanError: number; // Value function accuracy
policyEntropy: number; // Exploration measure
stateValueEstimates: Record;
actionDistribution: Record;
}
```
### Key RL Parameters
1. **Learning Parameters**
* Learning rate: 0.001
* Discount factor: 0.95
* Exploration rate: 15%
2. **Policy Metrics**
* Policy gradient: 0.73
* Value function: 0.85
* Advantage estimate: 0.28
3. **State Values**
* Greeting: 12.5
* Problem solving: 45.2
* Escalation: -5.8
* Resolution: 85.3
### Action Distribution
Optimal action probabilities:
* Provide solution: 45%
* Ask clarification: 25%
* Escalate: 5%
* Offer alternative: 25%
### Value Functions
Value functions estimate the long-term expected rewards from a given state, helping agents make farsighted decisions. Use explicit value functions to go beyond immediate rewards.
### Preventing Reward Hacking
Design reward functions carefully to avoid exploitation of loopholes. Incorporate human feedback via RLHF to align with intended goals.
### Modern Practices
* Use dense rewards for frequent feedback and sparse rewards for ultimate goals.
* Implement intrinsic rewards to encourage exploration.
## Implementation Guide
### 1. Setting Up Goals
```javascript theme={null}
// Create a new goal
const newGoal = {
title: "Improve Customer Satisfaction",
description: "Increase CSAT score through better response quality",
targetDate: "2024-06-30",
priority: "high",
owner: "Sarah Chen",
agent: "CustomerSupport-v2.1",
successMetrics: [
{
metric: "CSAT Score",
current: 4.2,
target: 4.6,
unit: "/5"
},
{
metric: "Response Quality",
current: 85,
target: 92,
unit: "%"
}
],
estimatedROI: "$200K annually",
businessImpact: "High - directly impacts customer retention"
};
```
### 2. Configuring Rewards
```javascript theme={null}
// Define a reward policy
const rewardPolicy = {
name: "Quality Response Bonus",
description: "Reward high-quality, helpful responses",
baseReward: 25,
conditions: [
"Response quality score > 90%",
"Customer feedback positive",
"No follow-up needed"
],
multipliers: [
{ condition: "Technical complexity high", multiplier: 1.5 },
{ condition: "First attempt resolution", multiplier: 1.3 }
],
penaltyConditions: [
"Incorrect information provided",
"Customer escalation required"
],
active: true
};
```
### 3. Tracking Performance
```javascript theme={null}
// Monitor agent performance
const agentMetrics = {
agentId: "CustomerSupport-v2.1",
totalRewards: 3500,
recentRewards: 450,
performance: {
successRate: 94,
avgReward: 15.2,
penalties: 12,
streak: 7
},
level: 12,
nextLevelProgress: 78
};
```
### 4. Running Experiments
```javascript theme={null}
// Design an experiment
const experiment = {
name: "Response Template Optimization",
hypothesis: "Structured templates will improve resolution rate by 10%",
type: "ab_test",
duration: "2 weeks",
successCriteria: [
"Resolution rate improves by >10%",
"Customer satisfaction maintained or improved",
"No increase in handle time"
],
sampleSize: 1000,
significanceLevel: 0.05
};
```
## Best Practices
### 1. Goal Setting
* **SMART Goals**: Specific, Measurable, Achievable, Relevant, Time-bound
* **Incremental Targets**: Set progressive milestones
* **Regular Reviews**: Weekly progress checks
* **Data-Driven**: Base targets on historical performance
### 2. Metric Selection
* **Balanced Scorecard**: Mix operational, quality, and business metrics
* **Leading Indicators**: Focus on predictive metrics
* **Actionable Insights**: Ensure metrics drive specific actions
* **Avoid Vanity Metrics**: Focus on impact, not activity
### 3. Reward Design
* **Immediate Feedback**: Real-time reward attribution
* **Clear Criteria**: Unambiguous reward conditions
* **Balanced Incentives**: Avoid gaming the system
* **Progressive Difficulty**: Scale rewards with agent maturity
### 4. Continuous Improvement
* **A/B Testing**: Regularly experiment with new approaches
* **Feedback Loops**: Incorporate learnings quickly
* **Cross-Agent Learning**: Share successful strategies
* **Human-in-the-Loop**: Regular coaching and guidance
### 5. Risk Management
* **Penalty Caps**: Limit maximum penalties
* **Safety Checks**: Prevent harmful optimizations
* **Rollback Plans**: Quick reversion capabilities
* **Monitoring Alerts**: Real-time anomaly detection
### 6. Reward Design Best Practices
* **Avoid Reward Hacking**: Design rewards to prevent agents from exploiting loopholes. Ensure rewards align with intended behaviors without unintended shortcuts.
* **Use RLHF**: Incorporate Reinforcement Learning from Human Feedback for aligning rewards with human preferences.
* **Dense vs. Sparse Rewards**: Balance immediate feedback (dense) with long-term goals (sparse) to guide learning effectively.
* **Intrinsic Motivation**: Add rewards for exploration and novelty to encourage robust learning.
* **Regular Audits**: Continuously monitor and update reward functions to adapt to new behaviors and prevent drift.
## Conclusion
This framework provides a comprehensive approach to managing agent objectives, goals, metrics, and rewards. By combining clear goal-setting, robust performance tracking, and intelligent reward systems with reinforcement learning principles, you can create a self-improving agent ecosystem that delivers measurable business value.
Remember to:
* Start with clear, measurable objectives
* Implement comprehensive tracking from day one
* Design rewards that align with business goals
* Use experiments to validate improvements
* Continuously iterate based on data
The key to success is maintaining a balance between automation and human oversight, ensuring your agents improve while staying aligned with your organization's values and objectives.
## References
* Sutton and Barto, "Reinforcement Learning: An Introduction"
* "What Agents Desire? Reward and Value Functions in AI" by Ksenia Se (Turing Post, 2025)
* "Establishing Best Practices for Building Rigorous Agentic Benchmarks" (arXiv:2507.02825)
# Agent Training Guide
Source: https://docs.stateset.com/guides/agent-trainer-guide
Comprehensive guide for training AI agents: knowledge bases, model selection, datasets, evaluation, and MCP tools
# Agent Training Guide
Welcome to the comprehensive Agent Training Guide. This document provides best practices and methodologies for training AI agents effectively, covering everything from knowledge base design to model selection and evaluation strategies.
## Table of Contents
1. [Introduction](#introduction)
2. [Knowledge Base vs Rules](#knowledge-base-vs-rules)
3. [Base Model vs Finetuned Model](#base-model-vs-finetuned-model)
4. [Datasets, Training, and Evaluations](#datasets-training-and-evaluations)
5. [MCP Tool for Google Drive Documents](#mcp-tool-for-google-drive-documents)
6. [Best Practices](#best-practices)
7. [Troubleshooting](#troubleshooting)
8. [Conclusion](#conclusion)
***
## Introduction
Training effective AI agents requires understanding the fundamental differences between various approaches and tools. This guide will help you make informed decisions about:
* When to use knowledge bases versus rule-based systems
* Choosing between base models and finetuned models
* Creating effective training datasets and evaluation frameworks
* Leveraging MCP (Model Context Protocol) tools for document integration
***
## Knowledge Base vs Rules
### Knowledge Base Approach
A **knowledge base** is a structured repository of information that agents can query and reference dynamically.
#### Advantages:
* **Flexibility**: Easy to update without retraining
* **Scalability**: Can handle vast amounts of information
* **Context-Aware**: Enables semantic search and retrieval
* **Dynamic Updates**: Real-time information updates possible
#### Disadvantages:
* **Retrieval Overhead**: May increase response latency
* **Context Limitations**: Limited by retrieval quality
* **Complexity**: Requires robust indexing and search infrastructure
#### Best Use Cases:
```yaml theme={null}
knowledge_base_ideal_for:
- FAQ systems
- Product documentation
- Dynamic information (prices, inventory)
- Multi-domain applications
- Frequently updated content
```
### Rule-Based Approach
**Rules** are predefined logic patterns that dictate agent behavior based on specific conditions.
#### Advantages:
* **Predictability**: Deterministic outcomes
* **Performance**: Fast execution without retrieval
* **Precision**: Exact control over responses
* **Auditability**: Clear decision paths
#### Disadvantages:
* **Rigidity**: Hard to scale and maintain
* **Limited Flexibility**: Cannot handle edge cases well
* **Manual Updates**: Requires code changes for modifications
* **Complexity Growth**: Rules become unwieldy as they multiply
#### Best Use Cases:
```yaml theme={null}
rules_ideal_for:
- Compliance requirements
- Simple decision trees
- High-stakes operations
- Regulatory workflows
- Fixed business logic
```
### Hybrid Approach
Often, the best solution combines both approaches:
```python theme={null}
class HybridAgent:
def process_query(self, query):
# Check rules first for critical paths
if self.check_compliance_rules(query):
return self.execute_rule_based_action(query)
# Fall back to knowledge base for general queries
context = self.knowledge_base.retrieve(query)
return self.generate_response(query, context)
```
***
## Base Model vs Finetuned Model
### Base Models
Base models are pre-trained on vast datasets but not specialized for specific tasks.
#### Characteristics:
* **General Purpose**: Broad knowledge across domains
* **Zero-Shot Capable**: Can handle diverse tasks without specific training
* **Large Context Windows**: Modern base models support extensive context
* **Consistent Updates**: Benefit from provider improvements
#### When to Use Base Models:
```yaml theme={null}
base_model_scenarios:
- Prototyping and POCs
- Multi-purpose agents
- When training data is limited
- Rapidly changing requirements
- Cost-sensitive applications
```
### Finetuned Models
Finetuned models are specialized versions trained on domain-specific data.
#### Characteristics:
* **Domain Expertise**: Superior performance on specific tasks
* **Consistency**: More predictable outputs
* **Efficiency**: Often smaller and faster
* **Custom Behavior**: Tailored to exact requirements
#### When to Use Finetuned Models:
```yaml theme={null}
finetuned_model_scenarios:
- Domain-specific applications
- High-volume, repetitive tasks
- When accuracy is critical
- Custom tone/style requirements
- Proprietary knowledge encoding
```
### Decision Flow: When to Finetune
Choosing between a base model and a finetuned model can be simplified with the following decision flow:
```mermaid theme={null}
graph TD
A[Start: New AI Task] --> B{Need domain-specific expertise or style?};
B -- No --> D[Use Base Model];
B -- Yes --> C{Have >1k high-quality training examples?};
C -- Yes --> E[Finetune a Model];
C -- No --> F{Can you generate/acquire high-quality data?};
F -- Yes --> G[Generate/Acquire Data];
G --> E;
F -- No --> H[Use Base Model with Advanced Prompting / RAG];
subgraph "Base Model Path"
D; H;
end
subgraph "Finetuning Path"
E; G;
end
D --> I[Deploy & Monitor];
E --> I;
H --> I;
```
### Comparison Matrix
| Aspect | Base Model | Finetuned Model |
| --------------------- | ---------------- | -------------------------- |
| **Setup Time** | Immediate | Weeks to months |
| **Cost** | Pay-per-use | Training + inference |
| **Flexibility** | High | Limited to training domain |
| **Performance** | Good general | Excellent specific |
| **Maintenance** | Provider managed | Self-managed |
| **Data Requirements** | None | Thousands of examples |
***
## Datasets, Training, and Evaluations
### Dataset Creation
Creating high-quality training datasets is crucial for agent performance.
#### Dataset Components:
```json theme={null}
{
"training_example": {
"input": "User query or context",
"expected_output": "Ideal agent response",
"metadata": {
"category": "customer_support",
"difficulty": "medium",
"tags": ["refund", "policy"]
}
}
}
```
#### Best Practices for Dataset Creation:
1. **Diversity**: Cover edge cases and variations
2. **Quality**: Ensure accuracy and consistency
3. **Balance**: Represent all categories equally
4. **Annotation**: Include clear labels and metadata
5. **Validation**: Have experts review samples
### Training Process
#### 1. Data Preparation
```python theme={null}
# Example data preprocessing pipeline
def prepare_training_data(raw_data):
processed_data = []
for item in raw_data:
# Clean and normalize text (e.g., lowercase, remove punctuation)
cleaned_input = normalize_text(item['input'])
cleaned_output = normalize_text(item['output'])
# Validate data quality (e.g., check for length, language, non-empty)
if validate_pair(cleaned_input, cleaned_output):
processed_data.append({
'input': cleaned_input,
'output': cleaned_output,
'metadata': item.get('metadata', {})
})
# Split into training, validation, and test sets (e.g., 80/10/10)
return split_data(processed_data) # train/val/test splits
```
#### 2. Training Configuration
```yaml theme={null}
training_config:
base_model: "claude-3.5-sonnet" # Updated to recent model
learning_rate: 1e-5
batch_size: 32
epochs: 3
validation_split: 0.2
early_stopping:
patience: 3
metric: "validation_loss"
```
#### 3. Monitoring Training
* Track loss curves
* Monitor validation metrics
* Check for overfitting
* Evaluate on holdout test set
### Evaluation Framework
#### Automated Metrics:
```python theme={null}
evaluation_metrics = {
"accuracy": calculate_exact_match,
"bleu_score": calculate_bleu,
"perplexity": calculate_perplexity,
"response_time": measure_latency,
"token_efficiency": count_tokens
}
```
#### Human Evaluation Criteria:
1. **Relevance**: Does the response address the query?
2. **Accuracy**: Is the information correct?
3. **Completeness**: Are all aspects covered?
4. **Tone**: Is the style appropriate?
5. **Coherence**: Is the response well-structured?
#### A/B Testing Framework:
```python theme={null}
class ABTestFramework:
def __init__(self, model_a, model_b):
self.model_a = model_a
self.model_b = model_b
self.results = {"model_a": [], "model_b": []}
def run_test(self, test_queries, metric_fn):
for query in test_queries:
response_a = self.model_a.generate(query)
response_b = self.model_b.generate(query)
score_a = metric_fn(query, response_a)
score_b = metric_fn(query, response_b)
self.results["model_a"].append(score_a)
self.results["model_b"].append(score_b)
return self.analyze_results()
def analyze_results(self):
# Example: Perform statistical test (e.g., t-test)
# to see if one model is significantly better.
import numpy as np
from scipy.stats import ttest_ind
scores_a = np.array(self.results["model_a"])
scores_b = np.array(self.results["model_b"])
if len(scores_a) < 2 or len(scores_b) < 2:
return {"error": "Not enough data to run t-test."}
t_stat, p_value = ttest_ind(scores_a, scores_b)
return {
"mean_score_a": np.mean(scores_a),
"mean_score_b": np.mean(scores_b),
"p_value": p_value,
"winner": "model_a" if np.mean(scores_a) > np.mean(scores_b) else "model_b"
}
```
***
## Reinforcement Learning in Agent Training
### Overview
Reinforcement Learning (RL) is a key method for training agents to make sequential decisions by interacting with an environment, receiving rewards or penalties based on actions. Recent shifts in LLM training emphasize post-training with RL to enable complex, agentic behaviors.
#### Key Advantages:
* **Handles Long-Horizon Tasks**: RL excels in scenarios requiring multi-step reasoning, such as planning in games or real-world simulations.
* **Exploration and Curiosity**: Encourages agents to explore novel strategies, reducing compounding errors seen in pure imitation learning.
* **Alignment with Human Values**: Techniques like RLHF (Reinforcement Learning from Human Feedback) and Constitutional AI align agents with ethical guidelines.
#### Best Practices:
* **Combine with Imitation Learning**: Start with imitation for basic behaviors, then use RL for refinement.
* **Use Reward Models**: Train models to evaluate outputs, enabling scalable feedback without constant human input.
* **Incorporate Human-in-the-Loop**: Platforms like GUIDE allow real-time human feedback for nuanced guidance.
* **Benchmark and Avoid Overfitting**: Use diverse environments and standardize evaluations to ensure real-world applicability.
#### Example: Training an Agent in a Game Environment
```python theme={null}
import gym
env = gym.make('CartPole-v1')
# RL training loop example
for episode in range(1000):
state = env.reset()
done = False
while not done:
action = agent.select_action(state) # RL policy
next_state, reward, done, _ = env.step(action)
agent.update(reward, next_state) # Update with RL algorithm (e.g., Q-Learning)
```
Recent models like o1 and Claude 3.5 demonstrate RL's impact on reasoning capabilities.
***
## MCP Tool for Google Drive Documents
### Overview
The Model Context Protocol (MCP) enables agents to interact with Google Drive documents seamlessly, providing real-time access to organizational knowledge.
### Setup and Configuration
#### 1. Install MCP Server
```bash theme={null}
npm install @modelcontextprotocol/server-gdrive
```
#### 2. Configure Authentication
```json theme={null}
{
"google_drive_mcp": {
"client_id": "your-client-id",
"client_secret": "your-client-secret",
"redirect_uri": "https://yourapp.com:3000/callback",
"scopes": [
"https://www.googleapis.com/auth/drive.readonly",
"https://www.googleapis.com/auth/documents.readonly"
]
}
}
```
#### 3. Initialize MCP Tool
```javascript theme={null}
const { GoogleDriveMCP } = require('@modelcontextprotocol/server-gdrive');
const driveTool = new GoogleDriveMCP({
credentials: googleCredentials,
settings: {
maxResults: 10,
includeSharedDrives: true,
mimeTypes: [
'application/vnd.google-apps.document',
'application/vnd.google-apps.spreadsheet',
'application/pdf'
]
}
});
```
### Usage Patterns
#### Document Search
```javascript theme={null}
// Search for relevant documents
const searchResults = await driveTool.search({
query: "customer onboarding procedures",
filters: {
modifiedAfter: "2024-01-01",
owners: ["team@company.com"]
}
});
```
#### Content Extraction
```javascript theme={null}
// Extract content from a specific document
const documentContent = await driveTool.getDocument({
documentId: "1234567890abcdef",
format: "markdown",
includeMetadata: true
});
```
#### Integration with Agent
```python theme={null}
class GoogleDriveAgent:
def __init__(self, mcp_tool, llm):
self.mcp_tool = mcp_tool
self.llm = llm
async def answer_with_docs(self, query):
# Search relevant documents
docs = await self.mcp_tool.search({
"query": query,
"limit": 5
})
# Extract content
context = ""
for doc in docs:
content = await self.mcp_tool.get_content(doc.id)
context += f"\n\n{doc.title}:\n{content[:1000]}"
# Generate response with context
prompt = f"""
Based on the following documents, answer the query: {query}
Documents:
{context}
"""
return await self.llm.generate(prompt)
```
### Best Practices
1. **Caching**: Implement caching for frequently accessed documents
2. **Permissions**: Respect document permissions and access controls
3. **Rate Limiting**: Handle API rate limits gracefully
4. **Error Handling**: Implement robust error handling for network issues
5. **Incremental Sync**: Use change tokens for efficient updates
***
## Best Practices
### 1. Start Simple
* Begin with base models and simple prompts
* Add complexity incrementally
* Measure improvements at each step
### 2. Data Quality Over Quantity
* 1,000 high-quality examples are more valuable than 10,000 mediocre ones.
* **Invest in data cleaning and validation**:
* **Clarity**: Unambiguous input/output pairs.
* **Consistency**: Uniform style, format, and tone.
* **Coverage**: Represents the full range of expected user interactions, including edge cases.
* **Correctness**: Factually accurate and grammatically correct.
* **Regularly audit training data** to remove outdated or incorrect examples.
* **Incorporate Diverse Sources**: Use human-synthetic data blends and ensure representativeness to avoid biases (from Toloka guide).
### 3. Continuous Evaluation and Learning
* Set up automated evaluation pipelines to monitor performance on key metrics.
* Regular human evaluation sessions to assess nuanced aspects of quality.
* Monitor production performance closely to catch regressions or new failure modes.
* Implement continuous learning post-deployment for adaptability.
### 4. Version Control
* **Use version control for everything**: training data, prompts, model configurations, and evaluation results.
* This allows for reproducibility, easy rollbacks, and clear tracking of experiments.
* Tools like Git, DVC (Data Version Control), and MLflow can be invaluable.
### 5. Security Considerations
* Sanitize all user inputs and training data to prevent data poisoning.
* Implement strict access controls for training infrastructure and models.
* **Be aware of prompt injection**: Design prompts and agent logic to be resilient against adversarial inputs.
* Conduct regular security audits of your entire AI/ML pipeline.
* Align agents with human values using RLHF to prevent misalignment (from arXiv papers).
***
## Challenges and Solutions in Agent Training
### Common Challenges
* **Data Scarcity and Quality**: Insufficient or biased data leads to poor generalization.
* **Misalignment with Human Values**: Agents may optimize for wrong objectives, ignoring ethics.
* **Overfitting to Benchmarks**: High benchmark scores may not translate to real-world performance.
* **Exploration in Complex Environments**: Agents struggle with long-horizon tasks and sparse rewards.
### Solutions
* **High-Quality Datasets**: Prioritize diverse, representative data; use synthetic data generation.
* **Alignment Techniques**: Employ RLHF, Constitutional AI, and human-in-the-loop feedback.
* **Robust Evaluation**: Use multi-metric benchmarks and real-world testing (e.g., GUIDE framework for human interactions).
* **Advanced Tools**: Leverage open-source like PyTorch or proprietary like Azure for scalable training.
***
## Troubleshooting
### Common Issues and Solutions
#### 1. Poor Model Performance
```yaml theme={null}
symptoms:
- Inaccurate responses
- Inconsistent behavior
- High error rates
solutions:
- Review training data quality
- Increase dataset diversity
- Adjust training parameters
- Consider different base models
```
#### 2. Knowledge Base Retrieval Issues
```yaml theme={null}
symptoms:
- Irrelevant results
- Missing information
- Slow retrieval
solutions:
- Improve indexing strategy
- Enhance search queries
- Optimize embedding models
- Implement caching
```
#### 3. MCP Integration Problems
```yaml theme={null}
symptoms:
- Authentication failures
- Timeout errors
- Missing documents
solutions:
- Verify credentials
- Check network connectivity
- Review permission scopes
- Implement retry logic
```
***
## Conclusion
Building powerful AI agents is a journey of iterative refinement. It begins with a strategic choice of architecture—balancing the predictability of rules with the flexibility of knowledge bases—and selecting the right model for your task.
Success hinges on a disciplined approach to data, training, and evaluation. By curating high-quality datasets, establishing robust evaluation frameworks, and continuously monitoring performance, you create a virtuous cycle of improvement. Integrating powerful tools like MCP for real-time data access further enhances your agent's capabilities.
Recent advancements emphasize reinforcement learning for enabling agentic behaviors and long-horizon reasoning. As AI evolves, focus on alignment, real-world benchmarks, and human-AI collaboration to build agents that are not only intelligent but truly effective and ethical.
The principles in this guide provide a roadmap for this journey. Embrace a mindset of continuous learning, rigorous experimentation, and a relentless focus on quality. By doing so, you can build reliable, intelligent, and valuable AI agents that are not just technically impressive, but truly effective.
# Agentic Commerce Protocol Handler
Source: https://docs.stateset.com/guides/agentic-commerce-protocol-handler
Self-hosted server implementing the Agentic Commerce Protocol for ChatGPT Instant Checkout
Agentic Commerce Protocol (ACP) Handler is a Rust server that implements OpenAI's Agentic Commerce Protocol. It provides checkout session APIs, delegated payments, and optional gRPC access so you can keep orders and compliance in your own stack while enabling ChatGPT Instant Checkout experiences.
## Key capabilities
* Full checkout session lifecycle for the ACP spec
* Delegated payment endpoint with vault token support
* Optional Stripe PaymentIntent integration
* Idempotency keys and request tracing
* Swagger UI at `/docs` and OpenAPI JSON at `/openapi.json`
* gRPC API mirroring the HTTP endpoints
## Architecture overview
```mermaid theme={null}
graph LR
ChatGPT[ChatGPT or client] -->|HTTP or gRPC| Handler[ACP Handler]
Handler --> Redis[Redis or in-memory sessions]
Handler --> Commerce[iCommerce or SQLite backend]
Handler --> PSP[Payment service provider]
```
## Quickstart
```bash theme={null}
cargo build --release
cargo run --release
```
The HTTP server listens on `http://0.0.0.0:8080` by default. The gRPC server listens on `0.0.0.0:50051`.
To run the demo flow:
```bash theme={null}
./demo_test.sh
```
## Create a checkout session
```bash theme={null}
curl -X POST https://yourapp.com:8080/checkout_sessions \
-H "Content-Type: application/json" \
-H "Authorization: Bearer api_key_123" \
-H "API-Version: 2025-09-29" \
-d '{
"items": [{ "id": "item_123", "quantity": 2 }],
"buyer": { "email": "buyer@example.com" }
}'
```
## Core endpoints
| Method | Endpoint | Description |
| ------ | ------------------------------------ | ---------------------------------- |
| POST | `/checkout_sessions` | Create a checkout session |
| GET | `/checkout_sessions/:id` | Retrieve a checkout session |
| POST | `/checkout_sessions/:id` | Update a checkout session |
| POST | `/checkout_sessions/:id/complete` | Complete checkout and create order |
| POST | `/checkout_sessions/:id/cancel` | Cancel a checkout session |
| POST | `/agentic_commerce/delegate_payment` | Delegated payment (vault token) |
| GET | `/health` | Health check |
| GET | `/ready` | Readiness check |
| GET | `/docs` | Swagger UI |
| GET | `/openapi.json` | OpenAPI spec |
## Delegated payments
The delegated payment endpoint accepts payment tokens from a PSP vault. Tokens are validated for allowance and expiry and are consumed after use.
## Stripe integration
Set the following environment variables before starting the server to process delegated payments with Stripe:
* `STRIPE_SECRET_KEY`
* `STRIPE_PUBLISHABLE_KEY` (optional)
* `STRIPE_WEBHOOK_SECRET` (optional, for webhook signature verification)
## gRPC access
The gRPC API mirrors the HTTP endpoints and uses the same API keys. Send `authorization: Bearer ` as gRPC metadata.
## Related components
The repository also includes:
* A Next.js dashboard for monitoring checkout sessions
* A ChatGPT widget server for MCP-based agent flows
* Kubernetes and Docker Compose deployment assets
# Agents Quickstart
Source: https://docs.stateset.com/guides/agents-quickstart
This guide will walk you through creating and managing Agents on ResponseCX.
## Prerequisites
Before you begin creating agents, ensure you have:
* A StateSet account ([Sign up here](https://StateSet.com/sign-up))
* API credentials from the [StateSet Dashboard](https://app.StateSet.com/settings/api-keys)
* ResponseCX enabled in your workspace
* Node.js 16+ installed on your development machine
* Basic understanding of REST APIs and JavaScript/TypeScript
* Text editor or IDE for code development
* Understanding of conversational AI concepts and customer service workflows
* Access to your customer support systems (if planning integrations)
* Knowledge of your brand voice and customer interaction requirements
## What are Agents?
In ResponseCX, an Agent is an autonomous conversational AI that can interact with your customers. You can customize its name, personality, and instructions to fit your business needs. Agents can be used in chat sessions to provide support, answer questions, and guide users.
## Creating an Agent
You can create an agent through the ResponseCX dashboard or using the SDK.
### Using the Dashboard
1. Navigate to the **Agents** section of the ResponseCX dashboard.
2. Click the **Add New Agent** button.
3. Fill in the agent's details:
* **Name:** A recognizable name for your agent (e.g., "Support Bot").
* **Description:** A brief summary of the agent's purpose.
* **Type:** The type of agent. For most use cases, you'll use `Conversational AI Agent`.
* **Voice Model:** The voice your agent will use for voice interactions. `Asteria` is a popular choice.
4. Click **Add Agent** to save your new agent.
### Using the SDK
Here's how to create an agent using our SDKs with proper error handling:
```javascript theme={null}
import { StateSetClient } from 'StateSet-node';
import winston from 'winston';
// Configure logger
const logger = winston.createLogger({
level: 'info',
format: winston.format.json(),
transports: [new winston.transports.Console()]
});
// Initialize the client
const client = new StateSetClient({
apiKey: process.env.STATESET_API_KEY
});
async function createAgent() {
try {
const agent = await client.agents.create({
name: "My SDK Agent",
description: "This agent was created via the SDK.",
type: "Conversational AI Agent",
role: "E-commerce Assistant",
instructions: "You are a friendly and helpful assistant for an online store.",
goal: "Help customers find products and answer questions about their orders.",
voice_model: "Asteria",
});
logger.info('Agent created successfully', {
agentId: agent.id,
name: agent.name
});
return agent;
} catch (error) {
logger.error('Failed to create agent', {
error: error.message,
stack: error.stack
});
throw error;
}
}
// Usage
const agent = await createAgent();
```
```python theme={null}
import os
import logging
from StateSet import StateSetClient
# Configure logging
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)
# Initialize the client
client = StateSetClient(api_key=os.getenv('STATESET_API_KEY'))
def create_agent():
try:
agent = client.agents.create(
name="My SDK Agent",
description="This agent was created via the SDK.",
type="Conversational AI Agent",
role="E-commerce Assistant",
instructions="You are a friendly and helpful assistant for an online store.",
goal="Help customers find products and answer questions about their orders.",
voice_model="Asteria"
)
logger.info(f'Agent created successfully: {agent.id} - {agent.name}')
return agent
except Exception as error:
logger.error(f'Failed to create agent: {str(error)}')
raise
# Usage
agent = create_agent()
```
```ruby theme={null}
require 'StateSet'
require 'logger'
# Configure logging
logger = Logger.new(STDOUT)
logger.level = Logger::INFO
# Configure client
StateSet.configure do |config|
config.api_key = ENV['STATESET_API_KEY']
end
def create_agent
agent = StateSet::Agent.create(
name: "My SDK Agent",
description: "This agent was created via the SDK.",
type: "Conversational AI Agent",
role: "E-commerce Assistant",
instructions: "You are a friendly and helpful assistant for an online store.",
goal: "Help customers find products and answer questions about their orders.",
voice_model: "Asteria"
)
logger.info "Agent created successfully: #{agent.id} - #{agent.name}"
agent
rescue => error
logger.error "Failed to create agent: #{error.message}"
raise
end
# Usage
agent = create_agent
```
```php theme={null}
pushHandler(new StreamHandler('php://stdout', Logger::INFO));
// Initialize the client
$client = new StateSetClient([
'api_key' => $_ENV['STATESET_API_KEY']
]);
function createAgent($client, $logger) {
try {
$agent = $client->agents->create([
'name' => 'My SDK Agent',
'description' => 'This agent was created via the SDK.',
'type' => 'Conversational AI Agent',
'role' => 'E-commerce Assistant',
'instructions' => 'You are a friendly and helpful assistant for an online store.',
'goal' => 'Help customers find products and answer questions about their orders.',
'voice_model' => 'Asteria'
]);
$logger->info('Agent created successfully', [
'agent_id' => $agent['id'],
'name' => $agent['name']
]);
return $agent;
} catch (Exception $error) {
$logger->error('Failed to create agent', [
'error' => $error->getMessage()
]);
throw $error;
}
}
// Usage
$agent = createAgent($client, $logger);
?>
```
```bash theme={null}
# Create an agent using cURL
curl -X POST "https://api.StateSet.com/v1/agents" \
-H "Authorization: Bearer $STATESET_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "My SDK Agent",
"description": "This agent was created via the SDK.",
"type": "Conversational AI Agent",
"role": "E-commerce Assistant",
"instructions": "You are a friendly and helpful assistant for an online store.",
"goal": "Help customers find products and answer questions about their orders.",
"voice_model": "Asteria"
}' | jq '.'
# Save the response to get the agent ID
AGENT_ID=$(curl -s -X POST "https://api.StateSet.com/v1/agents" \
-H "Authorization: Bearer $STATESET_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"name": "My SDK Agent",
"description": "This agent was created via the SDK.",
"type": "Conversational AI Agent",
"role": "E-commerce Assistant",
"instructions": "You are a friendly and helpful assistant for an online store.",
"goal": "Help customers find products and answer questions about their orders.",
"voice_model": "Asteria"
}' | jq -r '.id')
echo "Agent created with ID: $AGENT_ID"
```
**Agent Properties:**
* `name` (string, required): The name of the agent.
* `description` (string): A short description of the agent.
* `type` (string): The type of agent.
* `role` (string): The role you want the agent to adopt (e.g., "Customer Support Agent").
* `instructions` (string): Specific instructions for the agent on how to behave. This is where you define its personality and operational guidelines.
* `goal` (string): The primary objective for the agent in conversations.
* `voice_model` (string): The voice model for text-to-speech.
## Managing Agents
You can view, update, and delete your agents.
### Listing Agents
Retrieve a list of all your agents with pagination support:
```javascript theme={null}
async function listAgents(page = 1, limit = 10) {
try {
const agents = await client.agents.list({
page,
limit,
sort: 'created_at:desc'
});
return {
agents: agents.data,
totalCount: agents.total,
hasMore: agents.has_more
};
} catch (error) {
logger.error('Failed to list agents:', error);
throw new Error('Unable to retrieve agents at this time');
}
}
```
## Updating an Agent
You can update an agent's properties in the dashboard or through the SDK.
### Using the Dashboard
1. In the **Agents** list, click the **Update** button for the agent you want to modify.
2. Change the desired fields in the agent editor.
3. Click **Save** to apply the changes.
### Using the SDK
```javascript theme={null}
async function updateAgent(agentId, updates) {
try {
const updatedAgent = await client.agents.update({
id: agentId,
...updates
});
// Audit trail for compliance
await auditLog.record({
action: 'agent.updated',
agentId: agentId,
changes: updates,
timestamp: new Date()
});
return {
success: true,
agent: updatedAgent,
message: 'Agent updated successfully'
};
} catch (error) {
if (error.code === 'AGENT_NOT_FOUND') {
throw new Error('Agent not found');
}
logger.error('Failed to update agent:', error);
throw error;
}
}
// Example usage
const updates = {
name: "My Updated Agent Name",
description: "Updated description with new capabilities",
instructions: "You are now specialized in technical support..."
};
await updateAgent(agentId, updates);
```
## Deleting an Agent
You can delete an agent from the dashboard or via the SDK. Deleting an agent is permanent and cannot be undone.
```javascript theme={null}
async function deleteAgent(agentId) {
try {
// Check if agent has active conversations
const activeConversations = await client.conversations.list({
agent_id: agentId,
status: 'active'
});
if (activeConversations.total > 0) {
throw new Error('Cannot delete agent with active conversations');
}
// Archive agent data before deletion (for compliance)
await archiveAgentData(agentId);
// Delete the agent
await client.agents.delete({ id: agentId });
return {
success: true,
message: 'Agent deleted successfully'
};
} catch (error) {
logger.error('Failed to delete agent:', error);
throw error;
}
}
```
## Best Practices
### 1. Agent Instructions
Be specific and clear in your instructions:
```javascript theme={null}
const goodInstructions = `You are a friendly customer support agent for Acme Store.
- Always greet customers warmly
- Ask clarifying questions before providing solutions
- Never share customer personal information
- Escalate to human support for refund requests over $100`;
const poorInstructions = "Help customers";
```
### 2. Error Handling
Always implement robust error handling:
```javascript theme={null}
async function safeAgentOperation(operation) {
const maxRetries = 3;
let lastError;
for (let i = 0; i < maxRetries; i++) {
try {
return await operation();
} catch (error) {
lastError = error;
// Don't retry on client errors
if (error.status >= 400 && error.status < 500) {
throw error;
}
// Exponential backoff
await new Promise(resolve => setTimeout(resolve, Math.pow(2, i) * 1000));
}
}
throw lastError;
}
```
### 3. Monitoring Agent Performance
Track your agent's effectiveness:
```javascript theme={null}
async function getAgentMetrics(agentId, timeframe = '7d') {
const metrics = await client.agents.getMetrics({
id: agentId,
timeframe
});
return {
conversationCount: metrics.total_conversations,
satisfactionScore: metrics.avg_satisfaction,
resolutionRate: metrics.resolution_rate,
avgResponseTime: metrics.avg_response_time_ms
};
}
```
## Next Steps
Now that you've created an agent, you can start using it in your application. Here are some things you might want to do next:
* **Create a Chat:** Learn how to initiate a chat session with your new agent.
* **Explore advanced features:** Dive into more complex agent capabilities like using functions and knowledge bases.
For more information on how to use Agents, please reach out at [support@StateSet.com](mailto:support@StateSet.com)
# API Rate Limiting & Optimization
Source: https://docs.stateset.com/guides/api-rate-limiting
Understanding StateSet API rate limits, implementing efficient request patterns, and optimizing API usage for better performance
# API Rate Limiting & Optimization
StateSet implements rate limiting to ensure fair usage and maintain service reliability for all users. This guide covers understanding rate limits, implementing efficient request patterns, and optimizing your API usage.
## Rate Limit Overview
StateSet uses a **sliding window** rate limiting algorithm that provides smooth, predictable limits across different time windows.
Prevents burst traffic spikes and ensures responsive service
Controls sustained request volume over longer periods
Manages overall API consumption and prevents abuse
## Current Rate Limits
### By Plan Type
| Endpoint Category | Per Second | Per Minute | Per Hour |
| ----------------- | ---------- | ---------- | -------- |
| **Orders API** | 10 | 300 | 5,000 |
| **Customers API** | 5 | 150 | 2,500 |
| **Returns API** | 5 | 150 | 2,500 |
| **Webhooks** | 20 | 600 | 10,000 |
| **Analytics** | 2 | 60 | 1,000 |
| Endpoint Category | Per Second | Per Minute | Per Hour |
| ----------------- | ---------- | ---------- | -------- |
| **Orders API** | 50 | 1,500 | 25,000 |
| **Customers API** | 25 | 750 | 12,500 |
| **Returns API** | 25 | 750 | 12,500 |
| **Webhooks** | 100 | 3,000 | 50,000 |
| **Analytics** | 10 | 300 | 5,000 |
| Endpoint Category | Per Second | Per Minute | Per Hour |
| ----------------- | ---------- | ---------- | -------- |
| **Orders API** | 200 | 6,000 | 100,000 |
| **Customers API** | 100 | 3,000 | 50,000 |
| **Returns API** | 100 | 3,000 | 50,000 |
| **Webhooks** | 500 | 15,000 | 250,000 |
| **Analytics** | 50 | 1,500 | 25,000 |
### Special Considerations
* Batch endpoints have **higher rate limits** but count as multiple requests
* Each item in a batch counts toward your rate limit
* Maximum batch size: **100 items per request**
* List endpoints with large `limit` parameters consume more quota
* Requests with `limit > 100` count as `Math.ceil(limit/100)` requests
* Use pagination instead of large limit values
* Webhook deliveries **do not count** against your rate limits
* Failed webhook retries use separate retry quotas
* Webhook verification calls are not rate limited
## Rate Limit Headers
Every API response includes rate limit information in the headers:
```http theme={null}
HTTP/1.1 200 OK
X-RateLimit-Limit: 1500
X-RateLimit-Remaining: 1247
X-RateLimit-Reset: 1640995200
X-RateLimit-Window: 60
X-RateLimit-Category: orders-api
Retry-After: 45
```
### Header Descriptions
| Header | Description |
| ----------------------- | ----------------------------------------------------------- |
| `X-RateLimit-Limit` | Maximum requests allowed in the current window |
| `X-RateLimit-Remaining` | Requests remaining in the current window |
| `X-RateLimit-Reset` | Unix timestamp when the window resets |
| `X-RateLimit-Window` | Window duration in seconds (60 for per-minute limits) |
| `X-RateLimit-Category` | API category for this endpoint |
| `Retry-After` | Seconds to wait before retrying (present when rate limited) |
## Implementing Rate Limit Handling
### Basic Rate Limit Detection
```javascript theme={null}
import { StateSetClient } from 'StateSet-node';
import winston from 'winston';
const logger = winston.createLogger({
level: 'info',
format: winston.format.json(),
transports: [new winston.transports.Console()]
});
class RateLimitHandler {
constructor(client) {
this.client = client;
this.requestCounts = new Map();
}
async makeRequest(operation, ...args) {
try {
const response = await operation(...args);
this.logRateLimitInfo(response);
return response;
} catch (error) {
if (error.status === 429) {
return this.handleRateLimit(error, operation, ...args);
}
throw error;
}
}
logRateLimitInfo(response) {
const headers = response.headers || {};
logger.info('Rate limit status', {
remaining: headers['x-ratelimit-remaining'],
limit: headers['x-ratelimit-limit'],
resetTime: new Date(headers['x-ratelimit-reset'] * 1000),
category: headers['x-ratelimit-category']
});
}
async handleRateLimit(error, operation, ...args) {
const retryAfter = error.headers?.['retry-after'] || 60;
logger.warn('Rate limit exceeded, waiting before retry', {
retryAfter,
category: error.headers?.['x-ratelimit-category']
});
await this.sleep(retryAfter * 1000);
return this.makeRequest(operation, ...args);
}
sleep(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
}
// Usage
const client = new StateSetClient({ apiKey: process.env.STATESET_API_KEY });
const rateLimitHandler = new RateLimitHandler(client);
const orders = await rateLimitHandler.makeRequest(
() => client.orders.list({ limit: 50 })
);
```
### Advanced Rate Limiting with Queue
```javascript theme={null}
import PQueue from 'p-queue';
class AdvancedRateLimitHandler {
constructor(client, options = {}) {
this.client = client;
this.queues = new Map();
this.rateLimitInfo = new Map();
// Default queue options
this.defaultQueueOptions = {
concurrency: 5,
interval: 1000,
intervalCap: 10,
...options.queueOptions
};
}
getQueue(category = 'default') {
if (!this.queues.has(category)) {
const queueOptions = this.getCategoryQueueOptions(category);
this.queues.set(category, new PQueue(queueOptions));
}
return this.queues.get(category);
}
getCategoryQueueOptions(category) {
const categorySettings = {
'orders-api': { concurrency: 10, interval: 1000, intervalCap: 10 },
'customers-api': { concurrency: 5, interval: 1000, intervalCap: 5 },
'returns-api': { concurrency: 5, interval: 1000, intervalCap: 5 },
'analytics': { concurrency: 2, interval: 1000, intervalCap: 2 }
};
return {
...this.defaultQueueOptions,
...categorySettings[category]
};
}
async makeRequest(operation, category = 'default', priority = 0) {
const queue = this.getQueue(category);
return queue.add(async () => {
try {
const response = await operation();
this.updateRateLimitInfo(category, response);
return response;
} catch (error) {
if (error.status === 429) {
await this.handleRateLimit(error, category);
throw error; // Re-queue will happen automatically
}
throw error;
}
}, { priority });
}
updateRateLimitInfo(category, response) {
const headers = response.headers || {};
this.rateLimitInfo.set(category, {
remaining: parseInt(headers['x-ratelimit-remaining']) || 0,
limit: parseInt(headers['x-ratelimit-limit']) || 1000,
resetTime: parseInt(headers['x-ratelimit-reset']) || 0,
lastUpdated: Date.now()
});
}
async handleRateLimit(error, category) {
const retryAfter = parseInt(error.headers?.['retry-after']) || 60;
const queue = this.getQueue(category);
logger.warn('Rate limit exceeded for category', {
category,
retryAfter,
queueSize: queue.size,
pending: queue.pending
});
// Pause the queue
queue.pause();
await this.sleep(retryAfter * 1000);
// Resume the queue
queue.start();
}
getRateLimitStatus(category = 'default') {
return this.rateLimitInfo.get(category) || null;
}
sleep(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
}
// Usage with priority queueing
const handler = new AdvancedRateLimitHandler(client);
// High priority request (emergency order processing)
const criticalOrder = await handler.makeRequest(
() => client.orders.get(orderId),
'orders-api',
10
);
// Normal priority batch processing
const orders = await Promise.all([
handler.makeRequest(() => client.orders.list({ page: 1 }), 'orders-api', 0),
handler.makeRequest(() => client.orders.list({ page: 2 }), 'orders-api', 0),
handler.makeRequest(() => client.orders.list({ page: 3 }), 'orders-api', 0)
]);
```
## Optimization Strategies
### 1. Efficient Pagination
Instead of requesting large datasets at once:
```javascript theme={null}
// ❌ Inefficient - May trigger rate limits
const allOrders = await client.orders.list({ limit: 1000 });
// ✅ Efficient - Paginated requests
async function getAllOrdersPaginated() {
const allOrders = [];
let hasMore = true;
let cursor = null;
while (hasMore) {
const response = await client.orders.list({
limit: 100,
cursor: cursor
});
allOrders.push(...response.data);
cursor = response.next_cursor;
hasMore = response.has_more;
// Small delay to respect rate limits
await new Promise(resolve => setTimeout(resolve, 100));
}
return allOrders;
}
```
### 2. Batch Operations
Use batch endpoints when available:
```javascript theme={null}
// ❌ Multiple individual requests
for (const order of orders) {
await client.orders.update(order.id, { status: 'processed' });
}
// ✅ Single batch request
await client.orders.batchUpdate(
orders.map(order => ({
id: order.id,
status: 'processed'
}))
);
```
### 3. Webhook-First Architecture
Reduce polling by using webhooks:
```javascript theme={null}
// ❌ Constant polling
setInterval(async () => {
const orders = await client.orders.list({
status: 'pending',
updated_since: lastCheck
});
processNewOrders(orders);
}, 30000);
// ✅ Webhook-driven updates
app.post('/webhooks/StateSet', (req, res) => {
const event = req.body;
if (event.type === 'order.updated') {
processOrderUpdate(event.data);
}
res.status(200).send('OK');
});
```
### 4. Intelligent Caching
Cache frequently requested data:
```javascript theme={null}
class StateSetCache {
constructor(client, ttl = 300000) { // 5 minutes default TTL
this.client = client;
this.cache = new Map();
this.ttl = ttl;
}
async get(key, fetchFunction) {
const cached = this.cache.get(key);
const now = Date.now();
if (cached && (now - cached.timestamp) < this.ttl) {
logger.debug('Cache hit', { key });
return cached.data;
}
logger.debug('Cache miss, fetching', { key });
const data = await fetchFunction();
this.cache.set(key, {
data,
timestamp: now
});
return data;
}
clear(key) {
if (key) {
this.cache.delete(key);
} else {
this.cache.clear();
}
}
}
// Usage
const cache = new StateSetCache(client);
const customer = await cache.get(
`customer:${customerId}`,
() => client.customers.get(customerId)
);
```
## Monitoring Rate Limits
### Rate Limit Dashboard
Create a monitoring dashboard for your rate limit usage:
```javascript theme={null}
class RateLimitMonitor {
constructor() {
this.metrics = {
requests: new Map(),
rateLimits: new Map(),
errors: new Map()
};
}
recordRequest(category, success = true) {
const key = `${category}:${this.getTimeWindow()}`;
const current = this.metrics.requests.get(key) || { success: 0, total: 0 };
current.total++;
if (success) current.success++;
this.metrics.requests.set(key, current);
}
recordRateLimit(category, remainingRequests, totalLimit) {
const key = `${category}:${this.getTimeWindow()}`;
this.metrics.rateLimits.set(key, {
remaining: remainingRequests,
total: totalLimit,
utilizationPct: ((totalLimit - remainingRequests) / totalLimit) * 100,
timestamp: Date.now()
});
}
getTimeWindow() {
return Math.floor(Date.now() / 60000); // 1-minute windows
}
getUtilizationReport() {
const report = {};
for (const [key, data] of this.metrics.rateLimits) {
const [category] = key.split(':');
if (!report[category]) report[category] = [];
report[category].push(data);
}
return report;
}
// Alert when utilization is high
checkAlerts() {
const report = this.getUtilizationReport();
for (const [category, dataPoints] of Object.entries(report)) {
const latest = dataPoints[dataPoints.length - 1];
if (latest.utilizationPct > 80) {
logger.warn('High API utilization detected', {
category,
utilization: latest.utilizationPct,
remaining: latest.remaining
});
}
}
}
}
// Usage with middleware
const monitor = new RateLimitMonitor();
const monitoredClient = new Proxy(client, {
get(target, prop) {
const original = target[prop];
if (typeof original === 'object' && original !== null) {
return new Proxy(original, {
get(apiTarget, apiProp) {
const apiMethod = apiTarget[apiProp];
if (typeof apiMethod === 'function') {
return async (...args) => {
const category = `${prop}-api`;
try {
const result = await apiMethod.apply(apiTarget, args);
monitor.recordRequest(category, true);
if (result.headers) {
monitor.recordRateLimit(
category,
parseInt(result.headers['x-ratelimit-remaining']),
parseInt(result.headers['x-ratelimit-limit'])
);
}
return result;
} catch (error) {
monitor.recordRequest(category, false);
throw error;
}
};
}
return apiMethod;
}
});
}
return original;
}
});
```
## Best Practices Summary
* Use pagination instead of large limit values
* Implement batch operations where possible
* Cache frequently requested data
* Use webhooks to reduce polling
* Always check rate limit headers
* Implement exponential backoff for retries
* Use queues to manage request flow
* Monitor and alert on high utilization
* Design webhook-first integrations
* Implement circuit breakers for resilience
* Use separate queues for different priorities
* Cache aggressively with smart invalidation
* Track utilization across all categories
* Set alerts at 80% utilization threshold
* Monitor request success rates
* Review patterns during peak usage
## Getting Help
If you're consistently hitting rate limits or need higher limits:
1. **Review your usage patterns** using the monitoring tools above
2. **Optimize your integration** following the strategies in this guide
3. **Consider upgrading** to a higher plan with increased limits
4. **Contact support** at [support@StateSet.com](mailto:support@StateSet.com) for custom rate limits
## Related Resources
* [Error Handling Best Practices](/guides/error-handling-best-practices)
* [Webhook Security Guide](/guides/webhook-security)
* [API Testing Strategies](/guides/api-testing)
* [Performance Optimization](/guides/performance-optimization)
# API Testing Guide
Source: https://docs.stateset.com/guides/api-testing
Comprehensive guide to testing StateSet API integrations with practical examples and best practices
# API Testing Guide
Testing your StateSet API integration is crucial for ensuring reliability, catching bugs early, and maintaining confidence in your application. This guide covers comprehensive testing strategies from unit tests to end-to-end integration testing.
Test individual API calls and error handling
Test complete workflows and data flow
Test without hitting live APIs
Test real user scenarios end-to-end
## Testing Strategy Overview
### Test Pyramid for API Integration
```
🔺 E2E Tests (Few)
↗ Complex user workflows
↗ Critical business paths
↗ Cross-system integration
🔷 Integration Tests (Some)
↗ API endpoint interactions
↗ Data transformation
↗ Error handling flows
🔲 Unit Tests (Many)
↗ Individual functions
↗ Input validation
↗ Business logic
↗ Error scenarios
```
## Environment Setup
### Test Environment Configuration
```javascript theme={null}
// test/setup.js
import { StateSetClient } from 'StateSet-node';
import dotenv from 'dotenv';
// Load test environment variables
dotenv.config({ path: '.env.test' });
// Test configuration
export const testConfig = {
apiKey: process.env.STATESET_TEST_API_KEY,
baseUrl: process.env.STATESET_TEST_BASE_URL || 'https://api.sandbox.StateSet.com/v1',
timeout: 10000,
retries: 3
};
// Create test client
export const testClient = new StateSetClient({
apiKey: testConfig.apiKey,
baseUrl: testConfig.baseUrl,
timeout: testConfig.timeout
});
// Test data factory
export const createTestData = {
customer: (overrides = {}) => ({
email: `test+${Date.now()}@example.com`,
first_name: 'Test',
last_name: 'Customer',
phone: '+1-555-123-4567',
...overrides
}),
order: (customerId, overrides = {}) => ({
customer_id: customerId,
items: [
{
sku: 'TEST-ITEM-001',
quantity: 1,
price: 29.99
}
],
currency: 'USD',
...overrides
}),
address: (overrides = {}) => ({
street1: '123 Test Street',
city: 'Test City',
state: 'CA',
postal_code: '12345',
country: 'US',
...overrides
})
};
// Test helpers
export const testHelpers = {
generateUniqueEmail: () => `test+${Date.now()}+${Math.random().toString(36)}@example.com`,
waitFor: (ms) => new Promise(resolve => setTimeout(resolve, ms)),
retry: async (fn, maxAttempts = 3, delay = 1000) => {
for (let attempt = 1; attempt <= maxAttempts; attempt++) {
try {
return await fn();
} catch (error) {
if (attempt === maxAttempts) throw error;
await testHelpers.waitFor(delay * attempt);
}
}
},
cleanupResources: async (resources) => {
for (const resource of resources) {
try {
await resource.cleanup();
} catch (error) {
console.warn('Cleanup failed:', error.message);
}
}
}
};
```
### Environment Variables
```bash theme={null}
# .env.test
STATESET_TEST_API_KEY=sk_test_your_test_key_here
STATESET_TEST_BASE_URL=https://api.sandbox.StateSet.com/v1
NODE_ENV=test
LOG_LEVEL=warn
# Test database (if applicable)
TEST_DATABASE_URL=postgresql://user:pass@localhost:5432/test_db
# External service mocks
MOCK_STRIPE_ENABLED=true
MOCK_EMAIL_ENABLED=true
```
## Unit Testing
### Testing API Client Methods
```javascript theme={null}
// test/unit/StateSetClient.test.js
import { jest } from '@jest/globals';
import { StateSetClient } from 'StateSet-node';
import { StateSetAPIError } from 'StateSet-node/errors';
describe('StateSetClient', () => {
let client;
let mockFetch;
beforeEach(() => {
mockFetch = jest.fn();
global.fetch = mockFetch;
client = new StateSetClient({
apiKey: 'sk_test_123',
baseUrl: 'https://api.test.StateSet.com/v1'
});
});
afterEach(() => {
jest.restoreAllMocks();
});
describe('customers.create', () => {
it('should create customer successfully', async () => {
const customerData = {
email: 'test@example.com',
first_name: 'John',
last_name: 'Doe'
};
const expectedResponse = {
id: 'cust_123',
...customerData,
created_at: '2024-01-15T10:30:00Z'
};
mockFetch.mockResolvedValueOnce({
ok: true,
status: 201,
json: async () => expectedResponse
});
const result = await client.customers.create(customerData);
expect(mockFetch).toHaveBeenCalledWith(
'https://api.test.StateSet.com/v1/customers',
{
method: 'POST',
headers: {
'Authorization': 'Bearer sk_test_123',
'Content-Type': 'application/json'
},
body: JSON.stringify(customerData)
}
);
expect(result).toEqual(expectedResponse);
});
it('should handle validation errors', async () => {
const invalidCustomerData = {
email: 'invalid-email',
first_name: '',
last_name: 'Doe'
};
const errorResponse = {
error: {
code: 'VALIDATION_ERROR',
message: 'Request validation failed',
errors: [
{ field: 'email', message: 'Invalid email format' },
{ field: 'first_name', message: 'First name is required' }
]
}
};
mockFetch.mockResolvedValueOnce({
ok: false,
status: 400,
json: async () => errorResponse
});
await expect(client.customers.create(invalidCustomerData))
.rejects.toThrow(StateSetAPIError);
try {
await client.customers.create(invalidCustomerData);
} catch (error) {
expect(error.code).toBe('VALIDATION_ERROR');
expect(error.details.errors).toHaveLength(2);
expect(error.details.errors[0].field).toBe('email');
}
});
it('should handle network errors', async () => {
mockFetch.mockRejectedValueOnce(new Error('Network error'));
await expect(client.customers.create({}))
.rejects.toThrow('Network error');
});
it('should handle rate limiting with retry', async () => {
const customerData = { email: 'test@example.com' };
const successResponse = { id: 'cust_123', ...customerData };
// First call returns rate limit error
mockFetch
.mockResolvedValueOnce({
ok: false,
status: 429,
headers: new Map([['Retry-After', '1']]),
json: async () => ({
error: {
code: 'RATE_LIMITED',
message: 'Rate limit exceeded'
}
})
})
// Second call succeeds
.mockResolvedValueOnce({
ok: true,
status: 201,
json: async () => successResponse
});
const result = await client.customers.create(customerData);
expect(mockFetch).toHaveBeenCalledTimes(2);
expect(result).toEqual(successResponse);
});
});
describe('orders.list', () => {
it('should list orders with filters', async () => {
const filters = {
status: 'shipped',
created_after: '2024-01-01',
limit: 10
};
const expectedResponse = {
orders: [
{ id: 'ord_1', status: 'shipped' },
{ id: 'ord_2', status: 'shipped' }
],
pagination: {
has_more: false,
total_count: 2
}
};
mockFetch.mockResolvedValueOnce({
ok: true,
status: 200,
json: async () => expectedResponse
});
const result = await client.orders.list(filters);
// Verify URL construction with query parameters
const expectedUrl = 'https://api.test.StateSet.com/v1/orders?' +
'status=shipped&created_after=2024-01-01&limit=10';
expect(mockFetch).toHaveBeenCalledWith(
expectedUrl,
expect.objectContaining({
method: 'GET',
headers: expect.objectContaining({
'Authorization': 'Bearer sk_test_123'
})
})
);
expect(result).toEqual(expectedResponse);
});
});
});
```
### Testing Error Handling
```javascript theme={null}
// test/unit/errorHandling.test.js
import { StateSetErrorHandler } from '../../src/utils/errorHandler';
describe('StateSetErrorHandler', () => {
describe('validation errors', () => {
it('should extract field errors correctly', () => {
const error = {
code: 'VALIDATION_ERROR',
message: 'Request validation failed',
details: {
errors: [
{ field: 'email', message: 'Invalid email format' },
{ field: 'phone', message: 'Phone number required' }
]
}
};
const result = StateSetErrorHandler.handle(error);
expect(result.type).toBe('validation');
expect(result.fieldErrors).toEqual({
email: 'Invalid email format',
phone: 'Phone number required'
});
});
});
describe('rate limiting', () => {
it('should handle rate limit with retry delay', () => {
const error = {
code: 'RATE_LIMITED',
details: { retry_after: 30 }
};
const result = StateSetErrorHandler.handle(error);
expect(result.type).toBe('rate_limit');
expect(result.retryAfter).toBe(30);
expect(result.message).toContain('30 seconds');
});
});
describe('duplicate resources', () => {
it('should suggest appropriate action for duplicate email', () => {
const error = {
code: 'DUPLICATE_EMAIL',
details: {
email: 'test@example.com',
existing_customer_id: 'cust_123'
}
};
const result = StateSetErrorHandler.handle(error);
expect(result.type).toBe('duplicate');
expect(result.suggestion).toBe('Try logging in instead');
});
});
});
```
### Testing Business Logic
```javascript theme={null}
// test/unit/orderProcessor.test.js
import { OrderProcessor } from '../../src/services/orderProcessor';
import { StateSetClient } from 'StateSet-node';
jest.mock('StateSet-node');
describe('OrderProcessor', () => {
let orderProcessor;
let mockClient;
beforeEach(() => {
mockClient = {
customers: {
create: jest.fn(),
get: jest.fn()
},
orders: {
create: jest.fn()
},
inventory: {
check: jest.fn(),
reserve: jest.fn()
}
};
StateSetClient.mockImplementation(() => mockClient);
orderProcessor = new OrderProcessor();
});
describe('processOrder', () => {
it('should create customer and order successfully', async () => {
const orderData = {
customer: {
email: 'test@example.com',
first_name: 'John',
last_name: 'Doe'
},
items: [
{ sku: 'ITEM-001', quantity: 1, price: 29.99 }
]
};
// Mock customer creation
mockClient.customers.create.mockResolvedValue({
id: 'cust_123',
email: 'test@example.com'
});
// Mock inventory check
mockClient.inventory.check.mockResolvedValue({
available: true,
items: [{ sku: 'ITEM-001', available: true, quantity: 10 }]
});
// Mock order creation
mockClient.orders.create.mockResolvedValue({
id: 'ord_123',
status: 'pending',
customer_id: 'cust_123'
});
const result = await orderProcessor.processOrder(orderData);
expect(mockClient.customers.create).toHaveBeenCalledWith(orderData.customer);
expect(mockClient.inventory.check).toHaveBeenCalledWith({
items: orderData.items
});
expect(mockClient.orders.create).toHaveBeenCalledWith({
customer_id: 'cust_123',
items: orderData.items
});
expect(result.orderId).toBe('ord_123');
expect(result.customerId).toBe('cust_123');
});
it('should handle insufficient inventory', async () => {
const orderData = {
customer: { email: 'test@example.com' },
items: [{ sku: 'ITEM-001', quantity: 5 }]
};
mockClient.inventory.check.mockResolvedValue({
available: false,
items: [{ sku: 'ITEM-001', available: false, quantity: 2 }]
});
await expect(orderProcessor.processOrder(orderData))
.rejects.toThrow('Insufficient inventory');
expect(mockClient.orders.create).not.toHaveBeenCalled();
});
it('should handle existing customer', async () => {
const orderData = {
customer: { email: 'existing@example.com' },
items: [{ sku: 'ITEM-001', quantity: 1 }]
};
// Customer creation fails with duplicate email
mockClient.customers.create.mockRejectedValue({
code: 'DUPLICATE_EMAIL',
details: { existing_customer_id: 'cust_existing' }
});
// Get existing customer
mockClient.customers.get.mockResolvedValue({
id: 'cust_existing',
email: 'existing@example.com'
});
mockClient.inventory.check.mockResolvedValue({ available: true });
mockClient.orders.create.mockResolvedValue({
id: 'ord_456',
customer_id: 'cust_existing'
});
const result = await orderProcessor.processOrder(orderData);
expect(mockClient.customers.get).toHaveBeenCalledWith('cust_existing');
expect(result.customerId).toBe('cust_existing');
});
});
});
```
## Integration Testing
### Testing API Endpoints
```javascript theme={null}
// test/integration/customers.test.js
import { testClient, createTestData, testHelpers } from '../setup.js';
describe('Customer API Integration', () => {
const createdResources = [];
afterEach(async () => {
await testHelpers.cleanupResources(createdResources);
createdResources.length = 0;
});
describe('Customer lifecycle', () => {
it('should create, update, and delete customer', async () => {
// Create customer
const customerData = createTestData.customer();
const customer = await testClient.customers.create(customerData);
createdResources.push({
cleanup: () => testClient.customers.delete(customer.id)
});
expect(customer.id).toBeDefined();
expect(customer.email).toBe(customerData.email);
expect(customer.status).toBe('active');
// Update customer
const updateData = {
first_name: 'Updated',
customer_tier: 'gold'
};
const updatedCustomer = await testClient.customers.update(
customer.id,
updateData
);
expect(updatedCustomer.first_name).toBe('Updated');
expect(updatedCustomer.customer_tier).toBe('gold');
expect(updatedCustomer.email).toBe(customerData.email); // Should remain unchanged
// Get customer
const retrievedCustomer = await testClient.customers.get(customer.id);
expect(retrievedCustomer).toEqual(updatedCustomer);
// List customers (should include our customer)
const customers = await testClient.customers.list({
email: customerData.email
});
expect(customers.customers).toHaveLength(1);
expect(customers.customers[0].id).toBe(customer.id);
});
it('should prevent duplicate email addresses', async () => {
const customerData = createTestData.customer();
// Create first customer
const customer1 = await testClient.customers.create(customerData);
createdResources.push({
cleanup: () => testClient.customers.delete(customer1.id)
});
// Try to create second customer with same email
await expect(testClient.customers.create(customerData))
.rejects.toMatchObject({
code: 'DUPLICATE_EMAIL',
details: expect.objectContaining({
email: customerData.email,
existing_customer_id: customer1.id
})
});
});
it('should validate required fields', async () => {
const invalidData = {
email: 'invalid-email',
first_name: '', // Required but empty
last_name: 'Test'
};
await expect(testClient.customers.create(invalidData))
.rejects.toMatchObject({
code: 'VALIDATION_ERROR',
details: expect.objectContaining({
errors: expect.arrayContaining([
expect.objectContaining({
field: 'email',
message: expect.stringContaining('Invalid email format')
}),
expect.objectContaining({
field: 'first_name',
message: expect.stringContaining('required')
})
])
})
});
});
});
describe('Customer search and filtering', () => {
beforeEach(async () => {
// Create test customers with different tiers and statuses
const customers = [
{ ...createTestData.customer(), customer_tier: 'bronze', first_name: 'Alice' },
{ ...createTestData.customer(), customer_tier: 'gold', first_name: 'Bob' },
{ ...createTestData.customer(), customer_tier: 'platinum', first_name: 'Charlie' }
];
for (const customerData of customers) {
const customer = await testClient.customers.create(customerData);
createdResources.push({
cleanup: () => testClient.customers.delete(customer.id)
});
}
// Wait for eventual consistency
await testHelpers.waitFor(1000);
});
it('should filter customers by tier', async () => {
const goldCustomers = await testClient.customers.list({
customer_tier: 'gold'
});
expect(goldCustomers.customers).toHaveLength(1);
expect(goldCustomers.customers[0].first_name).toBe('Bob');
});
it('should search customers by name', async () => {
const searchResults = await testClient.customers.list({
search: 'Alice'
});
expect(searchResults.customers).toHaveLength(1);
expect(searchResults.customers[0].first_name).toBe('Alice');
});
it('should paginate results correctly', async () => {
const page1 = await testClient.customers.list({
limit: 2,
offset: 0
});
expect(page1.customers).toHaveLength(2);
expect(page1.pagination.has_more).toBe(true);
const page2 = await testClient.customers.list({
limit: 2,
offset: 2
});
expect(page2.customers).toHaveLength(1);
expect(page2.pagination.has_more).toBe(false);
// Ensure no overlap between pages
const page1Ids = page1.customers.map(c => c.id);
const page2Ids = page2.customers.map(c => c.id);
expect(page1Ids).not.toEqual(expect.arrayContaining(page2Ids));
});
});
});
```
### Testing Complex Workflows
```javascript theme={null}
// test/integration/orderWorkflow.test.js
import { testClient, createTestData, testHelpers } from '../setup.js';
describe('Order Workflow Integration', () => {
const createdResources = [];
afterEach(async () => {
await testHelpers.cleanupResources(createdResources);
createdResources.length = 0;
});
describe('Complete order lifecycle', () => {
it('should process order from creation to fulfillment', async () => {
// 1. Create customer
const customerData = createTestData.customer();
const customer = await testClient.customers.create(customerData);
createdResources.push({
cleanup: () => testClient.customers.delete(customer.id)
});
// 2. Create order
const orderData = createTestData.order(customer.id);
const order = await testClient.orders.create(orderData);
createdResources.push({
cleanup: () => testClient.orders.delete(order.id)
});
expect(order.status).toBe('pending');
expect(order.customer_id).toBe(customer.id);
// 3. Process payment (mock payment in sandbox)
const payment = await testClient.orders.pay(order.id, {
payment_method: {
type: 'card',
card: {
number: '4242424242424242', // Test card
exp_month: 12,
exp_year: 2025,
cvc: '123'
}
}
});
expect(payment.status).toBe('succeeded');
// 4. Check order status updated
const paidOrder = await testClient.orders.get(order.id);
expect(paidOrder.status).toBe('paid');
expect(paidOrder.payment_status).toBe('paid');
// 5. Ship order
const shipment = await testClient.orders.ship(order.id, {
carrier: 'fedex',
tracking_number: 'TEST123456789',
items: orderData.items
});
expect(shipment.tracking_number).toBe('TEST123456789');
// 6. Verify final status
const shippedOrder = await testClient.orders.get(order.id);
expect(shippedOrder.status).toBe('shipped');
expect(shippedOrder.tracking_number).toBe('TEST123456789');
// 7. Create return
const returnRequest = await testClient.returns.create({
order_id: order.id,
items: [
{
sku: orderData.items[0].sku,
quantity: 1,
reason: 'not_as_described'
}
],
customer_email: customer.email,
reason_code: 'not_satisfied'
});
expect(returnRequest.status).toBe('requested');
expect(returnRequest.order_id).toBe(order.id);
createdResources.push({
cleanup: () => testClient.returns.delete(returnRequest.id)
});
});
it('should handle inventory constraints', async () => {
const customer = await testClient.customers.create(createTestData.customer());
createdResources.push({
cleanup: () => testClient.customers.delete(customer.id)
});
// Try to order more items than available
const orderData = {
customer_id: customer.id,
items: [
{
sku: 'LIMITED-STOCK-ITEM',
quantity: 999999, // Exceeds available inventory
price: 29.99
}
]
};
await expect(testClient.orders.create(orderData))
.rejects.toMatchObject({
code: 'INSUFFICIENT_INVENTORY',
details: expect.objectContaining({
unavailable_items: expect.arrayContaining(['LIMITED-STOCK-ITEM'])
})
});
});
});
describe('Bulk operations', () => {
it('should handle bulk customer creation', async () => {
const customerBatch = Array.from({ length: 5 }, () => createTestData.customer());
const results = await Promise.all(
customerBatch.map(data => testClient.customers.create(data))
);
// Clean up created customers
results.forEach(customer => {
createdResources.push({
cleanup: () => testClient.customers.delete(customer.id)
});
});
expect(results).toHaveLength(5);
results.forEach((customer, index) => {
expect(customer.email).toBe(customerBatch[index].email);
expect(customer.id).toBeDefined();
});
});
it('should respect rate limits during bulk operations', async () => {
const customerBatch = Array.from({ length: 20 }, () => createTestData.customer());
// Create customers with proper rate limiting
const results = [];
for (const customerData of customerBatch) {
try {
const customer = await testClient.customers.create(customerData);
results.push(customer);
createdResources.push({
cleanup: () => testClient.customers.delete(customer.id)
});
// Small delay to avoid hitting rate limits
await testHelpers.waitFor(100);
} catch (error) {
if (error.code === 'RATE_LIMITED') {
// Wait for rate limit reset and retry
await testHelpers.waitFor(error.details.retry_after * 1000);
const customer = await testClient.customers.create(customerData);
results.push(customer);
} else {
throw error;
}
}
}
expect(results).toHaveLength(20);
});
});
});
```
## Mock Testing
### Setting Up API Mocks
```javascript theme={null}
// test/mocks/StateSetMock.js
import { rest } from 'msw';
import { setupServer } from 'msw/node';
// Mock data store
const mockData = {
customers: new Map(),
orders: new Map(),
returns: new Map()
};
// ID generators
const generateId = (prefix) => `${prefix}_${Date.now()}_${Math.random().toString(36).substring(2)}`;
// Mock API handlers
const handlers = [
// Customer endpoints
rest.post('https://api.sandbox.StateSet.com/v1/customers', (req, res, ctx) => {
const customerData = req.body;
// Validate required fields
if (!customerData.email || !customerData.first_name || !customerData.last_name) {
return res(
ctx.status(400),
ctx.json({
error: {
code: 'VALIDATION_ERROR',
message: 'Missing required fields',
errors: [
...(customerData.email ? [] : [{ field: 'email', message: 'Email is required' }]),
...(customerData.first_name ? [] : [{ field: 'first_name', message: 'First name is required' }]),
...(customerData.last_name ? [] : [{ field: 'last_name', message: 'Last name is required' }])
]
}
})
);
}
// Check for duplicate email
const existingCustomer = Array.from(mockData.customers.values())
.find(c => c.email === customerData.email);
if (existingCustomer) {
return res(
ctx.status(409),
ctx.json({
error: {
code: 'DUPLICATE_EMAIL',
message: 'Customer with this email already exists',
details: {
email: customerData.email,
existing_customer_id: existingCustomer.id
}
}
})
);
}
// Create customer
const customer = {
id: generateId('cust'),
...customerData,
status: 'active',
created_at: new Date().toISOString(),
updated_at: new Date().toISOString()
};
mockData.customers.set(customer.id, customer);
return res(
ctx.status(201),
ctx.json(customer)
);
}),
rest.get('https://api.sandbox.StateSet.com/v1/customers/:id', (req, res, ctx) => {
const { id } = req.params;
const customer = mockData.customers.get(id);
if (!customer) {
return res(
ctx.status(404),
ctx.json({
error: {
code: 'RESOURCE_NOT_FOUND',
message: 'Customer not found'
}
})
);
}
return res(ctx.json(customer));
}),
rest.get('https://api.sandbox.StateSet.com/v1/customers', (req, res, ctx) => {
const searchParams = req.url.searchParams;
const limit = parseInt(searchParams.get('limit')) || 20;
const offset = parseInt(searchParams.get('offset')) || 0;
const email = searchParams.get('email');
const tier = searchParams.get('customer_tier');
let customers = Array.from(mockData.customers.values());
// Apply filters
if (email) {
customers = customers.filter(c => c.email === email);
}
if (tier) {
customers = customers.filter(c => c.customer_tier === tier);
}
// Apply pagination
const totalCount = customers.length;
const paginatedCustomers = customers.slice(offset, offset + limit);
return res(
ctx.json({
customers: paginatedCustomers,
pagination: {
has_more: offset + limit < totalCount,
total_count: totalCount
}
})
);
}),
// Order endpoints
rest.post('https://api.sandbox.StateSet.com/v1/orders', (req, res, ctx) => {
const orderData = req.body;
// Validate customer exists
if (!mockData.customers.has(orderData.customer_id)) {
return res(
ctx.status(400),
ctx.json({
error: {
code: 'INVALID_CUSTOMER',
message: 'Customer not found'
}
})
);
}
// Check inventory (simplified)
const hasLimitedStock = orderData.items.some(item =>
item.sku === 'LIMITED-STOCK-ITEM' && item.quantity > 10
);
if (hasLimitedStock) {
return res(
ctx.status(422),
ctx.json({
error: {
code: 'INSUFFICIENT_INVENTORY',
message: 'Insufficient inventory',
details: {
unavailable_items: ['LIMITED-STOCK-ITEM']
}
}
})
);
}
const order = {
id: generateId('ord'),
...orderData,
status: 'pending',
payment_status: 'pending',
created_at: new Date().toISOString(),
updated_at: new Date().toISOString()
};
mockData.orders.set(order.id, order);
return res(
ctx.status(201),
ctx.json(order)
);
}),
// Rate limiting simulation
rest.use((req, res, ctx) => {
// Simulate rate limiting for high-frequency requests
const isRateLimited = Math.random() < 0.1; // 10% chance
if (isRateLimited && req.method === 'POST') {
return res(
ctx.status(429),
ctx.json({
error: {
code: 'RATE_LIMITED',
message: 'Rate limit exceeded',
details: {
retry_after: 2
}
}
})
);
}
})
];
// Create mock server
export const mockServer = setupServer(...handlers);
// Helper functions
export const mockHelpers = {
resetData: () => {
mockData.customers.clear();
mockData.orders.clear();
mockData.returns.clear();
},
addCustomer: (customer) => {
const id = customer.id || generateId('cust');
const fullCustomer = {
id,
status: 'active',
created_at: new Date().toISOString(),
updated_at: new Date().toISOString(),
...customer
};
mockData.customers.set(id, fullCustomer);
return fullCustomer;
},
getCustomers: () => Array.from(mockData.customers.values()),
getOrders: () => Array.from(mockData.orders.values())
};
```
### Using Mocks in Tests
```javascript theme={null}
// test/unit/customerService.mock.test.js
import { mockServer, mockHelpers } from '../mocks/StateSetMock.js';
import { CustomerService } from '../../src/services/customerService.js';
describe('CustomerService with mocks', () => {
let customerService;
beforeAll(() => {
mockServer.listen();
});
beforeEach(() => {
mockHelpers.resetData();
customerService = new CustomerService({
apiKey: 'sk_test_mock',
baseUrl: 'https://api.sandbox.StateSet.com/v1'
});
});
afterEach(() => {
mockServer.resetHandlers();
});
afterAll(() => {
mockServer.close();
});
it('should create and retrieve customer', async () => {
const customerData = {
email: 'test@example.com',
first_name: 'John',
last_name: 'Doe'
};
// Create customer
const customer = await customerService.createCustomer(customerData);
expect(customer.id).toBeDefined();
expect(customer.email).toBe(customerData.email);
// Retrieve customer
const retrievedCustomer = await customerService.getCustomer(customer.id);
expect(retrievedCustomer).toEqual(customer);
});
it('should handle validation errors', async () => {
const invalidData = {
email: 'test@example.com',
// Missing required fields
};
await expect(customerService.createCustomer(invalidData))
.rejects.toMatchObject({
code: 'VALIDATION_ERROR'
});
});
it('should handle duplicate emails', async () => {
const customerData = {
email: 'duplicate@example.com',
first_name: 'John',
last_name: 'Doe'
};
// Create first customer
await customerService.createCustomer(customerData);
// Try to create duplicate
await expect(customerService.createCustomer(customerData))
.rejects.toMatchObject({
code: 'DUPLICATE_EMAIL'
});
});
it('should paginate customer list', async () => {
// Create multiple customers
const customers = [];
for (let i = 0; i < 5; i++) {
customers.push(mockHelpers.addCustomer({
email: `test${i}@example.com`,
first_name: `Test${i}`,
last_name: 'User'
}));
}
// Get first page
const page1 = await customerService.listCustomers({ limit: 2, offset: 0 });
expect(page1.customers).toHaveLength(2);
expect(page1.pagination.has_more).toBe(true);
// Get second page
const page2 = await customerService.listCustomers({ limit: 2, offset: 2 });
expect(page2.customers).toHaveLength(2);
expect(page2.pagination.has_more).toBe(true);
// Get third page
const page3 = await customerService.listCustomers({ limit: 2, offset: 4 });
expect(page3.customers).toHaveLength(1);
expect(page3.pagination.has_more).toBe(false);
});
});
```
## End-to-End Testing
### E2E Test Setup
```javascript theme={null}
// test/e2e/setup.js
import { Browser, chromium } from '@playwright/test';
import { testClient } from '../setup.js';
export class E2ETestEnvironment {
constructor() {
this.browser = null;
this.context = null;
this.page = null;
this.baseUrl = process.env.E2E_BASE_URL || 'https://yourapp.com:3000';
}
async setup() {
this.browser = await chromium.launch({
headless: process.env.CI === 'true'
});
this.context = await this.browser.newContext({
// Record videos for failed tests
recordVideo: {
dir: 'test-results/videos/',
size: { width: 1280, height: 720 }
}
});
this.page = await this.context.newPage();
// Setup API interception for debugging
this.page.on('request', request => {
if (request.url().includes('api.StateSet.com')) {
logger.info('API Request:', request.method(), request.url());
}
});
this.page.on('response', response => {
if (response.url().includes('api.StateSet.com')) {
logger.info('API Response:', response.status(), response.url());
}
});
}
async teardown() {
await this.page?.close();
await this.context?.close();
await this.browser?.close();
}
async createTestCustomer() {
const customerData = {
email: `e2e-test-${Date.now()}@example.com`,
first_name: 'E2E',
last_name: 'Test',
phone: '+1-555-123-4567'
};
return await testClient.customers.create(customerData);
}
async navigateTo(path) {
await this.page.goto(`${this.baseUrl}${path}`);
}
async waitForApiCall(urlPattern) {
return await this.page.waitForResponse(
response => response.url().includes(urlPattern) && response.status() === 200
);
}
}
```
### E2E User Journey Tests
```javascript theme={null}
// test/e2e/customerJourney.test.js
import { test, expect } from '@playwright/test';
import { E2ETestEnvironment } from './setup.js';
test.describe('Customer Journey E2E', () => {
let testEnv;
test.beforeEach(async () => {
testEnv = new E2ETestEnvironment();
await testEnv.setup();
});
test.afterEach(async () => {
await testEnv.teardown();
});
test('complete customer signup and first order', async () => {
const { page } = testEnv;
// 1. Navigate to signup page
await testEnv.navigateTo('/sign-up');
// 2. Fill out customer form
await page.fill('[data-testid="email"]', 'e2e-customer@example.com');
await page.fill('[data-testid="first-name"]', 'John');
await page.fill('[data-testid="last-name"]', 'Doe');
await page.fill('[data-testid="phone"]', '+1-555-123-4567');
// 3. Submit form and wait for API call
const createCustomerPromise = testEnv.waitForApiCall('/v1/customers');
await page.click('[data-testid="submit-button"]');
await createCustomerPromise;
// 4. Verify redirect to dashboard
await expect(page).toHaveURL(/\/dashboard/);
// 5. Check customer data is displayed
await expect(page.locator('[data-testid="customer-name"]')).toContainText('John Doe');
// 6. Navigate to products page
await page.click('[data-testid="products-link"]');
await expect(page).toHaveURL(/\/products/);
// 7. Add product to cart
await page.click('[data-testid="add-to-cart"]:first-of-type');
// 8. Verify cart updates
await expect(page.locator('[data-testid="cart-count"]')).toContainText('1');
// 9. Go to checkout
await page.click('[data-testid="cart-button"]');
await page.click('[data-testid="checkout-button"]');
// 10. Fill shipping address
await page.fill('[data-testid="street1"]', '123 Test Street');
await page.fill('[data-testid="city"]', 'Test City');
await page.selectOption('[data-testid="state"]', 'CA');
await page.fill('[data-testid="postal-code"]', '12345');
// 11. Enter payment information (test mode)
await page.fill('[data-testid="card-number"]', '4242424242424242');
await page.fill('[data-testid="card-expiry"]', '12/25');
await page.fill('[data-testid="card-cvc"]', '123');
// 12. Submit order
const createOrderPromise = testEnv.waitForApiCall('/v1/orders');
await page.click('[data-testid="place-order-button"]');
await createOrderPromise;
// 13. Verify order confirmation
await expect(page).toHaveURL(/\/order-confirmation/);
await expect(page.locator('[data-testid="order-number"]')).toBeVisible();
// 14. Extract order number for cleanup
const orderNumber = await page.locator('[data-testid="order-number"]').textContent();
logger.info('Created order:', orderNumber);
});
test('customer support chat flow', async () => {
const { page } = testEnv;
// Create a customer first
const customer = await testEnv.createTestCustomer();
// 1. Navigate to support page with customer context
await testEnv.navigateTo(`/support?customer_id=${customer.id}`);
// 2. Start chat
await page.click('[data-testid="start-chat-button"]');
// 3. Send message
await page.fill('[data-testid="chat-input"]', 'I need help with my order');
await page.click('[data-testid="send-message"]');
// 4. Wait for AI response
await page.waitForSelector('[data-testid="ai-response"]', { timeout: 10000 });
// 5. Verify response appears
const response = await page.locator('[data-testid="ai-response"]').textContent();
expect(response.length).toBeGreaterThan(0);
// 6. Test escalation to human
await page.fill('[data-testid="chat-input"]', 'I want to speak to a human');
await page.click('[data-testid="send-message"]');
// 7. Verify escalation UI appears
await expect(page.locator('[data-testid="human-handoff"]')).toBeVisible();
});
test('return request flow', async () => {
const { page } = testEnv;
// Setup: Create customer and order
const customer = await testEnv.createTestCustomer();
// Navigate to returns page
await testEnv.navigateTo('/returns/create');
// 1. Enter order information
await page.fill('[data-testid="order-number"]', 'ORD-TEST-123');
await page.fill('[data-testid="email"]', customer.email);
// 2. Click lookup order
await page.click('[data-testid="lookup-order"]');
// 3. Select items to return
await page.check('[data-testid="return-item-0"]');
// 4. Select reason
await page.selectOption('[data-testid="return-reason"]', 'defective');
// 5. Add description
await page.fill('[data-testid="return-description"]', 'Product arrived damaged');
// 6. Submit return request
const createReturnPromise = testEnv.waitForApiCall('/v1/returns');
await page.click('[data-testid="submit-return"]');
await createReturnPromise;
// 7. Verify return confirmation
await expect(page.locator('[data-testid="return-number"]')).toBeVisible();
await expect(page.locator('[data-testid="return-status"]')).toContainText('Requested');
});
});
```
## Performance Testing
### Load Testing API Endpoints
```javascript theme={null}
// test/performance/loadTest.js
import { check, sleep } from 'k6';
import http from 'k6/http';
export let options = {
stages: [
{ duration: '2m', target: 100 }, // Ramp up to 100 users
{ duration: '5m', target: 100 }, // Stay at 100 users
{ duration: '2m', target: 200 }, // Ramp up to 200 users
{ duration: '5m', target: 200 }, // Stay at 200 users
{ duration: '2m', target: 0 }, // Ramp down to 0 users
],
thresholds: {
http_req_duration: ['p(95)<500'], // 95% of requests under 500ms
http_req_failed: ['rate<0.1'], // Less than 10% error rate
},
};
const API_BASE_URL = 'https://api.sandbox.StateSet.com/v1';
const API_KEY = __ENV.STATESET_TEST_API_KEY;
export default function () {
const headers = {
'Authorization': `Bearer ${API_KEY}`,
'Content-Type': 'application/json',
};
// Test customer creation
const customerData = {
email: `loadtest-${__VU}-${__ITER}@example.com`,
first_name: 'Load',
last_name: 'Test',
};
const createResponse = http.post(
`${API_BASE_URL}/customers`,
JSON.stringify(customerData),
{ headers }
);
check(createResponse, {
'customer creation status is 201': (r) => r.status === 201,
'customer creation response time < 500ms': (r) => r.timings.duration < 500,
});
if (createResponse.status === 201) {
const customer = JSON.parse(createResponse.body);
// Test customer retrieval
const getResponse = http.get(
`${API_BASE_URL}/customers/${customer.id}`,
{ headers }
);
check(getResponse, {
'customer retrieval status is 200': (r) => r.status === 200,
'customer retrieval response time < 200ms': (r) => r.timings.duration < 200,
});
// Test customer list
const listResponse = http.get(
`${API_BASE_URL}/customers?limit=10`,
{ headers }
);
check(listResponse, {
'customer list status is 200': (r) => r.status === 200,
'customer list response time < 300ms': (r) => r.timings.duration < 300,
});
}
sleep(1);
}
```
## Continuous Integration
### GitHub Actions Workflow
```yaml theme={null}
# .github/workflows/api-tests.yml
name: API Tests
on:
push:
branches: [ main, develop ]
pull_request:
branches: [ main ]
jobs:
unit-tests:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v3
- name: Setup Node.js
uses: actions/setup-node@v3
with:
node-version: '18'
cache: 'npm'
- name: Install dependencies
run: npm ci
- name: Run unit tests
run: npm run test:unit
env:
NODE_ENV: test
- name: Upload coverage
uses: codecov/codecov-action@v3
with:
file: ./coverage/lcov.info
integration-tests:
runs-on: ubuntu-latest
needs: unit-tests
steps:
- uses: actions/checkout@v3
- name: Setup Node.js
uses: actions/setup-node@v3
with:
node-version: '18'
cache: 'npm'
- name: Install dependencies
run: npm ci
- name: Run integration tests
run: npm run test:integration
env:
STATESET_TEST_API_KEY: ${{ secrets.STATESET_TEST_API_KEY }}
NODE_ENV: test
- name: Upload test results
uses: actions/upload-artifact@v3
if: failure()
with:
name: integration-test-results
path: test-results/
e2e-tests:
runs-on: ubuntu-latest
needs: integration-tests
steps:
- uses: actions/checkout@v3
- name: Setup Node.js
uses: actions/setup-node@v3
with:
node-version: '18'
cache: 'npm'
- name: Install dependencies
run: npm ci
- name: Install Playwright
run: npx playwright install --with-deps
- name: Start application
run: |
npm run build
npm run start &
sleep 10
env:
NODE_ENV: test
- name: Run E2E tests
run: npm run test:e2e
env:
STATESET_TEST_API_KEY: ${{ secrets.STATESET_TEST_API_KEY }}
E2E_BASE_URL: https://yourapp.com:3000
- name: Upload E2E results
uses: actions/upload-artifact@v3
if: failure()
with:
name: e2e-test-results
path: test-results/
performance-tests:
runs-on: ubuntu-latest
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
steps:
- uses: actions/checkout@v3
- name: Run k6 performance tests
uses: grafana/k6-action@v0.3.0
with:
filename: test/performance/loadTest.js
env:
STATESET_TEST_API_KEY: ${{ secrets.STATESET_TEST_API_KEY }}
```
## Test Data Management
### Test Data Factory
```javascript theme={null}
// test/factories/testDataFactory.js
import { faker } from '@faker-js/faker';
export class TestDataFactory {
static customer(overrides = {}) {
return {
email: faker.internet.email(),
first_name: faker.person.firstName(),
last_name: faker.person.lastName(),
phone: faker.phone.number('+1-###-###-####'),
date_of_birth: faker.date.birthdate({ min: 18, max: 80, mode: 'age' }).toISOString().split('T')[0],
address: this.address(),
customer_tier: faker.helpers.arrayElement(['bronze', 'silver', 'gold', 'platinum']),
marketing_consent: faker.datatype.boolean(),
...overrides
};
}
static address(overrides = {}) {
return {
street1: faker.location.streetAddress(),
street2: faker.helpers.maybe(() => faker.location.secondaryAddress(), 0.3),
city: faker.location.city(),
state: faker.location.state({ abbreviated: true }),
postal_code: faker.location.zipCode(),
country: 'US',
...overrides
};
}
static order(customerId, overrides = {}) {
return {
customer_id: customerId,
items: [this.orderItem()],
currency: 'USD',
shipping_address: this.address(),
billing_address: this.address(),
...overrides
};
}
static orderItem(overrides = {}) {
return {
sku: faker.helpers.arrayElement(['WIDGET-001', 'GADGET-002', 'TOOL-003']),
quantity: faker.number.int({ min: 1, max: 5 }),
price: parseFloat(faker.commerce.price({ min: 10, max: 100, dec: 2 })),
...overrides
};
}
static returnRequest(orderId, overrides = {}) {
return {
order_id: orderId,
reason_code: faker.helpers.arrayElement(['defective', 'not_satisfied', 'wrong_item']),
customer_notes: faker.lorem.sentence(),
items: [this.returnItem()],
...overrides
};
}
static returnItem(overrides = {}) {
return {
sku: faker.helpers.arrayElement(['WIDGET-001', 'GADGET-002', 'TOOL-003']),
quantity: faker.number.int({ min: 1, max: 3 }),
reason: faker.helpers.arrayElement(['defective', 'not_as_described', 'wrong_item']),
condition: faker.helpers.arrayElement(['A', 'B', 'C']),
...overrides
};
}
// Scenario-based data generation
static scenarioData = {
// High-value enterprise customer
enterpriseCustomer: () => this.customer({
customer_tier: 'platinum',
custom_fields: {
company_name: faker.company.name(),
industry: 'Technology',
company_size: '500+'
}
}),
// Problem order for testing returns
problematicOrder: (customerId) => this.order(customerId, {
items: [
this.orderItem({ sku: 'DEFECTIVE-ITEM', quantity: 1 })
]
}),
// Bulk order
bulkOrder: (customerId) => this.order(customerId, {
items: Array.from({ length: 5 }, () => this.orderItem())
})
};
}
```
***
## Summary
Comprehensive API testing ensures:
1. **Unit Tests** - Fast feedback on individual components
2. **Integration Tests** - Verify API interactions work correctly
3. **Mock Tests** - Test without external dependencies
4. **E2E Tests** - Validate complete user workflows
5. **Performance Tests** - Ensure system handles load
6. **CI/CD Integration** - Automated testing in deployment pipeline
**Testing Best Practices:**
* Write tests before implementing features (TDD)
* Use descriptive test names that explain the scenario
* Keep tests isolated and independent
* Clean up test data after each test
* Mock external dependencies for faster, more reliable tests
* Monitor test performance and maintain fast feedback loops
This comprehensive testing approach helps ensure your StateSet API integration is robust, reliable, and ready for production.
# Agent Attributes & Personality
Source: https://docs.stateset.com/guides/attributes-quickstart
Design sophisticated agent personalities with dynamic attributes and behavioral patterns
## Prerequisites
Before creating agent attributes, ensure you have:
* StateSet account with API access
* At least one agent created in your StateSet workspace
* API credentials from the [StateSet Dashboard](https://app.StateSet.com/settings/api-keys)
* Node.js 16+ installed (for SDK examples)
* Basic understanding of JavaScript and REST APIs
* Text editor or IDE for development
* Familiarity with personality modeling and behavioral psychology concepts
* Understanding of your brand voice and customer interaction requirements
* Knowledge of customer service best practices and communication styles
Code examples focus on core API calls. For production-ready patterns (structured logging, retries, and error handling), see [Error Handling Best Practices](/guides/error-handling-best-practices).
## Introduction
Agent Attributes are the building blocks of personality in StateSet. They define not just how your agents communicate, but who they are—their tone, expertise level, decision-making style, and behavioral patterns. This guide shows you how to create agents with distinct, adaptable personalities that align with your brand and customer needs.
## What are Agent Attributes?
Agent Attributes are dynamic parameters that shape your agent's behavior, communication style, and decision-making. Unlike static prompts, attributes can change in real-time based on context, allowing your agents to adapt their personality to different situations.
### Core Concepts
Define communication style, empathy level, and formality
Control decision-making, proactivity, and problem-solving approach
Adjust attributes in real-time based on context and customer needs
## Attribute Categories
### 1. Communication Style Attributes
```javascript theme={null}
const communicationAttributes = {
// Tone and Voice
formality: {
type: 'scale',
range: [0, 100],
description: 'How formal vs casual the agent communicates',
examples: {
0: "Hey! What's up? How can I help? 😊",
50: "Hello! How can I assist you today?",
100: "Good afternoon. How may I be of service?"
}
},
// Empathy and Emotional Intelligence
empathy_level: {
type: 'scale',
range: [0, 100],
description: 'How much emotional understanding the agent shows',
impact: {
low: 'Direct, solution-focused responses',
medium: 'Acknowledges feelings while solving problems',
high: 'Deeply validates emotions before addressing issues'
}
},
// Communication Preferences
verbosity: {
type: 'enum',
values: ['concise', 'balanced', 'detailed'],
description: 'How much detail to include in responses',
use_cases: {
concise: 'Quick answers for simple questions',
balanced: 'Standard customer service',
detailed: 'Technical support or complex issues'
}
},
// Language Complexity
language_level: {
type: 'enum',
values: ['simple', 'standard', 'professional', 'technical'],
description: 'Vocabulary and sentence complexity',
adapts_to: ['customer_profile', 'topic_complexity']
}
};
```
### 2. Behavioral Attributes
```javascript theme={null}
const behavioralAttributes = {
// Decision Making
autonomy_level: {
type: 'scale',
range: [0, 100],
description: 'How independently the agent makes decisions',
thresholds: {
0: 'Always asks for confirmation',
30: 'Handles routine tasks independently',
70: 'Makes most decisions autonomously',
100: 'Full autonomy within defined bounds'
}
},
// Problem Solving Approach
solution_style: {
type: 'enum',
values: ['step_by_step', 'quick_fix', 'comprehensive', 'educational'],
description: 'How the agent approaches problem resolution',
when_to_use: {
step_by_step: 'Complex technical issues',
quick_fix: 'Simple, common problems',
comprehensive: 'VIP customers or critical issues',
educational: 'First-time users or learning opportunities'
}
},
// Proactivity
proactivity: {
type: 'scale',
range: [0, 100],
description: 'How proactive vs reactive the agent is',
behaviors: {
low: 'Answers only what is asked',
medium: 'Suggests related solutions',
high: 'Anticipates needs and offers preventive advice'
}
}
};
```
### 3. Expertise Attributes
```javascript theme={null}
const expertiseAttributes = {
// Domain Knowledge
domain_expertise: {
type: 'multi_select',
values: ['product', 'technical', 'billing', 'shipping', 'legal'],
description: 'Areas where the agent has deep knowledge',
confidence_modifiers: {
expert: 1.0,
familiar: 0.7,
basic: 0.4
}
},
// Technical Depth
technical_level: {
type: 'scale',
range: [0, 100],
description: 'How technical the agent can get',
auto_adjust: true,
based_on: ['customer_technical_level', 'topic_complexity']
},
// Industry Specialization
industry_focus: {
type: 'enum',
values: ['retail', 'saas', 'healthcare', 'finance', 'general'],
description: 'Industry-specific knowledge and compliance',
includes: ['terminology', 'regulations', 'best_practices']
}
};
```
## Creating Dynamic Attributes
### Basic Attribute Creation
```javascript theme={null}
import { StateSetClient } from 'StateSet-node';
const client = new StateSetClient({
apiKey: process.env.STATESET_API_KEY
});
async function createBasicAttribute(agentId) {
const attribute = await client.attributes.create({
agent_id: agentId,
type: 'personality',
name: 'friendliness',
description: 'How warm and friendly the agent appears',
value_type: 'scale',
default_value: 75,
range: {
min: 0,
max: 100
},
impact: {
greeting: 'Affects warmth of initial greeting',
sign_off: 'Influences closing statements',
emoji_usage: 'Controls emoji frequency'
}
});
return attribute;
}
```
### Advanced Attribute with Conditions
```javascript theme={null}
async function createConditionalAttribute(agentId) {
const attribute = await client.attributes.create({
agent_id: agentId,
type: 'behavioral',
name: 'urgency_response',
description: 'How the agent responds to urgent situations',
// Dynamic value based on conditions
value_logic: {
type: 'conditional',
conditions: [
{
if: 'ticket.priority === "critical"',
then: { urgency: 100, response_time: 'immediate' }
},
{
if: 'customer.tier === "vip" && ticket.priority === "high"',
then: { urgency: 90, response_time: '5_minutes' }
},
{
if: 'ticket.age > 24_hours',
then: { urgency: 'urgency + 20', response_time: '30_minutes' }
}
],
default: { urgency: 50, response_time: '2_hours' }
},
// How this affects behavior
behaviors: {
high_urgency: [
'Skip pleasantries',
'Get to solution immediately',
'Offer immediate escalation option',
'Follow up proactively'
],
low_urgency: [
'Full greeting and rapport building',
'Thorough explanation',
'Educational approach'
]
}
});
return attribute;
}
```
### Composite Personality Profiles
```javascript theme={null}
class PersonalityBuilder {
async createPersonalityProfile(agentId, profileType) {
const profiles = {
technical_expert: {
formality: 70,
empathy: 50,
technical_depth: 95,
verbosity: 'detailed',
solution_style: 'educational',
proactivity: 80,
emoji_usage: 0,
code_examples: true
},
friendly_support: {
formality: 20,
empathy: 90,
technical_depth: 40,
verbosity: 'balanced',
solution_style: 'step_by_step',
proactivity: 70,
emoji_usage: 80,
humor_allowed: true
},
enterprise_account_manager: {
formality: 90,
empathy: 70,
technical_depth: 60,
verbosity: 'concise',
solution_style: 'comprehensive',
proactivity: 95,
business_focus: true,
upsell_awareness: 80
},
crisis_manager: {
formality: 60,
empathy: 85,
urgency: 100,
verbosity: 'concise',
solution_style: 'quick_fix',
escalation_threshold: 20,
calm_reassurance: true
}
};
const profile = profiles[profileType];
const attributes = [];
for (const [name, value] of Object.entries(profile)) {
const attr = await client.attributes.create({
agent_id: agentId,
name,
value,
profile_group: profileType
});
attributes.push(attr);
}
return attributes;
}
}
```
## Dynamic Attribute Adjustment
### Real-time Adaptation
```javascript theme={null}
class DynamicPersonality {
constructor(agentId) {
this.agentId = agentId;
this.baselineAttributes = {};
this.currentAttributes = {};
}
async adaptToContext(context) {
const adjustments = this.calculateAdjustments(context);
for (const [attribute, adjustment] of Object.entries(adjustments)) {
await this.updateAttribute(attribute, adjustment);
}
}
calculateAdjustments(context) {
const adjustments = {};
// Adjust formality based on customer
if (context.customer.age > 60) {
adjustments.formality = 20; // More formal
} else if (context.customer.age < 25) {
adjustments.formality = -20; // Less formal
}
// Adjust empathy based on sentiment
if (context.sentiment === 'angry') {
adjustments.empathy = 30;
adjustments.patience = 40;
}
// Adjust technical level based on customer knowledge
if (context.customer.technical_score > 80) {
adjustments.technical_depth = 30;
adjustments.verbosity = 'detailed';
}
// Adjust urgency based on issue type
if (context.issue.type === 'outage') {
adjustments.urgency = 50;
adjustments.solution_style = 'quick_fix';
}
return adjustments;
}
async updateAttribute(name, adjustment) {
const current = this.currentAttributes[name] || this.baselineAttributes[name];
let newValue;
if (typeof adjustment === 'number') {
newValue = Math.max(0, Math.min(100, current + adjustment));
} else {
newValue = adjustment;
}
await client.attributes.update({
agent_id: this.agentId,
name,
value: newValue
});
this.currentAttributes[name] = newValue;
}
}
```
### Learning and Evolution
```javascript theme={null}
class EvolvingPersonality {
async learnFromInteraction(agentId, conversation) {
const feedback = await this.analyzeConversation(conversation);
// Identify successful patterns
if (feedback.satisfaction_score > 4.5) {
await this.reinforceAttributes(agentId, conversation.attributes);
}
// Identify areas for improvement
if (feedback.escalated || feedback.satisfaction_score < 3) {
await this.adjustWeakAttributes(agentId, feedback.issues);
}
// Update long-term personality trends
await this.updatePersonalityTrends(agentId, feedback);
}
async reinforceAttributes(agentId, successfulAttributes) {
for (const [attr, value] of Object.entries(successfulAttributes)) {
await client.attributes.updateTrend({
agent_id: agentId,
attribute: attr,
trend_direction: 'towards',
target_value: value,
learning_rate: 0.1
});
}
}
async analyzeConversation(conversation) {
return {
satisfaction_score: conversation.rating,
escalated: conversation.escalated,
resolution_time: conversation.duration,
sentiment_progression: this.analyzeSentiment(conversation),
successful_tactics: this.identifySuccessfulTactics(conversation)
};
}
}
```
## Attribute Templates
### Industry-Specific Templates
```javascript theme={null}
const industryTemplates = {
healthcare: {
attributes: {
compliance_awareness: 100,
empathy: 85,
privacy_consciousness: 100,
medical_terminology: true,
formality: 70
},
restricted_behaviors: ['humor', 'medical_advice'],
required_confirmations: ['patient_identity', 'consent']
},
financial_services: {
attributes: {
accuracy_focus: 100,
regulatory_compliance: 100,
formality: 80,
numerical_precision: true,
security_awareness: 95
},
audit_trail: true,
pii_handling: 'strict'
},
e_commerce: {
attributes: {
sales_awareness: 70,
product_knowledge: 90,
friendliness: 80,
urgency_creation: 60,
visual_description: true
},
upsell_enabled: true,
abandoned_cart_recovery: true
},
saas_technical: {
attributes: {
technical_depth: 85,
problem_solving: 'systematic',
documentation_reference: true,
code_literacy: 90,
patience: 80
},
integration_knowledge: true,
api_fluency: true
}
};
async function applyIndustryTemplate(agentId, industry) {
const template = industryTemplates[industry];
if (!template) {
throw new Error(`Unknown industry: ${industry}`);
}
// Apply all attributes
for (const [name, value] of Object.entries(template.attributes)) {
await client.attributes.create({
agent_id: agentId,
name,
value,
category: 'industry_standard',
locked: true // Prevent accidental changes
});
}
// Apply behavioral restrictions
if (template.restricted_behaviors) {
await client.agents.updateRestrictions({
agent_id: agentId,
restrictions: template.restricted_behaviors
});
}
return template;
}
```
## Testing and Validation
### Personality Consistency Testing
```javascript theme={null}
class PersonalityTester {
async testConsistency(agentId, scenarios) {
const results = [];
for (const scenario of scenarios) {
const response = await this.runScenario(agentId, scenario);
const analysis = await this.analyzeResponse(response, scenario.expected_attributes);
results.push({
scenario: scenario.name,
consistency_score: analysis.consistency,
attribute_alignment: analysis.alignment,
deviations: analysis.deviations
});
}
return {
overall_consistency: this.calculateOverallConsistency(results),
recommendations: this.generateRecommendations(results)
};
}
async runScenario(agentId, scenario) {
return client.agents.test({
agent_id: agentId,
input: scenario.input,
context: scenario.context,
expected_attributes: scenario.expected_attributes
});
}
analyzeResponse(response, expectedAttributes) {
const analysis = {
consistency: 0,
alignment: {},
deviations: []
};
// Check each expected attribute
for (const [attr, expected] of Object.entries(expectedAttributes)) {
const actual = this.measureAttribute(response, attr);
const deviation = Math.abs(actual - expected);
analysis.alignment[attr] = {
expected,
actual,
deviation
};
if (deviation > 20) {
analysis.deviations.push({
attribute: attr,
severity: 'high',
recommendation: `Adjust ${attr} baseline or add conditional logic`
});
}
}
analysis.consistency = 100 - (analysis.deviations.length * 10);
return analysis;
}
}
```
### A/B Testing Personalities
```javascript theme={null}
class PersonalityABTest {
async runTest(agentId, variantA, variantB, duration) {
const test = await client.experiments.create({
type: 'personality_test',
agent_id: agentId,
variants: {
control: variantA,
treatment: variantB
},
metrics: ['satisfaction_score', 'resolution_time', 'escalation_rate'],
duration,
traffic_split: 50
});
// Monitor results
const monitor = setInterval(async () => {
const results = await client.experiments.getResults(test.id);
if (results.significant) {
await this.applyWinner(agentId, results.winner);
clearInterval(monitor);
}
}, 3600000); // Check hourly
return test;
}
async applyWinner(agentId, winningVariant) {
await client.attributes.bulkUpdate({
agent_id: agentId,
attributes: winningVariant.attributes,
source: 'ab_test_winner'
});
}
}
```
## Best Practices
### 1. Attribute Hierarchies
```javascript theme={null}
// Good: Clear hierarchy and relationships
const attributeHierarchy = {
communication: {
parent: null,
children: ['tone', 'formality', 'verbosity'],
weight: 1.0
},
tone: {
parent: 'communication',
children: ['friendliness', 'professionalism', 'empathy'],
weight: 0.8
},
friendliness: {
parent: 'tone',
children: ['emoji_usage', 'casual_language'],
weight: 0.6,
constraints: {
max_if: { formality: '> 80', value: 30 }
}
}
};
// Bad: Conflicting flat attributes
const flatAttributes = {
friendly: 100,
formal: 100, // Conflicts with friendly
professional: 0 // Conflicts with formal
};
```
### 2. Context-Aware Defaults
```javascript theme={null}
// Good: Dynamic defaults based on context
const contextAwareDefaults = {
getDefaultAttributes(context) {
const defaults = { ...this.baseDefaults };
// Time-based adjustments
const hour = new Date().getHours();
if (hour < 9 || hour > 17) {
defaults.formality -= 10;
defaults.brevity += 20;
}
// Channel-based adjustments
if (context.channel === 'sms') {
defaults.verbosity = 'concise';
defaults.emoji_usage = 0;
} else if (context.channel === 'chat') {
defaults.response_speed = 'quick';
defaults.emoji_usage = 40;
}
return defaults;
}
};
```
### 3. Attribute Validation
```javascript theme={null}
class AttributeValidator {
validateAttributes(attributes) {
const errors = [];
// Check for conflicts
if (attributes.friendliness > 80 && attributes.formality > 80) {
errors.push({
type: 'conflict',
message: 'High friendliness conflicts with high formality',
suggestion: 'Consider professional_warmth instead'
});
}
// Check for missing required attributes
const required = ['empathy', 'clarity', 'helpfulness'];
for (const req of required) {
if (!(req in attributes)) {
errors.push({
type: 'missing',
attribute: req,
message: `Required attribute ${req} is missing`
});
}
}
// Check value ranges
for (const [attr, value] of Object.entries(attributes)) {
if (typeof value === 'number' && (value < 0 || value > 100)) {
errors.push({
type: 'range',
attribute: attr,
message: `${attr} value ${value} is out of range [0-100]`
});
}
}
return errors;
}
}
```
## Monitoring and Analytics
### Attribute Performance Tracking
```javascript theme={null}
async function trackAttributePerformance(agentId) {
const metrics = await client.attributes.getPerformanceMetrics({
agent_id: agentId,
timeframe: '30d',
group_by: 'attribute'
});
const insights = {
high_impact: metrics.filter(m => m.correlation_with_satisfaction > 0.7),
low_impact: metrics.filter(m => m.correlation_with_satisfaction < 0.3),
optimal_ranges: {},
recommendations: []
};
// Find optimal ranges
for (const metric of metrics) {
const optimal = metric.satisfaction_by_value.reduce((best, current) =>
current.satisfaction > best.satisfaction ? current : best
);
insights.optimal_ranges[metric.attribute] = {
range: optimal.value_range,
satisfaction: optimal.satisfaction
};
}
return insights;
}
```
## Next Steps
Pre-built personalities for common use cases
Build agents that understand and respond to emotions
***
**Pro Tip**: Start with a base personality and use conditional attributes to adapt to specific situations. This provides consistency while allowing flexibility.
For personality examples and templates, visit our [GitHub repository](https://github.com/StateSet/personality-templates) or contact [support@StateSet.com](mailto:support@StateSet.com).
# Batch Operations Guide
Source: https://docs.stateset.com/guides/batch-operations
Comprehensive guide to batch processing and bulk operations with StateSet API for high-volume data management
# Batch Operations Guide
Learn how to efficiently process large volumes of data using StateSet's batch operation capabilities. This guide covers bulk creation, updates, imports, exports, and advanced processing patterns for high-throughput scenarios.
## Prerequisites
Before you begin, ensure you have:
* A StateSet account with appropriate rate limits
* Understanding of asynchronous processing patterns
* Node.js 16+ installed
* Knowledge of database optimization techniques
* Experience with queue systems (recommended)
## Core Batch Concepts
### Batch Operation Types
Create multiple records in a single operation
Update multiple records simultaneously
Import large datasets from external sources
Export large datasets for reporting or migration
### Performance Considerations
```javascript theme={null}
// Batch processing configuration
const BATCH_CONFIG = {
// Optimal batch sizes for different operations
CREATE_BATCH_SIZE: 100,
UPDATE_BATCH_SIZE: 200,
IMPORT_BATCH_SIZE: 500,
EXPORT_BATCH_SIZE: 1000,
// Concurrency limits
MAX_CONCURRENT_BATCHES: 5,
MAX_RETRY_ATTEMPTS: 3,
// Rate limiting
REQUESTS_PER_SECOND: 10,
BURST_LIMIT: 50,
// Timeouts
BATCH_TIMEOUT: 60000, // 1 minute
OPERATION_TIMEOUT: 300000 // 5 minutes
};
```
## Setting Up Batch Processing
Install required packages for batch processing:
```bash theme={null}
npm install StateSet-node p-limit p-queue lodash csv-parser fast-csv
# or
yarn add StateSet-node p-limit p-queue lodash csv-parser fast-csv
```
Set up environment for batch operations:
```bash theme={null}
# .env
STATESET_API_KEY=your_api_key_here
STATESET_ENVIRONMENT=production
# Batch Processing Configuration
BATCH_WORKER_CONCURRENCY=5
BATCH_QUEUE_SIZE=1000
BATCH_RETRY_ATTEMPTS=3
BATCH_TIMEOUT_MS=300000
# Storage Configuration
TEMP_STORAGE_PATH=./temp/batch-files
RESULTS_STORAGE_PATH=./results
# Queue Configuration (Redis)
REDIS_URL=redis://localhost:6379
QUEUE_NAME=StateSet-batch-operations
```
Create a robust batch processing client:
```javascript theme={null}
import { StateSetClient } from 'StateSet-node';
import pLimit from 'p-limit';
import _ from 'lodash';
class BatchProcessor {
constructor(options = {}) {
this.client = new StateSetClient({
apiKey: process.env.STATESET_API_KEY,
timeout: options.timeout || 60000
});
this.concurrencyLimit = pLimit(options.concurrency || 5);
this.retryAttempts = options.retryAttempts || 3;
this.batchSizes = {
create: options.createBatchSize || 100,
update: options.updateBatchSize || 200,
import: options.importBatchSize || 500,
export: options.exportBatchSize || 1000
};
this.results = {
successful: [],
failed: [],
skipped: []
};
}
async processBatch(operation, data, options = {}) {
const startTime = Date.now();
logger.info(`Starting batch ${operation} for ${data.length} items`);
try {
const batchSize = this.batchSizes[operation] || 100;
const batches = _.chunk(data, batchSize);
const results = await Promise.allSettled(
batches.map((batch, index) =>
this.concurrencyLimit(() =>
this.processSingleBatch(operation, batch, index, options)
)
)
);
const summary = this.compileBatchResults(results);
logger.info(`Batch ${operation} completed in ${Date.now(); - startTime}ms`, summary);
return summary;
} catch (error) {
logger.error(`Batch ${operation} failed:`, error);
throw error;
}
}
async processSingleBatch(operation, batch, batchIndex, options) {
let attempt = 0;
let lastError;
while (attempt < this.retryAttempts) {
try {
logger.info(`Processing batch ${batchIndex + 1}, attempt ${attempt + 1}`);
const result = await this.executeBatchOperation(operation, batch, options);
return {
batchIndex,
success: true,
count: batch.length,
result
};
} catch (error) {
lastError = error;
attempt++;
if (attempt < this.retryAttempts) {
const delay = Math.pow(2, attempt) * 1000; // Exponential backoff
console.warn(`Batch ${batchIndex + 1} failed, retrying in ${delay}ms:`, error.message);
await this.delay(delay);
}
}
}
return {
batchIndex,
success: false,
count: batch.length,
error: lastError.message
};
}
delay(ms) {
return new Promise(resolve => setTimeout(resolve, ms));
}
compileBatchResults(results) {
const summary = {
total: results.length,
successful: 0,
failed: 0,
totalItems: 0,
errors: []
};
results.forEach(result => {
if (result.status === 'fulfilled' && result.value.success) {
summary.successful++;
summary.totalItems += result.value.count;
} else {
summary.failed++;
summary.errors.push(result.reason || result.value.error);
}
});
return summary;
}
}
```
## Bulk Order Operations
### Bulk Order Creation
Efficiently create multiple orders:
```javascript theme={null}
class OrderBatchProcessor extends BatchProcessor {
async bulkCreateOrders(ordersData, options = {}) {
return await this.processBatch('create', ordersData, {
...options,
validateInput: this.validateOrderData,
transformInput: this.transformOrderData
});
}
async executeBatchOperation(operation, batch, options) {
switch (operation) {
case 'create':
return await this.batchCreateOrders(batch, options);
case 'update':
return await this.batchUpdateOrders(batch, options);
case 'cancel':
return await this.batchCancelOrders(batch, options);
default:
throw new Error(`Unsupported operation: ${operation}`);
}
}
async batchCreateOrders(orders, options = {}) {
// Validate orders before processing
const validatedOrders = orders.map(order => {
if (options.validateInput) {
return options.validateInput(order);
}
return this.validateOrderData(order);
});
// Transform orders if needed
const transformedOrders = validatedOrders.map(order => {
if (options.transformInput) {
return options.transformInput(order);
}
return this.transformOrderData(order);
});
// Create orders in parallel with concurrency control
const createLimit = pLimit(3); // Limit concurrent creations
const results = await Promise.allSettled(
transformedOrders.map(order =>
createLimit(async () => {
try {
const result = await this.client.orders.create(order);
return { success: true, order: result, originalData: order };
} catch (error) {
return {
success: false,
error: error.message,
originalData: order
};
}
})
)
);
return this.processCreateResults(results);
}
validateOrderData(order) {
const required = ['customer_email', 'items'];
const missing = required.filter(field => !order[field]);
if (missing.length > 0) {
throw new Error(`Missing required fields: ${missing.join(', ')}`);
}
// Validate items
if (!Array.isArray(order.items) || order.items.length === 0) {
throw new Error('Order must have at least one item');
}
order.items.forEach((item, index) => {
if (!item.sku || !item.quantity || !item.price) {
throw new Error(`Item ${index + 1} missing required fields: sku, quantity, or price`);
}
});
return order;
}
transformOrderData(order) {
return {
...order,
// Add default values
status: order.status || 'pending',
source: order.source || 'batch_import',
created_at: order.created_at || new Date().toISOString(),
// Ensure proper data types
items: order.items.map(item => ({
...item,
quantity: parseInt(item.quantity, 10),
price: parseFloat(item.price)
})),
// Add metadata
metadata: {
...order.metadata,
batch_import: true,
import_timestamp: new Date().toISOString()
}
};
}
processCreateResults(results) {
const summary = {
created: [],
failed: [],
total: results.length
};
results.forEach(result => {
if (result.status === 'fulfilled') {
const value = result.value;
if (value.success) {
summary.created.push(value.order);
} else {
summary.failed.push({
error: value.error,
data: value.originalData
});
}
} else {
summary.failed.push({
error: result.reason.message,
data: null
});
}
});
return summary;
}
}
// Usage example
const orderProcessor = new OrderBatchProcessor({ concurrency: 3 });
const sampleOrders = [
{
customer_email: 'customer1@example.com',
items: [
{ sku: 'PRODUCT-001', quantity: 2, price: 29.99 },
{ sku: 'PRODUCT-002', quantity: 1, price: 19.99 }
],
shipping_address: {
street1: '123 Main St',
city: 'Anytown',
state: 'CA',
zip: '12345',
country: 'US'
}
},
// ... more orders
];
async function bulkCreateOrdersExample() {
try {
const result = await orderProcessor.bulkCreateOrders(sampleOrders);
logger.info(`Successfully created ${result.created.length} orders`);
logger.info(`Failed to create ${result.failed.length} orders`);
if (result.failed.length > 0) {
logger.info('Failed orders:', result.failed);
}
} catch (error) {
logger.error('Bulk order creation failed:', error);
}
}
```
### Bulk Order Updates
Update multiple orders efficiently:
```javascript theme={null}
class OrderUpdateProcessor extends OrderBatchProcessor {
async bulkUpdateOrders(updates, options = {}) {
return await this.processBatch('update', updates, options);
}
async batchUpdateOrders(updates, options = {}) {
const updateLimit = pLimit(5); // Higher concurrency for updates
const results = await Promise.allSettled(
updates.map(update =>
updateLimit(async () => {
try {
const { id, data } = update;
const result = await this.client.orders.update(id, data);
return { success: true, order: result, updateData: update };
} catch (error) {
return {
success: false,
error: error.message,
updateData: update
};
}
})
)
);
return this.processUpdateResults(results);
}
processUpdateResults(results) {
const summary = {
updated: [],
failed: [],
total: results.length
};
results.forEach(result => {
if (result.status === 'fulfilled') {
const value = result.value;
if (value.success) {
summary.updated.push(value.order);
} else {
summary.failed.push({
error: value.error,
data: value.updateData
});
}
} else {
summary.failed.push({
error: result.reason.message,
data: null
});
}
});
return summary;
}
// Bulk status updates
async bulkUpdateOrderStatus(orderIds, newStatus, options = {}) {
const updates = orderIds.map(id => ({
id,
data: {
status: newStatus,
updated_at: new Date().toISOString(),
status_history: [{
status: newStatus,
timestamp: new Date().toISOString(),
source: 'batch_update'
}]
}
}));
return await this.bulkUpdateOrders(updates, options);
}
// Bulk tracking number updates
async bulkUpdateTrackingNumbers(trackingUpdates, options = {}) {
const updates = trackingUpdates.map(({ orderId, trackingNumber, carrier }) => ({
id: orderId,
data: {
tracking_number: trackingNumber,
carrier: carrier,
status: 'shipped',
shipped_at: new Date().toISOString()
}
}));
return await this.bulkUpdateOrders(updates, options);
}
}
// Usage examples
const updateProcessor = new OrderUpdateProcessor();
// Bulk status update
await updateProcessor.bulkUpdateOrderStatus(
['ord_123', 'ord_124', 'ord_125'],
'processing'
);
// Bulk tracking number update
await updateProcessor.bulkUpdateTrackingNumbers([
{ orderId: 'ord_123', trackingNumber: 'TRACK123', carrier: 'UPS' },
{ orderId: 'ord_124', trackingNumber: 'TRACK124', carrier: 'FedEx' },
{ orderId: 'ord_125', trackingNumber: 'TRACK125', carrier: 'USPS' }
]);
```
## Bulk Inventory Operations
### Inventory Import and Synchronization
Handle large inventory datasets:
```javascript theme={null}
class InventoryBatchProcessor extends BatchProcessor {
async bulkUpdateInventory(inventoryData, options = {}) {
return await this.processBatch('update', inventoryData, {
...options,
validateInput: this.validateInventoryData,
transformInput: this.transformInventoryData
});
}
async executeBatchOperation(operation, batch, options) {
switch (operation) {
case 'update':
return await this.batchUpdateInventory(batch, options);
case 'sync':
return await this.batchSyncInventory(batch, options);
case 'adjust':
return await this.batchAdjustInventory(batch, options);
default:
throw new Error(`Unsupported inventory operation: ${operation}`);
}
}
async batchUpdateInventory(inventoryItems, options = {}) {
const updateLimit = pLimit(8); // Higher concurrency for inventory
const results = await Promise.allSettled(
inventoryItems.map(item =>
updateLimit(async () => {
try {
const result = await this.client.inventory.update(item.sku, {
quantity: item.quantity,
location: item.location || 'default',
updated_at: new Date().toISOString(),
source: 'batch_update'
});
return { success: true, item: result, originalData: item };
} catch (error) {
return {
success: false,
error: error.message,
originalData: item
};
}
})
)
);
return this.processInventoryResults(results);
}
// Advanced inventory synchronization
async batchSyncInventory(inventoryItems, options = {}) {
const { source = 'external_system' } = options;
// Group by location for efficient processing
const itemsByLocation = _.groupBy(inventoryItems, 'location');
const locationResults = await Promise.allSettled(
Object.entries(itemsByLocation).map(([location, items]) =>
this.syncLocationInventory(location, items, { source })
)
);
return this.compileSyncResults(locationResults);
}
async syncLocationInventory(location, items, options) {
const { source } = options;
// Get current inventory for comparison
const currentInventory = await this.getCurrentInventory(location);
const currentBySku = new Map(
currentInventory.map(item => [item.sku, item])
);
const syncOperations = [];
for (const item of items) {
const current = currentBySku.get(item.sku);
if (!current) {
// New item - create
syncOperations.push({
operation: 'create',
sku: item.sku,
data: {
...item,
location,
source,
created_at: new Date().toISOString()
}
});
} else if (current.quantity !== item.quantity) {
// Existing item with different quantity - update
syncOperations.push({
operation: 'update',
sku: item.sku,
data: {
quantity: item.quantity,
location,
source,
updated_at: new Date().toISOString(),
previous_quantity: current.quantity
}
});
}
// Remove from current map (remaining items will be marked as discontinued)
currentBySku.delete(item.sku);
}
// Handle discontinued items
for (const [sku, current] of currentBySku.entries()) {
if (options.markDiscontinued) {
syncOperations.push({
operation: 'discontinue',
sku,
data: {
quantity: 0,
location,
status: 'discontinued',
discontinued_at: new Date().toISOString(),
source
}
});
}
}
// Execute sync operations
return await this.executeSyncOperations(syncOperations);
}
async executeSyncOperations(operations) {
const operationLimit = pLimit(6);
const results = await Promise.allSettled(
operations.map(op =>
operationLimit(async () => {
try {
let result;
switch (op.operation) {
case 'create':
result = await this.client.inventory.create(op.data);
break;
case 'update':
result = await this.client.inventory.update(op.sku, op.data);
break;
case 'discontinue':
result = await this.client.inventory.update(op.sku, op.data);
break;
default:
throw new Error(`Unknown operation: ${op.operation}`);
}
return {
success: true,
operation: op.operation,
sku: op.sku,
result
};
} catch (error) {
return {
success: false,
operation: op.operation,
sku: op.sku,
error: error.message
};
}
})
)
);
return this.processSyncResults(results);
}
validateInventoryData(item) {
const required = ['sku', 'quantity'];
const missing = required.filter(field => item[field] === undefined || item[field] === null);
if (missing.length > 0) {
throw new Error(`Missing required fields: ${missing.join(', ')}`);
}
if (typeof item.quantity !== 'number' || item.quantity < 0) {
throw new Error('Quantity must be a non-negative number');
}
return item;
}
transformInventoryData(item) {
return {
...item,
sku: item.sku.toUpperCase().trim(),
quantity: parseInt(item.quantity, 10),
location: item.location || 'default',
updated_at: new Date().toISOString()
};
}
processInventoryResults(results) {
const summary = {
updated: [],
failed: [],
total: results.length
};
results.forEach(result => {
if (result.status === 'fulfilled') {
const value = result.value;
if (value.success) {
summary.updated.push(value.item);
} else {
summary.failed.push({
error: value.error,
data: value.originalData
});
}
} else {
summary.failed.push({
error: result.reason.message,
data: null
});
}
});
return summary;
}
}
// Usage example
const inventoryProcessor = new InventoryBatchProcessor({ concurrency: 8 });
const inventoryUpdates = [
{ sku: 'PRODUCT-001', quantity: 150, location: 'warehouse_1' },
{ sku: 'PRODUCT-002', quantity: 75, location: 'warehouse_1' },
{ sku: 'PRODUCT-003', quantity: 200, location: 'warehouse_2' },
// ... more inventory items
];
await inventoryProcessor.bulkUpdateInventory(inventoryUpdates);
```
## File-Based Batch Operations
### CSV Import Processing
Handle large CSV files efficiently:
```javascript theme={null}
import fs from 'fs';
import csv from 'csv-parser';
import { createReadStream } from 'fs';
class CSVBatchProcessor extends BatchProcessor {
async processCSVFile(filePath, options = {}) {
const {
batchSize = 1000,
skipHeader = true,
transform = null,
validate = null
} = options;
return new Promise((resolve, reject) => {
const results = [];
const errors = [];
let batch = [];
let lineNumber = 0;
createReadStream(filePath)
.pipe(csv())
.on('data', async (row) => {
lineNumber++;
try {
// Apply validation if provided
if (validate) {
validate(row, lineNumber);
}
// Apply transformation if provided
const transformedRow = transform ? transform(row, lineNumber) : row;
batch.push(transformedRow);
// Process batch when it reaches the specified size
if (batch.length >= batchSize) {
const batchResults = await this.processBatch('import', batch);
results.push(batchResults);
batch = [];
}
} catch (error) {
errors.push({
line: lineNumber,
data: row,
error: error.message
});
}
})
.on('end', async () => {
try {
// Process remaining items in the final batch
if (batch.length > 0) {
const batchResults = await this.processBatch('import', batch);
results.push(batchResults);
}
resolve({
totalLines: lineNumber,
totalBatches: results.length,
results,
errors
});
} catch (error) {
reject(error);
}
})
.on('error', reject);
});
}
// Order CSV import
async importOrdersFromCSV(filePath, options = {}) {
return await this.processCSVFile(filePath, {
...options,
validate: this.validateOrderCSVRow,
transform: this.transformOrderCSVRow
});
}
validateOrderCSVRow(row, lineNumber) {
const required = ['customer_email', 'item_sku', 'item_quantity', 'item_price'];
const missing = required.filter(field => !row[field] || row[field].trim() === '');
if (missing.length > 0) {
throw new Error(`Line ${lineNumber}: Missing required fields: ${missing.join(', ')}`);
}
// Validate email format
const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
if (!emailRegex.test(row.customer_email)) {
throw new Error(`Line ${lineNumber}: Invalid email format`);
}
// Validate numeric fields
if (isNaN(parseFloat(row.item_price)) || parseFloat(row.item_price) <= 0) {
throw new Error(`Line ${lineNumber}: Invalid item price`);
}
if (isNaN(parseInt(row.item_quantity)) || parseInt(row.item_quantity) <= 0) {
throw new Error(`Line ${lineNumber}: Invalid item quantity`);
}
}
transformOrderCSVRow(row, lineNumber) {
return {
customer_email: row.customer_email.trim().toLowerCase(),
customer_name: row.customer_name?.trim() || '',
items: [{
sku: row.item_sku.trim().toUpperCase(),
quantity: parseInt(row.item_quantity, 10),
price: parseFloat(row.item_price),
name: row.item_name?.trim() || ''
}],
shipping_address: {
street1: row.shipping_street1?.trim() || '',
street2: row.shipping_street2?.trim() || '',
city: row.shipping_city?.trim() || '',
state: row.shipping_state?.trim() || '',
zip: row.shipping_zip?.trim() || '',
country: row.shipping_country?.trim().toUpperCase() || 'US'
},
source: 'csv_import',
import_line_number: lineNumber,
imported_at: new Date().toISOString()
};
}
// Generate import report
generateImportReport(results, outputPath) {
const report = {
summary: {
total_lines: results.totalLines,
total_batches: results.totalBatches,
successful_imports: 0,
failed_imports: 0,
error_count: results.errors.length
},
batch_details: [],
errors: results.errors
};
results.results.forEach((batch, index) => {
report.summary.successful_imports += batch.successful || 0;
report.summary.failed_imports += batch.failed || 0;
report.batch_details.push({
batch_number: index + 1,
items_processed: batch.totalItems || 0,
successful: batch.successful || 0,
failed: batch.failed || 0,
errors: batch.errors || []
});
});
// Write report to file
fs.writeFileSync(outputPath, JSON.stringify(report, null, 2));
return report;
}
}
// Usage example
const csvProcessor = new CSVBatchProcessor({ concurrency: 3 });
async function importOrdersExample() {
try {
const results = await csvProcessor.importOrdersFromCSV('./orders.csv', {
batchSize: 500
});
logger.info(`Processed ${results.totalLines} lines in ${results.totalBatches} batches`);
logger.info(`Errors: ${results.errors.length}`);
// Generate and save report
const report = csvProcessor.generateImportReport(results, './import-report.json');
logger.info('Import report saved to ./import-report.json');
} catch (error) {
logger.error('CSV import failed:', error);
}
}
```
### Export Operations
Export large datasets efficiently:
```javascript theme={null}
import { createWriteStream } from 'fs';
import fastCsv from 'fast-csv';
class ExportProcessor extends BatchProcessor {
async exportOrdersToCSV(filters = {}, outputPath, options = {}) {
const {
batchSize = 1000,
includeFields = null,
transform = null
} = options;
const writeStream = createWriteStream(outputPath);
const csvStream = fastCsv.format({ headers: true });
csvStream.pipe(writeStream);
let offset = 0;
let hasMore = true;
let totalExported = 0;
try {
while (hasMore) {
logger.info(`Exporting batch starting at offset ${offset}`);
const orders = await this.client.orders.list({
...filters,
limit: batchSize,
offset,
include: ['line_items', 'customer', 'shipping_address']
});
if (orders.orders.length === 0) {
hasMore = false;
break;
}
// Transform orders for CSV export
const transformedOrders = orders.orders.map(order => {
const baseData = {
order_id: order.id,
order_number: order.order_number,
customer_email: order.customer_email,
customer_name: order.customer_name,
status: order.status,
total_amount: order.total_amount,
created_date: order.created_date,
updated_date: order.updated_date
};
// Include line items as separate rows or flatten
if (order.order_line_items && order.order_line_items.length > 0) {
return order.order_line_items.map(item => ({
...baseData,
item_sku: item.sku_name,
item_name: item.product_name,
item_quantity: item.quantity,
item_price: item.sale_price,
item_brand: item.brand
}));
}
return [baseData];
}).flat();
// Apply custom transformation if provided
const finalData = transform ?
transformedOrders.map(transform) :
transformedOrders;
// Filter fields if specified
const filteredData = includeFields ?
finalData.map(row => _.pick(row, includeFields)) :
finalData;
// Write to CSV
for (const row of filteredData) {
csvStream.write(row);
}
totalExported += filteredData.length;
offset += batchSize;
// Check if we have more data
hasMore = orders.orders.length === batchSize;
// Add delay to respect rate limits
await this.delay(100);
}
csvStream.end();
return new Promise((resolve, reject) => {
writeStream.on('finish', () => {
logger.info(`Export completed: ${totalExported} records exported to ${outputPath}`);
resolve({ totalExported, outputPath });
});
writeStream.on('error', reject);
});
} catch (error) {
csvStream.end();
throw error;
}
}
// Export with progress tracking
async exportOrdersWithProgress(filters = {}, outputPath, options = {}) {
const {
onProgress = null,
...exportOptions
} = options;
// Get total count first
const countResponse = await this.client.orders.list({
...filters,
limit: 1
});
const totalOrders = countResponse.total_count;
let processedOrders = 0;
// Wrap the export with progress tracking
const progressTracker = {
onProgress: (batch) => {
processedOrders += batch.length;
const progress = Math.round((processedOrders / totalOrders) * 100);
logger.info(`Export progress: ${processedOrders}/${totalOrders} (${progress}%);`);
if (onProgress) {
onProgress({
processed: processedOrders,
total: totalOrders,
percentage: progress
});
}
}
};
return await this.exportOrdersToCSV(filters, outputPath, {
...exportOptions,
progressTracker
});
}
}
// Usage example
const exportProcessor = new ExportProcessor();
// Export all orders from the last 30 days
const thirtyDaysAgo = new Date(Date.now() - 30 * 24 * 60 * 60 * 1000).toISOString();
await exportProcessor.exportOrdersWithProgress(
{
created_after: thirtyDaysAgo,
status_in: ['processing', 'shipped', 'delivered']
},
'./orders-export.csv',
{
batchSize: 500,
includeFields: [
'order_id', 'order_number', 'customer_email', 'status',
'total_amount', 'created_date', 'item_sku', 'item_quantity'
],
onProgress: (progress) => {
// Update progress bar or send notification
logger.info(`Progress: ${progress.percentage}%`);
}
}
);
```
## Queue-Based Batch Processing
### Background Job Processing
Implement robust background processing with queues:
```javascript theme={null}
import Queue from 'bull';
import Redis from 'ioredis';
class QueuedBatchProcessor extends BatchProcessor {
constructor(options = {}) {
super(options);
this.redis = new Redis(process.env.REDIS_URL);
this.batchQueue = new Queue('batch operations', process.env.REDIS_URL);
this.setupJobProcessors();
this.setupEventHandlers();
}
setupJobProcessors() {
// Process batch creation jobs
this.batchQueue.process('bulk-create-orders', 5, async (job) => {
const { orders, options } = job.data;
job.progress(0);
try {
const result = await this.bulkCreateOrders(orders, {
...options,
onProgress: (progress) => {
job.progress(Math.round((progress.completed / progress.total) * 100));
}
});
job.progress(100);
return result;
} catch (error) {
logger.error('Batch job failed:', error);
throw error;
}
});
// Process batch update jobs
this.batchQueue.process('bulk-update-orders', 3, async (job) => {
const { updates, options } = job.data;
job.progress(0);
const result = await this.bulkUpdateOrders(updates, {
...options,
onProgress: (progress) => {
job.progress(Math.round((progress.completed / progress.total) * 100));
}
});
job.progress(100);
return result;
});
// Process CSV import jobs
this.batchQueue.process('csv-import', 1, async (job) => {
const { filePath, type, options } = job.data;
job.progress(0);
let result;
switch (type) {
case 'orders':
result = await this.importOrdersFromCSV(filePath, {
...options,
onProgress: (progress) => {
job.progress(Math.round((progress.completed / progress.total) * 100));
}
});
break;
case 'inventory':
result = await this.importInventoryFromCSV(filePath, options);
break;
default:
throw new Error(`Unsupported import type: ${type}`);
}
job.progress(100);
return result;
});
}
setupEventHandlers() {
this.batchQueue.on('completed', (job, result) => {
logger.info(`Job ${job.id} completed successfully`);
this.notifyJobCompletion(job, result, 'completed');
});
this.batchQueue.on('failed', (job, err) => {
logger.error(`Job ${job.id} failed:`, err);
this.notifyJobCompletion(job, null, 'failed', err);
});
this.batchQueue.on('progress', (job, progress) => {
logger.info(`Job ${job.id} progress: ${progress}%`);
});
}
async queueBulkCreateOrders(orders, options = {}) {
const job = await this.batchQueue.add('bulk-create-orders', {
orders,
options
}, {
attempts: 3,
backoff: {
type: 'exponential',
delay: 2000
},
removeOnComplete: 10,
removeOnFail: 5
});
return {
jobId: job.id,
status: 'queued'
};
}
async queueCSVImport(filePath, type, options = {}) {
const job = await this.batchQueue.add('csv-import', {
filePath,
type,
options
}, {
attempts: 2,
timeout: 300000, // 5 minutes
removeOnComplete: 5,
removeOnFail: 3
});
return {
jobId: job.id,
status: 'queued'
};
}
async getJobStatus(jobId) {
const job = await this.batchQueue.getJob(jobId);
if (!job) {
return { status: 'not_found' };
}
const state = await job.getState();
const progress = job.progress();
return {
jobId: job.id,
status: state,
progress,
data: job.data,
result: job.returnvalue,
error: job.failedReason,
created: job.timestamp,
processed: job.processedOn,
finished: job.finishedOn
};
}
async notifyJobCompletion(job, result, status, error = null) {
const notification = {
jobId: job.id,
jobType: job.name,
status,
timestamp: new Date().toISOString(),
result,
error: error?.message
};
// Send webhook notification
if (process.env.WEBHOOK_NOTIFICATION_URL) {
try {
await fetch(process.env.WEBHOOK_NOTIFICATION_URL, {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(notification)
});
} catch (webhookError) {
logger.error('Failed to send webhook notification:', webhookError);
}
}
// Store notification in database or send email
// Implementation depends on your notification system
}
}
// Usage example
const queueProcessor = new QueuedBatchProcessor();
// Queue a bulk order creation job
const createJob = await queueProcessor.queueBulkCreateOrders(sampleOrders, {
validateInput: true,
notifyOnCompletion: true
});
logger.info(`Bulk create job queued with ID: ${createJob.jobId}`);
// Check job status
setInterval(async () => {
const status = await queueProcessor.getJobStatus(createJob.jobId);
logger.info(`Job ${createJob.jobId} status:`, status);
if (['completed', 'failed'].includes(status.status)) {
clearInterval(this);
}
}, 5000);
```
## Performance Optimization
### Memory Management and Streaming
Handle very large datasets efficiently:
```javascript theme={null}
class StreamingBatchProcessor extends BatchProcessor {
async streamProcessLargeDataset(dataStream, processor, options = {}) {
const {
batchSize = 1000,
maxMemoryUsage = 512 * 1024 * 1024, // 512MB
gcInterval = 10000 // Force GC every 10k items
} = options;
let batch = [];
let processedCount = 0;
let errorCount = 0;
return new Promise((resolve, reject) => {
dataStream
.on('data', async (item) => {
batch.push(item);
if (batch.length >= batchSize) {
try {
// Pause stream while processing batch
dataStream.pause();
const result = await processor(batch);
processedCount += result.successful || 0;
errorCount += result.failed || 0;
// Clear batch and force garbage collection if needed
batch = [];
if (processedCount % gcInterval === 0) {
this.forceGarbageCollection();
this.checkMemoryUsage(maxMemoryUsage);
}
// Resume stream
dataStream.resume();
} catch (error) {
dataStream.destroy(error);
return;
}
}
})
.on('end', async () => {
try {
// Process final batch
if (batch.length > 0) {
const result = await processor(batch);
processedCount += result.successful || 0;
errorCount += result.failed || 0;
}
resolve({
processed: processedCount,
errors: errorCount,
total: processedCount + errorCount
});
} catch (error) {
reject(error);
}
})
.on('error', reject);
});
}
forceGarbageCollection() {
if (global.gc) {
global.gc();
logger.info('Forced garbage collection');
}
}
checkMemoryUsage(maxUsage) {
const used = process.memoryUsage();
if (used.heapUsed > maxUsage) {
console.warn(`High memory usage detected: ${Math.round(used.heapUsed / 1024 / 1024)}MB`);
if (used.heapUsed > maxUsage * 1.5) {
throw new Error('Memory usage too high, aborting batch processing');
}
}
}
// Optimized batch processing with connection pooling
async optimizedBatchProcess(data, operation, options = {}) {
const {
connectionPoolSize = 10,
maxRetries = 3,
retryDelay = 1000
} = options;
// Create connection pool
const pool = Array.from({ length: connectionPoolSize }, () =>
new StateSetClient({
apiKey: process.env.STATESET_API_KEY,
timeout: 60000,
keepAlive: true
})
);
let poolIndex = 0;
const getClient = () => {
const client = pool[poolIndex % pool.length];
poolIndex++;
return client;
};
try {
const processLimit = pLimit(connectionPoolSize);
const results = await Promise.allSettled(
data.map(item =>
processLimit(async () => {
let attempt = 0;
let lastError;
while (attempt < maxRetries) {
try {
const client = getClient();
const result = await this.executeOperation(client, operation, item);
return { success: true, result, item };
} catch (error) {
lastError = error;
attempt++;
if (attempt < maxRetries) {
await this.delay(retryDelay * Math.pow(2, attempt - 1));
}
}
}
return { success: false, error: lastError.message, item };
})
)
);
return this.compileResults(results);
} finally {
// Clean up connection pool
for (const client of pool) {
if (client.destroy) {
client.destroy();
}
}
}
}
async executeOperation(client, operation, item) {
switch (operation) {
case 'create_order':
return await client.orders.create(item);
case 'update_order':
return await client.orders.update(item.id, item.data);
case 'update_inventory':
return await client.inventory.update(item.sku, item.data);
default:
throw new Error(`Unsupported operation: ${operation}`);
}
}
}
```
## Best Practices and Monitoring
### Comprehensive Monitoring
Monitor batch operation performance:
```javascript theme={null}
class BatchMonitor {
constructor() {
this.metrics = {
totalOperations: 0,
successfulOperations: 0,
failedOperations: 0,
averageProcessingTime: 0,
peakMemoryUsage: 0,
operationHistory: []
};
}
recordOperation(operation, duration, success, memoryUsage) {
this.metrics.totalOperations++;
if (success) {
this.metrics.successfulOperations++;
} else {
this.metrics.failedOperations++;
}
// Update average processing time
const totalTime = this.metrics.averageProcessingTime * (this.metrics.totalOperations - 1) + duration;
this.metrics.averageProcessingTime = totalTime / this.metrics.totalOperations;
// Track peak memory usage
if (memoryUsage > this.metrics.peakMemoryUsage) {
this.metrics.peakMemoryUsage = memoryUsage;
}
// Store operation history (keep last 1000)
this.metrics.operationHistory.push({
operation,
duration,
success,
memoryUsage,
timestamp: new Date().toISOString()
});
if (this.metrics.operationHistory.length > 1000) {
this.metrics.operationHistory.shift();
}
}
getSuccessRate() {
if (this.metrics.totalOperations === 0) return 0;
return (this.metrics.successfulOperations / this.metrics.totalOperations) * 100;
}
generateReport() {
return {
summary: {
total_operations: this.metrics.totalOperations,
successful_operations: this.metrics.successfulOperations,
failed_operations: this.metrics.failedOperations,
success_rate: `${this.getSuccessRate().toFixed(2)}%`,
average_processing_time: `${this.metrics.averageProcessingTime.toFixed(2)}ms`,
peak_memory_usage: `${(this.metrics.peakMemoryUsage / 1024 / 1024).toFixed(2)}MB`
},
recent_operations: this.metrics.operationHistory.slice(-10),
recommendations: this.generateRecommendations()
};
}
generateRecommendations() {
const recommendations = [];
const successRate = this.getSuccessRate();
if (successRate < 95) {
recommendations.push('Consider reducing batch size or improving error handling');
}
if (this.metrics.averageProcessingTime > 30000) {
recommendations.push('Processing time is high, consider optimizing batch operations');
}
if (this.metrics.peakMemoryUsage > 1024 * 1024 * 1024) {
recommendations.push('High memory usage detected, consider streaming or smaller batches');
}
return recommendations;
}
}
// Enhanced batch processor with monitoring
class MonitoredBatchProcessor extends StreamingBatchProcessor {
constructor(options = {}) {
super(options);
this.monitor = new BatchMonitor();
}
async processBatch(operation, data, options = {}) {
const startTime = Date.now();
const startMemory = process.memoryUsage().heapUsed;
try {
const result = await super.processBatch(operation, data, options);
const duration = Date.now() - startTime;
const endMemory = process.memoryUsage().heapUsed;
this.monitor.recordOperation(operation, duration, true, endMemory);
return {
...result,
processingTime: duration,
memoryUsed: endMemory - startMemory
};
} catch (error) {
const duration = Date.now() - startTime;
const endMemory = process.memoryUsage().heapUsed;
this.monitor.recordOperation(operation, duration, false, endMemory);
throw error;
}
}
getMonitoringReport() {
return this.monitor.generateReport();
}
}
```
## Troubleshooting
* Use streaming for large datasets
* Implement proper garbage collection
* Monitor memory usage and set limits
* Process data in smaller batches
* Implement proper retry logic with exponential backoff
* Use connection pooling
* Monitor API rate limits
* Distribute load across multiple time periods
* Implement comprehensive validation
* Use transformation functions
* Handle edge cases and malformed data
* Provide detailed error reporting
* Optimize batch sizes for your use case
* Use appropriate concurrency limits
* Implement caching where possible
* Monitor and profile operations
## Next Steps
Test your batch operations thoroughly
Set up comprehensive monitoring
Optimize batch processing performance
Learn integration best practices
## Conclusion
Efficient batch processing is crucial for handling large volumes of data in production systems. This guide provides comprehensive patterns for:
* ✅ Bulk order and inventory operations
* ✅ CSV import/export processing
* ✅ Queue-based background processing
* ✅ Memory-efficient streaming operations
* ✅ Performance monitoring and optimization
With these patterns, you can build robust, scalable batch processing systems that handle high-volume operations efficiently while maintaining data integrity and system performance.
# CCTP Module Integration Guide
Source: https://docs.stateset.com/guides/cctp-module-integration
Complete guide to integrating with StateSet's native CCTP module for cross-chain USDC transfers
# CCTP Module Integration Guide
## Overview
This guide covers integrating with StateSet's native CCTP module implementation. Unlike EVM chains where CCTP is implemented via smart contracts, StateSet has built CCTP directly into the blockchain as a Cosmos SDK module, providing superior performance, security, and integration capabilities.
## Architecture Overview
```mermaid theme={null}
graph TB
A[Your Application] --> B[StateSet CCTP Module]
B --> C[Message Handler]
B --> D[Attestation Manager]
B --> E[Burn/Mint Engine]
C --> F[Other Chains via IBC/CCTP]
D --> G[Circle Attestation Service]
E --> H[StateSet Bank Module]
B --> I[Orders Module]
B --> J[Finance Module]
B --> K[Agent Module]
```
## Setting Up Your Development Environment
### 1. Install StateSet CLI
```bash theme={null}
# Download and install the StateSet CLI
curl -L https://get.StateSet.network | bash
# Verify installation
StateSet version
# Output: v1.0.0
# Configure for testnet
StateSet config chain-id StateSet-testnet-1
StateSet config node https://rpc-test.StateSet.network:443
```
### 2. Create Test Accounts
```bash theme={null}
# Create a new account
StateSet keys add testaccount
# Get testnet USDC from faucet
curl -X POST https://faucet-test.StateSet.network/credit \
-H "Content-Type: application/json" \
-d '{"address": "StateSet1...", "coins": ["1000000usdc"]}'
```
### 3. Install SDKs
```bash theme={null}
# JavaScript/TypeScript
npm install @StateSet/cctp-sdk @StateSet/client
# Go
go get github.com/StateSet/StateSet/x/cctp
# Python
pip install StateSet-cctp
```
## Basic Integration
### JavaScript/TypeScript
```typescript theme={null}
import { StateSetClient } from '@StateSet/client';
import { CCTPModule } from '@StateSet/cctp-sdk';
// Initialize client
const client = await StateSetClient.connect('https://rpc.StateSet.network');
const cctp = new CCTPModule(client);
// Set up signer
const signer = await client.getSigner('your-mnemonic-or-private-key');
// Example: Burn USDC to transfer to Ethereum
async function transferToEthereum() {
const burnMsg = {
from: signer.address,
amount: {
denom: 'usdc',
amount: '1000000000' // 1000 USDC (6 decimals)
},
destinationDomain: 0, // Ethereum
mintRecipient: ethers.utils.hexZeroPad('0x742d35...', 32),
burnToken: 'usdc'
};
// Execute burn
const tx = await cctp.depositForBurn(burnMsg);
logger.info('Burn tx hash:', tx.transactionHash);
logger.info('Message hash:', tx.messageHash);
// Wait for attestation from Circle
const attestation = await cctp.waitForAttestation(tx.messageHash);
logger.info('Attestation received:', attestation);
// The attestation can now be used on Ethereum to mint the USDC
return { message: tx.message, attestation };
}
```
### Go Integration
```go theme={null}
package main
import (
"context"
"fmt"
"github.com/cosmos/cosmos-sdk/client"
"github.com/StateSet/StateSet/x/cctp/types"
"github.com/StateSet/StateSet/x/cctp/client/cli"
)
func TransferUSDC(ctx context.Context, clientCtx client.Context) error {
// Create deposit for burn message
msg := &types.MsgDepositForBurn{
From: clientCtx.GetFromAddress().String(),
Amount: sdk.NewCoin("usdc", sdk.NewInt(1000000000)),
DestinationDomain: 0, // Ethereum
MintRecipient: hexutil.MustDecode("0x742d35Cc6634C0532925a3b844Bc9e7595f6E321"),
BurnToken: "usdc",
}
// Validate message
if err := msg.ValidateBasic(); err != nil {
return fmt.Errorf("invalid message: %w", err)
}
// Broadcast transaction
res, err := cli.BroadcastTx(clientCtx, msg)
if err != nil {
return fmt.Errorf("broadcast failed: %w", err)
}
// Extract message hash from events
messageHash := ExtractMessageHash(res.Events)
fmt.Printf("Message hash: %s\n", messageHash)
return nil
}
```
### Python Integration
```python theme={null}
from StateSet_cctp import CCTPClient, DepositForBurnMsg
from StateSet_cctp.attestation import AttestationService
# Initialize client
client = CCTPClient(
rpc_endpoint="https://rpc.StateSet.network",
private_key="your-private-key"
)
# Transfer USDC to Arbitrum
async def transfer_to_arbitrum():
# Create burn message
msg = DepositForBurnMsg(
from_address=client.address,
amount={"denom": "usdc", "amount": "500000000"}, # 500 USDC
destination_domain=3, # Arbitrum
mint_recipient=format_evm_address("0x742d35..."),
burn_token="usdc"
)
# Execute burn
result = await client.deposit_for_burn(msg)
print(f"Transaction hash: {result.tx_hash}")
print(f"Message hash: {result.message_hash}")
# Get attestation
attestation_service = AttestationService()
attestation = await attestation_service.get_attestation(
result.message_hash
)
return {
"message": result.message,
"attestation": attestation
}
```
## Advanced Integration Patterns
### 1. Cross-Chain Order Processing
```typescript theme={null}
// Process orders with payment on any supported chain
class CrossChainOrderProcessor {
constructor(
private cctp: CCTPModule,
private orderModule: OrderModule
) {}
async processOrderWithCrossChainPayment(
orderId: string,
paymentChain: number,
paymentTx: string
) {
// Verify payment on source chain
const payment = await this.verifyPayment(paymentChain, paymentTx);
if (paymentChain !== STATESET_DOMAIN) {
// Wait for CCTP transfer to complete
const cctpTransfer = await this.waitForCCTPTransfer(
payment.messageHash
);
// Update order with payment
await this.orderModule.updatePayment({
orderId,
paymentInfo: {
type: 'cross_chain_usdc',
sourceChain: paymentChain,
amount: cctpTransfer.amount,
transactionHash: cctpTransfer.txHash
}
});
}
// Fulfill order
await this.orderModule.fulfillOrder(orderId);
}
private async waitForCCTPTransfer(messageHash: string) {
// Monitor for receive message transaction
return new Promise((resolve) => {
const subscription = this.cctp.subscribeToEvents({
messageHash
}).subscribe(event => {
if (event.type === 'mint_and_withdraw') {
subscription.unsubscribe();
resolve(event);
}
});
});
}
}
```
### 2. Multi-Signature CCTP Operations
```typescript theme={null}
// Require multiple signatures for large CCTP transfers
class MultiSigCCTP {
constructor(
private cctp: CCTPModule,
private multisig: MultisigModule
) {}
async proposeTransfer(params: CCTPTransferParams) {
// Create multisig proposal
const proposal = await this.multisig.createProposal({
messages: [{
type: 'cctp/MsgDepositForBurn',
value: {
from: this.multisig.address,
amount: params.amount,
destinationDomain: params.destinationDomain,
mintRecipient: params.recipient,
burnToken: 'usdc'
}
}],
metadata: {
title: `CCTP Transfer ${params.amount.amount} USDC to chain ${params.destinationDomain}`,
description: params.description
}
});
return proposal.id;
}
async executeTransfer(proposalId: string) {
// Check if proposal is approved
const proposal = await this.multisig.getProposal(proposalId);
if (!proposal.isApproved()) {
throw new Error('Proposal not approved');
}
// Execute the transfer
return await this.multisig.executeProposal(proposalId);
}
}
```
### 3. Automated Cross-Chain Treasury Management
```typescript theme={null}
// Automatically rebalance treasury across chains
class TreasuryManager {
private readonly TARGET_BALANCE = 100000; // $100k USDC per chain
private readonly REBALANCE_THRESHOLD = 0.2; // 20% deviation
async rebalanceAllChains() {
const balances = await this.getAllChainBalances();
const transfers = this.calculateOptimalTransfers(balances);
// Execute transfers in parallel where possible
const transferPromises = transfers.map(transfer =>
this.executeCCTPTransfer(transfer)
);
const results = await Promise.allSettled(transferPromises);
// Log results
results.forEach((result, index) => {
if (result.status === 'fulfilled') {
logger.info(`Transfer ${index} completed:`, result.value);
} else {
logger.error(`Transfer ${index} failed:`, result.reason);
}
});
}
private calculateOptimalTransfers(balances: ChainBalance[]): Transfer[] {
const totalBalance = balances.reduce((sum, b) => sum + b.amount, 0);
const targetPerChain = totalBalance / balances.length;
const transfers: Transfer[] = [];
const surplus = balances.filter(b => b.amount > targetPerChain * (1 + this.REBALANCE_THRESHOLD));
const deficit = balances.filter(b => b.amount < targetPerChain * (1 - this.REBALANCE_THRESHOLD));
// Match surplus with deficit chains
for (const source of surplus) {
for (const dest of deficit) {
const transferAmount = Math.min(
source.amount - targetPerChain,
targetPerChain - dest.amount
);
if (transferAmount > 1000) { // Min $1k transfer
transfers.push({
sourceChain: source.domain,
destChain: dest.domain,
amount: transferAmount
});
source.amount -= transferAmount;
dest.amount += transferAmount;
}
}
}
return transfers;
}
}
```
### 4. CCTP Rate Limiting and Compliance
```typescript theme={null}
// Implement rate limiting and compliance checks
class ComplianceCCTP {
private dailyLimits = new Map();
private readonly MAX_DAILY_LIMIT = 1000000; // $1M USDC
async transferWithCompliance(params: CCTPTransferParams) {
// Check daily limits
const dailyTotal = await this.getDailyTotal(params.from);
if (dailyTotal + parseInt(params.amount.amount) > this.MAX_DAILY_LIMIT) {
throw new Error('Daily transfer limit exceeded');
}
// Compliance checks
if (await this.isBlacklisted(params.mintRecipient)) {
throw new Error('Recipient address is blacklisted');
}
// Check destination chain restrictions
if (!await this.isDestinationAllowed(params.from, params.destinationDomain)) {
throw new Error('Transfers to this destination not allowed');
}
// Execute transfer with monitoring
const result = await this.cctp.depositForBurn(params);
// Record for compliance
await this.recordTransfer({
from: params.from,
amount: params.amount,
destination: params.destinationDomain,
recipient: params.mintRecipient,
timestamp: Date.now(),
messageHash: result.messageHash
});
return result;
}
}
```
## Module Queries
### CLI Queries
```bash theme={null}
# Query module configuration
StateSet query cctp owner
StateSet query cctp signature-threshold
StateSet query cctp max-message-body-size
# Query attesters
StateSet query cctp attesters
StateSet query cctp attester StateSet1attester...
# Query token pairs
StateSet query cctp token-pairs
StateSet query cctp token-pair 0 0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48
# Query burn limits
StateSet query cctp per-message-burn-limit usdc
# Query paused state
StateSet query cctp burning-minting-paused
StateSet query cctp sending-receiving-paused
```
### SDK Queries
```typescript theme={null}
// Query module state
const owner = await cctp.query.owner();
const threshold = await cctp.query.signatureThreshold();
const attesters = await cctp.query.attesters();
// Query specific token pair
const tokenPair = await cctp.query.tokenPair({
remoteDomain: 0,
remoteToken: '0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48'
});
// Query burn limits
const burnLimit = await cctp.query.perMessageBurnLimit({
token: 'usdc'
});
```
## Event Monitoring
### Subscribe to CCTP Events
```typescript theme={null}
// Monitor all CCTP events
const subscription = cctp.subscribeToEvents()
.subscribe(event => {
switch(event.type) {
case 'deposit_for_burn':
logger.info('Burn initiated:', event);
trackBurn(event);
break;
case 'message_sent':
logger.info('Message sent:', event);
break;
case 'message_received':
logger.info('Message received:', event);
trackReceive(event);
break;
case 'mint_and_withdraw':
logger.info('USDC minted:', event);
completeTrasfer(event);
break;
}
});
// Monitor specific message
const messageSubscription = cctp.subscribeToMessage(messageHash)
.subscribe(update => {
logger.info('Message status:', update.status);
if (update.status === 'completed') {
messageSubscription.unsubscribe();
}
});
```
### Webhook Integration
```typescript theme={null}
// Set up webhooks for CCTP events
app.post('/webhooks/cctp', async (req, res) => {
const event = req.body;
// Verify webhook signature
if (!verifyWebhookSignature(req)) {
return res.status(401).send('Invalid signature');
}
// Process event
switch(event.type) {
case 'cctp.deposit_for_burn':
await handleBurnEvent(event);
break;
case 'cctp.mint_and_withdraw':
await handleMintEvent(event);
break;
case 'cctp.message_received':
await handleMessageReceived(event);
break;
}
res.status(200).send('OK');
});
```
## Testing
### Unit Tests
```typescript theme={null}
import { MockCCTPModule } from '@StateSet/cctp-sdk/testing';
describe('CCTP Integration', () => {
let cctp: MockCCTPModule;
beforeEach(() => {
cctp = new MockCCTPModule();
});
it('should burn USDC for cross-chain transfer', async () => {
const burnMsg = {
from: 'StateSet1test...',
amount: { denom: 'usdc', amount: '1000000' },
destinationDomain: 0,
mintRecipient: '0x742d35...',
burnToken: 'usdc'
};
const result = await cctp.depositForBurn(burnMsg);
expect(result.transactionHash).toBeDefined();
expect(result.messageHash).toBeDefined();
expect(result.nonce).toBeGreaterThan(0);
});
});
```
### Integration Tests
```typescript theme={null}
// Test full cross-chain flow
describe('Cross-chain USDC Transfer', () => {
it('should complete transfer from StateSet to Ethereum', async () => {
// 1. Burn on StateSet
const burnResult = await StateSetCCTP.depositForBurn({
amount: { denom: 'usdc', amount: '1000000000' },
destinationDomain: 0,
mintRecipient: ethRecipient,
burnToken: 'usdc'
});
// 2. Wait for attestation
const attestation = await waitForAttestation(burnResult.messageHash);
expect(attestation).toBeDefined();
// 3. Mint on Ethereum
const mintTx = await ethereumCCTP.receiveMessage(
burnResult.message,
attestation
);
// 4. Verify balance
const balance = await ethereumUSDC.balanceOf(ethRecipient);
expect(balance.toString()).toBe('1000000000');
});
});
```
## Error Handling
### Common Errors and Solutions
```typescript theme={null}
class CCTPErrorHandler {
async handleCCTPOperation(operation: () => Promise) {
try {
return await operation();
} catch (error) {
if (error.code === 'INSUFFICIENT_FUNDS') {
throw new Error('Insufficient USDC balance for transfer');
}
if (error.code === 'INVALID_RECIPIENT') {
throw new Error('Recipient address format is invalid');
}
if (error.code === 'PAUSED') {
throw new Error('CCTP operations are currently paused');
}
if (error.code === 'BURN_LIMIT_EXCEEDED') {
throw new Error('Transfer amount exceeds per-message burn limit');
}
if (error.code === 'NONCE_ALREADY_USED') {
throw new Error('This message has already been processed');
}
// Unknown error
logger.error('CCTP operation failed:', error);
throw error;
}
}
}
```
## Performance Optimization
### 1. Batch Processing
```typescript theme={null}
// Process multiple transfers efficiently
class BatchCCTPProcessor {
async processBatch(transfers: Transfer[]) {
// Group by destination domain
const grouped = this.groupByDomain(transfers);
// Process each group in parallel
const results = await Promise.all(
Object.entries(grouped).map(([domain, transfers]) =>
this.processGroup(parseInt(domain), transfers)
)
);
return results.flat();
}
private async processGroup(domain: number, transfers: Transfer[]) {
// For same destination, can optimize with batching
if (transfers.length > 10) {
return this.processBatchMessage(domain, transfers);
}
// Otherwise process individually in parallel
return Promise.all(transfers.map(t => this.processSingle(t)));
}
}
```
### 2. Caching and Memoization
```typescript theme={null}
// Cache attestations and frequently used data
class CachedCCTP {
private attestationCache = new Map();
private tokenPairCache = new Map();
async getAttestation(messageHash: string): Promise {
// Check cache first
if (this.attestationCache.has(messageHash)) {
return this.attestationCache.get(messageHash)!;
}
// Fetch from service
const attestation = await this.attestationService.get(messageHash);
// Cache for future use
this.attestationCache.set(messageHash, attestation);
return attestation;
}
}
```
## Security Best Practices
### 1. Input Validation
```typescript theme={null}
function validateCCTPTransfer(params: CCTPTransferParams) {
// Validate amount
const amount = parseInt(params.amount.amount);
if (isNaN(amount) || amount <= 0) {
throw new Error('Invalid amount');
}
// Validate destination domain
if (!SUPPORTED_DOMAINS.includes(params.destinationDomain)) {
throw new Error('Unsupported destination domain');
}
// Validate recipient address format
if (!isValidAddressFormat(params.mintRecipient, params.destinationDomain)) {
throw new Error('Invalid recipient address format');
}
// Validate sender has sufficient balance
if (!hasSufficientBalance(params.from, amount)) {
throw new Error('Insufficient balance');
}
}
```
### 2. Rate Limiting
```typescript theme={null}
// Implement rate limiting for CCTP operations
class RateLimitedCCTP {
private limits = new Map();
async checkRateLimit(address: string, amount: number) {
const limit = this.limits.get(address) || this.createLimit(address);
// Check per-transaction limit
if (amount > limit.maxPerTransaction) {
throw new Error('Transaction exceeds maximum allowed amount');
}
// Check hourly limit
const hourlyTotal = await this.getHourlyTotal(address);
if (hourlyTotal + amount > limit.maxPerHour) {
throw new Error('Hourly transfer limit exceeded');
}
// Check daily limit
const dailyTotal = await this.getDailyTotal(address);
if (dailyTotal + amount > limit.maxPerDay) {
throw new Error('Daily transfer limit exceeded');
}
}
}
```
## Migration from Other CCTP Implementations
### From Noble to StateSet
```typescript theme={null}
// Update your integration to use StateSet's native module
class CCTPMigration {
// Old Noble integration
async oldTransfer() {
await nobleClient.execute(
nobleContract,
{ deposit_for_burn: { ... } }
);
}
// New StateSet integration
async newTransfer() {
await StateSetCCTP.depositForBurn({
from: signer.address,
amount: { denom: 'usdc', amount: '1000000' },
destinationDomain: 0,
mintRecipient: recipient,
burnToken: 'usdc'
});
}
}
```
## Resources
* [StateSet CCTP Module Source](https://github.com/StateSet/StateSet/tree/main/x/cctp)
* [CCTP SDK Documentation](https://docs.StateSet.network/sdks/cctp)
* [Example Applications](https://github.com/StateSet/cctp-examples)
* [Circle CCTP Docs](https://developers.circle.com/cctp)
## Support
For integration support:
* Discord: [#cctp-dev](https://discord.gg/VfcaqgZywq)
* GitHub Issues: [github.com/StateSet/cctp-module/issues](https://github.com/StateSet/cctp-module/issues)
* Email: [developers@StateSet.com](mailto:developers@StateSet.com)
# COGS
Source: https://docs.stateset.com/guides/cogs-quickstart
Implement accurate Cost of Goods Sold (COGS) calculations using the StateSet API.
# Cost of Goods Sold (COGS) Calculation with StateSet API
This guide provides comprehensive instructions for calculating the Cost of Goods Sold (COGS) using the StateSet API. Designed for manufacturers and businesses managing inventory, this document details how to leverage StateSet to track inventory value, production costs, and ultimately determine COGS for improved profitability analysis and cost control.
By following this guide, you will learn to integrate StateSet for managing inventory lifecycles, tracking costs associated with production, implementing standard COGS calculation methodologies, and recording COGS entries directly via the API.
**Note:** This guide emphasizes a perpetual inventory system (real-time tracking of inventory and costs), which StateSet supports through inventory movements. For periodic systems, adjust reporting accordingly.
## Table of Contents
1. [Introduction](#introduction)
2. [Prerequisites](#prerequisites)
3. [Getting Started: SDK Setup](#getting-started-sdk-setup)
4. [Core Concepts: COGS, COGM, and Inventory Flow](#core-concepts-cogs-cogm-and-inventory-flow)
5. [API Workflow: Tracking Costs for COGS Calculation](#api-workflow-tracking-costs-for-cogs-calculation)
* [Step 1: Recording Purchase Costs](#step-1-recording-purchase-costs)
* [Step 2: Tracking Production Costs (Work Orders & BOMs)](#step-2-tracking-production-costs-work-orders--boms)
* [Step 3: Calculating Cost of Goods Manufactured (COGM)](#step-3-calculating-cost-of-goods-manufactured-cogm)
* [Step 4: Calculating COGS Using Inventory Data](#step-4-calculating-cogs-using-inventory-data)
* [Step 5: Recording COGS Entries](#step-5-recording-cogs-entries)
* [Step 6: Periodic COGS Reporting](#step-6-periodic-cogs-reporting)
6. [Costing Methodologies](#costing-methodologies)
7. [Advanced COGS Considerations](#advanced-cogs-considerations)
8. [Error Handling Best Practices](#error-handling-best-practices)
9. [Troubleshooting Common Issues](#troubleshooting-common-issues)
10. [Support Resources](#support-resources)
11. [Conclusion](#conclusion)
***
## Introduction
Cost of Goods Sold (COGS) represents the direct costs incurred in producing goods sold by a company. Accurate COGS calculation is fundamental for assessing gross profit, managing operational expenses, and making strategic business decisions. This guide demonstrates how the StateSet API facilitates precise COGS tracking by managing purchase orders, inventory movements, work orders, and associated costs.
**Key Distinction: COGM vs. COGS**
* **Cost of Goods Manufactured (COGM):** The total cost of producing finished goods during a period, including direct materials, direct labor, and manufacturing overhead (MOH), adjusted for changes in Work-in-Progress (WIP) inventory.
* **Cost of Goods Sold (COGS):** The cost of finished goods that were actually sold during the period. In a manufacturing context, COGS = Beginning Finished Goods Inventory + COGM - Ending Finished Goods Inventory.
StateSet helps track these by recording costed inventory movements throughout the lifecycle.
**What You'll Achieve:**
* Configure the StateSet Node.js SDK for API interaction.
* Understand the relationship between COGS, COGM, inventory valuation, and production processes.
* Utilize the StateSet API to record costs from purchasing through production and sales.
* Implement logic to calculate COGM and COGS using tracked data.
* Record COGS entries directly via the API.
* Generate periodic COGS reports for analysis.
* Apply best practices for error handling and data integrity.
***
## Prerequisites
* Node.js (version 16 or higher recommended).
* An active StateSet account and API key.
* Basic understanding of JavaScript (`async`/`await`) and REST APIs.
* Familiarity with manufacturing concepts (Purchase Orders, Work Orders, BOMs, Inventory).
* Understanding of accounting principles (e.g., GAAP/IFRS) for COGS methods.
***
## Getting Started: SDK Setup
Begin by integrating the StateSet SDK into your application environment.
### 1. Install the StateSet Node.js SDK
Use npm or yarn to add the SDK package to your project.
```bash theme={null}
npm install @stateset/embedded
```
***
## Core Concepts: COGS, COGM, and Inventory Flow
Understanding these core concepts is essential for implementing COGS calculations effectively.
**What is COGS?**
COGS includes all direct costs associated with producing goods that a company sells. For manufacturers, this encompasses raw materials, direct labor, and manufacturing overhead directly tied to production. It excludes indirect costs like sales, marketing, or general administrative expenses.
**What is COGM?**
COGM calculates the cost of goods completed and transferred to finished goods inventory: Direct Materials Used + Direct Labor + MOH + Beginning WIP - Ending WIP.
**COGS Formula (Periodic System):**
COGS = Beginning Finished Goods Inventory Value + COGM - Ending Finished Goods Inventory Value.
In a perpetual system (recommended with StateSet), COGS is the sum of costs assigned to inventory outflows (sales/shipments) during the period.
**The Role of Inventory:**
Inventory is central to COGS. The flow of costs through inventory directly impacts the final COGS value. StateSet helps track inventory quantity and value as it moves through different stages:
```mermaid theme={null}
graph LR
A[Purchase Order (Record Initial Cost)] --> B(Raw Materials Inventory (Value Increased));
B -- Consumption --> C{Work Order / BOM (Allocate Costs, Add Labor/MOH)};
C --> D[Work in Progress (WIP) Inventory (Value Transformed)];
D -- Completion --> E[Finished Goods Inventory (Value Finalized as COGM)];
E -- Sale/Shipment --> F{Sales Transaction (Recognize COGS)};
```
* **Purchase Order (PO):** Captures the initial cost of raw materials, increasing raw material inventory value.
* **Work Order (WO) / Bill of Materials (BOM):** Defines the components (raw materials, sub-assemblies) and potentially labor/overhead needed. Consuming components transfers their cost from Raw Materials to Work-in-Progress (WIP).
* **Work-in-Progress (WIP):** Represents the value of partially completed goods. Track labor and overhead here if possible (e.g., via custom fields on WOs).
* **Finished Goods:** Upon WO completion, the total cost accumulated in WIP transfers to Finished Goods inventory (this is COGM).
* **Sale:** When a finished good is sold/shipped, its cost is removed from inventory and recognized as COGS on the income statement.
**Costing Methods:**
The method used to value inventory withdrawn affects COGS:
* **Average Cost:** Uses a simple average cost of all identical items in inventory.
* **Weighted Average Cost:** Recalculates average after each purchase, weighting by quantity.
* **FIFO (First-In, First-Out):** Assumes oldest items sold first.
* **LIFO (Last-In, First-Out):** Assumes newest items sold first (permitted under US GAAP but not IFRS; check local regulations as of 2025).
StateSet provides the data foundation (tracking individual inventory receipts/movements with costs) to implement these methods. When creating negative inventory movements (consumptions/sales), assign costs based on your method and record them.
**Perpetual vs. Periodic Inventory:**
* **Perpetual:** Updates inventory and COGS in real-time with each transaction (StateSet supports this via movements).
* **Periodic:** Calculates COGS at period-end using the formula above (use for reporting).
***
## API Workflow: Tracking Costs for COGS Calculation
This section details using the StateSet API to track costs throughout the inventory lifecycle, enabling accurate COGS calculation.
### Step 1: Recording Purchase Costs
Capture the cost of incoming raw materials via Purchase Orders and Inventory updates.
#### A. Create a Purchase Order
Record the details of a purchase, including items, quantities, and unit costs.
```javascript theme={null}
/**
* Creates a Purchase Order in StateSet.
* @param {object} poData - Data for the new Purchase Order.
* @returns {Promise