Skip to content

Commit

Permalink
Merge pull request #701 from mollie/feature/add-auto-pagination-iterator
Browse files Browse the repository at this point in the history
Feature/add auto pagination iterator
  • Loading branch information
Naoray authored Nov 6, 2023
2 parents feb6d52 + 1e54ac4 commit b2934d7
Show file tree
Hide file tree
Showing 40 changed files with 1,851 additions and 82 deletions.
57 changes: 57 additions & 0 deletions examples/pagination/backwards.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
<?php
/*
* How to use pagination with the Mollie API.
*
* pagination is supported on:
* - balances
* - balanceTransactions
* - chargebacks
* - clients
* - clientLinks
* - customers
* - invoices
* - mandates
* - orders
* - paymentCaptures
* - paymentChargebacks
* - payments
* - paymentLinks
* - paymentRefunds
* - profiles
* - refunds
* - settlementCaptures
* - settlementChargebacks
* - settlementPayments
* - settlementRefunds
* - settlements
* - subscriptions
* - terminals
*/

try {
/*
* Initialize the Mollie API library with your API key or OAuth access token.
*/
require "../initialize.php";

$orderId = 'ord_8wmqcHMN4U';

// cursor paginating backwards through all orders
$page = $mollie->orders->page($orderId);

while ($page->hasPrevious()) {
foreach ($page as $order) {
echo($order->id);
}

$page = $page->previous();
}

// iterating backwards using the iterator by passing iterateBackwards = true
// in php 8.0+ you could also use the named parameter syntax iterator(iterateBackwards: true)
foreach ($mollie->orders->iterator(null, null, [], true) as $order) {
echo($order->id);
}
} catch (\Mollie\Api\Exceptions\ApiException $e) {
echo "API call failed: " . htmlspecialchars($e->getMessage());
}
56 changes: 56 additions & 0 deletions examples/pagination/basic_usage.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
<?php
/*
* How to use pagination with the Mollie API.
*
* pagination is supported on:
* - balances
* - balanceTransactions
* - chargebacks
* - clients
* - clientLinks
* - customers
* - invoices
* - mandates
* - orders
* - paymentCaptures
* - paymentChargebacks
* - payments
* - paymentLinks
* - paymentRefunds
* - profiles
* - refunds
* - settlementCaptures
* - settlementChargebacks
* - settlementPayments
* - settlementRefunds
* - settlements
* - subscriptions
* - terminals
*/

try {
/*
* Initialize the Mollie API library with your API key or OAuth access token.
*/
require "../initialize.php";


// cursor paginating through all orders
$page = $mollie->orders->page();

while ($page->hasNext()) {
foreach ($page as $order) {
echo($order->id);
}

$page = $page->next();
}


// using the iterator we can iterate over all orders directly
foreach ($mollie->orders->iterator() as $order) {
echo($order->id);
}
} catch (\Mollie\Api\Exceptions\ApiException $e) {
echo "API call failed: " . htmlspecialchars($e->getMessage());
}
18 changes: 17 additions & 1 deletion src/Endpoints/BalanceEndpoint.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace Mollie\Api\Endpoints;

use Generator;
use Mollie\Api\Exceptions\ApiException;
use Mollie\Api\Resources\Balance;
use Mollie\Api\Resources\BalanceCollection;
Expand Down Expand Up @@ -45,7 +46,7 @@ protected function getResourceObject()
public function get(string $balanceId, array $parameters = [])
{
if (empty($balanceId) || strpos($balanceId, self::RESOURCE_ID_PREFIX) !== 0) {
throw new ApiException("Invalid balance ID: '{$balanceId}'. A balance ID should start with '".self::RESOURCE_ID_PREFIX."'.");
throw new ApiException("Invalid balance ID: '{$balanceId}'. A balance ID should start with '" . self::RESOURCE_ID_PREFIX . "'.");
}

return parent::rest_read($balanceId, $parameters);
Expand Down Expand Up @@ -79,4 +80,19 @@ public function page(?string $from = null, ?int $limit = null, array $parameters
{
return $this->rest_list($from, $limit, $parameters);
}

/**
* Create an iterator for iterating over balances retrieved from Mollie.
*
* @param string $from The first Balance ID you want to include in your list.
* @param int $limit
* @param array $parameters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
*
* @return Generator
*/
public function iterator(?string $from = null, ?int $limit = null, array $parameters = [], bool $iterateBackwards = false): Generator
{
return $this->rest_iterator($from, $limit, $parameters, $iterateBackwards);
}
}
46 changes: 46 additions & 0 deletions src/Endpoints/BalanceTransactionEndpoint.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@

namespace Mollie\Api\Endpoints;

use Generator;
use Mollie\Api\Resources\Balance;
use Mollie\Api\Resources\BalanceTransaction;
use Mollie\Api\Resources\BalanceTransactionCollection;
Expand Down Expand Up @@ -50,6 +51,20 @@ public function listFor(Balance $balance, array $parameters = [])
return $this->listForId($balance->id, $parameters);
}

