Skip to content
Open

d #1

Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions .env.test.example
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
# CashBill Test Configuration
# Copy this file to .env.test and fill in your credentials

CASHBILL_MODE=dev
CASHBILL_SHOP_ID=
CASHBILL_SECRET_KEY=
84 changes: 84 additions & 0 deletions .github/workflows/tests.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
name: Tests

on:
push:
branches: [main, master, develop]
pull_request:
branches: [main, master, develop]

jobs:
test:
runs-on: ubuntu-latest

strategy:
fail-fast: false
matrix:
include:
# Laravel 10 → Testbench 8.x (PHP 8.1, 8.2)
- php: "8.2"
laravel: "10"
testbench: "^8.0"
phpunit: "^10.5"
# Laravel 11 → Testbench 9.x (PHP 8.2, 8.3)
- php: "8.2"
laravel: "11"
testbench: "^9.0"
phpunit: "^10.5"
- php: "8.3"
laravel: "11"
testbench: "^9.0"
phpunit: "^10.5"
# Laravel 12 → Testbench 10.x (PHP 8.2, 8.3, 8.4)
- php: "8.2"
laravel: "12"
testbench: "^10.0"
phpunit: "^11.5"
- php: "8.3"
laravel: "12"
testbench: "^10.0"
phpunit: "^11.5"
- php: "8.4"
laravel: "12"
testbench: "^10.0"
phpunit: "^11.5"
# Laravel 13 → Testbench 11.x (PHP 8.3, 8.4)
- php: "8.3"
laravel: "13"
testbench: "^11.0"
phpunit: "^11.5"
- php: "8.4"
laravel: "13"
testbench: "^11.0"
phpunit: "^11.5"

name: PHP ${{ matrix.php }} | Laravel ${{ matrix.laravel }}

steps:
- name: Checkout code
uses: actions/checkout@v4

- name: Setup PHP
uses: shivammathur/setup-php@v2
with:
php-version: ${{ matrix.php }}
extensions: pdo_sqlite, mbstring, json
coverage: none

- name: Remove lock file
run: rm -f composer.lock

- name: Install dependencies
run: |
composer remove --dev orchestra/testbench phpunit/phpunit --no-interaction
composer require --dev "orchestra/testbench:${{ matrix.testbench }}" "phpunit/phpunit:${{ matrix.phpunit }}" "illuminate/support:^${{ matrix.laravel }}" --no-interaction --no-progress --prefer-stable -W

- name: Run unit tests
run: vendor/bin/phpunit --testsuite=Unit

- name: Run integration tests
env:
CASHBILL_MODE: dev
CASHBILL_SHOP_ID: ${{ secrets.CASHBILL_SHOP_ID }}
CASHBILL_SECRET_KEY: ${{ secrets.CASHBILL_SECRET_KEY }}
run: vendor/bin/phpunit --testsuite=Integration
continue-on-error: true
11 changes: 11 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,2 +1,13 @@
/vendor
composer.lock
.env
.env.test
.phpunit.cache
.phpunit.result.cache
*.log
.DS_Store
.idea/
.vscode/
*.swp
*.swo
*~
7 changes: 6 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@

# Cashbill payment system for Laravel

Package for easily integrating Cashbill payments with Laravel.

## Compatibility

This package supports **Laravel 10, 11, 12, and 13**.

## Support
If this package is helpful for you, you can support my work on Ko-fi.
Expand Down Expand Up @@ -45,7 +49,7 @@ Ensure that you specify the same notification route as in the CashBill shop sett

## Usage/Examples

To initiate a transaction, create a **Payload** object in your controller and assign values. Then, create a **Payment** object, pass the **Payload**, and call **redirect()**. This action will start the transaction and redirect the user to the Cashbill payment page. You can also create a **PersonalData** object. The *first name*, *surname*, and *email address* will be automatically filled on the Cashbill page.
To initiate a transaction, create a **Payload** object in your controller and assign values. To link your item to the transaction use **additionalData** field. Then, create a **Payment** object, pass the **Payload**, and call **redirect()**. This action will start the transaction and redirect the user to the Cashbill payment page. You can also create a **PersonalData** object. The *first name*, *surname*, and *email address* will be automatically filled on the Cashbill page.

