blessdarah / php-campay
PHP package wrapper for campay momo integration
Requires
- php: ^8.4
- ext-json: *
- guzzlehttp/guzzle: ^8.2
Requires (Dev)
- pestphp/pest: ^5.3
- phpstan/phpstan: ^2.3
Suggests
None
Provides
None
Conflicts
None
Replaces
None
This package is auto-updated.
Last update: 2026-10-14 10:21:09 UTC
README
A PHP wrapper for the Campay API that makes it easy to integrate Mobile Money payments into your PHP application.
Requirements
- PHP
8.4or newer ext-json- Guzzle
8.x(installed automatically)
How to install this package
To install this package, run:
composer require blessdarah/php-campay
Usage
The package automatically requests a token, caches it on the instance, and refreshes it once if Campay reports it expired.
Configuration
Pass your application credentials (from your Campay dashboard) and the API base URL to the constructor:
use BlessDarah\PhpCampay\Campay; $campay = new Campay( username: getenv('CAMPAY_USERNAME'), password: getenv('CAMPAY_PASSWORD'), baseUrl: Campay::DEMO_BASE_URL, // or Campay::LIVE_BASE_URL in production );
Load the credentials however your application manages secrets (environment variables, a secrets manager, your framework's config). The package never reads .env files or $_ENV itself.
Security notes
- Never commit your credentials or expose them to the browser.
- The base URL must use
https://. Plainhttp://URLs are rejected so credentials and tokens are never sent in clear text.- Redirects are not followed, TLS verification is always on, and requests time out after 30 seconds.
You can pass your own Guzzle client as the fourth argument (useful for testing or adding middleware). The package still enforces its own base URL and secure request options.
Responses and errors
Every API method returns the raw JSON response body as a string:
$response = json_decode($campay->getAppBalance(), true, flags: JSON_THROW_ON_ERROR);
Errors are thrown as exceptions that all extend BlessDarah\PhpCampay\Exceptions\CampayException:
| Exception | When |
|---|---|
ValidationException |
Invalid input, checked before any request is sent |
AuthenticationException |
Campay rejected the credentials or returned no token |
ApiException |
HTTP error, network failure, or an invalid response from Campay |
CampayException |
Invalid configuration (missing credentials, non-https base URL) |
use BlessDarah\PhpCampay\Exceptions\CampayException; try { $response = $campay->collect($data); } catch (CampayException $e) { // log $e and show a generic error to your user }
Collect payment
$response = $campay->collect([ 'amount' => 3, 'currency' => 'XAF', 'from' => '237******', 'description' => 'test payment', ]);
Withdraw funds
$response = $campay->withdraw([ 'amount' => 3, 'currency' => 'XAF', 'to' => '237******', 'description' => 'test payment', ]);
The response contains the reference of your transaction, which you can use to check its status.
Check transaction status
$collection = json_decode($campay->collect($data), true, flags: JSON_THROW_ON_ERROR); $status = json_decode( $campay->getTransactionStatus($collection['reference']), // e.g: b1d44bc7-648d-451b-a3ef-c5807738ec82 true, flags: JSON_THROW_ON_ERROR, ); switch ($status['status']) { case 'SUCCESSFUL': // success logic break; case 'PENDING': // pending logic break; case 'FAILED': // error logic break; }
References may only contain letters, numbers, - and _. Anything else throws a ValidationException.
Get your application balance
$response = $campay->getAppBalance();
Get transaction history
By default, this returns your app's transactions for the past 7 days:
$response = $campay->transactionHistory();
You can pass specific dates as YYYY-MM-DD strings or DateTimeInterface objects:
$response = $campay->transactionHistory('2022-06-13', new DateTimeImmutable('2022-08-13'));
Generate payment link
$response = $campay->generatePaymentUrl([ 'amount' => 4, 'currency' => 'XAF', 'description' => 'Sample description', 'first_name' => 'John', 'last_name' => 'Doe', 'email' => 'example@mail.com', 'external_reference' => '', 'redirect_url' => 'https://example.com', 'failure_redirect_url' => 'https://example.com', 'payment_options' => 'MOMO', // or CARD for credit card payments ]);
redirect_url and failure_redirect_url must be https:// URLs.
Handling webhooks
Campay notifies your webhook URL when a transaction completes. Treat the payload as untrusted input:
$reference = $_GET['reference'] ?? ''; // Never echo request data back, and never trust the reported status on its own. // Confirm it with Campay before fulfilling the order: $status = json_decode($campay->getTransactionStatus($reference), true, flags: JSON_THROW_ON_ERROR); if ($status['status'] === 'SUCCESSFUL') { // mark the order as paid (idempotently) } http_response_code(200);
Development
composer test # run the test suite composer analyse # run PHPStan composer audit # check dependencies for known vulnerabilities
Upgrading from 1.x
See CHANGELOG.md.