Skip to content

Commit

Permalink
Merge pull request #235 from mollie/pimm/v3.6.0
Browse files Browse the repository at this point in the history
Implement iteration API, in addition to pagination API.
  • Loading branch information
Pimm committed Nov 17, 2021
2 parents 8bdc1b4 + feaa16e commit 39679f2
Show file tree
Hide file tree
Showing 84 changed files with 18,909 additions and 1,017 deletions.
26 changes: 26 additions & 0 deletions jest.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
const nockfulTests = ['iteration'];

function createProject(displayName, testRegex, rest) {
return Object.assign({}, rest, {
testEnvironment: 'node',
setupFilesAfterEnv: ['jest-bluster'],
displayName,
testRegex
});
}

const projects = [
createProject('nockless tests', `/tests/(?!${nockfulTests.join('|')}).*/.+\\.test\\.[jt]s$`)
];

// Only execute the Nockful tests on Node.js 8+.
if (parseInt(process.version.substring(1)) >= 8) {
projects.push(createProject('nockful tests', `/tests/(?:${nockfulTests.join('|')}).*/.+\\.test\\.[jt]s$`));
}

module.exports = {
projects,
transform: {
'\\.[jt]s$': 'babel-jest'
}
};
25 changes: 3 additions & 22 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -62,35 +62,16 @@
"eslint-plugin-prettier": "^3.4.0",
"jest": "24.9.0",
"jest-bluster": "^1.0.1",
"nock": "^13.2.1",
"nock-record": "^0.3.9",
"prettier": "^2.3.2",
"rollup": "^2.55.1",
"rollup-plugin-babel": "^4.4.0",
"rollup-plugin-json": "^4.0.0",
"rollup-plugin-node-resolve": "^5.2.0",
"ruply": "^1.0.0",
"typescript": "^4.3.5"
},
"jest": {
"testEnvironment": "node",
"moduleDirectories": [
"node_modules",
"dist",
"src"
],
"moduleFileExtensions": [
"ts",
"js"
],
"transform": {
"^.+\\.(js|jsx|ts|tsx)$": "babel-jest",
"^.+\\.pem$": "<rootDir>/tests/unit/__stubs__/fileTransformer.js"
},
"testMatch": [
"<rootDir>/tests/**/*.test.ts"
],
"setupFilesAfterEnv": [
"jest-bluster"
]
},
"config": {
"commitizen": {
"path": "cz-conventional-changelog"
Expand Down
17 changes: 2 additions & 15 deletions src/binders/Binder.ts
Original file line number Diff line number Diff line change
@@ -1,20 +1,7 @@
// If support for Node.js < 10.0.0 is ever dropped, this import can be removed.
import { URL } from 'url';

import parseQueryInUrl from '../communication/parseQueryInUrl';
import List from '../data/list/List';
import buildFromEntries from '../plumbing/buildFromEntries';
import Maybe from '../types/Maybe';

/**
* Returns the parsed search parameters from the passed URL. For example: `'https://example.com?id=5'` is converted to
* `{ id: 5 }` (and `'https://example.com'` is converted to `{}`).
*
* If multiple parameters have the same key (`'https://example.com?id=5&id=6'`), exactly one of them will be
* represented in the returned object.
*/
function parseQueryInUrl(url: string) {
return buildFromEntries(new URL(url).searchParams);
}
/**
* A binder is the interface for a certain type of information. There is a binder for orders, and one for customers, et
* cetera.
Expand All @@ -23,7 +10,7 @@ export default class Binder<R, T extends R> {
/**
* Injects `nextPage`, `nextPageCursor`, `previousPage`, and `previousPageCursor` into the passed list.
*/
protected injectPaginationHelpers<P>(input: Array<T> & Pick<List<T>, 'count' | 'links'>, list: (parameters: P) => Promise<List<T>>, selfParameters: P): List<T> {
protected injectPaginationHelpers<P>(input: Array<T> & Pick<List<T>, 'count' | 'links'>, list: (parameters: P) => Promise<List<T>>, selfParameters: P = {} as P): List<T> {
const { links } = input;
let nextPage: Maybe<() => Promise<List<T>>>;
let nextPageCursor: Maybe<string>;
Expand Down
2 changes: 1 addition & 1 deletion src/binders/applePay/ApplePayBinder.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import NetworkClient from '../../communication/NetworkClient';
import ApplePaySession from '../../data/applePaySession/ApplePaySession';
import NetworkClient from '../../NetworkClient';
import renege from '../../plumbing/renege';
import Callback from '../../types/Callback';
import { RequestPaymentSessionParameters } from './parameters';
Expand Down
15 changes: 14 additions & 1 deletion src/binders/chargebacks/ChargebacksBinder.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
import TransformingNetworkClient from '../../communication/TransformingNetworkClient';
import Chargeback, { ChargebackData, transform } from '../../data/chargebacks/Chargeback';
import List from '../../data/list/List';
import HelpfulIterator from '../../plumbing/HelpfulIterator';
import renege from '../../plumbing/renege';
import TransformingNetworkClient from '../../TransformingNetworkClient';
import Callback from '../../types/Callback';
import InnerBinder from '../InnerBinder';
import { ListParameters } from './parameters';
Expand Down Expand Up @@ -48,4 +49,16 @@ export default class ChargebacksBinder extends InnerBinder<ChargebackData, Charg
if (renege(this, this.page, ...arguments)) return;
return this.networkClient.list<ChargebackData, Chargeback>(pathSegment, 'chargebacks', parameters).then(result => this.injectPaginationHelpers(result, this.page, parameters));
}

/**
* Retrieve all received chargebacks. If the payment-specific endpoint is used, only chargebacks for that specific payment are returned.
*
* The results are paginated. See pagination for more information.
*
* @since 3.6.0
* @see https://docs.mollie.com/reference/v2/chargebacks-api/list-chargebacks
*/
public iterate(parameters?: Omit<ListParameters, 'limit'>): HelpfulIterator<Chargeback> {
return this.networkClient.iterate<ChargebackData, Chargeback>(pathSegment, 'chargebacks', { ...parameters, limit: 64 });
}
}
4 changes: 2 additions & 2 deletions src/binders/chargebacks/parameters.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { ChargebackEmbed } from '../../data/chargebacks/Chargeback';
import { CommonListParameters } from '../../types/parameters';
import { PaginationParameters } from '../../types/parameters';

export type ListParameters = CommonListParameters & {
export type ListParameters = PaginationParameters & {
embed?: ChargebackEmbed[];
};
16 changes: 14 additions & 2 deletions src/binders/customers/CustomersBinder.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import TransformingNetworkClient from '../../communication/TransformingNetworkClient';
import Customer, { CustomerData } from '../../data/customers/Customer';
import List from '../../data/list/List';
import ApiError from '../../errors/ApiError';
import checkId from '../../plumbing/checkId';
import renege from '../../plumbing/renege';
import TransformingNetworkClient from '../../TransformingNetworkClient';
import Callback from '../../types/Callback';
import Binder from '../Binder';
import { CreateParameters, DeleteParameters, GetParameters, ListParameters, UpdateParameters } from './parameters';
Expand Down Expand Up @@ -84,11 +84,23 @@ export default class CustomersBinder extends Binder<CustomerData, Customer> {
*/
public page(parameters?: ListParameters): Promise<List<Customer>>;
public page(parameters: ListParameters, callback: Callback<List<Customer>>): void;
public page(parameters: ListParameters = {}) {
public page(parameters?: ListParameters) {
if (renege(this, this.page, ...arguments)) return;
return this.networkClient.list<CustomerData, Customer>(pathSegment, 'customers', parameters).then(result => this.injectPaginationHelpers(result, this.page, parameters));
}

/**
* Retrieve all customers created.
*
* The results are paginated. See pagination for more information.
*
* @since 3.6.0
* @see https://docs.mollie.com/reference/v2/customers-api/list-customers
*/
public iterate(parameters?: Omit<ListParameters, 'limit'>) {
return this.networkClient.iterate<CustomerData, Customer>(pathSegment, 'customers', { ...parameters, limit: 64 });
}

/**
* Update an existing customer.
*
Expand Down
20 changes: 19 additions & 1 deletion src/binders/customers/mandates/CustomerMandatesBinder.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import TransformingNetworkClient from '../../../communication/TransformingNetworkClient';
import { MandateData } from '../../../data/customers/mandates/data';
import Mandate from '../../../data/customers/mandates/Mandate';
import List from '../../../data/list/List';
import ApiError from '../../../errors/ApiError';
import checkId from '../../../plumbing/checkId';
import renege from '../../../plumbing/renege';
import TransformingNetworkClient from '../../../TransformingNetworkClient';
import Callback from '../../../types/Callback';
import InnerBinder from '../../InnerBinder';
import { CreateParameters, GetParameters, ListParameters, RevokeParameters } from './parameters';
Expand Down Expand Up @@ -119,6 +119,24 @@ export default class CustomerMandatesBinder extends InnerBinder<MandateData, Man
return this.networkClient.list<MandateData, Mandate>(getPathSegments(customerId), 'mandates', query).then(result => this.injectPaginationHelpers(result, this.page, parameters ?? {}));
}

/**
* Retrieve all mandates for the given `customerId`, ordered from newest to oldest.
*
* The results are paginated. See pagination for more information.
*
* @since 3.6.0
* @see https://docs.mollie.com/reference/v2/mandates-api/list-mandates
*/
public iterate(parameters: Omit<ListParameters, 'limit'>) {
// parameters ?? {} is used here, because in case withParent is used, parameters could be omitted.
const customerId = this.getParentId((parameters ?? {}).customerId);
if (!checkId(customerId, 'customer')) {
throw new ApiError('The customer id is invalid');
}
const { customerId: _, ...query } = parameters ?? {};
return this.networkClient.iterate<MandateData, Mandate>(getPathSegments(customerId), 'mandates', { ...query, limit: 64 });
}

/**
* Revoke a customer's mandate. You will no longer be able to charge the consumer's bank account or credit card with this mandate and all connected subscriptions will be canceled.
*
Expand Down
4 changes: 2 additions & 2 deletions src/binders/customers/mandates/parameters.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { MandateData } from '../../../data/customers/mandates/data';
import { CommonListParameters } from '../../../types/parameters';
import { PaginationParameters } from '../../../types/parameters';

interface ContextParameters {
customerId: string;
Expand Down Expand Up @@ -55,6 +55,6 @@ export type CreateParameters = ContextParameters &

export type GetParameters = ContextParameters;

export type ListParameters = ContextParameters & CommonListParameters;
export type ListParameters = ContextParameters & PaginationParameters;

export type RevokeParameters = ContextParameters;
4 changes: 2 additions & 2 deletions src/binders/customers/parameters.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { CustomerData } from '../../data/customers/Customer';
import { CommonListParameters } from '../../types/parameters';
import { PaginationParameters } from '../../types/parameters';
import PickOptional from '../../types/PickOptional';

interface ContextParameters {
Expand All @@ -10,7 +10,7 @@ export type CreateParameters = ContextParameters & PickOptional<CustomerData, 'n

export type GetParameters = ContextParameters;

export type ListParameters = ContextParameters & CommonListParameters;
export type ListParameters = ContextParameters & PaginationParameters;

export type UpdateParameters = ContextParameters & PickOptional<CustomerData, 'name' | 'email' | 'locale' | 'metadata'>;

Expand Down
18 changes: 17 additions & 1 deletion src/binders/customers/payments/CustomerPaymentsBinder.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import TransformingNetworkClient from '../../../communication/TransformingNetworkClient';
import List from '../../../data/list/List';
import { PaymentData } from '../../../data/payments/data';
import Payment from '../../../data/payments/Payment';
import ApiError from '../../../errors/ApiError';
import checkId from '../../../plumbing/checkId';
import renege from '../../../plumbing/renege';
import TransformingNetworkClient from '../../../TransformingNetworkClient';
import Callback from '../../../types/Callback';
import InnerBinder from '../../InnerBinder';
import { CreateParameters, ListParameters } from './parameters';
Expand Down Expand Up @@ -78,4 +78,20 @@ export default class CustomerPaymentsBinder extends InnerBinder<PaymentData, Pay
const { customerId: _, ...query } = parameters ?? {};
return this.networkClient.list<PaymentData, Payment>(getPathSegments(customerId), 'payments', query).then(result => this.injectPaginationHelpers(result, this.page, parameters ?? {}));
}

/**
* Retrieve all Payments linked to the Customer.
*
* @since 3.6.0
* @see https://docs.mollie.com/reference/v2/customers-api/list-customer-payments
*/
public iterate(parameters: Omit<ListParameters, 'limit'>) {
// parameters ?? {} is used here, because in case withParent is used, parameters could be omitted.
const customerId = this.getParentId((parameters ?? {}).customerId);
if (!checkId(customerId, 'customer')) {
throw new ApiError('The customer id is invalid');
}
const { customerId: _, ...query } = parameters ?? {};
return this.networkClient.iterate<PaymentData, Payment>(getPathSegments(customerId), 'payments', { ...query, limit: 64 });
}
}
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import TransformingNetworkClient from '../../../communication/TransformingNetworkClient';
import List from '../../../data/list/List';
import { SubscriptionData } from '../../../data/subscription/data';
import Subscription from '../../../data/subscription/Subscription';
import ApiError from '../../../errors/ApiError';
import checkId from '../../../plumbing/checkId';
import renege from '../../../plumbing/renege';
import TransformingNetworkClient from '../../../TransformingNetworkClient';
import Callback from '../../../types/Callback';
import InnerBinder from '../../InnerBinder';
import { CancelParameters, CreateParameters, GetParameters, ListParameters, UpdateParameters } from './parameters';
Expand Down Expand Up @@ -114,6 +114,22 @@ export default class CustomerSubscriptionsBinder extends InnerBinder<Subscriptio
.then(result => this.injectPaginationHelpers(result, this.page, parameters ?? {}));
}

/**
* Retrieve all subscriptions of a customer.
*
* @since 3.6.0
* @see https://docs.mollie.com/reference/v2/subscriptions-api/list-subscriptions
*/
public iterate(parameters: ListParameters) {
// parameters ?? {} is used here, because in case withParent is used, parameters could be omitted.
const customerId = this.getParentId((parameters ?? {}).customerId);
if (!checkId(customerId, 'customer')) {
throw new ApiError('The customer id is invalid');
}
const { customerId: _, ...query } = parameters ?? {};
return this.networkClient.iterate<SubscriptionData, Subscription>(getPathSegments(customerId), 'subscriptions', { ...query, limit: 64 });
}

/**
* Some fields of a subscription can be updated by calling `PATCH` on the resource endpoint. Each field is optional.
*
Expand Down
4 changes: 2 additions & 2 deletions src/binders/customers/subscriptions/parameters.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { SubscriptionData } from '../../../data/subscription/data';
import { CommonListParameters } from '../../../types/parameters';
import { PaginationParameters } from '../../../types/parameters';
import PickOptional from '../../../types/PickOptional';

interface ContextParameters {
Expand All @@ -13,7 +13,7 @@ export type CreateParameters = ContextParameters &

export type GetParameters = ContextParameters;

export type ListParameters = ContextParameters & CommonListParameters;
export type ListParameters = ContextParameters & PaginationParameters;

export type UpdateParameters = ContextParameters &
Pick<SubscriptionData, 'mandateId'> &
Expand Down
2 changes: 1 addition & 1 deletion src/binders/methods/MethodsBinder.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
import TransformingNetworkClient from '../../communication/TransformingNetworkClient';
import List from '../../data/list/List';
import { MethodData } from '../../data/methods/data';
import Method from '../../data/methods/Method';
import renege from '../../plumbing/renege';
import TransformingNetworkClient from '../../TransformingNetworkClient';
import Callback from '../../types/Callback';
import Binder from '../Binder';
import { GetParameters, ListParameters } from './parameters';
Expand Down
2 changes: 1 addition & 1 deletion src/binders/onboarding/OnboardingBinder.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import TransformingNetworkClient from '../../communication/TransformingNetworkClient';
import { OnboardingData } from '../../data/onboarding/data';
import Onboarding from '../../data/onboarding/Onboarding';
import renege from '../../plumbing/renege';
import TransformingNetworkClient from '../../TransformingNetworkClient';
import Callback from '../../types/Callback';
import Binder from '../Binder';
import { SubmitParameters } from './parameters';
Expand Down
16 changes: 14 additions & 2 deletions src/binders/orders/OrdersBinder.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import TransformingNetworkClient from '../../communication/TransformingNetworkClient';
import List from '../../data/list/List';
import { OrderData } from '../../data/orders/data';
import Order from '../../data/orders/Order';
import ApiError from '../../errors/ApiError';
import checkId from '../../plumbing/checkId';
import renege from '../../plumbing/renege';
import TransformingNetworkClient from '../../TransformingNetworkClient';
import Callback from '../../types/Callback';
import Binder from '../Binder';
import { CancelParameters, CreateParameters, GetParameters, ListParameters, UpdateParameters } from './parameters';
Expand Down Expand Up @@ -124,11 +124,23 @@ export default class OrdersBinder extends Binder<OrderData, Order> {
*/
public page(parameters?: ListParameters): Promise<List<Order>>;
public page(parameters: ListParameters, callback: Callback<List<Order>>): void;
public page(parameters: ListParameters = {}) {
public page(parameters?: ListParameters) {
if (renege(this, this.page, ...arguments)) return;
return this.networkClient.list<OrderData, Order>(pathSegment, 'orders', parameters).then(result => this.injectPaginationHelpers(result, this.page, parameters));
}

/**
* Retrieve all orders.
*
* The results are paginated. See pagination for more information.
*
* @since 3.6.0
* @see https://docs.mollie.com/reference/v2/orders-api/list-orders
*/
public iterate(parameters?: Omit<ListParameters, 'limit'>) {
return this.networkClient.iterate<OrderData, Order>(pathSegment, 'orders', { ...parameters, limit: 64 });
}

/**
* This endpoint can be used to update the billing and/or shipping address of an order.
*
Expand Down
2 changes: 1 addition & 1 deletion src/binders/orders/orderlines/OrderLinesBinder.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,9 @@
import TransformingNetworkClient from '../../../communication/TransformingNetworkClient';
import { OrderData } from '../../../data/orders/data';
import Order from '../../../data/orders/Order';
import ApiError from '../../../errors/ApiError';
import checkId from '../../../plumbing/checkId';
import renege from '../../../plumbing/renege';
import TransformingNetworkClient from '../../../TransformingNetworkClient';
import Callback from '../../../types/Callback';
import InnerBinder from '../../InnerBinder';
import { CancelParameters, UpdateParameters } from './parameters';
Expand Down
Loading

0 comments on commit 39679f2

Please sign in to comment.