```php
<?php
Expand All @@ -63,6 +67,7 @@ class CashbillExample extends Controller
$payload = new Payload();
$payload->setTitle("Example title");
$payload->setAmount(9.5);
$payload->setAdditionalData($productId); //Use this field to link transaction to the item

$personalData = new PersonalData();
$personalData->setEmail("email@example.com");
Expand Down
165 changes: 165 additions & 0 deletions TESTING.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,165 @@
# Testing CashBill Package

This package includes comprehensive tests to ensure everything works correctly, both with mocked data and with real CashBill API integration.

## Test Structure

The test suite is divided into two parts:

### 1. **Unit Tests** (`tests/Unit/`)
Tests that use HTTP mocking to simulate CashBill API responses. No real API calls are made, so these tests run fast and don't require credentials.

**What's tested:**
- Payload creation and validation
- Payment initialization with proper error handling
- Order status updates and detection
- Notification webhook handling
- Event dispatching
- Signature verification

**Run unit tests:**
```bash
vendor/bin/phpunit --testsuite=Unit
```

### 2. **Integration Tests** (`tests/Integration/`)
Tests that make **real API calls** to CashBill's testing environment. These verify that the package works correctly with the actual payment system.

**What's tested:**
- Real payment creation with CashBill API
- Fetching payment details from live system
- Batch payment processing
- End-to-end transaction flow

**Prerequisites:**

1. Copy the example test environment file:
```bash
cp .env.test.example .env.test
```

2. Fill in your CashBill credentials in `.env.test`:
```env
CASHBILL_MODE=dev
CASHBILL_SHOP_ID=your_shop_id_here
CASHBILL_SECRET_KEY=your_secret_key_here
```

You can obtain these values from your CashBill account settings. The `CASHBILL_MODE=dev` ensures you're using the testing environment, so no real money is processed.

**Run integration tests:**
```bash
vendor/bin/phpunit --testsuite=Integration
```

> **Note:** Integration tests will be automatically skipped if credentials are not configured.

## Setup

### 1. Install dependencies

```bash
composer install
```

This will install both production dependencies and dev dependencies (including `orchestra/testbench` for Laravel package testing).

### 2. Run all tests

```bash
# Run everything (unit + integration)
vendor/bin/phpunit

# Run only unit tests (no credentials needed)
vendor/bin/phpunit --testsuite=Unit

# Run integration tests (credentials required)
vendor/bin/phpunit --testsuite=Integration
```

### 3. Run specific test file

```bash
vendor/bin/phpunit tests/Unit/PaymentTest.php
```

## Configuration

Test configuration is located in `phpunit.xml.dist`. Key settings:
- Uses SQLite in-memory database for fast tests
- Loads migrations automatically
- Sets default test environment variables

## Writing Your Own Tests

If you're using this package in your Laravel application, you can test it in two ways:

### Option 1: Mock the HTTP calls (recommended for CI/CD)

```php
use Illuminate\Support\Facades\Http;

Http::fake([
'pay.cashbill.pl/*' => Http::response([
'id' => 'test_order_id',
'redirectUrl' => 'https://pay.cashbill.pl/test/redirect'
], 200)
]);

$payload = new Payload();
$payload->setTitle('Test Order');
$payload->setAmount(10.00);

$payment = new Payment($payload);
$response = $payment->redirect();

