@workos-inc/node 7.16.0 → 7.17.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/lib/common/interfaces/get-options.interface.d.ts +1 -0
- package/lib/common/interfaces/post-options.interface.d.ts +1 -0
- package/lib/common/utils/fetch-and-deserialize.d.ts +2 -2
- package/lib/common/utils/fetch-and-deserialize.js +2 -4
- package/lib/fga/fga-live-test.spec.d.ts +1 -0
- package/lib/fga/fga-live-test.spec.js +872 -0
- package/lib/fga/fga.d.ts +18 -0
- package/lib/fga/fga.js +105 -0
- package/lib/fga/fga.spec.d.ts +1 -0
- package/lib/fga/fga.spec.js +518 -0
- package/lib/fga/interfaces/check-op.enum.d.ts +5 -0
- package/lib/fga/interfaces/check-op.enum.js +9 -0
- package/lib/fga/interfaces/check.interface.d.ts +71 -0
- package/lib/fga/interfaces/check.interface.js +21 -0
- package/lib/fga/interfaces/index.d.ts +7 -0
- package/lib/fga/interfaces/index.js +23 -0
- package/lib/fga/interfaces/query.interface.d.ts +30 -0
- package/lib/fga/interfaces/query.interface.js +2 -0
- package/lib/fga/interfaces/resource.interface.d.ts +60 -0
- package/lib/fga/interfaces/resource.interface.js +2 -0
- package/lib/fga/interfaces/warrant-op.enum.d.ts +4 -0
- package/lib/fga/interfaces/warrant-op.enum.js +8 -0
- package/lib/fga/interfaces/warrant-token.interface.d.ts +6 -0
- package/lib/fga/interfaces/warrant-token.interface.js +2 -0
- package/lib/fga/interfaces/warrant.interface.d.ts +65 -0
- package/lib/fga/interfaces/warrant.interface.js +2 -0
- package/lib/fga/serializers/check-options.serializer.d.ts +4 -0
- package/lib/fga/serializers/check-options.serializer.js +62 -0
- package/lib/fga/serializers/create-resource-options.serializer.d.ts +2 -0
- package/lib/fga/serializers/create-resource-options.serializer.js +16 -0
- package/lib/fga/serializers/delete-resource-options.serializer.d.ts +2 -0
- package/lib/fga/serializers/delete-resource-options.serializer.js +15 -0
- package/lib/fga/serializers/index.d.ts +11 -0
- package/lib/fga/serializers/index.js +27 -0
- package/lib/fga/serializers/list-resources-options.serializer.d.ts +2 -0
- package/lib/fga/serializers/list-resources-options.serializer.js +12 -0
- package/lib/fga/serializers/list-warrants-options.serializer.d.ts +2 -0
- package/lib/fga/serializers/list-warrants-options.serializer.js +14 -0
- package/lib/fga/serializers/query-options.serializer.d.ts +2 -0
- package/lib/fga/serializers/query-options.serializer.js +12 -0
- package/lib/fga/serializers/query-result.serializer.d.ts +2 -0
- package/lib/fga/serializers/query-result.serializer.js +21 -0
- package/lib/fga/serializers/resource.serializer.d.ts +2 -0
- package/lib/fga/serializers/resource.serializer.js +9 -0
- package/lib/fga/serializers/warrant-token.serializer.d.ts +2 -0
- package/lib/fga/serializers/warrant-token.serializer.js +7 -0
- package/lib/fga/serializers/warrant.serializer.d.ts +2 -0
- package/lib/fga/serializers/warrant.serializer.js +14 -0
- package/lib/fga/serializers/write-warrant-options.serializer.d.ts +2 -0
- package/lib/fga/serializers/write-warrant-options.serializer.js +27 -0
- package/lib/fga/utils/interface-check.d.ts +3 -0
- package/lib/fga/utils/interface-check.js +15 -0
- package/lib/workos.d.ts +2 -0
- package/lib/workos.js +19 -7
- package/package.json +1 -1
|
@@ -0,0 +1,872 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
3
|
+
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
4
|
+
return new (P || (P = Promise))(function (resolve, reject) {
|
|
5
|
+
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
6
|
+
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
7
|
+
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
8
|
+
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
9
|
+
});
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
const jest_fetch_mock_1 = require("jest-fetch-mock");
|
|
13
|
+
const workos_1 = require("../workos");
|
|
14
|
+
const interfaces_1 = require("./interfaces");
|
|
15
|
+
describe.skip('FGA Live Test', () => {
|
|
16
|
+
let workos;
|
|
17
|
+
beforeAll(() => {
|
|
18
|
+
(0, jest_fetch_mock_1.disableFetchMocks)();
|
|
19
|
+
workos = new workos_1.WorkOS('API_KEY');
|
|
20
|
+
});
|
|
21
|
+
afterAll(() => {
|
|
22
|
+
(0, jest_fetch_mock_1.enableFetchMocks)();
|
|
23
|
+
});
|
|
24
|
+
it('CRUD resources', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
25
|
+
const resource1 = yield workos.fga.createResource({
|
|
26
|
+
resource: { resourceType: 'document' },
|
|
27
|
+
});
|
|
28
|
+
expect(resource1.resourceType).toEqual('document');
|
|
29
|
+
expect(resource1.resourceId).toBeDefined();
|
|
30
|
+
expect(resource1.meta).toBeUndefined();
|
|
31
|
+
let resource2 = yield workos.fga.createResource({
|
|
32
|
+
resource: { resourceType: 'folder', resourceId: 'planning' },
|
|
33
|
+
});
|
|
34
|
+
let refetchedResource = yield workos.fga.getResource(resource2);
|
|
35
|
+
expect(refetchedResource.resourceType).toEqual(resource2.resourceType);
|
|
36
|
+
expect(refetchedResource.resourceId).toEqual(resource2.resourceId);
|
|
37
|
+
expect(refetchedResource.meta).toEqual(resource2.meta);
|
|
38
|
+
resource2 = yield workos.fga.updateResource({
|
|
39
|
+
resource: { resourceType: 'folder', resourceId: 'planning' },
|
|
40
|
+
meta: { description: 'Second document' },
|
|
41
|
+
});
|
|
42
|
+
refetchedResource = yield workos.fga.getResource(resource2);
|
|
43
|
+
expect(refetchedResource.resourceType).toEqual(resource2.resourceType);
|
|
44
|
+
expect(refetchedResource.resourceId).toEqual(resource2.resourceId);
|
|
45
|
+
expect(refetchedResource.meta).toEqual(resource2.meta);
|
|
46
|
+
let resourcesList = yield workos.fga.listResources({ limit: 10 });
|
|
47
|
+
expect(resourcesList.data.length).toEqual(2);
|
|
48
|
+
expect(resourcesList.data[0].resourceType).toEqual(resource2.resourceType);
|
|
49
|
+
expect(resourcesList.data[0].resourceId).toEqual(resource2.resourceId);
|
|
50
|
+
expect(resourcesList.data[1].resourceType).toEqual(resource1.resourceType);
|
|
51
|
+
expect(resourcesList.data[1].resourceId).toEqual(resource1.resourceId);
|
|
52
|
+
resourcesList = yield workos.fga.listResources({
|
|
53
|
+
limit: 10,
|
|
54
|
+
search: 'planning',
|
|
55
|
+
});
|
|
56
|
+
expect(resourcesList.data.length).toEqual(1);
|
|
57
|
+
expect(resourcesList.data[0].resourceType).toEqual(resource2.resourceType);
|
|
58
|
+
expect(resourcesList.data[0].resourceId).toEqual(resource2.resourceId);
|
|
59
|
+
yield workos.fga.deleteResource(resource1);
|
|
60
|
+
yield workos.fga.deleteResource(resource2);
|
|
61
|
+
resourcesList = yield workos.fga.listResources({ limit: 10 });
|
|
62
|
+
expect(resourcesList.data.length).toEqual(0);
|
|
63
|
+
}));
|
|
64
|
+
it('multi-tenancy example', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
65
|
+
// Create users
|
|
66
|
+
const user1 = yield workos.fga.createResource({
|
|
67
|
+
resource: { resourceType: 'user' },
|
|
68
|
+
});
|
|
69
|
+
const user2 = yield workos.fga.createResource({
|
|
70
|
+
resource: { resourceType: 'user' },
|
|
71
|
+
});
|
|
72
|
+
// Create tenants
|
|
73
|
+
const tenant1 = yield workos.fga.createResource({
|
|
74
|
+
resource: { resourceType: 'tenant', resourceId: 'tenant-1' },
|
|
75
|
+
meta: { name: 'Tenant 1' },
|
|
76
|
+
});
|
|
77
|
+
const tenant2 = yield workos.fga.createResource({
|
|
78
|
+
resource: { resourceType: 'tenant', resourceId: 'tenant-2' },
|
|
79
|
+
meta: { name: 'Tenant 2' },
|
|
80
|
+
});
|
|
81
|
+
let user1TenantsList = yield workos.fga.query({
|
|
82
|
+
q: `select tenant where user:${user1.resourceId} is member`,
|
|
83
|
+
limit: 10,
|
|
84
|
+
}, { warrantToken: 'latest' });
|
|
85
|
+
expect(user1TenantsList.data.length).toEqual(0);
|
|
86
|
+
let tenant1UsersList = yield workos.fga.query({
|
|
87
|
+
q: `select member of type user for tenant:${tenant1.resourceId}`,
|
|
88
|
+
limit: 10,
|
|
89
|
+
}, { warrantToken: 'latest' });
|
|
90
|
+
expect(tenant1UsersList.data.length).toEqual(0);
|
|
91
|
+
// Assign user1 -> tenant1
|
|
92
|
+
yield workos.fga.writeWarrant({
|
|
93
|
+
resource: tenant1,
|
|
94
|
+
relation: 'member',
|
|
95
|
+
subject: user1,
|
|
96
|
+
});
|
|
97
|
+
user1TenantsList = yield workos.fga.query({
|
|
98
|
+
q: `select tenant where user:${user1.resourceId} is member`,
|
|
99
|
+
limit: 10,
|
|
100
|
+
}, { warrantToken: 'latest' });
|
|
101
|
+
expect(user1TenantsList.data.length).toEqual(1);
|
|
102
|
+
expect(user1TenantsList.data[0].resourceType).toEqual('tenant');
|
|
103
|
+
expect(user1TenantsList.data[0].resourceId).toEqual('tenant-1');
|
|
104
|
+
expect(user1TenantsList.data[0].meta).toEqual({ name: 'Tenant 1' });
|
|
105
|
+
tenant1UsersList = yield workos.fga.query({
|
|
106
|
+
q: `select member of type user for tenant:${tenant1.resourceId}`,
|
|
107
|
+
limit: 10,
|
|
108
|
+
}, { warrantToken: 'latest' });
|
|
109
|
+
expect(tenant1UsersList.data.length).toEqual(1);
|
|
110
|
+
expect(tenant1UsersList.data[0].resourceType).toEqual('user');
|
|
111
|
+
expect(tenant1UsersList.data[0].resourceId).toEqual(user1.resourceId);
|
|
112
|
+
expect(tenant1UsersList.data[0].meta).toBeUndefined();
|
|
113
|
+
// Remove user1 -> tenant1
|
|
114
|
+
yield workos.fga.writeWarrant({
|
|
115
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
116
|
+
resource: tenant1,
|
|
117
|
+
relation: 'member',
|
|
118
|
+
subject: user1,
|
|
119
|
+
});
|
|
120
|
+
user1TenantsList = yield workos.fga.query({
|
|
121
|
+
q: `select tenant where user:${user1.resourceId} is member`,
|
|
122
|
+
limit: 10,
|
|
123
|
+
}, { warrantToken: 'latest' });
|
|
124
|
+
expect(user1TenantsList.data.length).toEqual(0);
|
|
125
|
+
tenant1UsersList = yield workos.fga.query({
|
|
126
|
+
q: `select member of type user for tenant:${tenant1.resourceId}`,
|
|
127
|
+
limit: 10,
|
|
128
|
+
}, { warrantToken: 'latest' });
|
|
129
|
+
expect(tenant1UsersList.data.length).toEqual(0);
|
|
130
|
+
// Clean up
|
|
131
|
+
yield workos.fga.deleteResource(user1);
|
|
132
|
+
yield workos.fga.deleteResource(user2);
|
|
133
|
+
yield workos.fga.deleteResource(tenant1);
|
|
134
|
+
yield workos.fga.deleteResource(tenant2);
|
|
135
|
+
}));
|
|
136
|
+
it('RBAC example', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
137
|
+
// Create users
|
|
138
|
+
const adminUser = yield workos.fga.createResource({
|
|
139
|
+
resource: { resourceType: 'user' },
|
|
140
|
+
});
|
|
141
|
+
const viewerUser = yield workos.fga.createResource({
|
|
142
|
+
resource: { resourceType: 'user' },
|
|
143
|
+
});
|
|
144
|
+
// Create roles
|
|
145
|
+
const adminRole = yield workos.fga.createResource({
|
|
146
|
+
resource: { resourceType: 'role', resourceId: 'admin' },
|
|
147
|
+
meta: { name: 'Admin', description: 'The admin role' },
|
|
148
|
+
});
|
|
149
|
+
const viewerRole = yield workos.fga.createResource({
|
|
150
|
+
resource: { resourceType: 'role', resourceId: 'viewer' },
|
|
151
|
+
meta: { name: 'Viewer', description: 'The viewer role' },
|
|
152
|
+
});
|
|
153
|
+
// Create permissions
|
|
154
|
+
const createPermission = yield workos.fga.createResource({
|
|
155
|
+
resource: { resourceType: 'permission', resourceId: 'create-report' },
|
|
156
|
+
meta: {
|
|
157
|
+
name: 'Create Report',
|
|
158
|
+
description: 'Permission to create reports',
|
|
159
|
+
},
|
|
160
|
+
});
|
|
161
|
+
const viewPermission = yield workos.fga.createResource({
|
|
162
|
+
resource: { resourceType: 'permission', resourceId: 'view-report' },
|
|
163
|
+
meta: { name: 'View Report', description: 'Permission to view reports' },
|
|
164
|
+
});
|
|
165
|
+
let adminUserRolesList = yield workos.fga.query({
|
|
166
|
+
q: `select role where user:${adminUser.resourceId} is member`,
|
|
167
|
+
limit: 10,
|
|
168
|
+
}, { warrantToken: 'latest' });
|
|
169
|
+
let adminRolePermissionsList = yield workos.fga.query({
|
|
170
|
+
q: `select permission where role:${adminRole.resourceId} is member`,
|
|
171
|
+
limit: 10,
|
|
172
|
+
}, { warrantToken: 'latest' });
|
|
173
|
+
expect(adminUserRolesList.data.length).toEqual(0);
|
|
174
|
+
expect(adminRolePermissionsList.data.length).toEqual(0);
|
|
175
|
+
let adminUserHasPermission = yield workos.fga.check({
|
|
176
|
+
checks: [
|
|
177
|
+
{
|
|
178
|
+
resource: createPermission,
|
|
179
|
+
relation: 'member',
|
|
180
|
+
subject: adminUser,
|
|
181
|
+
},
|
|
182
|
+
],
|
|
183
|
+
}, { warrantToken: 'latest' });
|
|
184
|
+
expect(adminUserHasPermission.isAuthorized()).toEqual(false);
|
|
185
|
+
// Assign 'create-report' -> admin role -> admin user
|
|
186
|
+
yield workos.fga.writeWarrant({
|
|
187
|
+
resource: createPermission,
|
|
188
|
+
relation: 'member',
|
|
189
|
+
subject: adminRole,
|
|
190
|
+
});
|
|
191
|
+
yield workos.fga.writeWarrant({
|
|
192
|
+
resource: adminRole,
|
|
193
|
+
relation: 'member',
|
|
194
|
+
subject: adminUser,
|
|
195
|
+
});
|
|
196
|
+
adminUserHasPermission = yield workos.fga.check({
|
|
197
|
+
checks: [
|
|
198
|
+
{
|
|
199
|
+
resource: createPermission,
|
|
200
|
+
relation: 'member',
|
|
201
|
+
subject: adminUser,
|
|
202
|
+
},
|
|
203
|
+
],
|
|
204
|
+
}, { warrantToken: 'latest' });
|
|
205
|
+
expect(adminUserHasPermission.isAuthorized()).toEqual(true);
|
|
206
|
+
adminUserRolesList = yield workos.fga.query({
|
|
207
|
+
q: `select role where user:${adminUser.resourceId} is member`,
|
|
208
|
+
limit: 10,
|
|
209
|
+
}, { warrantToken: 'latest' });
|
|
210
|
+
expect(adminUserRolesList.data.length).toEqual(1);
|
|
211
|
+
expect(adminUserRolesList.data[0].resourceType).toEqual('role');
|
|
212
|
+
expect(adminUserRolesList.data[0].resourceId).toEqual('admin');
|
|
213
|
+
expect(adminUserRolesList.data[0].meta).toEqual({
|
|
214
|
+
name: 'Admin',
|
|
215
|
+
description: 'The admin role',
|
|
216
|
+
});
|
|
217
|
+
adminRolePermissionsList = yield workos.fga.query({
|
|
218
|
+
q: `select permission where role:${adminRole.resourceId} is member`,
|
|
219
|
+
limit: 10,
|
|
220
|
+
}, { warrantToken: 'latest' });
|
|
221
|
+
expect(adminRolePermissionsList.data.length).toEqual(1);
|
|
222
|
+
expect(adminRolePermissionsList.data[0].resourceType).toEqual('permission');
|
|
223
|
+
expect(adminRolePermissionsList.data[0].resourceId).toEqual('create-report');
|
|
224
|
+
expect(adminRolePermissionsList.data[0].meta).toEqual({
|
|
225
|
+
name: 'Create Report',
|
|
226
|
+
description: 'Permission to create reports',
|
|
227
|
+
});
|
|
228
|
+
yield workos.fga.writeWarrant({
|
|
229
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
230
|
+
resource: createPermission,
|
|
231
|
+
relation: 'member',
|
|
232
|
+
subject: adminRole,
|
|
233
|
+
});
|
|
234
|
+
yield workos.fga.writeWarrant({
|
|
235
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
236
|
+
resource: adminRole,
|
|
237
|
+
relation: 'member',
|
|
238
|
+
subject: adminUser,
|
|
239
|
+
});
|
|
240
|
+
adminUserHasPermission = yield workos.fga.check({
|
|
241
|
+
checks: [
|
|
242
|
+
{
|
|
243
|
+
resource: createPermission,
|
|
244
|
+
relation: 'member',
|
|
245
|
+
subject: adminUser,
|
|
246
|
+
},
|
|
247
|
+
],
|
|
248
|
+
}, { warrantToken: 'latest' });
|
|
249
|
+
expect(adminUserHasPermission.isAuthorized()).toEqual(false);
|
|
250
|
+
adminUserRolesList = yield workos.fga.query({
|
|
251
|
+
q: `select role where user:${adminUser.resourceId} is member`,
|
|
252
|
+
limit: 10,
|
|
253
|
+
}, { warrantToken: 'latest' });
|
|
254
|
+
expect(adminUserRolesList.data.length).toEqual(0);
|
|
255
|
+
adminRolePermissionsList = yield workos.fga.query({
|
|
256
|
+
q: `select permission where role:${adminRole.resourceId} is member`,
|
|
257
|
+
limit: 10,
|
|
258
|
+
}, { warrantToken: 'latest' });
|
|
259
|
+
expect(adminRolePermissionsList.data.length).toEqual(0);
|
|
260
|
+
// Assign 'view-report' -> viewer user
|
|
261
|
+
let viewerUserHasPermission = yield workos.fga.check({
|
|
262
|
+
checks: [
|
|
263
|
+
{ resource: viewPermission, relation: 'member', subject: viewerUser },
|
|
264
|
+
],
|
|
265
|
+
}, { warrantToken: 'latest' });
|
|
266
|
+
expect(viewerUserHasPermission.isAuthorized()).toEqual(false);
|
|
267
|
+
let viewerUserPermissionsList = yield workos.fga.query({
|
|
268
|
+
q: `select permission where user:${viewerUser.resourceId} is member`,
|
|
269
|
+
limit: 10,
|
|
270
|
+
}, { warrantToken: 'latest' });
|
|
271
|
+
expect(viewerUserPermissionsList.data.length).toEqual(0);
|
|
272
|
+
yield workos.fga.writeWarrant({
|
|
273
|
+
resource: viewPermission,
|
|
274
|
+
relation: 'member',
|
|
275
|
+
subject: viewerUser,
|
|
276
|
+
});
|
|
277
|
+
viewerUserHasPermission = yield workos.fga.check({
|
|
278
|
+
checks: [
|
|
279
|
+
{ resource: viewPermission, relation: 'member', subject: viewerUser },
|
|
280
|
+
],
|
|
281
|
+
}, { warrantToken: 'latest' });
|
|
282
|
+
expect(viewerUserHasPermission.isAuthorized()).toEqual(true);
|
|
283
|
+
viewerUserPermissionsList = yield workos.fga.query({
|
|
284
|
+
q: `select permission where user:${viewerUser.resourceId} is member`,
|
|
285
|
+
limit: 10,
|
|
286
|
+
}, { warrantToken: 'latest' });
|
|
287
|
+
expect(viewerUserPermissionsList.data.length).toEqual(1);
|
|
288
|
+
expect(viewerUserPermissionsList.data[0].resourceType).toEqual('permission');
|
|
289
|
+
expect(viewerUserPermissionsList.data[0].resourceId).toEqual('view-report');
|
|
290
|
+
expect(viewerUserPermissionsList.data[0].meta).toEqual({
|
|
291
|
+
name: 'View Report',
|
|
292
|
+
description: 'Permission to view reports',
|
|
293
|
+
});
|
|
294
|
+
yield workos.fga.writeWarrant({
|
|
295
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
296
|
+
resource: viewPermission,
|
|
297
|
+
relation: 'member',
|
|
298
|
+
subject: viewerUser,
|
|
299
|
+
});
|
|
300
|
+
viewerUserHasPermission = yield workos.fga.check({
|
|
301
|
+
checks: [
|
|
302
|
+
{ resource: viewPermission, relation: 'member', subject: viewerUser },
|
|
303
|
+
],
|
|
304
|
+
}, { warrantToken: 'latest' });
|
|
305
|
+
expect(viewerUserHasPermission.isAuthorized()).toEqual(false);
|
|
306
|
+
viewerUserPermissionsList = yield workos.fga.query({
|
|
307
|
+
q: `select permission where user:${viewerUser.resourceId} is member`,
|
|
308
|
+
limit: 10,
|
|
309
|
+
}, { warrantToken: 'latest' });
|
|
310
|
+
expect(viewerUserPermissionsList.data.length).toEqual(0);
|
|
311
|
+
// Clean up
|
|
312
|
+
yield workos.fga.deleteResource(adminUser);
|
|
313
|
+
yield workos.fga.deleteResource(viewerUser);
|
|
314
|
+
yield workos.fga.deleteResource(adminRole);
|
|
315
|
+
yield workos.fga.deleteResource(viewerRole);
|
|
316
|
+
yield workos.fga.deleteResource(createPermission);
|
|
317
|
+
yield workos.fga.deleteResource(viewPermission);
|
|
318
|
+
}), 10000);
|
|
319
|
+
it('pricing tiers, features, and users example', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
320
|
+
// Create users
|
|
321
|
+
const freeUser = yield workos.fga.createResource({
|
|
322
|
+
resource: { resourceType: 'user' },
|
|
323
|
+
});
|
|
324
|
+
const paidUser = yield workos.fga.createResource({
|
|
325
|
+
resource: { resourceType: 'user' },
|
|
326
|
+
});
|
|
327
|
+
// Create pricing tiers
|
|
328
|
+
const freeTier = yield workos.fga.createResource({
|
|
329
|
+
resource: { resourceType: 'pricing-tier', resourceId: 'free' },
|
|
330
|
+
meta: { name: 'Free Tier' },
|
|
331
|
+
});
|
|
332
|
+
const paidTier = yield workos.fga.createResource({
|
|
333
|
+
resource: { resourceType: 'pricing-tier', resourceId: 'paid' },
|
|
334
|
+
});
|
|
335
|
+
// Create features
|
|
336
|
+
const customFeature = yield workos.fga.createResource({
|
|
337
|
+
resource: { resourceType: 'feature', resourceId: 'custom-feature' },
|
|
338
|
+
meta: { name: 'Custom Feature' },
|
|
339
|
+
});
|
|
340
|
+
const feature1 = yield workos.fga.createResource({
|
|
341
|
+
resource: { resourceType: 'feature', resourceId: 'feature-1' },
|
|
342
|
+
});
|
|
343
|
+
const feature2 = yield workos.fga.createResource({
|
|
344
|
+
resource: { resourceType: 'feature', resourceId: 'feature-2' },
|
|
345
|
+
});
|
|
346
|
+
// Assign 'custom-feature' -> paid user
|
|
347
|
+
let paidUserHasFeature = yield workos.fga.check({
|
|
348
|
+
checks: [
|
|
349
|
+
{ resource: customFeature, relation: 'member', subject: paidUser },
|
|
350
|
+
],
|
|
351
|
+
}, { warrantToken: 'latest' });
|
|
352
|
+
expect(paidUserHasFeature.isAuthorized()).toEqual(false);
|
|
353
|
+
let paidUserFeaturesList = yield workos.fga.query({
|
|
354
|
+
q: `select feature where user:${paidUser.resourceId} is member`,
|
|
355
|
+
limit: 10,
|
|
356
|
+
}, { warrantToken: 'latest' });
|
|
357
|
+
expect(paidUserFeaturesList.data.length).toEqual(0);
|
|
358
|
+
yield workos.fga.writeWarrant({
|
|
359
|
+
resource: customFeature,
|
|
360
|
+
relation: 'member',
|
|
361
|
+
subject: paidUser,
|
|
362
|
+
});
|
|
363
|
+
paidUserHasFeature = yield workos.fga.check({
|
|
364
|
+
checks: [
|
|
365
|
+
{ resource: customFeature, relation: 'member', subject: paidUser },
|
|
366
|
+
],
|
|
367
|
+
}, { warrantToken: 'latest' });
|
|
368
|
+
expect(paidUserHasFeature.isAuthorized()).toEqual(true);
|
|
369
|
+
paidUserFeaturesList = yield workos.fga.query({
|
|
370
|
+
q: `select feature where user:${paidUser.resourceId} is member`,
|
|
371
|
+
limit: 10,
|
|
372
|
+
}, { warrantToken: 'latest' });
|
|
373
|
+
expect(paidUserFeaturesList.data.length).toEqual(1);
|
|
374
|
+
expect(paidUserFeaturesList.data[0].resourceType).toEqual('feature');
|
|
375
|
+
expect(paidUserFeaturesList.data[0].resourceId).toEqual('custom-feature');
|
|
376
|
+
expect(paidUserFeaturesList.data[0].meta).toEqual({
|
|
377
|
+
name: 'Custom Feature',
|
|
378
|
+
});
|
|
379
|
+
yield workos.fga.writeWarrant({
|
|
380
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
381
|
+
resource: customFeature,
|
|
382
|
+
relation: 'member',
|
|
383
|
+
subject: paidUser,
|
|
384
|
+
});
|
|
385
|
+
paidUserHasFeature = yield workos.fga.check({
|
|
386
|
+
checks: [
|
|
387
|
+
{ resource: customFeature, relation: 'member', subject: paidUser },
|
|
388
|
+
],
|
|
389
|
+
}, { warrantToken: 'latest' });
|
|
390
|
+
expect(paidUserHasFeature.isAuthorized()).toEqual(false);
|
|
391
|
+
paidUserFeaturesList = yield workos.fga.query({
|
|
392
|
+
q: `select feature where user:${paidUser.resourceId} is member`,
|
|
393
|
+
limit: 10,
|
|
394
|
+
}, { warrantToken: 'latest' });
|
|
395
|
+
expect(paidUserFeaturesList.data.length).toEqual(0);
|
|
396
|
+
// Assign 'feature-1' -> 'free' tier -> free user
|
|
397
|
+
let freeUserHasFeature = yield workos.fga.check({
|
|
398
|
+
checks: [{ resource: feature1, relation: 'member', subject: freeUser }],
|
|
399
|
+
}, { warrantToken: 'latest' });
|
|
400
|
+
expect(freeUserHasFeature.isAuthorized()).toEqual(false);
|
|
401
|
+
let freeUserFeaturesList = yield workos.fga.query({
|
|
402
|
+
q: `select feature where user:${freeUser.resourceId} is member`,
|
|
403
|
+
limit: 10,
|
|
404
|
+
}, { warrantToken: 'latest' });
|
|
405
|
+
expect(freeUserFeaturesList.data.length).toEqual(0);
|
|
406
|
+
let freeUserTiersList = yield workos.fga.query({
|
|
407
|
+
q: `select pricing-tier where user:${freeUser.resourceId} is member`,
|
|
408
|
+
limit: 10,
|
|
409
|
+
}, { warrantToken: 'latest' });
|
|
410
|
+
expect(freeUserTiersList.data.length).toEqual(0);
|
|
411
|
+
yield workos.fga.writeWarrant({
|
|
412
|
+
resource: feature1,
|
|
413
|
+
relation: 'member',
|
|
414
|
+
subject: freeTier,
|
|
415
|
+
});
|
|
416
|
+
yield workos.fga.writeWarrant({
|
|
417
|
+
resource: freeTier,
|
|
418
|
+
relation: 'member',
|
|
419
|
+
subject: freeUser,
|
|
420
|
+
});
|
|
421
|
+
freeUserHasFeature = yield workos.fga.check({
|
|
422
|
+
checks: [{ resource: feature1, relation: 'member', subject: freeUser }],
|
|
423
|
+
}, { warrantToken: 'latest' });
|
|
424
|
+
expect(freeUserHasFeature.isAuthorized()).toEqual(true);
|
|
425
|
+
freeUserFeaturesList = yield workos.fga.query({
|
|
426
|
+
q: `select feature where user:${freeUser.resourceId} is member`,
|
|
427
|
+
limit: 10,
|
|
428
|
+
}, { warrantToken: 'latest' });
|
|
429
|
+
expect(freeUserFeaturesList.data.length).toEqual(1);
|
|
430
|
+
expect(freeUserFeaturesList.data[0].resourceType).toEqual('feature');
|
|
431
|
+
expect(freeUserFeaturesList.data[0].resourceId).toEqual('feature-1');
|
|
432
|
+
expect(freeUserFeaturesList.data[0].meta).toBeUndefined();
|
|
433
|
+
freeUserTiersList = yield workos.fga.query({
|
|
434
|
+
q: `select pricing-tier where user:${freeUser.resourceId} is member`,
|
|
435
|
+
limit: 10,
|
|
436
|
+
}, { warrantToken: 'latest' });
|
|
437
|
+
expect(freeUserTiersList.data.length).toEqual(1);
|
|
438
|
+
expect(freeUserTiersList.data[0].resourceType).toEqual('pricing-tier');
|
|
439
|
+
expect(freeUserTiersList.data[0].resourceId).toEqual('free');
|
|
440
|
+
expect(freeUserTiersList.data[0].meta).toEqual({ name: 'Free Tier' });
|
|
441
|
+
yield workos.fga.writeWarrant({
|
|
442
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
443
|
+
resource: feature1,
|
|
444
|
+
relation: 'member',
|
|
445
|
+
subject: freeTier,
|
|
446
|
+
});
|
|
447
|
+
yield workos.fga.writeWarrant({
|
|
448
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
449
|
+
resource: freeTier,
|
|
450
|
+
relation: 'member',
|
|
451
|
+
subject: freeUser,
|
|
452
|
+
});
|
|
453
|
+
freeUserHasFeature = yield workos.fga.check({
|
|
454
|
+
checks: [{ resource: feature1, relation: 'member', subject: freeUser }],
|
|
455
|
+
}, { warrantToken: 'latest' });
|
|
456
|
+
expect(freeUserHasFeature.isAuthorized()).toEqual(false);
|
|
457
|
+
freeUserFeaturesList = yield workos.fga.query({
|
|
458
|
+
q: `select feature where user:${freeUser.resourceId} is member`,
|
|
459
|
+
limit: 10,
|
|
460
|
+
}, { warrantToken: 'latest' });
|
|
461
|
+
expect(freeUserFeaturesList.data.length).toEqual(0);
|
|
462
|
+
freeUserTiersList = yield workos.fga.query({
|
|
463
|
+
q: `select pricing-tier where user:${freeUser.resourceId} is member`,
|
|
464
|
+
limit: 10,
|
|
465
|
+
}, { warrantToken: 'latest' });
|
|
466
|
+
expect(freeUserTiersList.data.length).toEqual(0);
|
|
467
|
+
// Clean up
|
|
468
|
+
yield workos.fga.deleteResource(freeUser);
|
|
469
|
+
yield workos.fga.deleteResource(paidUser);
|
|
470
|
+
yield workos.fga.deleteResource(freeTier);
|
|
471
|
+
yield workos.fga.deleteResource(paidTier);
|
|
472
|
+
yield workos.fga.deleteResource(customFeature);
|
|
473
|
+
yield workos.fga.deleteResource(feature1);
|
|
474
|
+
yield workos.fga.deleteResource(feature2);
|
|
475
|
+
}), 10000);
|
|
476
|
+
it('warrants', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
477
|
+
const user1 = yield workos.fga.createResource({
|
|
478
|
+
resource: { resourceType: 'user', resourceId: 'userA' },
|
|
479
|
+
});
|
|
480
|
+
const user2 = yield workos.fga.createResource({
|
|
481
|
+
resource: { resourceType: 'user', resourceId: 'userB' },
|
|
482
|
+
});
|
|
483
|
+
const newPermission = yield workos.fga.createResource({
|
|
484
|
+
resource: { resourceType: 'permission', resourceId: 'perm1' },
|
|
485
|
+
meta: { name: 'Permission 1', description: 'Permission 1' },
|
|
486
|
+
});
|
|
487
|
+
let userHasPermission = yield workos.fga.check({
|
|
488
|
+
checks: [
|
|
489
|
+
{ resource: newPermission, relation: 'member', subject: user1 },
|
|
490
|
+
],
|
|
491
|
+
}, { warrantToken: 'latest' });
|
|
492
|
+
expect(userHasPermission.isAuthorized()).toEqual(false);
|
|
493
|
+
const warrant1 = yield workos.fga.writeWarrant({
|
|
494
|
+
resource: newPermission,
|
|
495
|
+
relation: 'member',
|
|
496
|
+
subject: user1,
|
|
497
|
+
});
|
|
498
|
+
expect(warrant1.warrantToken).toBeDefined();
|
|
499
|
+
const warrant2 = yield workos.fga.writeWarrant({
|
|
500
|
+
resource: newPermission,
|
|
501
|
+
relation: 'member',
|
|
502
|
+
subject: user2,
|
|
503
|
+
});
|
|
504
|
+
expect(warrant2.warrantToken).toBeDefined();
|
|
505
|
+
const warrants1 = yield workos.fga.listWarrants({ limit: 1 }, { warrantToken: 'latest' });
|
|
506
|
+
expect(warrants1.data.length).toEqual(1);
|
|
507
|
+
expect(warrants1.data[0].resourceType).toEqual('permission');
|
|
508
|
+
expect(warrants1.data[0].resourceId).toEqual('perm1');
|
|
509
|
+
expect(warrants1.data[0].relation).toEqual('member');
|
|
510
|
+
expect(warrants1.data[0].subject.resourceType).toEqual('user');
|
|
511
|
+
expect(warrants1.data[0].subject.resourceId).toEqual(user2.resourceId);
|
|
512
|
+
const warrants2 = yield workos.fga.listWarrants({ limit: 1, after: warrants1.listMetadata.after }, { warrantToken: 'latest' });
|
|
513
|
+
expect(warrants2.data.length).toEqual(1);
|
|
514
|
+
expect(warrants2.data[0].resourceType).toEqual('permission');
|
|
515
|
+
expect(warrants2.data[0].resourceId).toEqual('perm1');
|
|
516
|
+
expect(warrants2.data[0].relation).toEqual('member');
|
|
517
|
+
expect(warrants2.data[0].subject.resourceType).toEqual('user');
|
|
518
|
+
expect(warrants2.data[0].subject.resourceId).toEqual(user1.resourceId);
|
|
519
|
+
const warrants3 = yield workos.fga.listWarrants({ subjectType: 'user', subjectId: user1.resourceId }, { warrantToken: 'latest' });
|
|
520
|
+
expect(warrants3.data.length).toEqual(1);
|
|
521
|
+
expect(warrants3.data[0].resourceType).toEqual('permission');
|
|
522
|
+
expect(warrants3.data[0].resourceId).toEqual('perm1');
|
|
523
|
+
expect(warrants3.data[0].relation).toEqual('member');
|
|
524
|
+
expect(warrants3.data[0].subject.resourceType).toEqual('user');
|
|
525
|
+
expect(warrants3.data[0].subject.resourceId).toEqual(user1.resourceId);
|
|
526
|
+
userHasPermission = yield workos.fga.check({
|
|
527
|
+
checks: [
|
|
528
|
+
{ resource: newPermission, relation: 'member', subject: user1 },
|
|
529
|
+
],
|
|
530
|
+
}, { warrantToken: 'latest' });
|
|
531
|
+
expect(userHasPermission.isAuthorized()).toEqual(true);
|
|
532
|
+
const query = `select permission where user:${user1.resourceId} is member`;
|
|
533
|
+
const response = yield workos.fga.query({ q: query }, { warrantToken: 'latest' });
|
|
534
|
+
expect(response.data.length).toEqual(1);
|
|
535
|
+
expect(response.data[0].resourceType).toEqual('permission');
|
|
536
|
+
expect(response.data[0].resourceId).toEqual('perm1');
|
|
537
|
+
expect(response.data[0].relation).toEqual('member');
|
|
538
|
+
yield workos.fga.writeWarrant({
|
|
539
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
540
|
+
resource: newPermission,
|
|
541
|
+
relation: 'member',
|
|
542
|
+
subject: user1,
|
|
543
|
+
});
|
|
544
|
+
userHasPermission = yield workos.fga.check({
|
|
545
|
+
checks: [
|
|
546
|
+
{ resource: newPermission, relation: 'member', subject: user1 },
|
|
547
|
+
],
|
|
548
|
+
}, { warrantToken: 'latest' });
|
|
549
|
+
expect(userHasPermission.isAuthorized()).toEqual(false);
|
|
550
|
+
// Clean up
|
|
551
|
+
yield workos.fga.deleteResource(user1);
|
|
552
|
+
yield workos.fga.deleteResource(user2);
|
|
553
|
+
yield workos.fga.deleteResource(newPermission);
|
|
554
|
+
}));
|
|
555
|
+
it('check many warrants', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
556
|
+
const newUser = yield workos.fga.createResource({
|
|
557
|
+
resource: { resourceType: 'user' },
|
|
558
|
+
});
|
|
559
|
+
const permission1 = yield workos.fga.createResource({
|
|
560
|
+
resource: { resourceType: 'permission', resourceId: 'perm1' },
|
|
561
|
+
meta: { name: 'Permission 1', description: 'Permission 1' },
|
|
562
|
+
});
|
|
563
|
+
const permission2 = yield workos.fga.createResource({
|
|
564
|
+
resource: { resourceType: 'permission', resourceId: 'perm2' },
|
|
565
|
+
meta: { name: 'Permission 2', description: 'Permission 2' },
|
|
566
|
+
});
|
|
567
|
+
const userHasPermissions = yield workos.fga.check({
|
|
568
|
+
op: interfaces_1.CheckOp.AnyOf,
|
|
569
|
+
checks: [
|
|
570
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
571
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
572
|
+
],
|
|
573
|
+
}, { warrantToken: 'latest' });
|
|
574
|
+
expect(userHasPermissions.isAuthorized()).toEqual(false);
|
|
575
|
+
let warrantResponse = yield workos.fga.writeWarrant({
|
|
576
|
+
resource: permission1,
|
|
577
|
+
relation: 'member',
|
|
578
|
+
subject: newUser,
|
|
579
|
+
});
|
|
580
|
+
expect(warrantResponse.warrantToken).toBeDefined();
|
|
581
|
+
let userHasAtLeastOnePermission = yield workos.fga.check({
|
|
582
|
+
op: interfaces_1.CheckOp.AnyOf,
|
|
583
|
+
checks: [
|
|
584
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
585
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
586
|
+
],
|
|
587
|
+
}, { warrantToken: 'latest' });
|
|
588
|
+
expect(userHasAtLeastOnePermission.isAuthorized()).toEqual(true);
|
|
589
|
+
let userHasAllPermissions = yield workos.fga.check({
|
|
590
|
+
op: interfaces_1.CheckOp.AllOf,
|
|
591
|
+
checks: [
|
|
592
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
593
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
594
|
+
],
|
|
595
|
+
}, { warrantToken: 'latest' });
|
|
596
|
+
expect(userHasAllPermissions.isAuthorized()).toEqual(false);
|
|
597
|
+
warrantResponse = yield workos.fga.writeWarrant({
|
|
598
|
+
resource: permission2,
|
|
599
|
+
relation: 'member',
|
|
600
|
+
subject: newUser,
|
|
601
|
+
});
|
|
602
|
+
expect(warrantResponse.warrantToken).toBeDefined();
|
|
603
|
+
userHasAtLeastOnePermission = yield workos.fga.check({
|
|
604
|
+
op: interfaces_1.CheckOp.AnyOf,
|
|
605
|
+
checks: [
|
|
606
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
607
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
608
|
+
],
|
|
609
|
+
}, { warrantToken: 'latest' });
|
|
610
|
+
expect(userHasAtLeastOnePermission.isAuthorized()).toEqual(true);
|
|
611
|
+
userHasAllPermissions = yield workos.fga.check({
|
|
612
|
+
op: interfaces_1.CheckOp.AllOf,
|
|
613
|
+
checks: [
|
|
614
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
615
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
616
|
+
],
|
|
617
|
+
}, { warrantToken: 'latest' });
|
|
618
|
+
expect(userHasAllPermissions.isAuthorized()).toEqual(true);
|
|
619
|
+
warrantResponse = yield workos.fga.batchWriteWarrants([
|
|
620
|
+
{
|
|
621
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
622
|
+
resource: permission1,
|
|
623
|
+
relation: 'member',
|
|
624
|
+
subject: newUser,
|
|
625
|
+
},
|
|
626
|
+
{
|
|
627
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
628
|
+
resource: permission2,
|
|
629
|
+
relation: 'member',
|
|
630
|
+
subject: newUser,
|
|
631
|
+
},
|
|
632
|
+
]);
|
|
633
|
+
expect(warrantResponse.warrantToken).toBeDefined();
|
|
634
|
+
// Clean up
|
|
635
|
+
yield workos.fga.deleteResource(newUser);
|
|
636
|
+
yield workos.fga.deleteResource(permission1);
|
|
637
|
+
yield workos.fga.deleteResource(permission2);
|
|
638
|
+
}));
|
|
639
|
+
it('batch create/delete/check warrants', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
640
|
+
const newUser = yield workos.fga.createResource({
|
|
641
|
+
resource: { resourceType: 'user' },
|
|
642
|
+
});
|
|
643
|
+
const permission1 = yield workos.fga.createResource({
|
|
644
|
+
resource: { resourceType: 'permission', resourceId: 'perm1' },
|
|
645
|
+
meta: { name: 'Permission 1', description: 'Permission 1' },
|
|
646
|
+
});
|
|
647
|
+
const permission2 = yield workos.fga.createResource({
|
|
648
|
+
resource: { resourceType: 'permission', resourceId: 'perm2' },
|
|
649
|
+
meta: { name: 'Permission 2', description: 'Permission 2' },
|
|
650
|
+
});
|
|
651
|
+
let userHasPermissions = yield workos.fga.checkBatch({
|
|
652
|
+
checks: [
|
|
653
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
654
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
655
|
+
],
|
|
656
|
+
}, { warrantToken: 'latest' });
|
|
657
|
+
expect(userHasPermissions[0].isAuthorized()).toEqual(false);
|
|
658
|
+
expect(userHasPermissions[1].isAuthorized()).toEqual(false);
|
|
659
|
+
const warrants = yield workos.fga.batchWriteWarrants([
|
|
660
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
661
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
662
|
+
]);
|
|
663
|
+
expect(warrants.warrantToken).toBeDefined();
|
|
664
|
+
userHasPermissions = yield workos.fga.checkBatch({
|
|
665
|
+
checks: [
|
|
666
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
667
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
668
|
+
],
|
|
669
|
+
}, { warrantToken: 'latest' });
|
|
670
|
+
expect(userHasPermissions[0].isAuthorized()).toEqual(true);
|
|
671
|
+
expect(userHasPermissions[1].isAuthorized()).toEqual(true);
|
|
672
|
+
const warrantToken = yield workos.fga.batchWriteWarrants([
|
|
673
|
+
{
|
|
674
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
675
|
+
resource: permission1,
|
|
676
|
+
relation: 'member',
|
|
677
|
+
subject: newUser,
|
|
678
|
+
},
|
|
679
|
+
{
|
|
680
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
681
|
+
resource: permission2,
|
|
682
|
+
relation: 'member',
|
|
683
|
+
subject: newUser,
|
|
684
|
+
},
|
|
685
|
+
]);
|
|
686
|
+
expect(warrantToken).toBeDefined();
|
|
687
|
+
userHasPermissions = yield workos.fga.checkBatch({
|
|
688
|
+
checks: [
|
|
689
|
+
{ resource: permission1, relation: 'member', subject: newUser },
|
|
690
|
+
{ resource: permission2, relation: 'member', subject: newUser },
|
|
691
|
+
],
|
|
692
|
+
}, { warrantToken: 'latest' });
|
|
693
|
+
expect(userHasPermissions[0].isAuthorized()).toEqual(false);
|
|
694
|
+
expect(userHasPermissions[1].isAuthorized()).toEqual(false);
|
|
695
|
+
yield workos.fga.deleteResource(newUser);
|
|
696
|
+
yield workos.fga.deleteResource(permission1);
|
|
697
|
+
yield workos.fga.deleteResource(permission2);
|
|
698
|
+
}));
|
|
699
|
+
it('warrant with policy', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
700
|
+
let writeResult = yield workos.fga.writeWarrant({
|
|
701
|
+
resource: { resourceType: 'permission', resourceId: 'test-permission' },
|
|
702
|
+
relation: 'member',
|
|
703
|
+
subject: { resourceType: 'user', resourceId: 'user-1' },
|
|
704
|
+
policy: `geo == "us"`,
|
|
705
|
+
});
|
|
706
|
+
expect(writeResult.warrantToken).toBeDefined();
|
|
707
|
+
let checkResult = yield workos.fga.check({
|
|
708
|
+
checks: [
|
|
709
|
+
{
|
|
710
|
+
resource: {
|
|
711
|
+
resourceType: 'permission',
|
|
712
|
+
resourceId: 'test-permission',
|
|
713
|
+
},
|
|
714
|
+
relation: 'member',
|
|
715
|
+
subject: { resourceType: 'user', resourceId: 'user-1' },
|
|
716
|
+
context: { geo: 'us' },
|
|
717
|
+
},
|
|
718
|
+
],
|
|
719
|
+
}, {
|
|
720
|
+
warrantToken: 'latest',
|
|
721
|
+
});
|
|
722
|
+
expect(checkResult.isAuthorized()).toEqual(true);
|
|
723
|
+
checkResult = yield workos.fga.check({
|
|
724
|
+
checks: [
|
|
725
|
+
{
|
|
726
|
+
resource: {
|
|
727
|
+
resourceType: 'permission',
|
|
728
|
+
resourceId: 'test-permission',
|
|
729
|
+
},
|
|
730
|
+
relation: 'member',
|
|
731
|
+
subject: { resourceType: 'user', resourceId: 'user-1' },
|
|
732
|
+
context: { geo: 'eu' },
|
|
733
|
+
},
|
|
734
|
+
],
|
|
735
|
+
}, {
|
|
736
|
+
warrantToken: 'latest',
|
|
737
|
+
});
|
|
738
|
+
expect(checkResult.isAuthorized()).toEqual(false);
|
|
739
|
+
writeResult = yield workos.fga.writeWarrant({
|
|
740
|
+
op: interfaces_1.WarrantOp.Delete,
|
|
741
|
+
resource: { resourceType: 'permission', resourceId: 'test-permission' },
|
|
742
|
+
relation: 'member',
|
|
743
|
+
subject: { resourceType: 'user', resourceId: 'user-1' },
|
|
744
|
+
policy: `geo == "us"`,
|
|
745
|
+
});
|
|
746
|
+
expect(writeResult.warrantToken).toBeDefined();
|
|
747
|
+
// Clean up
|
|
748
|
+
yield workos.fga.deleteResource({
|
|
749
|
+
resourceType: 'permission',
|
|
750
|
+
resourceId: 'test-permission',
|
|
751
|
+
});
|
|
752
|
+
yield workos.fga.deleteResource({
|
|
753
|
+
resourceType: 'user',
|
|
754
|
+
resourceId: 'user-1',
|
|
755
|
+
});
|
|
756
|
+
}));
|
|
757
|
+
it('query', () => __awaiter(void 0, void 0, void 0, function* () {
|
|
758
|
+
const userA = yield workos.fga.createResource({
|
|
759
|
+
resource: { resourceType: 'user', resourceId: 'userA' },
|
|
760
|
+
});
|
|
761
|
+
const userB = yield workos.fga.createResource({
|
|
762
|
+
resource: { resourceType: 'user', resourceId: 'userB' },
|
|
763
|
+
});
|
|
764
|
+
const permission1 = yield workos.fga.createResource({
|
|
765
|
+
resource: { resourceType: 'permission', resourceId: 'perm1' },
|
|
766
|
+
meta: { name: 'Permission 1', description: 'This is permission 1.' },
|
|
767
|
+
});
|
|
768
|
+
const permission2 = yield workos.fga.createResource({
|
|
769
|
+
resource: { resourceType: 'permission', resourceId: 'perm2' },
|
|
770
|
+
});
|
|
771
|
+
const permission3 = yield workos.fga.createResource({
|
|
772
|
+
resource: { resourceType: 'permission', resourceId: 'perm3' },
|
|
773
|
+
meta: { name: 'Permission 3', description: 'This is permission 3.' },
|
|
774
|
+
});
|
|
775
|
+
const role1 = yield workos.fga.createResource({
|
|
776
|
+
resource: { resourceType: 'role', resourceId: 'role1' },
|
|
777
|
+
meta: { name: 'Role 1', description: 'This is role 1.' },
|
|
778
|
+
});
|
|
779
|
+
const role2 = yield workos.fga.createResource({
|
|
780
|
+
resource: { resourceType: 'role', resourceId: 'role2' },
|
|
781
|
+
meta: { name: 'Role 2' },
|
|
782
|
+
});
|
|
783
|
+
yield workos.fga.writeWarrant({
|
|
784
|
+
resource: permission1,
|
|
785
|
+
relation: 'member',
|
|
786
|
+
subject: role1,
|
|
787
|
+
});
|
|
788
|
+
yield workos.fga.writeWarrant({
|
|
789
|
+
resource: permission2,
|
|
790
|
+
relation: 'member',
|
|
791
|
+
subject: role2,
|
|
792
|
+
});
|
|
793
|
+
yield workos.fga.writeWarrant({
|
|
794
|
+
resource: permission3,
|
|
795
|
+
relation: 'member',
|
|
796
|
+
subject: role2,
|
|
797
|
+
});
|
|
798
|
+
yield workos.fga.writeWarrant({
|
|
799
|
+
resource: role2,
|
|
800
|
+
relation: 'member',
|
|
801
|
+
subject: role1,
|
|
802
|
+
});
|
|
803
|
+
yield workos.fga.writeWarrant({
|
|
804
|
+
resource: permission1,
|
|
805
|
+
relation: 'member',
|
|
806
|
+
subject: role2,
|
|
807
|
+
policy: 'tenantId == 123',
|
|
808
|
+
});
|
|
809
|
+
yield workos.fga.writeWarrant({
|
|
810
|
+
resource: role1,
|
|
811
|
+
relation: 'member',
|
|
812
|
+
subject: userA,
|
|
813
|
+
});
|
|
814
|
+
yield workos.fga.writeWarrant({
|
|
815
|
+
resource: role2,
|
|
816
|
+
relation: 'member',
|
|
817
|
+
subject: userB,
|
|
818
|
+
});
|
|
819
|
+
let resultSet = yield workos.fga.query({ q: 'select role where user:userA is member', limit: 1, order: 'asc' }, { warrantToken: 'latest' });
|
|
820
|
+
expect(resultSet.data.length).toEqual(1);
|
|
821
|
+
expect(resultSet.data[0].resourceType).toEqual('role');
|
|
822
|
+
expect(resultSet.data[0].resourceId).toEqual('role1');
|
|
823
|
+
expect(resultSet.data[0].relation).toEqual('member');
|
|
824
|
+
expect(resultSet.data[0].warrant.resourceType).toEqual('role');
|
|
825
|
+
expect(resultSet.data[0].warrant.resourceId).toEqual('role1');
|
|
826
|
+
expect(resultSet.data[0].warrant.relation).toEqual('member');
|
|
827
|
+
expect(resultSet.data[0].warrant.subject.resourceType).toEqual('user');
|
|
828
|
+
expect(resultSet.data[0].warrant.subject.resourceId).toEqual('userA');
|
|
829
|
+
expect(resultSet.data[0].warrant.policy).toBeUndefined();
|
|
830
|
+
expect(resultSet.data[0].isImplicit).toEqual(false);
|
|
831
|
+
resultSet = yield workos.fga.query({
|
|
832
|
+
q: 'select role where user:userA is member',
|
|
833
|
+
limit: 1,
|
|
834
|
+
order: 'asc',
|
|
835
|
+
after: resultSet.listMetadata.after,
|
|
836
|
+
}, { warrantToken: 'latest' });
|
|
837
|
+
expect(resultSet.data.length).toEqual(1);
|
|
838
|
+
expect(resultSet.data[0].resourceType).toEqual('role');
|
|
839
|
+
expect(resultSet.data[0].resourceId).toEqual('role2');
|
|
840
|
+
expect(resultSet.data[0].relation).toEqual('member');
|
|
841
|
+
expect(resultSet.data[0].warrant.resourceType).toEqual('role');
|
|
842
|
+
expect(resultSet.data[0].warrant.resourceId).toEqual('role2');
|
|
843
|
+
expect(resultSet.data[0].warrant.relation).toEqual('member');
|
|
844
|
+
expect(resultSet.data[0].warrant.subject.resourceType).toEqual('role');
|
|
845
|
+
expect(resultSet.data[0].warrant.subject.resourceId).toEqual('role1');
|
|
846
|
+
expect(resultSet.data[0].warrant.policy).toBeUndefined();
|
|
847
|
+
expect(resultSet.data[0].isImplicit).toEqual(true);
|
|
848
|
+
resultSet = yield workos.fga.query({
|
|
849
|
+
q: 'select permission where user:userB is member',
|
|
850
|
+
context: { tenantId: 123 },
|
|
851
|
+
order: 'asc',
|
|
852
|
+
}, { warrantToken: 'latest' });
|
|
853
|
+
expect(resultSet.data.length).toEqual(3);
|
|
854
|
+
expect(resultSet.data[0].resourceType).toEqual('permission');
|
|
855
|
+
expect(resultSet.data[0].resourceId).toEqual('perm1');
|
|
856
|
+
expect(resultSet.data[0].relation).toEqual('member');
|
|
857
|
+
expect(resultSet.data[1].resourceType).toEqual('permission');
|
|
858
|
+
expect(resultSet.data[1].resourceId).toEqual('perm2');
|
|
859
|
+
expect(resultSet.data[1].relation).toEqual('member');
|
|
860
|
+
expect(resultSet.data[2].resourceType).toEqual('permission');
|
|
861
|
+
expect(resultSet.data[2].resourceId).toEqual('perm3');
|
|
862
|
+
expect(resultSet.data[2].relation).toEqual('member');
|
|
863
|
+
// Clean up
|
|
864
|
+
yield workos.fga.deleteResource(role1);
|
|
865
|
+
yield workos.fga.deleteResource(role2);
|
|
866
|
+
yield workos.fga.deleteResource(permission1);
|
|
867
|
+
yield workos.fga.deleteResource(permission2);
|
|
868
|
+
yield workos.fga.deleteResource(permission3);
|
|
869
|
+
yield workos.fga.deleteResource(userA);
|
|
870
|
+
yield workos.fga.deleteResource(userB);
|
|
871
|
+
}));
|
|
872
|
+
});
|