Dynamic QR Code
⚠️Important
Dynamic QR Codes can only be scanned and completed from inside the M-Pesa mobile application. They are not usable from generic QR readers.
Generate and manage dynamic M-Pesa QR codes for payments and transfers. Dynamic QR lets you create a QR payload for a single transaction that includes amount, reference and recipient details.
User Stories
- As a fintech product owner, I want to programmatically generate dynamic QR codes so that customers can easily make payments.
- As an integrations developer, I want a simple client and clear webhook callbacks so I can implement reliable end-to-end flows with minimal boilerplate.
- As a billing operations engineer, I want result and timeout notifications with acknowledgements so I can reconcile transactions and trigger retries or alerts when needed.
- As a reseller partner, I want a tested SDK and examples so I can onboard quickly and reduce integration defects.
Parameters
Parameter | Type | Description |
---|---|---|
MerchantNamerequired str | String | Merchant or business name shown on the QR experience (e.g., store name). |
RefNorequired str | String | Transaction reference or account identifier (e.g., invoice or order id). |
Amountrequired int | Integer | Amount in KES. Must be greater than zero. |
TrxCoderequired str | String | Transaction type code. Supported values: BG, WA, PB, SM, SB. |
CPIrequired str | String | Credit Party Identifier: mobile number, paybill, till or business identifier depending on TrxCode. |
Sizerequired str | String | QR image size in pixels (square). Example: '300'. |
Integration Overview
Two integration patterns: use the library-level client (recommended) for quick setup or the lower-level service for custom workflows.
💡Recommended
Use the high-level client to handle authentication and common defaults. It gives a simple surface for generating dynamic QR codes.
Quick Start (Python)
Python
# Example: using MpesaClient facade to create a dynamic QRfrom mpesakit import MpesaClientfrom mpesakit.dynamic_qr_code import DynamicQRTransactionType
client = MpesaClient( consumer_key="YOUR_KEY", consumer_secret="YOUR_SECRET", environment="sandbox",)
response = client.dynamic_qr.generate( merchant_name="Corner Store", ref_no="ORDER-1001", amount=250, trx_code=DynamicQRTransactionType.BUY_GOODS, cpi="373132", size="300",)
if response.is_successful(): print("QR generated", response.QRCode)else: print("Failed:", response.ResponseDescription)
💡Notes
- Provide either numeric/traditional values for TrxCode (use the transaction type enum) and ensure CPI matches the TrxCode semantics (mobile vs business).
- Amount must be > 0.
Response
- Response objects are typed models with attributes matching the API response fields.
- Use
is_successful()
to check if the request succeeded. - If you need the raw response data, use
model_dump(mode="json")
to get a dictionary representation.
Sample Response
{ "ResponseCode": "00", "ResponseDescription": "QR Code generated successfully", "QRCode": "iVBORw0KGgoAAAANSUhEUgAA..."}
Python
# Check success and extract QR payloadif response.is_successful(): payload = response.QRCode # store or render payload as neededelse: print("Failed to generate QR:", response.ResponseDescription)
💡Error handling
- Validation errors (invalid TrxCode, bad CPI for SEND_MONEY, etc.) raise exceptions at request model creation time.
- HTTP or API-level errors should be caught and inspected (use the library exceptions to get code, message and HTTP status).
Next Steps
💡What's next?
- Implement a flow to render or serve the QR image to customers after generation.
- Monitor flow completion via M-Pesa app actions and reconcile transactions using your normal payment notifications and webhooks.