Why your app needs SMS
If you're building an app or website in Uganda, SMS is probably one of the highest-impact features you can add. Use cases:
- OTP verification — for sign-ups, password resets, transaction confirmations
- Order/booking confirmations — instant peace of mind for customers
- Payment notifications — fintech, e-commerce, marketplaces
- Appointment reminders — clinics, salons, services
- Low-stock alerts — for admin staff
- 2FA security — for sensitive accounts
Yoola SMS gives you a free REST API to send SMS from any programming language. Here's how to integrate it.
Step 1: Get your API key
- Sign up for a free Yoola SMS account at yoolasms.com/register
- Log in and click "My API Key" in the sidebar
- Copy your unique API key (looks like: a3b8c9d2e1f0...)
- Top up your account with at least UGX 2,500 via Mobile Money
Step 2: Understand the API
The Yoola SMS API has a single endpoint for sending SMS:
POST https://yoolasms.com/api/v1/send.php
Body (JSON):
{
"api_key": "YOUR_API_KEY",
"phone": "256712345678",
"message": "Your OTP is 123456",
"sender": "ATInfo"
}
Response (JSON):
{
"status": "success",
"message_id": "abc123",
"sender_used": "ATInfo",
"credit_remaining": 285
}
Multiple recipients
Send to multiple numbers in one request by passing a comma-separated list:
"phone": "256712345678,256772123456,256755987654"
Code samples in 5 languages
PHP
<?php
$apiKey = "YOUR_API_KEY";
$data = [
"api_key" => $apiKey,
"phone" => "256712345678",
"message" => "Hello from your app!",
"sender" => "ATInfo"
];
$ch = curl_init("https://yoolasms.com/api/v1/send.php");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode($data));
curl_setopt($ch, CURLOPT_HTTPHEADER, ["Content-Type: application/json"]);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$response = curl_exec($ch);
curl_close($ch);
echo $response;
?>
Python
import requests
api_key = "YOUR_API_KEY"
response = requests.post(
"https://yoolasms.com/api/v1/send.php",
json={
"api_key": api_key,
"phone": "256712345678",
"message": "Hello from your Python app!",
"sender": "ATInfo"
}
)
print(response.json())
JavaScript (Node.js)
const fetch = require('node-fetch');
const apiKey = 'YOUR_API_KEY';
async function sendSMS() {
const response = await fetch('https://yoolasms.com/api/v1/send.php', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
api_key: apiKey,
phone: '256712345678',
message: 'Hello from Node.js!',
sender: 'ATInfo'
})
});
const data = await response.json();
console.log(data);
}
sendSMS();
Python Django (in a view)
import requests
from django.http import JsonResponse
def send_otp(request):
phone = request.POST.get('phone')
otp = generate_otp() # your function
requests.post(
'https://yoolasms.com/api/v1/send.php',
json={
'api_key': settings.YOOLA_API_KEY,
'phone': phone,
'message': f'Your OTP is {otp}. Valid for 5 minutes.',
'sender': 'ATInfo'
}
)
return JsonResponse({'sent': True})
Laravel (PHP)
use IlluminateSupportFacadesHttp;
$response = Http::post('https://yoolasms.com/api/v1/send.php', [
'api_key' => config('services.yoola.key'),
'phone' => $user->phone,
'message' => "Welcome to MyApp, {$user->name}!",
'sender' => 'MYAPP'
]);
return response()->json($response->json());
OTP implementation example
Here's a complete OTP flow in PHP:
<?php
// 1. Generate OTP
$otp = rand(100000, 999999);
// 2. Save to database with expiry
$stmt = $pdo->prepare(
"INSERT INTO otps (phone, otp, expires_at) VALUES (?, ?, NOW() + INTERVAL 5 MINUTE)"
);
$stmt->execute([$phone, password_hash($otp, PASSWORD_DEFAULT)]);
// 3. Send via Yoola SMS
$ch = curl_init("https://yoolasms.com/api/v1/send.php");
curl_setopt($ch, CURLOPT_POST, true);
curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode([
"api_key" => YOOLA_API_KEY,
"phone" => $phone,
"message" => "Your verification code is {$otp}. Valid for 5 minutes. Do not share.",
"sender" => "MYAPPOTP" // use a transactional sender ID for OTPs
]));
curl_setopt($ch, CURLOPT_HTTPHEADER, ["Content-Type: application/json"]);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
$result = json_decode(curl_exec($ch), true);
curl_close($ch);
if($result['status'] === 'success'){
echo "OTP sent. Check your phone.";
}
?>
Best practices for production
1. Use environment variables for your API key
Never hardcode your API key in source files committed to Git. Use .env files:
YOOLA_API_KEY=a3b8c9d2e1f0...
2. Implement retry logic
If a send fails due to network issues, retry once with exponential backoff:
for ($attempt = 1; $attempt <= 3; $attempt++) {
$result = sendSMS($phone, $message);
if ($result['status'] === 'success') break;
sleep($attempt * 2); // 2s, 4s, 6s between retries
}
3. Validate phone numbers before sending
Save SMS credits by rejecting invalid numbers before the API call:
function isValidUgandaNumber($phone) {
$phone = preg_replace('/[^0-9]/', '', $phone);
return preg_match('/^(256|0)(7|3)[0-9]{8}$/', $phone);
}
4. Log every SMS sent
Maintain your own log table for audit, debugging, and disputes:
CREATE TABLE sms_log (
id INT AUTO_INCREMENT PRIMARY KEY,
phone VARCHAR(20),
message TEXT,
status VARCHAR(20),
response JSON,
sent_at DATETIME DEFAULT CURRENT_TIMESTAMP
);
5. Handle credit-low scenarios
Yoola SMS returns your remaining credit balance on every send. Alert your admin when it gets low:
if ($result['credit_remaining'] < 100) {
// email admin to top up
mail($adminEmail, 'SMS credits low', 'Only ' . $result['credit_remaining'] . ' credits left.');
}
Common API integration questions
What's the rate limit?
For regular accounts: 100 SMS/second. For high-volume reseller accounts: custom limits. If you exceed the rate, requests queue automatically.
How do I send to multiple countries?
Just include the destination country code in the phone number: 254... for Kenya, 255... for Tanzania, 250... for Rwanda. Rates vary by country — see Coverage page.
How do I get delivery status?
The API returns the initial send status. For final delivery status, poll the message_id endpoint or set up a webhook URL in your dashboard.
Is there a sandbox environment?
The free 3 SMS on signup is your sandbox — test there. Or use a "test" sender that won't charge but logs the request.
Ready to integrate?
Get your free API key in 60 seconds. Yoola SMS API is free to use — you only pay for the SMS sent through it.
Or read the full API documentation
Comments (0)