Skip to main content

Flow Client API

Authentication

The Flow Client API allows authorized clients to interact with the platform. Authentication uses Signed JWT Assertions (RS256), which provides high security without ever sharing your Private Key with our servers.

Obtaining Your Credentials

To obtain your Client ID and Private Key, you must first configure a Webhook URL on the Flow Platform. Once you have saved your webhook configuration, the platform will generate and display your unique credentials.

For a step-by-step guide on configuring webhooks, see the Webhooks documentation.

Test in Sandbox First

We recommend performing all initial integration tests in the Sandbox environment. This allows you to verify your authentication logic and API calls safely before switching to the Live environment.


Authentication Process

Authentication is a two-step process:

  1. Exchange a Signed Assertion for a short-lived Bearer Token.
  2. Use the Bearer Token in the Authorization header for all API calls.

1. Obtain an Access Token

You must generate a JWT locally, sign it with your RSA Private Key, and send it to the token endpoint.

Endpoint: POST access.1flow/v1/clients/token

Assertion Requirements (JWT Claims):

ClaimValueDescription
issYOUR_CLIENT_IDYour unique Client ID provided by on the Flow Platform.
subYOUR_CLIENT_IDSame as Client ID.
iatTimestampIssued At (Current Unix time).
expTimestampExpiry.

Python Authentication Example

import jwt
import time
import requests

CLIENT_ID = "your_client_id"
PRIVATE_KEY = """Your Private key"""

def get_access_token():
now = int(time.time())
payload = {
"iss": CLIENT_ID,
"sub": CLIENT_ID,
"iat": now,
"exp": now + 300 # Valid for 5 minutes
}

# Sign the assertion using RS256
assertion = jwt.encode(payload, PRIVATE_KEY, algorithm="RS256")

# Exchange assertion for a real Bearer Token
response = requests.post(
"(https://access.1flow/v1/clients/token)",
data={
"grant_type": "client_credentials",
"client_assertion_type": "urn:ietf:params:oauth:client-assertion-type:jwt-bearer",
"client_assertion": assertion,
"client_id": CLIENT_ID
}
)

if response.status_code == 200:
return response.json()["access_token"]
else:
raise Exception(f"Auth Failed: {response.text}")

# Authenticate once and reuse the token
token = get_access_token()

Customer Lookup

Before initiating a recharge, you can look up a customer to verify their details and the devices associated with them.

Endpoint: POST access.1flow/v1/clients/lookup

Request Examples

headers = {"Authorization": f"Bearer {token}"}
payload = {"phoneNumber": "+254700000000"}

response = requests.post(
'https://access.1flow/v1/clients/lookup',
headers=headers,
json=payload
)
print(response.json())

Initiate Recharge

To add water credit to a customer's device, use the Initiate Recharge endpoint. This process is asynchronous.

Endpoint: POST access.1flow/v1/clients/recharge

Request Examples

headers = {"Authorization": f"Bearer {token}"}
payload = {
"deviceId": "68753500140920",
"amount": 100.0
}

response = requests.post(
'https://access.1flow/v1/clients/recharge',
headers=headers,
json=payload
)
print(response.json())

Response

The API will return a 202 Accepted status with a rechargeId. You can use this ID to track the status of the recharge.

{
"success": true,
"timestamp": 1777885301197,
"message": "success",
"data": {
"id": "98466062-2548-4dca-9ef9-f1b4b09c92dc",
"serialNumber": "68753500140920",
"deviceType": "DEVICE",
"status": "PENDING",
"amount": 100.5,
"createdAt": "2026-05-04T09:01:41.197617901Z",
"customer": {
"name": "Jane Doe",
"phoneNumber": "+254712345678"
}
}
}

Verify Recharge

Check the current status of a recharge using its ID.

Endpoint: GET access.1flow/v1/clients/recharge/{id}

Request Examples

recharge_id = "98466062-2548-4dca-9ef9-f1b4b09c92dc"
headers = {"Authorization": f"Bearer {token}"}

response = requests.get(
f'https://access.1flow/v1/clients/recharge/{recharge_id}',
headers=headers
)
print(response.json())

Response

Returns the current status of the recharge (e.g., PENDING, COMPLETED, FAILED).

{
"success": true,
"timestamp": 1777890516031,
"message": "success",
"data": {
"id": "800cb2a6-1b5f-4e5d-aba0-22550fab12bb",
"serialNumber": "68753500140920",
"deviceType": "DEVICE",
"status": "COMPLETED",
"amount": 100.5,
"currency": "GHS",
"litres": 20.1,
"pricePerLitre": 5,
"balance": 150052,
"createdAt": "2026-05-04T09:36:30.112536Z",
"completedAt": "2026-05-04T09:46:28.331923Z",
"customer": {
"name": "Jane Doe",
"phoneNumber": "+254712345678"
}
}
}