@tellescope/sdk 1.242.9 → 1.243.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/cjs/enduser.d.ts +20 -0
- package/lib/cjs/enduser.d.ts.map +1 -1
- package/lib/cjs/sdk.d.ts +45 -0
- package/lib/cjs/sdk.d.ts.map +1 -1
- package/lib/cjs/sdk.js +2 -0
- package/lib/cjs/sdk.js.map +1 -1
- package/lib/cjs/tests/api_tests/concurrent_build_threads.test.d.ts +6 -0
- package/lib/cjs/tests/api_tests/concurrent_build_threads.test.d.ts.map +1 -0
- package/lib/cjs/tests/api_tests/concurrent_build_threads.test.js +169 -0
- package/lib/cjs/tests/api_tests/concurrent_build_threads.test.js.map +1 -0
- package/lib/cjs/tests/api_tests/custom_aggregation.test.d.ts.map +1 -1
- package/lib/cjs/tests/api_tests/custom_aggregation.test.js +109 -7
- package/lib/cjs/tests/api_tests/custom_aggregation.test.js.map +1 -1
- package/lib/cjs/tests/api_tests/custom_dashboards.test.d.ts +6 -0
- package/lib/cjs/tests/api_tests/custom_dashboards.test.d.ts.map +1 -0
- package/lib/cjs/tests/api_tests/custom_dashboards.test.js +304 -0
- package/lib/cjs/tests/api_tests/custom_dashboards.test.js.map +1 -0
- package/lib/cjs/tests/api_tests/inbox_thread_assignment_updates.test.d.ts.map +1 -1
- package/lib/cjs/tests/api_tests/inbox_thread_assignment_updates.test.js +655 -139
- package/lib/cjs/tests/api_tests/inbox_thread_assignment_updates.test.js.map +1 -1
- package/lib/cjs/tests/api_tests/no_access_permission_checks.test.d.ts +20 -0
- package/lib/cjs/tests/api_tests/no_access_permission_checks.test.d.ts.map +1 -0
- package/lib/cjs/tests/api_tests/no_access_permission_checks.test.js +481 -0
- package/lib/cjs/tests/api_tests/no_access_permission_checks.test.js.map +1 -0
- package/lib/cjs/tests/tests.d.ts.map +1 -1
- package/lib/cjs/tests/tests.js +125 -112
- package/lib/cjs/tests/tests.js.map +1 -1
- package/lib/esm/enduser.d.ts +20 -0
- package/lib/esm/enduser.d.ts.map +1 -1
- package/lib/esm/sdk.d.ts +45 -0
- package/lib/esm/sdk.d.ts.map +1 -1
- package/lib/esm/sdk.js +2 -0
- package/lib/esm/sdk.js.map +1 -1
- package/lib/esm/tests/api_tests/concurrent_build_threads.test.d.ts +6 -0
- package/lib/esm/tests/api_tests/concurrent_build_threads.test.d.ts.map +1 -0
- package/lib/esm/tests/api_tests/concurrent_build_threads.test.js +165 -0
- package/lib/esm/tests/api_tests/concurrent_build_threads.test.js.map +1 -0
- package/lib/esm/tests/api_tests/custom_aggregation.test.d.ts.map +1 -1
- package/lib/esm/tests/api_tests/custom_aggregation.test.js +110 -8
- package/lib/esm/tests/api_tests/custom_aggregation.test.js.map +1 -1
- package/lib/esm/tests/api_tests/custom_dashboards.test.d.ts +6 -0
- package/lib/esm/tests/api_tests/custom_dashboards.test.d.ts.map +1 -0
- package/lib/esm/tests/api_tests/custom_dashboards.test.js +300 -0
- package/lib/esm/tests/api_tests/custom_dashboards.test.js.map +1 -0
- package/lib/esm/tests/api_tests/inbox_thread_assignment_updates.test.d.ts.map +1 -1
- package/lib/esm/tests/api_tests/inbox_thread_assignment_updates.test.js +655 -139
- package/lib/esm/tests/api_tests/inbox_thread_assignment_updates.test.js.map +1 -1
- package/lib/esm/tests/api_tests/no_access_permission_checks.test.d.ts +20 -0
- package/lib/esm/tests/api_tests/no_access_permission_checks.test.d.ts.map +1 -0
- package/lib/esm/tests/api_tests/no_access_permission_checks.test.js +477 -0
- package/lib/esm/tests/api_tests/no_access_permission_checks.test.js.map +1 -0
- package/lib/esm/tests/tests.d.ts.map +1 -1
- package/lib/esm/tests/tests.js +125 -112
- package/lib/esm/tests/tests.js.map +1 -1
- package/lib/tsconfig.tsbuildinfo +1 -1
- package/package.json +10 -10
- package/src/sdk.ts +9 -1
- package/src/tests/api_tests/concurrent_build_threads.test.ts +103 -0
- package/src/tests/api_tests/custom_aggregation.test.ts +74 -0
- package/src/tests/api_tests/custom_dashboards.test.ts +258 -0
- package/src/tests/api_tests/inbox_thread_assignment_updates.test.ts +431 -1
- package/src/tests/api_tests/no_access_permission_checks.test.ts +365 -0
- package/src/tests/tests.ts +8 -1
- package/test_generated.pdf +0 -0
|
@@ -0,0 +1,365 @@
|
|
|
1
|
+
require('source-map-support').install();
|
|
2
|
+
|
|
3
|
+
import { Session } from "../../sdk"
|
|
4
|
+
import {
|
|
5
|
+
async_test,
|
|
6
|
+
log_header,
|
|
7
|
+
wait,
|
|
8
|
+
} from "@tellescope/testing"
|
|
9
|
+
import { setup_tests } from "../setup"
|
|
10
|
+
import { PROVIDER_PERMISSIONS } from "@tellescope/constants"
|
|
11
|
+
|
|
12
|
+
const host = process.env.API_URL || 'http://localhost:8080' as const
|
|
13
|
+
const [nonAdminEmail, nonAdminPassword] = [process.env.NON_ADMIN_EMAIL, process.env.NON_ADMIN_PASSWORD]
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Security tests for endpoints with noAccessPermissions: true
|
|
17
|
+
*
|
|
18
|
+
* These tests verify that endpoints which bypass the standard middleware access check
|
|
19
|
+
* still properly enforce NO_ACCESS restrictions in their handlers.
|
|
20
|
+
*
|
|
21
|
+
* Test approach:
|
|
22
|
+
* 1. Create a role with NO_ACCESS (null) for a specific model
|
|
23
|
+
* 2. Assign that role to a non-admin user
|
|
24
|
+
* 3. Attempt to call the endpoint
|
|
25
|
+
* 4. Verify whether access is properly denied
|
|
26
|
+
*
|
|
27
|
+
* If a test shows data is returned when it shouldn't be, that endpoint needs a fix.
|
|
28
|
+
*/
|
|
29
|
+
export const no_access_permission_checks_tests = async ({ sdk, sdkNonAdmin } : { sdk: Session, sdkNonAdmin: Session }) => {
|
|
30
|
+
log_header("NO_ACCESS Permission Checks Tests")
|
|
31
|
+
|
|
32
|
+
// Create test data
|
|
33
|
+
const testEnduser = await sdk.api.endusers.createOne({
|
|
34
|
+
fname: 'NoAccessTest',
|
|
35
|
+
lname: 'User',
|
|
36
|
+
email: 'no-access-test@example.com',
|
|
37
|
+
})
|
|
38
|
+
|
|
39
|
+
// Create a role with NO_ACCESS to multiple models we want to test
|
|
40
|
+
const noAccessTestRole = 'no-access-test-role'
|
|
41
|
+
const rbap = await sdk.api.role_based_access_permissions.createOne({
|
|
42
|
+
role: noAccessTestRole,
|
|
43
|
+
permissions: {
|
|
44
|
+
...PROVIDER_PERMISSIONS,
|
|
45
|
+
// Set NO_ACCESS for models we want to test
|
|
46
|
+
endusers: {
|
|
47
|
+
create: null,
|
|
48
|
+
read: null,
|
|
49
|
+
update: null,
|
|
50
|
+
delete: null,
|
|
51
|
+
},
|
|
52
|
+
inbox_threads: {
|
|
53
|
+
create: null,
|
|
54
|
+
read: null,
|
|
55
|
+
update: null,
|
|
56
|
+
delete: null,
|
|
57
|
+
},
|
|
58
|
+
templates: {
|
|
59
|
+
create: null,
|
|
60
|
+
read: null,
|
|
61
|
+
update: null,
|
|
62
|
+
delete: null,
|
|
63
|
+
},
|
|
64
|
+
waitlists: {
|
|
65
|
+
create: null,
|
|
66
|
+
read: null,
|
|
67
|
+
update: null,
|
|
68
|
+
delete: null,
|
|
69
|
+
},
|
|
70
|
+
background_errors: {
|
|
71
|
+
create: null,
|
|
72
|
+
read: null,
|
|
73
|
+
update: null,
|
|
74
|
+
delete: null,
|
|
75
|
+
},
|
|
76
|
+
},
|
|
77
|
+
})
|
|
78
|
+
|
|
79
|
+
// Save original role to restore later
|
|
80
|
+
const originalRoles = sdkNonAdmin.userInfo.roles
|
|
81
|
+
|
|
82
|
+
try {
|
|
83
|
+
// Assign the restricted role to non-admin user
|
|
84
|
+
await sdk.api.users.updateOne(sdkNonAdmin.userInfo.id, { roles: [noAccessTestRole] }, { replaceObjectFields: true })
|
|
85
|
+
await wait(undefined, 1500) // wait for role change to propagate
|
|
86
|
+
await sdkNonAdmin.authenticate(nonAdminEmail!, nonAdminPassword!)
|
|
87
|
+
|
|
88
|
+
// ========================================
|
|
89
|
+
// Test 1: /bulk-actions/read (HIGH PRIORITY)
|
|
90
|
+
// ========================================
|
|
91
|
+
log_header("Test 1: /bulk-actions/read with NO_ACCESS to endusers")
|
|
92
|
+
|
|
93
|
+
await async_test(
|
|
94
|
+
"bulk_load - should block NO_ACCESS user from reading endusers",
|
|
95
|
+
() => sdkNonAdmin.bulk_load({
|
|
96
|
+
load: [{ model: 'endusers' as any, options: { limit: 10 } }]
|
|
97
|
+
}),
|
|
98
|
+
{
|
|
99
|
+
// If this returns records, it's a vulnerability
|
|
100
|
+
// If it returns empty records or errors, it's safe
|
|
101
|
+
onResult: r => {
|
|
102
|
+
const enduserResult = r.results[0]
|
|
103
|
+
if (enduserResult === null) {
|
|
104
|
+
console.log(" ✅ SAFE: bulk_load returned null for NO_ACCESS model")
|
|
105
|
+
return true
|
|
106
|
+
}
|
|
107
|
+
if (enduserResult.records.length === 0) {
|
|
108
|
+
console.log(" ✅ SAFE: bulk_load returned empty records for NO_ACCESS model")
|
|
109
|
+
return true
|
|
110
|
+
}
|
|
111
|
+
console.log(` ❌ VULNERABILITY: bulk_load returned ${enduserResult.records.length} records when user has NO_ACCESS!`)
|
|
112
|
+
return false
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
)
|
|
116
|
+
|
|
117
|
+
// ========================================
|
|
118
|
+
// Test 2: inbox_threads/build_threads
|
|
119
|
+
// ========================================
|
|
120
|
+
log_header("Test 2: inbox_threads/build_threads with NO_ACCESS")
|
|
121
|
+
|
|
122
|
+
await async_test(
|
|
123
|
+
"build_threads - should block NO_ACCESS user",
|
|
124
|
+
() => sdkNonAdmin.api.inbox_threads.build_threads({
|
|
125
|
+
from: new Date(Date.now() - 7 * 24 * 60 * 60 * 1000), // 1 week ago
|
|
126
|
+
to: new Date(),
|
|
127
|
+
}),
|
|
128
|
+
{ shouldError: true, onError: (e: any) => e.message === "You do not have access to this resource" }
|
|
129
|
+
)
|
|
130
|
+
|
|
131
|
+
// ========================================
|
|
132
|
+
// Test 2b: inbox_threads/load_threads with NO_ACCESS
|
|
133
|
+
// ========================================
|
|
134
|
+
log_header("Test 2b: load_threads with NO_ACCESS")
|
|
135
|
+
|
|
136
|
+
await async_test(
|
|
137
|
+
"load_threads - should block NO_ACCESS user",
|
|
138
|
+
() => sdkNonAdmin.api.inbox_threads.load_threads({ limit: 10 }),
|
|
139
|
+
{ shouldError: true, onError: (e: any) => e.message === "You do not have access to this resource" }
|
|
140
|
+
)
|
|
141
|
+
|
|
142
|
+
// ========================================
|
|
143
|
+
// Test 3a: get_templated_message - NO_ACCESS to templates
|
|
144
|
+
// ========================================
|
|
145
|
+
log_header("Test 3a: get_templated_message (templates NO_ACCESS)")
|
|
146
|
+
|
|
147
|
+
await async_test(
|
|
148
|
+
"get_templated_message - should block user with NO_ACCESS to templates",
|
|
149
|
+
() => sdkNonAdmin.api.templates.get_templated_message({
|
|
150
|
+
message: "Hello {{enduser.fname}}!",
|
|
151
|
+
userId: sdkNonAdmin.userInfo.id,
|
|
152
|
+
enduserId: testEnduser.id,
|
|
153
|
+
channel: 'Email',
|
|
154
|
+
}),
|
|
155
|
+
{ shouldError: true, onError: (e: any) => e.message === "You do not have access to this resource" }
|
|
156
|
+
)
|
|
157
|
+
|
|
158
|
+
// ========================================
|
|
159
|
+
// Test 3b: get_templated_message - NO_ACCESS to endusers (PHI leak prevention)
|
|
160
|
+
// ========================================
|
|
161
|
+
log_header("Test 3b: get_templated_message (endusers NO_ACCESS)")
|
|
162
|
+
|
|
163
|
+
// Create a role with templates access but NO_ACCESS to endusers
|
|
164
|
+
const templatesOnlyRole = 'templates-only-test-role'
|
|
165
|
+
const rbapTemplatesOnly = await sdk.api.role_based_access_permissions.createOne({
|
|
166
|
+
role: templatesOnlyRole,
|
|
167
|
+
permissions: {
|
|
168
|
+
...PROVIDER_PERMISSIONS,
|
|
169
|
+
// Allow templates access
|
|
170
|
+
templates: {
|
|
171
|
+
create: 'All',
|
|
172
|
+
read: 'All',
|
|
173
|
+
update: 'All',
|
|
174
|
+
delete: 'All',
|
|
175
|
+
},
|
|
176
|
+
// But NO_ACCESS to endusers
|
|
177
|
+
endusers: {
|
|
178
|
+
create: null,
|
|
179
|
+
read: null,
|
|
180
|
+
update: null,
|
|
181
|
+
delete: null,
|
|
182
|
+
},
|
|
183
|
+
},
|
|
184
|
+
})
|
|
185
|
+
|
|
186
|
+
try {
|
|
187
|
+
// Temporarily assign the templates-only role
|
|
188
|
+
await sdk.api.users.updateOne(sdkNonAdmin.userInfo.id, { roles: [templatesOnlyRole] }, { replaceObjectFields: true })
|
|
189
|
+
await wait(undefined, 1500)
|
|
190
|
+
await sdkNonAdmin.authenticate(nonAdminEmail!, nonAdminPassword!)
|
|
191
|
+
|
|
192
|
+
await async_test(
|
|
193
|
+
"get_templated_message - should block user with NO_ACCESS to endusers (prevents PHI leak)",
|
|
194
|
+
() => sdkNonAdmin.api.templates.get_templated_message({
|
|
195
|
+
message: "Hello {{enduser.fname}} {{enduser.lname}} {{enduser.email}}!",
|
|
196
|
+
userId: sdkNonAdmin.userInfo.id,
|
|
197
|
+
enduserId: testEnduser.id,
|
|
198
|
+
channel: 'Email',
|
|
199
|
+
}),
|
|
200
|
+
{ shouldError: true, onError: (e: any) => e.message === "You do not have access to this resource" }
|
|
201
|
+
)
|
|
202
|
+
} finally {
|
|
203
|
+
// Restore the original test role
|
|
204
|
+
await sdk.api.users.updateOne(sdkNonAdmin.userInfo.id, { roles: [noAccessTestRole] }, { replaceObjectFields: true })
|
|
205
|
+
await wait(undefined, 1000)
|
|
206
|
+
await sdkNonAdmin.authenticate(nonAdminEmail!, nonAdminPassword!)
|
|
207
|
+
|
|
208
|
+
// Cleanup the templates-only role
|
|
209
|
+
await sdk.api.role_based_access_permissions.deleteOne(rbapTemplatesOnly.id)
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
// ========================================
|
|
213
|
+
// Test 4: waitlists/grant_access_from_waitlist
|
|
214
|
+
// ========================================
|
|
215
|
+
log_header("Test 4: waitlists/grant_access_from_waitlist with NO_ACCESS")
|
|
216
|
+
|
|
217
|
+
// First create a journey and waitlist entry to test with (as admin)
|
|
218
|
+
const testJourney = await sdk.api.journeys.createOne({
|
|
219
|
+
title: 'Waitlist Test Journey',
|
|
220
|
+
})
|
|
221
|
+
|
|
222
|
+
const waitlistEntry = await sdk.api.waitlists.createOne({
|
|
223
|
+
title: 'Test Waitlist',
|
|
224
|
+
journeyId: testJourney.id,
|
|
225
|
+
enduserIds: [],
|
|
226
|
+
})
|
|
227
|
+
|
|
228
|
+
try {
|
|
229
|
+
await async_test(
|
|
230
|
+
"grant_access_from_waitlist - should block NO_ACCESS user",
|
|
231
|
+
() => sdkNonAdmin.api.waitlists.grant_access_from_waitlist({
|
|
232
|
+
id: waitlistEntry.id,
|
|
233
|
+
count: 1,
|
|
234
|
+
}),
|
|
235
|
+
{ shouldError: true, onError: (e: any) => e.message === "You do not have access to this resource" }
|
|
236
|
+
)
|
|
237
|
+
} finally {
|
|
238
|
+
// Cleanup
|
|
239
|
+
await sdk.api.waitlists.deleteOne(waitlistEntry.id)
|
|
240
|
+
await sdk.api.journeys.deleteOne(testJourney.id)
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
// ========================================
|
|
244
|
+
// Test 5: background_errors/mark_read
|
|
245
|
+
// ========================================
|
|
246
|
+
log_header("Test 5: background_errors/mark_read with NO_ACCESS")
|
|
247
|
+
|
|
248
|
+
await async_test(
|
|
249
|
+
"mark_read (background_errors) - should block NO_ACCESS user",
|
|
250
|
+
() => sdkNonAdmin.api.background_errors.mark_read({}),
|
|
251
|
+
{ shouldError: true, onError: (e: any) => e.message === "You do not have access to this resource" }
|
|
252
|
+
)
|
|
253
|
+
|
|
254
|
+
// ========================================
|
|
255
|
+
// Test 6: load_threads searchKeywords redaction
|
|
256
|
+
// ========================================
|
|
257
|
+
log_header("Test 6: load_threads searchKeywords redaction")
|
|
258
|
+
|
|
259
|
+
// Create role with Assigned access to endusers (not 'All') but full message access
|
|
260
|
+
const assignedEnduserRole = 'assigned-enduser-test-role'
|
|
261
|
+
const rbapAssigned = await sdk.api.role_based_access_permissions.createOne({
|
|
262
|
+
role: assignedEnduserRole,
|
|
263
|
+
permissions: {
|
|
264
|
+
...PROVIDER_PERMISSIONS,
|
|
265
|
+
endusers: { create: 'All', read: 'Assigned', update: 'Assigned', delete: 'Assigned' },
|
|
266
|
+
emails: { create: 'All', read: 'All', update: 'All', delete: 'All' },
|
|
267
|
+
sms_messages: { create: 'All', read: 'All', update: 'All', delete: 'All' },
|
|
268
|
+
inbox_threads: { create: 'All', read: 'All', update: 'All', delete: 'All' },
|
|
269
|
+
},
|
|
270
|
+
})
|
|
271
|
+
|
|
272
|
+
try {
|
|
273
|
+
await sdk.api.users.updateOne(sdkNonAdmin.userInfo.id, { roles: [assignedEnduserRole] }, { replaceObjectFields: true })
|
|
274
|
+
await wait(undefined, 1500)
|
|
275
|
+
await sdkNonAdmin.authenticate(nonAdminEmail!, nonAdminPassword!)
|
|
276
|
+
|
|
277
|
+
// Load threads and verify searchKeywords is redacted for Assigned enduser access
|
|
278
|
+
const resultAssigned = await sdkNonAdmin.api.inbox_threads.load_threads({ limit: 10 })
|
|
279
|
+
|
|
280
|
+
await async_test(
|
|
281
|
+
"load_threads - searchKeywords redacted for Assigned enduser access",
|
|
282
|
+
async () => resultAssigned,
|
|
283
|
+
{
|
|
284
|
+
onResult: r => {
|
|
285
|
+
// All threads should have searchKeywords undefined/missing
|
|
286
|
+
const allRedacted = r.threads.every((t: any) => t.searchKeywords === undefined)
|
|
287
|
+
if (!allRedacted) {
|
|
288
|
+
console.log(" ❌ VULNERABILITY: searchKeywords visible to user with Assigned enduser access!")
|
|
289
|
+
} else {
|
|
290
|
+
console.log(" ✅ SAFE: searchKeywords properly redacted")
|
|
291
|
+
}
|
|
292
|
+
return allRedacted
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
)
|
|
296
|
+
} finally {
|
|
297
|
+
// Restore the original test role
|
|
298
|
+
await sdk.api.users.updateOne(sdkNonAdmin.userInfo.id, { roles: [noAccessTestRole] }, { replaceObjectFields: true })
|
|
299
|
+
await wait(undefined, 1000)
|
|
300
|
+
await sdkNonAdmin.authenticate(nonAdminEmail!, nonAdminPassword!)
|
|
301
|
+
|
|
302
|
+
// Cleanup the assigned role
|
|
303
|
+
await sdk.api.role_based_access_permissions.deleteOne(rbapAssigned.id)
|
|
304
|
+
}
|
|
305
|
+
|
|
306
|
+
// Test that admin/full access users CAN see searchKeywords
|
|
307
|
+
await async_test(
|
|
308
|
+
"load_threads - searchKeywords visible for admin/full enduser access",
|
|
309
|
+
() => sdk.api.inbox_threads.load_threads({ limit: 10 }),
|
|
310
|
+
{
|
|
311
|
+
onResult: r => {
|
|
312
|
+
// Skip check if no threads exist (can't verify without data)
|
|
313
|
+
if (r.threads.length === 0) {
|
|
314
|
+
console.log(" ⏭️ SKIPPED: No threads exist to verify searchKeywords visibility")
|
|
315
|
+
return true
|
|
316
|
+
}
|
|
317
|
+
// At least some threads should have searchKeywords
|
|
318
|
+
const hasSearchKeywords = r.threads.some((t: any) => t.searchKeywords !== undefined)
|
|
319
|
+
if (hasSearchKeywords) {
|
|
320
|
+
console.log(" ✅ Admin can see searchKeywords")
|
|
321
|
+
} else {
|
|
322
|
+
console.log(" ⚠️ No searchKeywords found on threads (may not have been built yet)")
|
|
323
|
+
}
|
|
324
|
+
return true // Don't fail if keywords don't exist yet
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
)
|
|
328
|
+
|
|
329
|
+
console.log("\n" + "=".repeat(60))
|
|
330
|
+
console.log("NO_ACCESS Permission Checks Tests Complete")
|
|
331
|
+
console.log("=".repeat(60))
|
|
332
|
+
|
|
333
|
+
} finally {
|
|
334
|
+
// Restore original role
|
|
335
|
+
await sdk.api.users.updateOne(sdkNonAdmin.userInfo.id, { roles: originalRoles }, { replaceObjectFields: true })
|
|
336
|
+
await wait(undefined, 1000)
|
|
337
|
+
await sdkNonAdmin.authenticate(nonAdminEmail!, nonAdminPassword!)
|
|
338
|
+
|
|
339
|
+
// Cleanup
|
|
340
|
+
await sdk.api.role_based_access_permissions.deleteOne(rbap.id)
|
|
341
|
+
await sdk.api.endusers.deleteOne(testEnduser.id)
|
|
342
|
+
}
|
|
343
|
+
}
|
|
344
|
+
|
|
345
|
+
// Allow running this test file independently
|
|
346
|
+
if (require.main === module) {
|
|
347
|
+
console.log(`🌐 Using API URL: ${host}`)
|
|
348
|
+
const sdk = new Session({ host })
|
|
349
|
+
const sdkNonAdmin = new Session({ host })
|
|
350
|
+
|
|
351
|
+
const runTests = async () => {
|
|
352
|
+
await setup_tests(sdk, sdkNonAdmin)
|
|
353
|
+
await no_access_permission_checks_tests({ sdk, sdkNonAdmin })
|
|
354
|
+
}
|
|
355
|
+
|
|
356
|
+
runTests()
|
|
357
|
+
.then(() => {
|
|
358
|
+
console.log("✅ NO_ACCESS permission checks test suite completed successfully")
|
|
359
|
+
process.exit(0)
|
|
360
|
+
})
|
|
361
|
+
.catch((error) => {
|
|
362
|
+
console.error("❌ NO_ACCESS permission checks test suite failed:", error)
|
|
363
|
+
process.exit(1)
|
|
364
|
+
})
|
|
365
|
+
}
|
package/src/tests/tests.ts
CHANGED
|
@@ -40,6 +40,7 @@ import { create_user_notifications_trigger_tests } from "./api_tests/create_user
|
|
|
40
40
|
import { inbox_thread_assignment_updates_tests } from "./api_tests/inbox_thread_assignment_updates.test"
|
|
41
41
|
import { inbox_thread_draft_scheduled_tests } from "./api_tests/inbox_thread_draft_scheduled.test"
|
|
42
42
|
import { load_threads_autobuild_tests } from "./api_tests/load_threads_autobuild.test"
|
|
43
|
+
import { concurrent_build_threads_tests } from "./api_tests/concurrent_build_threads.test"
|
|
43
44
|
import { appointment_completed_trigger_tests } from "./api_tests/appointment_completed_trigger.test"
|
|
44
45
|
import { purchase_made_trigger_tests } from "./api_tests/purchase_made_trigger.test"
|
|
45
46
|
import { appointment_rescheduled_trigger_tests } from "./api_tests/appointment_rescheduled_trigger.test"
|
|
@@ -70,11 +71,13 @@ import {
|
|
|
70
71
|
|
|
71
72
|
import fs from "fs"
|
|
72
73
|
import { load_inbox_data_tests } from "./api_tests/load_inbox_data.test";
|
|
74
|
+
import { custom_dashboards_tests } from "./api_tests/custom_dashboards.test";
|
|
73
75
|
import { message_assignment_trigger_tests } from "./api_tests/message_assignment_trigger.test";
|
|
74
76
|
import { time_tracks_tests } from "./api_tests/time_tracks.test";
|
|
75
77
|
import { monthly_availability_restrictions_tests } from "./api_tests/monthly_availability_restrictions.test";
|
|
76
78
|
import { calendar_event_limits_tests } from "./api_tests/calendar_event_limits.test";
|
|
77
79
|
import { custom_aggregation_tests } from "./api_tests/custom_aggregation.test";
|
|
80
|
+
import { no_access_permission_checks_tests } from "./api_tests/no_access_permission_checks.test";
|
|
78
81
|
import { bulk_assignment_tests } from "./api_tests/bulk_assignment.test";
|
|
79
82
|
import { managed_content_enduser_access_tests } from "./api_tests/managed_content_enduser_access.test";
|
|
80
83
|
import { auto_merge_form_submission_tests } from "./api_tests/auto_merge_form_submission.test";
|
|
@@ -9183,6 +9186,7 @@ const tests: { [K in keyof ClientModelForName]: () => void } = {
|
|
|
9183
9186
|
superbill_providers: NO_TEST,
|
|
9184
9187
|
superbills: NO_TEST,
|
|
9185
9188
|
enduser_profile_views: NO_TEST,
|
|
9189
|
+
custom_dashboards: NO_TEST, // Called in main runner with SDK dependency
|
|
9186
9190
|
enduser_custom_types: NO_TEST,
|
|
9187
9191
|
table_views: NO_TEST,
|
|
9188
9192
|
email_sync_denials: NO_TEST,
|
|
@@ -13924,6 +13928,10 @@ const ip_address_form_tests = async () => {
|
|
|
13924
13928
|
await replace_enduser_template_values_tests()
|
|
13925
13929
|
await mfa_tests()
|
|
13926
13930
|
await setup_tests(sdk, sdkNonAdmin)
|
|
13931
|
+
await custom_dashboards_tests({ sdk, sdkNonAdmin })
|
|
13932
|
+
await concurrent_build_threads_tests({ sdk, sdkNonAdmin })
|
|
13933
|
+
await custom_aggregation_tests({ sdk, sdkNonAdmin })
|
|
13934
|
+
await no_access_permission_checks_tests({ sdk, sdkNonAdmin })
|
|
13927
13935
|
await enduser_tests()
|
|
13928
13936
|
await form_started_trigger_tests({ sdk, sdkNonAdmin })
|
|
13929
13937
|
await load_team_chat_tests({ sdk, sdkNonAdmin })
|
|
@@ -13938,7 +13946,6 @@ const ip_address_form_tests = async () => {
|
|
|
13938
13946
|
await managed_content_enduser_access_tests({ sdk, sdkNonAdmin })
|
|
13939
13947
|
await afteraction_day_of_month_delay_tests({ sdk, sdkNonAdmin })
|
|
13940
13948
|
await bulk_assignment_tests({ sdk, sdkNonAdmin })
|
|
13941
|
-
await custom_aggregation_tests({ sdk, sdkNonAdmin })
|
|
13942
13949
|
await formsort_tests()
|
|
13943
13950
|
await self_serve_appointment_booking_tests()
|
|
13944
13951
|
await time_tracks_tests({ sdk, sdkNonAdmin })
|
package/test_generated.pdf
CHANGED
|
Binary file
|