> ## Documentation Index
> Fetch the complete documentation index at: https://docs.uw.stargate.is/llms.txt
> Use this file to discover all available pages before exploring further.

# Create Operation

> Create a new distributor operation (cash-in or cash-out)

## Endpoint

```
POST /api/v1/distributors/{distributorID}/operations
```

## Authentication

<ParamField header="Authorization" type="string" required>
  Bearer token with your API key. Must have **Perform Operations** permission.
</ParamField>

<ParamField header="Content-Type" type="string" required>
  Must be `application/json`
</ParamField>

## Path Parameters

<ParamField path="distributorID" type="string" required>
  The unique identifier of the distributor. Must match the distributor ID associated with the API key.
</ParamField>

## Request Body

### Cash-In Operation

<ParamField body="operationType" type="string" required>
  Must be `"cash-in"`
</ParamField>

<ParamField body="amount" type="string" required>
  Amount to credit to the destination wallet (e.g., "5000.00")
</ParamField>

<ParamField body="phoneTo" type="string">
  End user's mobile phone number in international format (e.g., "+234 8123456781"). Required when cashing in to an individual wallet. Cannot be used together with `merchantToShortCode`.
</ParamField>

<ParamField body="merchantToShortCode" type="string">
  Merchant's short code number (e.g., "100000"). Required when cashing in to a merchant wallet. Cannot be used together with `phoneTo`.
</ParamField>

<ParamField body="memo" type="string">
  Optional reference note or description for the operation (e.g., "Receipt #1234", "Customer deposit").
</ParamField>

<Note>
  For cash-in operations, you must provide either `phoneTo` (individual wallet) or `merchantToShortCode` (merchant wallet), but not both.
</Note>

### Cash-Out Operation

<ParamField body="operationType" type="string" required>
  Must be `"cash-out-fulfillment"`
</ParamField>

<ParamField body="amount" type="string" required>
  Amount to debit from the user's wallet (e.g., "3000.00")
</ParamField>

<ParamField body="phoneFrom" type="string" required>
  End user's mobile phone number in international format (e.g., "+234 8123456781")
</ParamField>

<ParamField body="cashOutFulfillmentType" type="string" required>
  Type of fulfillment. Currently only `"cash"` is supported.
</ParamField>

<ParamField body="cashOutFulfillmentID" type="string" required>
  Receipt or reference ID for the cash-out transaction
</ParamField>

<ParamField body="memo" type="string">
  Optional reference note or description for the operation.
</ParamField>

## Response

<ResponseField name="operationID" type="string">
  Unique identifier for the created operation
</ResponseField>

<RequestExample>
  ```bash Cash-In (Individual) cURL theme={null}
  curl -X POST "https://api.yourdomain.com/api/v1/distributors/36e48800-22ce-4ea0-b37a-198f7978cd53/operations" \
    -H "Authorization: Bearer uwk_YOUR_API_KEY_HERE" \
    -H "Content-Type: application/json" \
    -d '{
      "operationType": "cash-in",
      "amount": "5000.00",
      "phoneTo": "+234 8123456781",
      "memo": "Cash deposit - Receipt #1234"
    }'
  ```

  ```bash Cash-In (Merchant) cURL theme={null}
  curl -X POST "https://api.yourdomain.com/api/v1/distributors/36e48800-22ce-4ea0-b37a-198f7978cd53/operations" \
    -H "Authorization: Bearer uwk_YOUR_API_KEY_HERE" \
    -H "Content-Type: application/json" \
    -d '{
      "operationType": "cash-in",
      "amount": "25000.00",
      "merchantToShortCode": "100000"
    }'
  ```

  ```bash Cash-Out cURL theme={null}
  curl -X POST "https://api.yourdomain.com/api/v1/distributors/36e48800-22ce-4ea0-b37a-198f7978cd53/operations" \
    -H "Authorization: Bearer uwk_YOUR_API_KEY_HERE" \
    -H "Content-Type: application/json" \
    -d '{
      "operationType": "cash-out-fulfillment",
      "amount": "3000.00",
      "phoneFrom": "+234 8123456781",
      "cashOutFulfillmentType": "cash",
      "cashOutFulfillmentID": "receipt-12345"
    }'
  ```

  ```javascript Cash-In (Individual) Node.js theme={null}
  const axios = require('axios');

  const response = await axios.post(
    'https://api.yourdomain.com/api/v1/distributors/36e48800-22ce-4ea0-b37a-198f7978cd53/operations',
    {
      operationType: 'cash-in',
      amount: '5000.00',
      phoneTo: '+234 8123456781'
    },
    {
      headers: {
        'Authorization': 'Bearer uwk_YOUR_API_KEY_HERE',
        'Content-Type': 'application/json'
      }
    }
  );

  console.log('Operation ID:', response.data.operationID);
  ```

  ```javascript Cash-In (Merchant) Node.js theme={null}
  const axios = require('axios');

  const response = await axios.post(
    'https://api.yourdomain.com/api/v1/distributors/36e48800-22ce-4ea0-b37a-198f7978cd53/operations',
    {
      operationType: 'cash-in',
      amount: '25000.00',
      merchantToShortCode: '100000'
    },
    {
      headers: {
        'Authorization': 'Bearer uwk_YOUR_API_KEY_HERE',
        'Content-Type': 'application/json'
      }
    }
  );

  console.log('Operation ID:', response.data.operationID);
  ```

  ```javascript Cash-Out Node.js theme={null}
  const axios = require('axios');

  const response = await axios.post(
    'https://api.yourdomain.com/api/v1/distributors/36e48800-22ce-4ea0-b37a-198f7978cd53/operations',
    {
      operationType: 'cash-out-fulfillment',
      amount: '3000.00',
      phoneFrom: '+234 8123456781',
      cashOutFulfillmentType: 'cash',
      cashOutFulfillmentID: 'receipt-12345'
    },
    {
      headers: {
        'Authorization': 'Bearer uwk_YOUR_API_KEY_HERE',
        'Content-Type': 'application/json'
      }
    }
  );

  console.log('Operation ID:', response.data.operationID);
  ```
