dp-soft-co / payments
Payment helper for Paypal, Paymob, Kashier, Hyperpay, Fawry and more - Forked from nafezly/payments with Kashier Payment Sessions API fix
Requires
- php: >=7.2
- ext-curl: *
- ext-json: *
- laravel/framework: >=6.0
- paypal/paypal-server-sdk: ^2.3
This package is auto-updated.
Last update: 2026-07-24 12:16:11 UTC
README
A Laravel package for integrating multiple payment gateways with a unified API. Supports 19+ gateways including PayPal, Paymob, Kashier, Fawry, Fawaterk, HyperPay, Thawani, Tap, Opay, Paytabs, Binance, PerfectMoney, NowPayments, Payeer, Telr, Clickpay, MyFatoorah, Stripe, and E-Wallets.
Supported Gateways
| Gateway | Key | Modes | Notes |
|---|---|---|---|
| PayPal | paypal |
Sandbox / Live | REST API v2 with redirect & button checkout |
| PayPal Buttons | paypal_button |
Sandbox / Live | JS SDK button integration |
| PayMob | paymob |
Test / Live | Card payments with redirect & pixel checkout |
| PayMob Wallets | paymob_wallet |
Test / Live | Vodafone Cash, Orange Money, Meza Wallet, Etisalat Cash, We Cash |
| Kashier | kashier |
Test / Live | Payment Sessions API with iframe |
| Fawry | fawry |
Test / Live | Popup / inside page / side page |
| Fawaterk | fawaterk |
Test / Live | API v3 — OAuth + hosted checkout & iframe |
| HyperPay | hyperpay |
Test / Live | Credit, MADA, Apple Pay |
| Thawani | thawani |
Test / Live | Oman-based gateway |
| Tap | tap |
Test / Live | Multi-currency |
| Opay | opay |
Test / Live | Egypt & Nigeria |
| Paytabs | paytabs |
Test / Live | Multi-region |
| Binance Pay | binance |
Live | Crypto payments |
| PerfectMoney | perfectmoney |
Live | SCI form-based |
| NowPayments | nowpayments |
Live | Crypto invoices |
| Payeer | payeer |
Live | Multi-currency e-wallet |
| Telr | telr |
Test / Live | UAE-based gateway |
| Clickpay | clickpay |
Test / Live | Saudi-based |
| MyFatoorah | myfatoorah |
Test / Live | Multi-country (EG, SA, AE, QA, KW) |
| Stripe | stripe |
Test / Live | Checkout Sessions |
Installation
composer require dp-soft-co/payments
Publish Vendor Files
php artisan vendor:publish --tag="dpsoft-payments-config" php artisan vendor:publish --tag="dpsoft-payments-lang"
Configuration
All gateway settings are driven by environment variables. After publishing, edit config/dpsoft-payments.php and add the keys you need to your .env.
PayMob
PAYMOB_BASE_URL=https://accept.paymob.com PAYMOB_PUBLIC_KEY=your_public_key PAYMOB_SECRET_KEY=your_secret_key PAYMOB_HMAC=your_hmac_secret PAYMOB_INTEGRATION_ID=your_integration_id PAYMOB_CURRENCY=EGP PAYMOB_NOTIFICATION_URL=https://yoursite.com/payment/verify/paymob PAYMOB_CHECKOUT_MODE=redirect # redirect or pixel PAYMOB_PIXEL_PAYMENT_METHODS=card # card, google-pay, apple-pay PAYMOB_WALLET_INTEGRATION_ID=wallet_integration_id
Fawaterk (API v3)
Fawaterk v3 uses OAuth client credentials for API calls and Vendor API Key for hash signing (iframe & webhooks).
# OAuth — dashboard → Integrations → OAuth client credentials FAWATERK_CLIENT_ID=9d4e2c1a-b3f5-4e8a-9c1d-2a3b4c5d6e7f FAWATERK_CLIENT_SECRET=your_client_secret # Vendor API Key — dashboard → Integrations → Get API Key (for hash signing only) FAWATERK_API_KEY=d83a5d07aaeb8442dcbe259e6dae80a3f2e21a3a581e1a5acd # Provider Key — dashboard → Integrations → Fawaterk (required for iframe) FAWATERK_PROVIDER_KEY=FAWATERAK_29503 # Environment FAWATERK_MODE=test # test or live (auto-resolves base URL) # FAWATERK_BASE_URL=https://staging.fawaterk.com # optional, auto from mode # Checkout FAWATERK_CHECKOUT_MODE=redirect # redirect or iframe FAWATERK_CURRENCY=EGP FAWATERK_IFRAME_LISTING=horizontal # horizontal or vertical
Endpoints used:
POST /api/v3/createTransaction— create payment (OAuth Bearer token)POST /api/v3/getTransactionData— verify payment (OAuth Bearer token)POST /oauth/token— obtain access token (client credentials grant)
Webhook hash verification:
- Paid webhook:
transactionHashKey=HMAC-SHA256("TransactionId={id}&TransactionKey={key}&PaymentMethod={method}", vendor_api_key) - Failed webhook:
hashKey= same formula as above - Cancel webhook:
hashKey=HMAC-SHA256("referenceId={refId}&PaymentMethod={method}", vendor_api_key) - Legacy v2 webhooks still supported via
hashKeywithInvoiceId/InvoiceKey
Iframe hash:
hashKey=HMAC-SHA256("Domain={your_domain}&ProviderKey={provider_key}", vendor_api_key)- Uses
fawaterkCheckoutV2()andfawaterkPlugin.js
Kashier
KASHIER_ACCOUNT_KEY=your_account_key KASHIER_IFRAME_KEY=your_iframe_key KASHIER_TOKEN=your_api_token KASHIER_URL=https://checkout.kashier.io KASHIER_MODE=test # test or live KASHIER_CURRENCY=EGP KASHIER_WEBHOOK_URL=https://yoursite.com/payment/verify/kashier
HyperPay
HYPERPAY_BASE_URL=https://eu-test.oppwa.com HYPERPAY_TOKEN=your_access_token HYPERPAY_CREDIT_ID=your_credit_entity_id HYPERPAY_MADA_ID=your_mada_entity_id HYPERPAY_APPLE_ID=your_apple_entity_id HYPERPAY_CURRENCY=SAR
Fawry
FAWRY_URL=https://atfawry.fawrystaging.com/ # https://www.atfawry.com/ for production FAWRY_SECRET=your_secret FAWRY_MERCHANT=your_merchant_code FAWRY_DISPLAY_MODE=POPUP # POPUP, INSIDE_PAGE, SIDE_PAGE, SEPARATED FAWRY_PAY_MODE=CARD # CashOnDelivery, PayAtFawry, MWALLET, CARD, VALU
PayPal
PAYPAL_CLIENT_ID=your_client_id PAYPAL_SECRET=your_secret PAYPAL_CURRENCY=USD PAYPAL_MODE=sandbox # sandbox or live
Stripe
STRIPE_SECRET_KEY=sk_test_xxx STRIPE_PUBLISHABLE_KEY=pk_test_xxx STRIPE_CURRENCY=USD
Thawani
THAWANI_API_KEY=your_api_key THAWANI_PUBLISHABLE_KEY=your_publishable_key THAWANI_URL=https://uatcheckout.thawani.om/
Tap
TAP_SECRET_KEY=your_secret_key TAP_PUBLIC_KEY=your_public_key TAP_CURRENCY=USD TAP_LANG_KEY=ar
Opay
OPAY_SECRET_KEY=your_secret_key OPAY_PUBLIC_KEY=your_public_key OPAY_MERCHANT_ID=your_merchant_id OPAY_COUNTRY_CODE=EG OPAY_CURRENCY=EGP OPAY_BASE_URL=https://sandboxapi.opaycheckout.com # https://api.opaycheckout.com for production
Paytabs
PAYTABS_PROFILE_ID=your_profile_id PAYTABS_SERVER_KEY=your_server_key PAYTABS_BASE_URL=https://secure-egypt.paytabs.com PAYTABS_CHECKOUT_LANG=AR PAYTABS_CURRENCY=EGP
Binance Pay
BINANCE_API=your_api_key BINANCE_SECRET=your_api_secret
NowPayments
NOWPAYMENTS_API_KEY=your_api_key
Payeer
PAYEER_MERCHANT_ID=your_merchant_id PAYEER_API_KEY=your_api_key PAYEER_ADDITIONAL_API_KEY=your_additional_api_key
PerfectMoney
PERFECT_MONEY_ID=UXXXXXXX PERFECT_MONEY_PASSPHRASE=your_passphrase
Telr
TELR_MERCHANT_ID=your_merchant_id TELR_API_KEY=your_api_key TELR_MODE=test # test or live
Clickpay
CLICKPAY_SERVER_KEY=your_server_key CLICKPAY_PROFILE_ID=your_profile_id
MyFatoorah
MYFATOORAH_API_KEY=your_api_key MYFATOORAH_MODE=test # test or live MYFATOORAH_COUNTRY= # eg, sa, ae, qa or empty for global MYFATOORAH_CURRENCY=KWD
How To Use
Standard Controller Example
The following Laravel controller pattern works with every gateway supported by the package. Store the gateway class name used to create the invoice so the callback can use the same gateway. Replace Invoice, the payment view, and success/failure routes with your application equivalents.
use App\Models\Invoice; use Dpsoft\Payments\Facades\DpsoftPaymentsFacade as DpsoftPayments; use Illuminate\Http\Request; public function pay(Request $request) { $data = $request->validate([ 'gateway' => ['required', 'string'], 'amount' => ['required', 'numeric', 'min:0.01'], ]); $user = $request->user(); $gateway = $data['gateway']; $source = match (strtolower($gateway)) { 'kashier' => 'card,bank_installments,wallet,fawry', 'hyperpay' => 'CREDIT', default => null, }; $response = DpsoftPayments::gateway($gateway) ->setPaymentData([ 'amount' => $data['amount'], 'user_id' => $user->id, 'user_first_name' => $user->firstname, 'user_last_name' => $user->lastname, 'user_email' => $user->email, 'user_phone' => $user->phone, 'source' => $source, ]) ->pay(); if (empty($response['payment_id'])) { abort(422, strip_tags($response['html'] ?? 'Payment creation failed.')); } Invoice::create([ 'user_id' => $user->id, 'amount' => $data['amount'], 'status' => 'pending', 'pid' => $response['payment_id'], 'gateway' => $gateway, ]); if (!empty($response['redirect_url'])) { return redirect()->away($response['redirect_url']); } if (!empty($response['html'])) { return view('payments.pay', ['link' => $response['html']]); } abort(422, 'Invalid gateway response.'); } public function verify(string $gateway, Request $request) { $result = DpsoftPayments::gateway($gateway)->verify($request); $invoice = Invoice::where('pid', $result['payment_id'] ?? null) ->where('gateway', $gateway) ->firstOrFail(); if ($result['success']) { $invoice->update(['status' => 'paid']); return redirect()->route('payments.success'); } return redirect()->route('payments.failed'); }
Render gateway HTML only when it comes directly from the package response:
{!! $link !!}
Register the verification route:
Route::match(['get', 'post'], '/payments/verify/{gateway}', [PaymentController::class, 'verify']) ->name('verify-payment');
CSRF Protection
Payment gateways send POST callbacks from an iframe or external page and will not include the Laravel CSRF token. You must exclude the verification route from CSRF validation:
-
Laravel 11 (
bootstrap/app.php):$middleware->validateCsrfTokens(except: [ '*payment/verify*', ]);
-
Laravel 10 (
app/Http/Middleware/VerifyCsrfToken.php):protected $except = [ '*payment/verify*', ];
Adjust the wildcard to match your actual route path and any language prefix (e.g. *payments/verify*).
Gateway-specific source values
| Gateway | source values |
|---|---|
kashier |
Comma-separated allowed methods: card,wallet, card,bank_installments,wallet,fawry, etc. Defaults to card,wallet. |
hyperpay |
CREDIT, MADA, or APPLE. Required to select the matching HyperPay entity ID and payment brand. |
Most other gateways do not use source; passing null is valid.
Test Cards
Fawaterk (Staging)
| Brand | Card Number | Expiry | CVV | Result |
|---|---|---|---|---|
| Mastercard | 5123450000000008 |
12/26 | 100 | Success |
| Visa | 4005 5500 0000 0001 |
12/26 | 100 | Success |
| Mastercard | 5543474002249996 |
05/26 | 123 | Decline |
| Visa | 4222 0000 0672 4235 |
12/26 | 123 | Decline |
Other Gateways
License
MIT License. See LICENSE file for details.
