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

# USSD Session Webhook

> Set up an endpoint to receive and respond to USSD session requests

## USSD Session Webhook

The USSD API sends `POST` requests to your configured endpoint for each stage of a USSD session. Your endpoint should parse the payload and return a JSON response that tells the network whether to continue or end the session.

## Overview

The USSD session follows three stages:

1. **Begin**: Starts a new session.
2. **Continue**: Sends user input during an active session.
3. **End**: Closes the session and displays a final response.

<Warning>
  Your endpoint must be reachable and return valid JSON quickly. If the callback fails or times out, the session may terminate for the user.
</Warning>

## Endpoint Setup

Provide a publicly reachable `POST` URL that can:

* Receive JSON payloads for `begin` and `continue` events.
* Return JSON responses in the expected format.
* Handle optional `backend` data when provided by the network/backend.

## Request Format

### Begin Request

```json theme={null}
{
  "backend": {
    "cuap": {
      "body": {
        "code_scheme": 15,
        "msisdn": "2348099999999",
        "service_code": "*123",
        "ussd_content": "1",
        "ussd_op_type": 3,
        "ussd_version": 32
      },
      "header": {
        "command_id": 112,
        "command_length": 66,
        "command_status": 0,
        "receiver_id": 6904,
        "sender_id": 135477
      }
    }
  },
  "id": {
    "session": "",
    "ussd": "2417796521717513624645694627"
  },
  "msisdn": "2348099999999",
  "network": "9mobile",
  "session": {
    "type": {
      "code": 2,
      "name": "begin"
    },
    "ui": {
      "code": 1,
      "name": "input"
    }
  },
  "shortcode": "123",
  "status": {
    "code": 200,
    "message": "OK"
  },
  "text": "*123#"
}
```

### Continue Request

```json theme={null}
{
  "backend": {
    "cuap": {
      "header": {
        "command_id": 112,
        "command_len": 172,
        "receiver_id": "135477",
        "sender_id": "135477"
      }
    }
  },
  "msisdn": "2348099999999",
  "network": "9mobile",
  "op_type": 1,
  "session": {
    "type": {
      "code": 3,
      "name": "continue"
    },
    "ui": {
      "code": 1,
      "name": "input"
    }
  },
  "shortcode": "123",
  "status": {
    "code": 200,
    "message": "OK"
  },
  "text": "1"
}
```

## Response Format

### Continue Response (Prompt User for More Input)

Use this response when you want the session to remain active.

```json theme={null}
{
  "backend": {
    "cuap": {
      "header": {
        "command_id": 112,
        "command_len": 172,
        "receiver_id": "135477",
        "sender_id": "135477"
      }
    }
  },
  "msisdn": "2348099999999",
  "network": "9mobile",
  "op_type": 1,
  "session": {
    "type": {
      "code": 3,
      "name": "continue"
    },
    "ui": {
      "code": 1,
      "name": "input"
    }
  },
  "shortcode": "123",
  "text": "Select an option:\n1. Balance\n2. Buy Airtime"
}
```

### End Response (Close Session)

Use this response when the interaction is complete.

```json theme={null}
{
  "backend": {
    "cuap": {
      "header": {
        "command_id": 113,
        "command_len": 60,
        "receiver_id": "135477",
        "sender_id": "135477"
      }
    }
  },
  "msisdn": "2348099441402",
  "network": "9mobile",
  "op_type": 2,
  "session": {
    "type": {
      "code": 4,
      "name": "end"
    },
    "ui": {
      "code": 2,
      "name": "dialog"
    }
  },
  "shortcode": "123",
  "text": "Thank you for using our service."
}
```

## Field Descriptions

### Common Fields

<ParamField body="msisdn" type="string" required>
  Subscriber phone number (for example, `2348099999999`).
</ParamField>

<ParamField body="network" type="string" required>
  Mobile network name. Expected values include `9mobile`, `mtn`, `glo`, and `airtel`.
</ParamField>

<ParamField body="shortcode" type="string" required>
  USSD shortcode used for the session (for example, `123`).
</ParamField>

<ParamField body="text" type="string" required>
  Current USSD input/message content.
</ParamField>

### Session Fields

<ParamField body="session.type.code" type="number" required>
  Session stage code (`2` = begin, `3` = continue, `4` = end).
</ParamField>

<ParamField body="session.type.name" type="string" required>
  Session stage name (`begin`, `continue`, `end`).
</ParamField>

<ParamField body="session.ui.code" type="number">
  UI mode code (`0` = none, `1` = input, `2` = dialog).
</ParamField>

<ParamField body="session.ui.name" type="string">
  UI mode name (`none`, `input`, `dialog`).
</ParamField>

### Optional Backend Fields

<ParamField body="backend" type="object">
  Optional backend payload. This may vary by telco/network integration and can be omitted in responses.
</ParamField>

<ParamField body="backend.cuap.body" type="object">
  USSD backend body information.
</ParamField>

<ParamField body="backend.cuap.header" type="object">
  USSD backend header information.
</ParamField>

### Status Fields

<ParamField body="status.code" type="number">
  Request status code (for example, `200`).
</ParamField>

<ParamField body="status.message" type="string">
  Request status message (for example, `OK`).
</ParamField>

## Best Practices

* Return only valid JSON in the expected shape.
* Keep responses short and fast to avoid session timeout.
* Treat `backend` as optional and parse defensively.
* Log `msisdn`, `session.type`, and `text` for troubleshooting.
