paynexus / laravel-paynexus
Laravel SDK for the PayNexus payment orchestration platform. Accept M-Pesa STK Push payments, track payment status in real time, and keep local payment records synchronized with PayNexus.
Requires
- php: ^8.2
- illuminate/database: ^11.0|^12.0
- illuminate/http: ^11.0|^12.0
- illuminate/support: ^11.0|^12.0
Requires (Dev)
- orchestra/testbench: ^9.0|^10.0
README
PayNexus Laravel Plugin
Accept M-Pesa payments through PayNexus in any Laravel application
A powerful client SDK that connects your Laravel application to the PayNexus payment platform, handling M-Pesa STK Push, real-time payment status tracking, webhook processing, and automatic local record-keeping.
Getting Started • Examples • API Reference
⚡ Quick Start
composer require paynexus/laravel-paynexus
PAYNEXUS_SECRET_KEY=sk_your_secret_key_here PAYNEXUS_BASE_URL=https://paynexus.co.ke PAYNEXUS_WEBHOOK_SECRET=whsec_your_webhook_secret
⚠️ Important: The official PayNexus documentation at
paynexus.co.ke/docs/laravelcontains outdated information. Always refer to this README for accurate installation instructions. The correct package name ispaynexus/laravel-paynexus(notpaynexus/laravel), and the base URL should behttps://paynexus.co.kewithout/apisuffix.
php artisan vendor:publish --tag=paynexus-config php artisan vendor:publish --tag=paynexus-migrations php artisan migrate
use PayNexus\Facades\PayNexus; $result = PayNexus::initiatePayment([ 'amount' => 1000, 'phone' => '254712345678', 'description' => 'Order #123', ]); if ($result['success']) { return redirect()->route('payment.status', $result['data']['checkout_request_id']); }
See GETTING_STARTED.md for the complete 5-minute tutorial.
✨ Features
- 🚀 Easy Integration - Simple facade-based API
- 💳 M-Pesa STK Push - Seamless mobile payments
- 🔄 Real-time Tracking - Poll or use webhooks
- 📊 Local Records - Automatic database sync
- 🔔 Laravel Events - Payment state change events
- 🔒 Secure - HMAC webhook verification
- 🎯 Polymorphic Relations - Link payments to any model
- 📄 Invoices - Create and manage invoices
- 🧾 Receipts - Generate and send receipts
- 🛒 Checkout Sessions - Hosted payment pages
📚 Documentation
| Document | Description |
|---|---|
| GETTING_STARTED.md | 5-minute quick start guide |
| EXAMPLES.md | Real-world integration examples |
| API Reference | Complete API documentation |
🎯 Common Use Cases
Ecommerce Store
use PayNexus\Facades\PayNexus; use PayNexus\Models\PaynexusPayment; // Create order $order = Order::create([...]); // Initiate payment $result = PayNexus::initiatePayment([ 'amount' => $order->total, 'phone' => $request->phone, 'description' => "Order {$order->order_number}", ]); // Link payment to order if ($result['success']) { $payment = PaynexusPayment::where('checkout_request_id', $result['data']['checkout_request_id'])->first(); $payment->update([ 'payable_type' => Order::class, 'payable_id' => $order->id, ]); }
Subscriptions
$result = PayNexus::initiatePayment([ 'amount' => 1000, 'phone' => $user->phone, 'description' => 'Monthly subscription', ]); if ($result['success']) { $payment = PaynexusPayment::where('checkout_request_id', $result['data']['checkout_request_id'])->first(); $payment->update([ 'payable_type' => Subscription::class, 'payable_id' => $subscription->id, ]); }
Invoices
// Create invoice $invoice = PayNexus::createInvoice([ 'customer_name' => 'John Doe', 'customer_email' => 'john@example.com', 'amount' => 5000, 'line_items' => [ ['description' => 'Consulting', 'amount' => 5000], ], ]); // Send invoice if ($invoice['success']) { PayNexus::sendInvoice($invoice['data']['id']); }
🔔 Webhook Events
Listen for these events in your EventServiceProvider:
use PayNexus\Events\PaymentCompleted; use PayNexus\Events\PaymentFailed; protected $listen = [ PaymentCompleted::class => [ \App\Listeners\HandlePaymentSuccess::class, ], PaymentFailed::class => [ \App\Listeners\HandlePaymentFailure::class, ], ];
Webhook URL: https://yourapp.com/paynexus/webhook
📦 Local Payment Records
Every payment creates a paynexus_payments record:
use PayNexus\Models\PaynexusPayment; // Find payment $payment = PaynexusPayment::where('reference', 'PNX123')->first(); // Check status $payment->isPending(); $payment->isCompleted(); $payment->isFailed(); // Mark as verified (admin review) $payment->markVerified(1500.00, '254712345678', 'bank_statement');
🔑 API Reference
Payments
// Initiate payment PayNexus::initiatePayment(['amount' => 1000, 'phone' => '254712345678', 'description' => '...']); PayNexus::initiateMpesaPayment(['amount' => 1000, 'phone' => '254712345678', 'description' => '...']); // Check status PayNexus::getPaymentByReference('PNX123'); PayNexus::getPaymentById(42); PayNexus::getPaymentByCheckoutId('ws_CO_...'); PayNexus::checkMpesaStatus('ws_CO_...'); PayNexus::pollStatus('ws_CO_...'); // List payments PayNexus::listPayments(['status' => 'completed', 'from_date' => '2026-01-01']);
Invoices
PayNexus::createInvoice(['customer_name' => 'John', 'amount' => 5000, ...]); PayNexus::getInvoice(123); PayNexus::listInvoices(['status' => 'pending']); PayNexus::updateInvoice(123, ['status' => 'sent']); PayNexus::deleteInvoice(123); PayNexus::sendInvoice(123);
Receipts
PayNexus::getReceipt(123); PayNexus::listReceipts(['payment_id' => 456]); PayNexus::resendReceipt(123);
Checkout Sessions
PayNexus::createCheckoutSession([ 'amount' => 1000, 'customer_email' => 'john@example.com', 'success_url' => 'https://yourapp.com/success', 'cancel_url' => 'https://yourapp.com/cancel', ]);
Merchant
PayNexus::getMerchant(); PayNexus::getBusinesses(); PayNexus::getPaymentAccounts();
Webhooks
PayNexus::registerWebhook('My App', 'https://yourapp.com/paynexus/webhook', ['payment.completed']); PayNexus::listWebhooks(); PayNexus::updateWebhook(1, ['active' => false]); PayNexus::deleteWebhook(1);
Phone Validation
PayNexus::validatePhone('0712345678'); // Returns: ['valid' => true, 'normalized' => '254712345678']
⚙️ Configuration
| Option | Env Variable | Default | Description |
|---|---|---|---|
secret_key |
PAYNEXUS_SECRET_KEY |
— | Your secret API key (required) |
public_key |
PAYNEXUS_PUBLIC_KEY |
— | Your public API key (optional) |
base_url |
PAYNEXUS_BASE_URL |
https://paynexus.co.ke |
PayNexus API URL |
currency |
PAYNEXUS_CURRENCY |
KES |
Default currency |
webhook.secret |
PAYNEXUS_WEBHOOK_SECRET |
— | Webhook signature secret |
webhook.path |
PAYNEXUS_WEBHOOK_PATH |
/paynexus/webhook |
Webhook route path |
See config/paynexus.php for all options.
🧪 Testing
use Illuminate\Support\Facades\Http; Http::fake([ 'paynexus.co.ke/*' => Http::response([ 'success' => true, 'data' => [ 'payment_id' => 123, 'reference' => 'PNXTEST', 'checkout_request_id' => 'ws_CO_test', ], ]), ]); $result = PayNexus::initiatePayment([ 'amount' => 1000, 'phone' => '254712345678', ]);
🚨 Error Handling
use PayNexus\Exceptions\PayNexusAuthException; use PayNexus\Exceptions\PayNexusConnectionException; use PayNexus\Exceptions\PayNexusApiException; try { $result = PayNexus::initiatePayment([...]); if (!$result['success']) { return back()->with('error', $result['message']); } } catch (PayNexusAuthException $e) { // Invalid API key } catch (PayNexusConnectionException $e) { // Network error } catch (PayNexusApiException $e) { // API error }
📋 Requirements
- PHP 8.2+
- Laravel 11.x or 12.x
- Composer 2.x
💬 Support
- 📧 Email: support@paynexus.co.ke
- 📚 Docs: GETTING_STARTED.md
- 💡 Examples: EXAMPLES.md
- 🐛 Issues: GitHub Issues
- 🌐 Platform: paynexus.co.ke
📄 License
MIT — see LICENSE.
Built with ❤️ for the Laravel community