Skip to content

Commit

Permalink
Subscriptions resource implementation - #35
Browse files Browse the repository at this point in the history
* Maintain exception bubbling via PHPDoc `throws` tag.
* Consolidate sub-resources under their parent `Buyer` and `Refund` are sub-resources of `Invoice`, thus it is pragmatic to implement and test them within their parent's context.
* Relocate Rates resource actions trait to correct directory.
* Deprecate `Item()` in favor of `BillItem()` Discourage ambiguity of a BitPay `Item` where Bills and Subscriptions are concerned.
* Define commonly used BitPay constants, primarily to prevent typos.
* Subscriptions resource implementation.
* Update README
  • Loading branch information
alexstewartja authored Nov 13, 2021
1 parent c64d54c commit b156762
Show file tree
Hide file tree
Showing 18 changed files with 507 additions and 244 deletions.
125 changes: 109 additions & 16 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
# Laravel + BitPay Integration
# LaravelBitPay

![LaravelBitPay Social Image](https://banners.beyondco.de/Laravel%20BitPay.png?theme=light&packageManager=composer+require&packageName=vrajroham%2Flaravel-bitpay&pattern=circuitBoard&style=style_1&description=Transact+in+Bitcoin%2C+Bitcoin+Cash+and+10%2B+other+BitPay-supported+cryptocurrencies+within+your+Laravel+application.&md=1&showWatermark=0&fontSize=100px&images=https%3A%2F%2Flaravel.com%2Fimg%2Flogomark.min.svg)

[![Latest Version on Packagist](https://img.shields.io/packagist/v/vrajroham/laravel-bitpay.svg?style=for-the-badge)](https://packagist.org/packages/vrajroham/laravel-bitpay)
[![Build Status](https://img.shields.io/travis/vrajroham/laravel-bitpay/master.svg?style=for-the-badge)](https://travis-ci.org/vrajroham/laravel-bitpay)
Expand All @@ -17,7 +19,7 @@ LaravelBitpay enables you and your business to transact in Bitcoin, Bitcoin Cash
- :hourglass_flowing_sand: [Recipients](https://bitpay.com/api/#rest-api-resources-recipients)
- :hourglass_flowing_sand: [Payouts](https://bitpay.com/api/#rest-api-resources-payouts)
- :white_check_mark: [Bills](https://bitpay.com/api/#rest-api-resources-bills)
- :hourglass_flowing_sand: [Subscriptions](https://bitpay.com/api/#rest-api-resources-subscriptions)
- :white_check_mark: [Subscriptions](https://bitpay.com/api/#rest-api-resources-subscriptions)
- :white_check_mark: [Rates](https://bitpay.com/api/#rest-api-resources-rates)
- :hourglass_flowing_sand: [Sessions](https://bitpay.com/api/#rest-api-resources-sessions)
- :white_check_mark: [Currencies](https://bitpay.com/api/#rest-api-resources-currencies)
Expand Down Expand Up @@ -45,6 +47,11 @@ LaravelBitpay enables you and your business to transact in Bitcoin, Bitcoin Cash
+ [Retrieve a list of existing bills](#retrieve-a-list-of-existing-bills)
+ [Update a bill](#update-a-bill)
+ [Deliver a bill via email](#deliver-a-bill-via-email)
+ [Subscriptions](#subscriptions)
+ [Create a subscription](#create-a-subscription)
+ [Retrieve a subscription](#retrieve-a-subscription)
+ [Retrieve a list of existing subscriptions](#retrieve-a-list-of-existing-subscriptions)
+ [Update a subscription](#update-a-subscription)
+ [Currencies](#currencies)
+ [Retrieve the supported currencies](#retrieve-the-supported-currencies)
+ [Rates](#rates)
Expand Down Expand Up @@ -328,7 +335,7 @@ In the following example, we create a bill that's due in 10 days:
$billData = LaravelBitpay::Bill();
$billData->setNumber('bill1234-EFGH');
$billData->setCurrency(Currency::USD); // Always use the BitPay Currency model to prevent typos
$dueDate = date('Y-m-d\TH:i:s\Z', strtotime('+10 days')); // ISO-8601 formatted date
$dueDate = date(BitPayConstants::DATETIME_FORMAT, strtotime('+10 days')); // ISO-8601 formatted date
$billData->setDueDate($dueDate);
$billData->setPassProcessingFee(true); // Let the recipient shoulder BitPay's processing fee

Expand All @@ -345,12 +352,12 @@ $billData->setCc(['[email protected]']);
$billData->setPhone('555-123-456');

// Prepare Bill's line item(s)
$itemUno = LaravelBitpay::Item();
$itemUno = LaravelBitpay::BillItem();
$itemUno->setDescription('Squid Game "Front Man" Costume');
$itemUno->setPrice(49.99);
$itemUno->setQuantity(2);

$itemDos = LaravelBitpay::Item();
$itemDos = LaravelBitpay::BillItem();
$itemDos->setDescription('GOT "House Stark" Sterling Silver Pendant');
$itemDos->setPrice(35);
$itemDos->setQuantity(1);
Expand Down Expand Up @@ -381,10 +388,7 @@ $bill = LaravelBitpay::getBill('bill1234-EFGH');
You can narrow down the retrieved list by specifying a Bill status:

```php
// Status can be "draft", "sent", "new", "paid", or "complete"
$status = 'paid';

$paidBills = LaravelBitpay::getBills($status);
$paidBills = LaravelBitpay::getBills(BitPayConstants::BILL_STATUS_PAID);
```

#### Update a bill
Expand All @@ -396,33 +400,121 @@ $existingBill = LaravelBitpay::getBill('bill1234-EFGH');
$existingItems = $existingBill->getItems();

$billData = LaravelBitpay::Bill();
$billData->setId($existingBill->getId());

$itemTres = LaravelBitpay::Item();
$itemTres = LaravelBitpay::BillItem();
$itemTres->setDescription('The Tomorrow War "White Spike" Life-Size Wax Figure');
$itemTres->setPrice(189.99);
$itemTres->setQuantity(1);

$billData->setItems(array_merge($existingItems, [$itemTres]));

// Update Bill
$updatedBill = LaravelBitpay::updateBill($billData, 'bill1234-EFGH');
$updatedBill = LaravelBitpay::updateBill($billData, $billData->getId());
```

#### Deliver a bill via email

```php
$bill = LaravelBitpay::getBill('bill1234-EFGH');

$billId = $bill->getId();
$billToken = $bill->getToken();

$billDelivery = json_decode(LaravelBitpay::deliverBill($billId, $billToken));
$billDelivery = LaravelBitpay::deliverBill($bill->getId(), $bill->getToken());

if (isset($billDelivery->data) && $billDelivery->data == 'Success') {
if ($billDelivery === 'Success') {
// Bill delivered successfully. Do something about that... or not.
}
```

### Subscriptions

Subscriptions are repeat billing agreements with specific buyers. BitPay sends bill emails to buyers identified in active subscriptions according to the specified schedule.

#### Create a subscription

Let's create a subscription that's delivered on the 28th of each month and due on the first of the following month, at 9 AM, respectively:

```php
// Initialize Subscription
$subscriptionData = LaravelBitpay::Subscription();
$subscriptionData->setSchedule(BitPayConstants::SUBSCRIPTION_SCHEDULE_MONTHLY);

// Optional recurring bill data
$billData = [
'number' => 'subscription1234-ABCD',
'name' => 'John Doe',
'address1' => '2630 Hegal Place',
'address2' => 'Apt 42',
'city' => 'Alexandria',
'state' => 'VA',
'zip' => 23242,
'country' => 'US',
'cc' => ['[email protected]'],
'phone' => '555-123-456',
'passProcessingFee' => true,
];

$dueDate = date(BitPayConstants::DATETIME_FORMAT, strtotime('first day of next month 9 AM'));

$billItems = array(
LaravelBitpay::SubscriptionItem(100.00, 1, 'Web Hosting - 4 CPUs | 16GB Memory | 400GB SSD'),
LaravelBitpay::SubscriptionItem(80.00, 1, 'Basic Website Maintenance'),
);

// Autofill optional bill data
$mapper = new JsonMapper();
$billData = $mapper->map(
$billData,
LaravelBitpay::BillData(
Currency::USD, // Always use the BitPay Currency model to prevent typos
'[email protected]',
$dueDate,
$billItems
)
);

$subscriptionData->setBillData($billData);

// A little wizardry to always get the 28th day of the current month (leap year safe)
$deliveryDate = strtotime('first day of this month 9 AM');
$deliveryDate = new \DateTime("@$deliveryDate");
$deliveryDate = $deliveryDate->modify('+27 days')->getTimestamp();
$deliveryDate = date(BitPayConstants::DATETIME_FORMAT, $deliveryDate);

$subscriptionData->setNextDelivery($deliveryDate);

// Create the Subscription on BitPay
$subscription = LaravelBitpay::createSubscription($subscriptionData);

// You may then store the Subscription ID for future reference
$subscriptionId = $subscription->getId();
```

#### Retrieve a subscription

```php
$subscription = LaravelBitpay::getSubscription('6gqe8y5mkc5Qx2a9zmspgx');
```

#### Retrieve a list of existing subscriptions

You can narrow down the retrieved list by specifying a Subscription status:

```php
$activeSubscriptions = LaravelBitpay::getSubscriptions(BitPayConstants::SUBSCRIPTION_STATUS_ACTIVE);
```

#### Update a subscription

In this example we activate a Subscription by updating its status:

```php
$subscriptionData = LaravelBitpay::Subscription();
$subscriptionData->setId('6gqe8y5mkc5Qx2a9zmspgx');
$subscriptionData->setStatus(BitPayConstants::SUBSCRIPTION_STATUS_ACTIVE);

$activatedSubscription = LaravelBitpay::updateSubscription($subscriptionData, $subscriptionData->getId());
```

### Currencies

Currencies are fiat currencies supported by BitPay.
Expand Down Expand Up @@ -462,6 +554,7 @@ If you discover any security related issues, please email [email protected]
## Credits

- [Vaibhavraj Roham](https://github.com/vrajroham)
- [Alex Stewart](https://github.com/alexstewartja)
- [All Contributors](../../contributors)

## License
Expand Down
36 changes: 35 additions & 1 deletion src/Actions/ManageBills.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
namespace Vrajroham\LaravelBitpay\Actions;

use BitPaySDK\Model\Bill\Bill;
use BitPaySDK\Model\Bill\Item;


trait ManageBills
{
Expand All @@ -18,12 +20,32 @@ public static function Bill(): Bill
return new Bill();
}

/**
* @return Item A BitPay Bill Item
* @deprecated Use <code>LaravelBitpay::BillItem()</code> instead.
*/
public static function Item(): Item
{
return new Item();
}

/**
* @return Item A BitPay Bill Item
*/
public static function BillItem(): Item
{
return new Item();
}

/**
* Create a BitPay Bill.
*
* @link https://bitpay.com/api/#rest-api-resources-bills-create-a-bill
*
* @param $bill Bill A Bill object with request parameters defined.
*
* @return Bill A BitPay generated Bill object.
* @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
*/
public static function createBill(Bill $bill): Bill
{
Expand All @@ -34,8 +56,11 @@ public static function createBill(Bill $bill): Bill
* Retrieve a BitPay bill by its id.
*
* @link https://bitpay.com/api/#rest-api-resources-bills-retrieve-a-bill
*
* @param $billId string The id of the bill to retrieve.
*
* @return Bill A BitPay Bill object.
* @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
*/
public static function getBill(string $billId): Bill
{
Expand All @@ -46,8 +71,11 @@ public static function getBill(string $billId): Bill
* Retrieve a collection of BitPay bills.
*
* @link https://bitpay.com/api/#rest-api-resources-bills-retrieve-bills-by-status
*
* @param $status string|null The status to filter the bills.
*
* @return array A list of BitPay Bill objects.
* @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
*/
public static function getBills(string $status = null): array
{
Expand All @@ -58,9 +86,12 @@ public static function getBills(string $status = null): array
* Update a BitPay Bill.
*
* @link https://bitpay.com/api/#rest-api-resources-bills-update-a-bill
*
* @param $bill Bill A Bill object with the parameters to update defined.
* @param $billId string The ID of the Bill to update.
*
* @return Bill An updated Bill object.
* @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
*/
public static function updateBill(Bill $bill, string $billId): Bill
{
Expand All @@ -71,12 +102,15 @@ public static function updateBill(Bill $bill, string $billId): Bill
* Deliver a BitPay Bill.
*
* @link https://bitpay.com/api/#rest-api-resources-bills-deliver-a-bill-via-email
*
* @param $billId string The id of the requested bill.
* @param $billToken string The token of the requested bill.
*
* @return string A response status returned from the API.
* @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
*/
public static function deliverBill(string $billId, string $billToken): string
{
return (new self())->client->deliverBill($billId, $billToken);
}
}
}
16 changes: 0 additions & 16 deletions src/Actions/ManageBuyers.php

This file was deleted.

31 changes: 1 addition & 30 deletions src/Actions/ManageCurrencies.php
Original file line number Diff line number Diff line change
Expand Up @@ -28,39 +28,10 @@ public static function Currency(string $code = null): Currency
*
* @link https://bitpay.com/api/#rest-api-resources-currencies-retrieve-the-supported-currencies
* @return array A list of supported BitPay Currency objects.
* @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
*/
public static function getCurrencies(): array
{
return (new self())->client->getCurrencies();
}

// TODO: Implement the following if/when upstream gets merged: https://github.com/bitpay/php-bitpay-client-v2/pull/67
// /**
// * Retrieve all the rates for a given cryptocurrency
// *
// * @link https://bitpay.com/api/#rest-api-resources-rates-retrieve-all-the-rates-for-a-given-cryptocurrency
// * @param string $baseCurrency The cryptocurrency for which you want to fetch the rates.
// * Current supported values are BTC, BCH, ETH, XRP, DOGE and LTC
// * @return \BitPaySDK\Model\Rate\Rates A Rates object populated with the currency rates for the requested baseCurrency.
// * @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
// */
// public static function getCurrencyRates(string $baseCurrency): Rates
// {
// return (new self())->client->getCurrencyRates($baseCurrency);
// }
//
// /**
// * Retrieve the rate for a cryptocurrency / fiat pair
// *
// * @link https://bitpay.com/api/#rest-api-resources-rates-retrieve-the-rates-for-a-cryptocurrency-fiat-pair
// * @param string $baseCurrency The cryptocurrency for which you want to fetch the fiat-equivalent rate.
// * Current supported values are BTC, BCH, ETH, XRP, DOGE and LTC
// * @param string $currency The fiat currency for which you want to fetch the baseCurrency rate
// * @return \BitPaySDK\Model\Rate\Rate A Rate object populated with the currency rate for the requested baseCurrency.
// * @throws \BitPaySDK\Exceptions\BitPayException BitPayException class
// */
// public static function getCurrencyPairRate(string $baseCurrency, string $currency): Rate
// {
// return (new self())->client->getCurrencyPairRate($baseCurrency, $currency);
// }
}
Loading

0 comments on commit b156762

Please sign in to comment.