</RequestExample>

<ResponseExample>
  ```json 200 Success theme={null}
  {
    "operationID": "op_8b7c9d3e-4f5a-6b7c-8d9e-0f1a2b3c4d5e"
  }
  ```

  ```json 400 Bad Request - Invalid Amount theme={null}
  {
    "type": "/problems/input-validation-problems",
    "status": 400,
    "title": "There are some validation errors",
    "detail": "Please fix the validation issues and try again",
    "errors": [
      {
        "type": "/problems/input-validation-problems/invalid-field",
        "field": "amount",
        "detail": "Amount must be a valid decimal number"
      }
    ]
  }
  ```

  ```json 403 Forbidden - Insufficient Permission theme={null}
  {
    "type": "/problems/access-forbidden",
    "status": 403,
    "title": "Access Forbidden",
    "detail": "API key does not have Perform Operations permission"
  }
  ```

  ```json 403 Forbidden - Transaction Limit Exceeded theme={null}
  {
    "type": "/problems/transaction-limit-exceeded",
    "status": 403,
    "title": "Transaction Limit Exceeded",
    "detail": "This operation exceeds the maximum transaction amount allowed for this API key"
  }
  ```

  ```json 403 Forbidden - Daily Volume Exceeded theme={null}
  {
    "type": "/problems/daily-volume-exceeded",
    "status": 403,
    "title": "Daily Volume Limit Exceeded",
    "detail": "This operation would exceed the daily volume limit for this API key"
  }
  ```

  ```json 403 Forbidden - Insufficient Balance theme={null}
  {
    "type": "/problems/insufficient-balance",
    "status": 403,
    "title": "Insufficient Balance",
    "detail": "Insufficient balance to complete this operation"
  }
  ```

  ```json 400 Bad Request - Invalid Merchant Code theme={null}
  {
    "type": "/problems/input-validation-problems",
    "status": 400,
    "title": "There are some validation errors",
    "detail": "Please fix the validation issues and try again",
    "errors": [
      {
        "type": "/problems/input-validation-problems/invalid-field",
        "field": "merchantToShortCode",
        "detail": "Merchant with short code 999999 not found"
      }
    ]
  }
  ```

  ```json 400 Bad Request - Conflicting Destination theme={null}
  {
    "type": "/problems/input-validation-problems",
    "status": 400,
    "title": "There are some validation errors",
    "detail": "Please fix the validation issues and try again",
    "errors": [
      {
        "type": "/problems/input-validation-problems/invalid-field",
        "field": "phoneTo",
        "detail": "Provide either phoneTo or merchantToShortCode, not both"
      }
    ]
  }
  ```
</ResponseExample>

## Validation Rules

The API validates the following before creating an operation:

<AccordionGroup>
  <Accordion title="API Key Permissions">
    * Must have **Perform Operations** permission
    * Distributor ID must match the key's associated distributor
  </Accordion>

  <Accordion title="Amount Validation">
    * Must be a valid decimal number
    * Must be greater than 0
    * Cannot exceed API key's max transaction amount (if set)
  </Accordion>

  <Accordion title="Daily Volume Limit">
    * Sum of today's operations + this operation cannot exceed key's daily volume limit (if set)
  </Accordion>

  <Accordion title="Destination Validation">
    * For **individual wallets**: `phoneTo` must be in international format (e.g., +234 8123456781) and belong to a registered user
    * For **merchant wallets**: `merchantToShortCode` must be a valid, existing merchant short code
    * You must provide exactly one of `phoneTo` or `merchantToShortCode` for cash-in operations
  </Accordion>

  <Accordion title="Balance Checks">
    * **Cash-In**: Distributor must have sufficient balance
    * **Cash-Out**: User must have sufficient wallet balance
  </Accordion>
</AccordionGroup>

## Maker-Checker Workflow

<Note>
  Operations created via API follow the maker-checker approval pattern. The operation is created in a **pending** state and requires approval by a checker before execution.
</Note>

After creating an operation:

1. Operation is saved with status **pending**
2. A checker with appropriate permissions must approve it via the web interface
3. Once approved, the operation is executed on the blockchain
4. The operation status changes to **completed** or **failed**

## Related Endpoints

<CardGroup cols={2}>
  <Card title="Get Balance" icon="wallet" href="/api-reference/distributors/get-balance">
    Check distributor balance before creating operations
  </Card>

  <Card title="Get Operations" icon="list" href="/api-reference/distributors/get-operations">
    Query operation history and status
  </Card>
</CardGroup>