// Assert redirect URL
$this->assertEquals('https://pay.cashbill.pl/test/redirect', $response->getTargetUrl());
```

### Option 2: Use real credentials (for manual testing)

Set up your `.env` file with CashBill credentials and create a test route:

```php
Route::get('/test-cashbill', function () {
$payload = new Payload();
$payload->setTitle('Test Payment');
$payload->setAmount(1.00);
$payload->setAdditionalData('manual_test_' . time());

$payment = new Payment($payload);
return $payment->redirect();
});
```

Visit the route in your browser to verify the redirect works correctly.

## CI/CD Integration

For GitHub Actions or other CI systems, you can run tests with secrets:

```yaml
# .github/workflows/tests.yml
- name: Run tests
env:
CASHBILL_MODE: dev
CASHBILL_SHOP_ID: ${{ secrets.CASHBILL_SHOP_ID }}
CASHBILL_SECRET_KEY: ${{ secrets.CASHBILL_SECRET_KEY }}
run: vendor/bin/phpunit
```

## Troubleshooting

### Tests are skipped
If you see "skipped" messages, it means CashBill credentials are not set. Either:
- Set credentials in `.env.test` for integration tests
- Or run only unit tests with `--testsuite=Unit`

### HTTP request failed errors
- Check that your `CASHBILL_SHOP_ID` and `CASHBILL_SECRET_KEY` are correct
- Verify you're in `dev` mode for testing
- Check your internet connection

### Migration errors
Make sure migrations are loaded. The test base class handles this automatically.
20 changes: 18 additions & 2 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
"type": "library",
"license": "MIT",
"minimum-stability": "dev",
"prefer-stable": true,
"authors": [
{
"name": "Bartłomiej Stec"
Expand All @@ -16,7 +17,17 @@
}
},
"require": {
"illuminate/support": "^10.0"
"illuminate/support": "^10.0 || ^11.0 || ^12.0 || ^13.0"
},
"autoload-dev": {
"psr-4": {
"Barstec\\Cashbill\\Tests\\": "tests/"
}
},
"require-dev": {
"phpunit/phpunit": "^11.5",
"orchestra/testbench": "^11.0",
"guzzlehttp/guzzle": "^7.0"
},
"extra": {
"laravel": {
Expand All @@ -27,5 +38,10 @@
"Cashbill": "Barstec\\Cashbill\\CashbillFacade"
}
}
},
"scripts": {
"test": "vendor/bin/phpunit",
"test:unit": "vendor/bin/phpunit --testsuite=Unit",
"test:integration": "vendor/bin/phpunit --testsuite=Integration"
}
}
}
31 changes: 31 additions & 0 deletions phpunit.xml.dist
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
<?xml version="1.0" encoding="UTF-8"?>
<phpunit xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:noNamespaceSchemaLocation="https://schema.phpunit.de/10.0/phpunit.xsd"
bootstrap="vendor/autoload.php"
colors="true"
cacheDirectory=".phpunit.cache"
>
<testsuites>
<testsuite name="Unit">
<directory suffix="Test.php">./tests/Unit</directory>
</testsuite>
<testsuite name="Integration">
<directory suffix="Test.php">./tests/Integration</directory>
</testsuite>
</testsuites>

<source>
<include>
<directory suffix=".php">./src</directory>
</include>
</source>

<php>
<env name="APP_KEY" value="base64:test12345678901234567890123456789012="/>
<env name="DB_CONNECTION" value="sqlite"/>
<env name="DB_DATABASE" value=":memory:"/>
<env name="CASHBILL_MODE" value="dev"/>
<env name="CASHBILL_SHOP_ID" value=""/>
<env name="CASHBILL_SECRET_KEY" value="test_secret_key"/>
</php>
</phpunit>
1 change: 0 additions & 1 deletion src/Order.php
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,6 @@ protected function createPersonalData(array $data): PersonalData

protected function createPaymentDetails(array $cashbillResponse): PaymentDetails
{
//dd($cashbillResponse);
$paymentDetails = new PaymentDetails();
$paymentDetails->setOrderId($this->orderId);
$paymentDetails->setPaymentChannel($cashbillResponse['paymentChannel']);
Expand Down
Loading