/**
* Create an iterator for iterating over balance transactions for the given balance retrieved from Mollie.
*
* @param Balance $balance
* @param array $parameters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
*
* @return Generator
*/
public function iteratorFor(Balance $balance, array $parameters = [], bool $iterateBackwards = false): Generator
{
return $this->iteratorForId($balance->id, $parameters, $iterateBackwards);
}

/**
* List the transactions for a specific Balance ID.
*
Expand All @@ -66,6 +81,22 @@ public function listForId(string $balanceId, array $parameters = [])
return parent::rest_list(null, null, $parameters);
}

/**
* Create an iterator for iterating over balance transactions for the given balance id retrieved from Mollie.
*
* @param string $balanceId
* @param array $parameters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
*
* @return Generator
*/
public function iteratorForId(string $balanceId, array $parameters = [], bool $iterateBackwards = false): Generator
{
$this->parentId = $balanceId;

return $this->rest_iterator(null, null, $parameters, $iterateBackwards);
}

/**
* List the transactions for the primary Balance.
*
Expand All @@ -80,4 +111,19 @@ public function listForPrimary(array $parameters = [])

return parent::rest_list(null, null, $parameters);
}

/**
* Create an iterator for iterating over transactions for the primary balance retrieved from Mollie.
*
* @param array $parameters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
*
* @return Generator
*/
public function iteratorForPrimary(array $parameters = [], bool $iterateBackwards = false): Generator
{
$this->parentId = "primary";

return $this->rest_iterator(null, null, $parameters, $iterateBackwards);
}
}
18 changes: 17 additions & 1 deletion src/Endpoints/ChargebackEndpoint.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace Mollie\Api\Endpoints;

use Generator;
use Mollie\Api\Exceptions\ApiException;
use Mollie\Api\Resources\Chargeback;
use Mollie\Api\Resources\ChargebackCollection;
Expand Down Expand Up @@ -43,8 +44,23 @@ protected function getResourceCollectionObject($count, $_links)
* @return ChargebackCollection
* @throws ApiException
*/
public function page($from = null, $limit = null, array $parameters = [])
public function page(?string $from = null, ?int $limit = null, array $parameters = [])
{
return $this->rest_list($from, $limit, $parameters);
}

/**
* Create an iterator for iterating over chargeback retrieved from Mollie.
*
* @param string $from The first chargevback ID you want to include in your list.
* @param int $limit
* @param array $parameters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
*
* @return Generator
*/
public function iterator(?string $from = null, ?int $limit = null, array $parameters = [], bool $iterateBackwards = false): Generator
{
return $this->rest_iterator($from, $limit, $parameters, $iterateBackwards);
}
}
18 changes: 17 additions & 1 deletion src/Endpoints/ClientEndpoint.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace Mollie\Api\Endpoints;

use Generator;
use Mollie\Api\Exceptions\ApiException;
use Mollie\Api\Resources\Client;
use Mollie\Api\Resources\ClientCollection;
Expand Down Expand Up @@ -62,8 +63,23 @@ public function get($clientId, array $parameters = [])
* @return ClientCollection
* @throws ApiException
*/
public function page($from = null, $limit = null, array $parameters = [])
public function page(?string $from = null, ?int $limit = null, array $parameters = [])
{
return $this->rest_list($from, $limit, $parameters);
}

