fereydooni / money-port
A comprehensive Laravel payment package with strategy pattern for multiple payment gateways
Requires
- php: ^8.1
- guzzlehttp/guzzle: ^7.0
- illuminate/support: ^10.0|^11.0
- laravel/framework: ^10.0|^11.0
Requires (Dev)
- mockery/mockery: ^1.0
- orchestra/testbench: ^8.0|^9.0
- phpunit/phpunit: ^10.0
This package is auto-updated.
Last update: 2025-09-09 13:18:22 UTC
README
A comprehensive Laravel payment package with strategy pattern for multiple payment gateways, specifically designed for Iranian payment systems.
✨ Features
- 🔄 Strategy Pattern - Easy to switch between payment gateways
- 🏦 10 Iranian Gateways - Support for all major Iranian payment providers
- 🚀 Octane Compatible - Uses scoped bindings for better Octane performance
- 🔧 Easy Configuration - Simple configuration file with environment variables
- 🎯 Laravel Integration - Native Laravel service provider and facade
- 📦 Package Ready - Easy to install and use in any Laravel project
- 🛡️ Error Handling - Comprehensive error handling and logging
- 🔒 Secure - Built-in security features and validation
🏦 Supported Payment Gateways
1. Zarinpal - زرینپال
- Most popular Iranian payment gateway
- Simple API integration
- Supports sandbox mode
2. Mellat Bank - بانک ملت
- Official bank gateway
- SOAP-based API
- Comprehensive transaction support
3. Parsian Bank - بانک پارسیان
- PEP (Parsian Electronic Payment) system
- XML-based API
- High security standards
4. Saman Bank - بانک سامان
- SEP (Saman Electronic Payment) system
- RESTful API
- Fast transaction processing
5. Pasargad Bank - بانک پاسارگاد
- Advanced payment system
- Digital signature support
- Multi-currency support
6. IDPay - آیدیپی
- Modern REST API
- Comprehensive documentation
- Sandbox environment
7. NextPay - نکستپی
- Simple integration
- Multiple payment methods
- Developer-friendly API
8. Sepehr - سپهر
- Shaparak electronic payment
- Bank-independent
- High reliability
9. Shaparak - شاپرک
- Central Bank gateway
- Standardized API
- Multi-bank support
10. BehPardakht - بهپرداخت
- Comprehensive payment solutions
- Advanced reporting
- Multi-terminal support
📋 Requirements
- PHP 8.1 or higher
- Laravel 10.x or 11.x
- Guzzle HTTP Client
Laravel Octane Compatibility
This package is fully compatible with Laravel Octane. It uses scoped()
bindings instead of singleton()
to ensure that:
- Each request gets a fresh instance of the PaymentManager
- No state pollution between requests
- Better memory management in long-running processes
- Optimal performance in Octane environments
🚀 Installation
- Install the package via Composer:
composer require fereydooni/money-port
- Publish the configuration file:
php artisan vendor:publish --provider="Fereydooni\MoneyPort\MoneyPortServiceProvider"
- Configure your environment variables:
# Default Gateway MONEY_PORT_DEFAULT_GATEWAY=zarinpal # Zarinpal Configuration ZARINPAL_ENABLED=true ZARINPAL_MERCHANT_ID=your_merchant_id ZARINPAL_BASE_URL=https://www.zarinpal.com/pg ZARINPAL_SANDBOX=false # Mellat Configuration MELLAT_ENABLED=false MELLAT_TERMINAL_ID=your_terminal_id MELLAT_USERNAME=your_username MELLAT_PASSWORD=your_password # Parsian Configuration PARSIAN_ENABLED=false PARSIAN_PIN=your_pin PARSIAN_ORIGINATOR=your_originator # Saman Configuration SAMAN_ENABLED=false SAMAN_TERMINAL_ID=your_terminal_id SAMAN_SECRET_KEY=your_secret_key # Pasargad Configuration PASARGAD_ENABLED=false PASARGAD_MERCHANT_CODE=your_merchant_code PASARGAD_TERMINAL_CODE=your_terminal_code PASARGAD_PRIVATE_KEY=your_private_key # IDPay Configuration IDPAY_ENABLED=false IDPAY_API_KEY=your_api_key IDPAY_MERCHANT_NAME=your_merchant_name IDPAY_MERCHANT_PHONE=your_phone IDPAY_MERCHANT_EMAIL=your_email # NextPay Configuration NEXTPAY_ENABLED=false NEXTPAY_API_KEY=your_api_key NEXTPAY_CUSTOMER_PHONE=your_phone # Sepehr Configuration SEPEHR_ENABLED=false SEPEHR_TERMINAL_ID=your_terminal_id SEPEHR_SECRET_KEY=your_secret_key # Shaparak Configuration SHAPARAK_ENABLED=false SHAPARAK_MERCHANT_ID=your_merchant_id # BehPardakht Configuration BEHPARDAKHT_ENABLED=false BEHPARDAKHT_USERNAME=your_username BEHPARDAKHT_PASSWORD=your_password BEHPARDAKHT_PAYER_ID=your_payer_id # Logging Configuration MONEY_PORT_LOGGING=true MONEY_PORT_LOG_CHANNEL=payment MONEY_PORT_LOG_LEVEL=info # HTTP Configuration MONEY_PORT_TIMEOUT=30 MONEY_PORT_RETRY_ATTEMPTS=3 MONEY_PORT_RETRY_DELAY=1000
📖 Basic Usage
Gateway Selection Behavior
The package now uses a smart gateway selection system:
- Default Gateway: Zarinpal is always the default and fallback gateway
- Current Gateway: When you specify a gateway in
initialize()
, it becomes the current gateway for subsequent operations - Automatic Fallback: If no gateway is specified, the system uses the current gateway or falls back to Zarinpal
Using the Facade
use Fereydooni\MoneyPort\Facades\MoneyPort; // Initialize payment with default gateway (Zarinpal) $payment = MoneyPort::initialize([ 'amount' => 100000, // Amount in Rials 'description' => 'Payment for order #123', 'callback_url' => 'https://yoursite.com/payment/callback', 'currency' => 'IRR' ]); // Initialize payment with specific gateway $payment = MoneyPort::initialize([ 'amount' => 100000, 'description' => 'Payment for order #123', 'callback_url' => 'https://yoursite.com/payment/callback', 'currency' => 'IRR' ], 'mellat'); // This will set Mellat as current gateway for subsequent operations // Verify payment (will use the current gateway set in initialize, or default if none specified) $verification = MoneyPort::verify([ 'token' => 'payment_token_from_callback', 'amount' => 100000, 'transaction_id' => 'order_123' ]); // Or specify a different gateway for verification $verification = MoneyPort::verify([ 'token' => 'payment_token_from_callback', 'amount' => 100000, 'transaction_id' => 'order_123' ], 'mellat'); // Get available gateways $gateways = MoneyPort::getAvailableGateways();
Using the Service Class
use Fereydooni\MoneyPort\Services\PaymentManager; class PaymentController extends Controller { public function __construct( private PaymentManager $paymentManager ) {} public function processPayment(Request $request) { $payment = $this->paymentManager->initialize([ 'amount' => $request->amount, 'description' => $request->description, 'callback_url' => route('payment.callback'), 'currency' => 'IRR' ], 'zarinpal'); return redirect($payment['payment_url']); } public function verifyPayment(Request $request) { $verification = $this->paymentManager->verify([ 'token' => $request->token, 'amount' => $request->amount, 'transaction_id' => $request->transaction_id ], 'zarinpal'); if ($verification['success']) { // Payment successful return response()->json(['message' => 'Payment verified']); } return response()->json(['error' => 'Payment verification failed'], 400); } }
🔧 Adding New Gateways
To add a new payment gateway:
- Create a new gateway class:
<?php namespace App\Gateways; use Fereydooni\MoneyPort\Abstracts\AbstractPaymentGateway; use Fereydooni\MoneyPort\Contracts\PaymentDataInterface; class CustomGateway extends AbstractPaymentGateway { protected function validateConfig(): void { // Validate required configuration } public function initialize(array $data): array { // Initialize payment logic } public function verify(array $data): array { // Verify payment logic } public function refund(array $data): array { // Refund logic } public function getStatus(string $transactionId): array { // Get status logic } public function getGatewayName(): string { return 'custom'; } }
- Add the gateway to the enum:
// In src/Enums/Gateway.php case CUSTOM = 'custom'; public function getDisplayName(): string { return match($this) { // ... existing cases self::CUSTOM => 'Custom Gateway', }; }
- Register the gateway in PaymentManager:
// In src/Services/PaymentManager.php if (($config['custom']['enabled'] ?? false)) { $this->registerGateway(Gateway::CUSTOM, new CustomGateway($config['custom'] ?? [])); }
- Add configuration:
// In config/money-port.php 'custom' => [ 'enabled' => env('CUSTOM_ENABLED', false), // ... other configuration ],
- Register the gateway:
use App\Gateways\CustomGateway; // In your service provider or controller MoneyPort::registerGateway('custom', new CustomGateway());
⚙️ Configuration
The package configuration file (config/money-port.php
) contains:
- Default Gateway: Zarinpal is the default gateway (hardcoded)
- Gateway Configurations: Individual settings for each gateway with enabled/disabled flags
- Logging Options: Configure payment operation logging
- HTTP Settings: Timeout, retry attempts, and delay configuration
Gateway Management
Each gateway has an enabled
flag that controls whether it's registered and available:
# Enable/disable gateways ZARINPAL_ENABLED=true # Default: true (always enabled) MELLAT_ENABLED=false # Default: false PARSIAN_ENABLED=false # Default: false # ... other gateways default to false
Only enabled gateways will be registered and available for use. This prevents unnecessary gateway instantiation and improves performance.
🚨 Error Handling
The package includes comprehensive error handling:
use Fereydooni\MoneyPort\Exceptions\PaymentException; try { $payment = MoneyPort::initialize($data); } catch (PaymentException $e) { // Handle payment-specific errors Log::error('Payment failed: ' . $e->getMessage()); } catch (Exception $e) { // Handle general errors Log::error('Unexpected error: ' . $e->getMessage()); }
📝 Logging
Enable logging to track payment operations:
// Logs are automatically created for all payment operations // Configure in config/money-port.php 'logging' => [ 'enabled' => true, 'channel' => 'payment', 'level' => 'info', ],
🧪 Testing
Run the package tests:
composer test
🤝 Contributing
- Fork the repository
- Create your feature branch (
git checkout -b feature/amazing-feature
) - Commit your changes (
git commit -m 'Add some amazing feature'
) - Push to the branch (
git push origin feature/amazing-feature
) - Open a Pull Request
📄 License
This package is open-sourced software licensed under the MIT license.
🆘 Support
If you encounter any issues or have questions:
- Create an issue on GitHub
- Check the documentation
- Review the configuration examples
📈 Changelog
v1.1.0
- Added Gateway enum for type-safe gateway management
- Implemented smart gateway selection system
- Added enabled/disabled flags for each gateway
- Only Zarinpal is enabled by default, others must be explicitly enabled
- Improved gateway state management with current gateway tracking
- Better performance by only registering enabled gateways
v1.0.0
- Initial release with 10 Iranian payment gateways
- Strategy pattern implementation
- Laravel Octane compatibility
- Comprehensive error handling and logging
- Easy configuration management