Skip to content

Commit b709227

Browse files
committed
Add pagination cursor interface.
1 parent 3266b56 commit b709227

File tree

5 files changed

+157
-94
lines changed

5 files changed

+157
-94
lines changed

.eslintrc

+1-1
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,6 @@
2929
"@typescript-eslint/no-var-requires": "off",
3030
"@typescript-eslint/ban-ts-comment": "off",
3131
"no-use-before-define": "off",
32-
"@typescript-eslint/no-shadow": ["error"]
32+
"no-shadow": ["error"]
3333
}
3434
}

CHANGELOG.md

+3
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,9 @@
11
# Change log
22
This is the changelog for [Authress SDK](readme.md).
33

4+
## 1.3 ##
5+
* Add new `Pagination` type which pagination `next.cursor` to enable paging through resources.
6+
47
## 1.2 ##
58
* Removed legacy support for RS512 service client tokens.
69
* Add EdDSA support for `tokenVerifier()` class

README.md

+37
Original file line numberDiff line numberDiff line change
@@ -133,6 +133,43 @@ const temporaryServiceClientAccessToken = await serviceClientTokenProvider.getTo
133133
const response = await client.get(url, { 'Authorization': `Bearer: ${temporaryServiceClientAccessToken}` });
134134
```
135135
136+
#### Paginating through a collection resource
137+
Some of the resources in the API are paginated. These resources contain a `pagination.next.cursor` property when there is a next page. The cursor can be passed to query to fetch the next page. Here's an example usage:
138+
139+
```js
140+
const { AuthressClient } = require('authress-sdk');
141+
const authressClient = new AuthressClient({ baseUrl: 'https://DOMAIN.api-REGION.authress.io' })
142+
143+
// on api route
144+
async function (resourceId) {
145+
// Get the user token and pass it to authress
146+
const authorizationToken = request.headers.get('authorization');
147+
authressClient.setToken(authorizationToken);
148+
149+
// Get the users resources
150+
const response = await authressClient.userPermissions.getUserResources(userId, `resources/*`, 10, null, 'READ');
151+
for (const resource of response.data.resources) {
152+
// Iterate on resource
153+
}
154+
155+
// Get the next page:
156+
const nextPageResponse = await authressClient.userPermissions.getUserResources(userId, `resources/*`, 10, response.data.pagination.next.cursor, 'READ');
157+
for (const resource of nextPageResponse.data.resources) {
158+
// Iterate on resource
159+
}
160+
161+
// Get all the next pages:
162+
let cursor = response.data.pagination?.next?.cursor;
163+
while (cursor) {
164+
const response = await authressClient.userPermissions.getUserResources(userId, `resources/*`, 10, cursor, 'READ');
165+
cursor = response.data.pagination?.next?.cursor;
166+
for (const resource of response.data.resources) {
167+
// Iterate on resource
168+
}
169+
}
170+
}
171+
```
172+
136173
## Contributions
137174
138175
### Adding new DTO and methods

index.d.ts

+10-93
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
/* eslint-disable @typescript-eslint/no-empty-interface */
33
/* eslint-disable no-shadow */
44

5-
import { Response } from './src/response';
5+
import { Response, IPaginated, Links, Cursor } from './src/response';
66

77
import { ConnectionsApi } from './src/connections/api';
88
export * from './src/connections/api';
@@ -123,19 +123,13 @@ export namespace AccessRecord {
123123
* @export
124124
* @interface AccessRecordCollection
125125
*/
126-
export interface AccessRecordCollection {
126+
export interface AccessRecordCollection extends IPaginated<AccessRecordCollection> {
127127
/**
128128
*
129129
* @type {Array<AccessRecord>}
130130
* @memberof AccessRecordCollection
131131
*/
132132
records: Array<AccessRecord>;
133-
/**
134-
*
135-
* @type {CollectionLinks}
136-
* @memberof AccessRecordCollection
137-
*/
138-
links: CollectionLinks;
139133
}
140134

141135
/**
@@ -325,7 +319,7 @@ export interface IdentityRequest {
325319
* @export
326320
* @interface UserResources
327321
*/
328-
export interface UserResources {
322+
export interface UserResources extends IPaginated<UserResources> {
329323
/**
330324
*
331325
* @type {AccountLink}
@@ -350,32 +344,20 @@ export interface UserResources {
350344
* @memberof UserResources
351345
*/
352346
accessToAllSubResources?: boolean;
353-
/**
354-
*
355-
* @type {CollectionLinks}
356-
* @memberof UserResources
357-
*/
358-
links?: CollectionLinks;
359347
}
360348

361349
/**
362350
* The collection of a list of clients
363351
* @export
364352
* @interface ServiceClientCollection
365353
*/
366-
export interface ServiceClientCollection {
354+
export interface ServiceClientCollection extends IPaginated<ServiceClientCollection> {
367355
/**
368356
* A list of clients
369357
* @type {Array<ServiceClient>}
370358
* @memberof ServiceClientCollection
371359
*/
372360
clients: Array<ServiceClientSummary>;
373-
/**
374-
*
375-
* @type {CollectionLinks}
376-
* @memberof ServiceClientCollection
377-
*/
378-
links: CollectionLinks;
379361
}
380362
/**
381363
* A client configuration.
@@ -554,20 +536,13 @@ export interface ResourcePermissionsCollection {
554536
* @export
555537
* @interface ResourceUsersCollection
556538
*/
557-
export interface ResourceUsersCollection {
539+
export interface ResourceUsersCollection extends IPaginated<ResourceUsersCollection> {
558540
/**
559541
*
560542
* @type {Array<UserRoleCollection>}
561543
* @memberof ResourceUsersCollection
562544
*/
563545
users: Array<UserRoleCollection>;
564-
565-
/**
566-
*
567-
* @type {CollectionLinks}
568-
* @memberof ResourceUsersCollection
569-
*/
570-
links: CollectionLinks;
571546
}
572547

573548
/**
@@ -616,25 +591,6 @@ export interface Role {
616591
permissions: Array<PermissionObject>;
617592
}
618593

619-
/**
620-
* A url linking object that complies to application/links+json RFC. Either is an IANA approved link relation or has a custom rel specified.
621-
* @export
622-
* @interface Link
623-
*/
624-
export interface Link {
625-
/**
626-
* The absolute url pointing to the reference resource.
627-
* @type {string}
628-
* @memberof Link
629-
*/
630-
href: string;
631-
/**
632-
* Optional property indicating the type of link if it is not a default IANA approved global link relation.
633-
* @type {string}
634-
* @memberof Link
635-
*/
636-
rel?: string;
637-
}
638594
/**
639595
* Metadata and additional properties relevant.
640596
* @export
@@ -734,38 +690,13 @@ export interface ResourcePermission {
734690
* @export
735691
* @interface ResourcePermissionCollection
736692
*/
737-
export interface ResourcePermissionCollection {
693+
export interface ResourcePermissionCollection extends IPaginated<ResourcePermissionCollection> {
738694
/**
739695
*
740696
* @type {Array<ResourcePermission>}
741697
* @memberof ResourcePermissionCollection
742698
*/
743699
resources: Array<ResourcePermission>;
744-
/**
745-
*
746-
* @type {CollectionLinks}
747-
* @memberof ResourcePermissionCollection
748-
*/
749-
links: CollectionLinks;
750-
}
751-
/**
752-
*
753-
* @export
754-
* @interface CollectionLinks
755-
*/
756-
export interface CollectionLinks {
757-
/**
758-
*
759-
* @type {Link}
760-
* @memberof CollectionLinks
761-
*/
762-
self: Link;
763-
/**
764-
*
765-
* @type {Link}
766-
* @memberof CollectionLinks
767-
*/
768-
next?: Link;
769700
}
770701

771702
/**
@@ -858,20 +789,6 @@ export interface ServiceClientOptions {
858789
grantMetadataAccess?: boolean;
859790
}
860791

861-
/**
862-
*
863-
* @export
864-
* @interface Links
865-
*/
866-
export interface Links {
867-
/**
868-
*
869-
* @type {Link}
870-
* @memberof Links
871-
*/
872-
self: Link;
873-
}
874-
875792
/**
876793
*
877794
* @export
@@ -1039,12 +956,12 @@ export interface AccessRecordsApi {
1039956
* <i class=\"far fa-money-bill-alt text-primary\"></i> <span class=\"text-primary\">Billable</span> Returns a paginated records list for the account. Only records the user has access to are returned.
1040957
* @summary Get all account records.
1041958
* @param {number} [limit] Max number of results to return
1042-
* @param {string} [cursor] Continuation cursor for paging (will automatically be set)
959+
* @param {Cursor} [cursor] Continuation cursor for paging (will automatically be set)
1043960
* @param {string} [filter] Filter to search records by. This is a case insensitive search through every text field.
1044961
* @param {string} [status] Filter records by their current status.
1045962
* @throws {ArgumentRequiredError}
1046963
*/
1047-
getRecords(limit?: number, cursor?: string, filter?: string, status?: string): Promise<Response<AccessRecordCollection>>;
964+
getRecords(limit?: number, cursor?: Cursor, filter?: string, status?: string): Promise<Response<AccessRecordCollection>>;
1048965
/**
1049966
* Updates an access record adding or removing user permissions to resources.
1050967
* @summary Update an access record.
@@ -1291,11 +1208,11 @@ export interface UserPermissionsApi {
12911208
* @param {string} [userId] The user to check permissions on
12921209
* @param {string} [resourceUri] The top level uri path of a resource to query for. Will only match explicit or collection resource sub-resources. Will not partial match resource names.
12931210
* @param {number} [limit] Max number of results to return
1294-
* @param {string} [cursor] Continuation cursor for paging (will automatically be set)
1211+
* @param {Cursor} [cursor] Continuation cursor for paging (will automatically be set)
12951212
* @param {string} [permission] A required ALLOW action to check for. Resources a user does not have this permission will not be returned.
12961213
* @throws {ArgumentRequiredError}
12971214
*/
1298-
getUserResources(userId?: string, resourceUri?: string, limit?: number, cursor?: string, permission?: string): Promise<Response<UserResources>>;
1215+
getUserResources(userId?: string, resourceUri?: string, limit?: number, cursor?: Cursor, permission?: string): Promise<Response<UserResources>>;
12991216
/**
13001217
* <i class=\"far fa-money-bill-alt text-primary\"></i> <span class=\"text-primary\">Billable</span> Get an Authress signed JWT access token using with userId as the sub. Additionally, can be configured to limit the permissions for this particular token and the length of time the token is valid. Token validation is real-time, so deleted tokens are restricted from being used as soon as they are deleted. This gives full control to the user and client creating the token. Client must have access to impersonating the user in order to generate tokens on their behalf.
13011218
* @summary Request a user token with additional configuration

src/response.ts

+106
Original file line numberDiff line numberDiff line change
@@ -8,3 +8,109 @@ export interface Response<ResponseType> {
88
/** HTTP response status code for success responses */
99
status: number;
1010
}
11+
12+
/**
13+
*
14+
* @export
15+
* @interface Links
16+
*/
17+
export interface Links {
18+
/**
19+
*
20+
* @type {Link}
21+
* @memberof Links
22+
*/
23+
self: Link;
24+
}
25+
26+
/**
27+
* A url linking object that complies to application/links+json RFC. Either is an IANA approved link relation or has a custom rel specified.
28+
* @export
29+
* @interface Link
30+
*/
31+
export interface Link {
32+
/**
33+
* The absolute url pointing to the reference resource.
34+
* @type {string}
35+
* @memberof Link
36+
*/
37+
href: string;
38+
/**
39+
* Optional property indicating the type of link if it is not a default IANA approved global link relation.
40+
* @type {string}
41+
* @memberof Link
42+
*/
43+
rel?: string;
44+
}
45+
46+
/**
47+
*
48+
* @export
49+
* @interface CollectionLinks
50+
*/
51+
export interface CollectionLinks {
52+
/**
53+
*
54+
* @type {Link}
55+
* @memberof CollectionLinks
56+
*/
57+
self: Link;
58+
/**
59+
*
60+
* @type {Link}
61+
* @memberof CollectionLinks
62+
*/
63+
next?: Link;
64+
}
65+
66+
/**
67+
*
68+
* @export
69+
* @interface IPaginated<CollectionType>
70+
*/
71+
// @ts-ignore
72+
export interface IPaginated<CollectionType> {
73+
/**
74+
*
75+
* @type {CollectionLinks}
76+
* @memberof IPaginated<CollectionType>
77+
*/
78+
links: CollectionLinks;
79+
80+
/**
81+
* @type {Pagination}
82+
* @memberof IPaginated<CollectionType>
83+
* @summary returns the next page of the collection
84+
*/
85+
pagination?: Pagination;
86+
}
87+
88+
/**
89+
*
90+
* @export
91+
* @interface Pagination
92+
*/
93+
export interface Pagination {
94+
/**
95+
*
96+
* @type {PageMetadata}
97+
* @memberof Pagination
98+
*/
99+
next?: PageMetadata;
100+
}
101+
102+
/**
103+
*
104+
* @export
105+
* @interface PageMetadata
106+
*/
107+
export interface PageMetadata {
108+
/**
109+
*
110+
* @type {Cursor}
111+
* @memberof PageMetadata
112+
*/
113+
cursor: Cursor;
114+
}
115+
116+
export type Cursor = string;

0 commit comments

Comments
 (0)