/**
* Create an iterator for iterating over clients retrieved from Mollie.
*
* @param string $from The first client ID you want to include in your list.
* @param int $limit
* @param array $parameters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
*
* @return Generator
*/
public function iterator(?string $from = null, ?int $limit = null, array $parameters = [], bool $iterateBackwards = false): Generator
{
return $this->rest_iterator($from, $limit, $parameters, $iterateBackwards);
}
}
25 changes: 24 additions & 1 deletion src/Endpoints/CollectionEndpointAbstract.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@

namespace Mollie\Api\Endpoints;

use Generator;
use Mollie\Api\Exceptions\ApiException;
use Mollie\Api\Resources\BaseCollection;
use Mollie\Api\Resources\CursorCollection;
use Mollie\Api\Resources\ResourceFactory;

abstract class CollectionEndpointAbstract extends EndpointAbstract
Expand All @@ -18,7 +20,7 @@ abstract class CollectionEndpointAbstract extends EndpointAbstract
* @return mixed
* @throws ApiException
*/
protected function rest_list($from = null, $limit = null, array $filters = [])
protected function rest_list(?string $from = null, ?int $limit = null, array $filters = [])
{
$filters = array_merge(["from" => $from, "limit" => $limit], $filters);

Expand All @@ -36,6 +38,27 @@ protected function rest_list($from = null, $limit = null, array $filters = [])
return $collection;
}

/**
* Create a generator for iterating over a resource's collection using REST API calls.
*
* This function fetches paginated data from a RESTful resource endpoint and returns a generator
* that allows you to iterate through the items in the collection one by one. It supports forward
* and backward iteration, pagination, and filtering.
*
* @param string $from The first resource ID you want to include in your list.
* @param int $limit
* @param array $filters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
* @return Generator
*/
protected function rest_iterator(?string $from = null, ?int $limit = null, array $filters = [], bool $iterateBackwards = false): Generator
{
/** @var CursorCollection $page */
$page = $this->rest_list($from, $limit, $filters);

return $page->getAutoIterator($iterateBackwards);
}

/**
* Get the collection object that is used by this API endpoint. Every API endpoint uses one type of collection object.
*
Expand Down
20 changes: 18 additions & 2 deletions src/Endpoints/CustomerEndpoint.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@

namespace Mollie\Api\Endpoints;

use Generator;
use Mollie\Api\Exceptions\ApiException;
use Mollie\Api\Resources\Customer;
use Mollie\Api\Resources\CustomerCollection;
Expand Down Expand Up @@ -81,7 +82,7 @@ public function get($customerId, array $parameters = [])
public function update($customerId, array $data = [])
{
if (empty($customerId) || strpos($customerId, self::RESOURCE_ID_PREFIX) !== 0) {
throw new ApiException("Invalid order ID: '{$customerId}'. An order ID should start with '".self::RESOURCE_ID_PREFIX."'.");
throw new ApiException("Invalid order ID: '{$customerId}'. An order ID should start with '" . self::RESOURCE_ID_PREFIX . "'.");
}

return parent::rest_update($customerId, $data);
Expand Down Expand Up @@ -114,8 +115,23 @@ public function delete($customerId, array $data = [])
* @return CustomerCollection
* @throws ApiException
*/
public function page($from = null, $limit = null, array $parameters = [])
public function page(?string $from = null, ?int $limit = null, array $parameters = [])
{
return $this->rest_list($from, $limit, $parameters);
}

/**
* Create an iterator for iterating over customers retrieved from Mollie.
*
* @param string $from The first customer ID you want to include in your list.
* @param int $limit
* @param array $parameters
* @param bool $iterateBackwards Set to true for reverse order iteration (default is false).
*
* @return Generator
*/
public function iterator(?string $from = null, ?int $limit = null, array $parameters = [], bool $iterateBackwards = false): Generator
{
return $this->rest_iterator($from, $limit, $parameters, $iterateBackwards);
}
}
Loading

0 comments on commit b2934d7

Please sign in to comment.