@webex/webex-core 3.12.0-webex-services-ready.2 → 3.12.0-webex-services-ready.4
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/README.md +5 -2
- package/dist/config.js +15 -0
- package/dist/config.js.map +1 -1
- package/dist/lib/batcher.js +1 -1
- package/dist/lib/credentials/credentials.js +1 -1
- package/dist/lib/credentials/token.js +1 -1
- package/dist/lib/domains.js +90 -0
- package/dist/lib/domains.js.map +1 -0
- package/dist/lib/services/service-catalog.js +6 -10
- package/dist/lib/services/service-catalog.js.map +1 -1
- package/dist/lib/services/services.js +26 -22
- package/dist/lib/services/services.js.map +1 -1
- package/dist/lib/services-v2/service-catalog.js +6 -12
- package/dist/lib/services-v2/service-catalog.js.map +1 -1
- package/dist/lib/services-v2/services-v2.js +33 -24
- package/dist/lib/services-v2/services-v2.js.map +1 -1
- package/dist/plugins/logger.js +1 -1
- package/dist/webex-core.js +2 -2
- package/package.json +13 -13
- package/src/config.js +17 -0
- package/src/lib/domains.ts +94 -0
- package/src/lib/services/service-catalog.js +6 -10
- package/src/lib/services/services.js +37 -31
- package/src/lib/services-v2/service-catalog.ts +6 -11
- package/src/lib/services-v2/services-v2.ts +41 -31
- package/test/fixtures/activation-email.ts +22 -0
- package/test/integration/spec/services/service-catalog.js +7 -6
- package/test/integration/spec/services/services.js +11 -8
- package/test/integration/spec/services-v2/services-v2.js +11 -8
- package/test/unit/spec/interceptors/auth.js +56 -0
- package/test/unit/spec/services/service-catalog.js +93 -11
- package/test/unit/spec/services/services.js +6 -1
- package/test/unit/spec/services-v2/service-catalog.ts +93 -11
- package/test/unit/spec/services-v2/services-v2.ts +22 -1
- package/test/unit/spec/webex-core.js +0 -2
- package/test/unit/spec/webex-internal-core.js +0 -2
|
@@ -14,6 +14,8 @@ import {
|
|
|
14
14
|
AuthInterceptor,
|
|
15
15
|
config,
|
|
16
16
|
Credentials,
|
|
17
|
+
Services,
|
|
18
|
+
ServicesV2,
|
|
17
19
|
WebexHttpError,
|
|
18
20
|
Token,
|
|
19
21
|
serviceConstants,
|
|
@@ -380,6 +382,60 @@ describe('webex-core', () => {
|
|
|
380
382
|
});
|
|
381
383
|
});
|
|
382
384
|
|
|
385
|
+
describe('#onRequest() against a real service catalog', () => {
|
|
386
|
+
// The cases above stub `isAllowedDomainUrl`, so they answer the
|
|
387
|
+
// allowed-domain question themselves and cannot show that the catalog
|
|
388
|
+
// matcher is reached by the code that attaches the token. These use a
|
|
389
|
+
// real catalog and real allowed-domain methods.
|
|
390
|
+
[
|
|
391
|
+
{name: 'Services', Constructor: Services},
|
|
392
|
+
{name: 'ServicesV2', Constructor: ServicesV2},
|
|
393
|
+
].forEach(({name, Constructor}) => {
|
|
394
|
+
describe(name, () => {
|
|
395
|
+
let getUserToken;
|
|
396
|
+
|
|
397
|
+
beforeEach(() => {
|
|
398
|
+
const services = new Constructor(undefined, {parent: webex});
|
|
399
|
+
|
|
400
|
+
services._getCatalog().setAllowedDomains(['webex.com']);
|
|
401
|
+
// the catalog holds no services, so a url that is not covered by
|
|
402
|
+
// an allowed domain has nothing else to authorize it
|
|
403
|
+
services.waitForService = sinon.stub().rejects(new Error('no such service'));
|
|
404
|
+
|
|
405
|
+
webex.internal.services = services;
|
|
406
|
+
getUserToken = sinon.spy(webex.credentials, 'getUserToken');
|
|
407
|
+
});
|
|
408
|
+
|
|
409
|
+
afterEach(() => {
|
|
410
|
+
getUserToken.restore();
|
|
411
|
+
delete webex.internal.services;
|
|
412
|
+
});
|
|
413
|
+
|
|
414
|
+
it('adds the authorization header for a url under an allowed domain', () =>
|
|
415
|
+
interceptor
|
|
416
|
+
.onRequest({uri: 'https://api.webex.com/resource', headers: {}})
|
|
417
|
+
.then((options) => {
|
|
418
|
+
assert.equal(
|
|
419
|
+
options.headers.authorization,
|
|
420
|
+
webex.credentials.supertoken.toString()
|
|
421
|
+
);
|
|
422
|
+
assert.calledOnce(getUserToken);
|
|
423
|
+
}));
|
|
424
|
+
|
|
425
|
+
[
|
|
426
|
+
'https://notwebex.com/resource',
|
|
427
|
+
'https://webex.com.unrelated.example/resource',
|
|
428
|
+
].forEach((uri) => {
|
|
429
|
+
it(`does not add the authorization header for ${uri}`, () =>
|
|
430
|
+
interceptor.onRequest({uri, headers: {}}).then((options) => {
|
|
431
|
+
assert.notProperty(options.headers, 'authorization');
|
|
432
|
+
assert.notCalled(getUserToken);
|
|
433
|
+
}));
|
|
434
|
+
});
|
|
435
|
+
});
|
|
436
|
+
});
|
|
437
|
+
});
|
|
438
|
+
|
|
383
439
|
describe('#onResponseError()', () => {
|
|
384
440
|
describe('when the server responds with 401', () => {
|
|
385
441
|
nodeOnly(it)('refreshes the access token and replays the request', () => {
|
|
@@ -101,7 +101,24 @@ describe('webex-core', () => {
|
|
|
101
101
|
const domains = [];
|
|
102
102
|
|
|
103
103
|
beforeEach(() => {
|
|
104
|
-
|
|
104
|
+
// Shaped like a real catalog rather than a tidy list: the commercial
|
|
105
|
+
// domains the sdk ships with, a multi-part suffix, sites added at
|
|
106
|
+
// runtime from meeting preferences, an entry that overlaps another,
|
|
107
|
+
// and an unset entry, which callers can add and which must match
|
|
108
|
+
// nothing.
|
|
109
|
+
domains.push(
|
|
110
|
+
'wbx2.com',
|
|
111
|
+
'ciscospark.com',
|
|
112
|
+
'webex.com',
|
|
113
|
+
'webexapis.com',
|
|
114
|
+
'broadcloud.com.au',
|
|
115
|
+
'webexgov.us',
|
|
116
|
+
'example-a.com',
|
|
117
|
+
'example-b.com',
|
|
118
|
+
'example-c.com',
|
|
119
|
+
'go.example-a.com',
|
|
120
|
+
''
|
|
121
|
+
);
|
|
105
122
|
|
|
106
123
|
catalog.setAllowedDomains(domains);
|
|
107
124
|
});
|
|
@@ -110,10 +127,60 @@ describe('webex-core', () => {
|
|
|
110
127
|
domains.length = 0;
|
|
111
128
|
});
|
|
112
129
|
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
130
|
+
[
|
|
131
|
+
// real service hosts resolve to the entry that covers them
|
|
132
|
+
['https://u2c-a.wbx2.com/u2c/api/v1/limited/catalog', 'wbx2.com'],
|
|
133
|
+
['https://conv-a.wbx2.com/conversation/api/v1/conversations', 'wbx2.com'],
|
|
134
|
+
['https://foobar.ciscospark.com/resource/id', 'ciscospark.com'],
|
|
135
|
+
['https://idbroker.webex.com/idb/token', 'webex.com'],
|
|
136
|
+
['https://webexapis.com/v1/people/me', 'webexapis.com'],
|
|
137
|
+
// an entry is not required to be a bare registrable domain
|
|
138
|
+
['https://foo.broadcloud.com.au/resource/id', 'broadcloud.com.au'],
|
|
139
|
+
['https://a.b.webexgov.us/resource/id', 'webexgov.us'],
|
|
140
|
+
// the domain itself and its subdomains match
|
|
141
|
+
['https://example-a.com/resource/id', 'example-a.com'],
|
|
142
|
+
['https://sub.example-b.com/resource/id', 'example-b.com'],
|
|
143
|
+
['https://deep.sub.example-c.com/resource/id', 'example-c.com'],
|
|
144
|
+
// overlapping entries resolve to the first covering entry in the list
|
|
145
|
+
['https://go.example-a.com/resource/id', 'example-a.com'],
|
|
146
|
+
// an explicit port must not defeat the match
|
|
147
|
+
['https://example-a.com:8443/resource/id', 'example-a.com'],
|
|
148
|
+
['https://u2c-a.wbx2.com:8000/resource/id', 'wbx2.com'],
|
|
149
|
+
// hostname comparison is case insensitive
|
|
150
|
+
['https://U2C-A.WBX2.COM/resource/id', 'wbx2.com'],
|
|
151
|
+
// a trailing dot is the same name
|
|
152
|
+
['https://u2c-a.wbx2.com./resource/id', 'wbx2.com'],
|
|
153
|
+
// a sibling registrable domain must not match
|
|
154
|
+
['https://notwebex.com/resource/id', undefined],
|
|
155
|
+
['https://mywebexgov.us/resource/id', undefined],
|
|
156
|
+
['https://webex.company/resource/id', undefined],
|
|
157
|
+
['https://webex.com-unrelated.example/resource/id', undefined],
|
|
158
|
+
['https://example-a.community/resource/id', undefined],
|
|
159
|
+
// a partial label must not match, even against a multi-part entry
|
|
160
|
+
['https://broadcloud.com/resource/id', undefined],
|
|
161
|
+
// the domain matches only as a suffix, on a label boundary
|
|
162
|
+
['https://webex.com.unrelated.example/resource/id', undefined],
|
|
163
|
+
['https://unrelated.example/webex.com/resource/id', undefined],
|
|
164
|
+
['https://unrelated.example/?next=https://webex.com', undefined],
|
|
165
|
+
// userinfo is not the host
|
|
166
|
+
['https://webex.com@unrelated.example/resource/id', undefined],
|
|
167
|
+
// an encoded or unusual separator is not a label boundary, and the url
|
|
168
|
+
// parsers used by the transports do not agree on where these end the
|
|
169
|
+
// host, so they must not resolve to an allowed domain
|
|
170
|
+
['https://webex.com%2eunrelated.example/resource/id', undefined],
|
|
171
|
+
['https://webex.com%2Eunrelated.example/resource/id', undefined],
|
|
172
|
+
['https://unrelated.example%2ewebex.com/resource/id', undefined],
|
|
173
|
+
['https://unrelated.example%2Ewebex.com/resource/id', undefined],
|
|
174
|
+
['https://unrelated.example;.webex.com/resource/id', undefined],
|
|
175
|
+
// an empty allowed domain entry matches nothing
|
|
176
|
+
['https://unrelated.example/resource/id', undefined],
|
|
177
|
+
// unparseable urls
|
|
178
|
+
['', undefined],
|
|
179
|
+
['not a url', undefined],
|
|
180
|
+
].forEach(([url, expected]) => {
|
|
181
|
+
it(`returns ${expected} for ${url || '<empty>'}`, () => {
|
|
182
|
+
assert.equal(catalog.findAllowedDomain(url), expected);
|
|
183
|
+
});
|
|
117
184
|
});
|
|
118
185
|
});
|
|
119
186
|
|
|
@@ -121,7 +188,7 @@ describe('webex-core', () => {
|
|
|
121
188
|
const domains = [];
|
|
122
189
|
|
|
123
190
|
beforeEach(() => {
|
|
124
|
-
domains.push('example-a', 'example-b', 'example-c');
|
|
191
|
+
domains.push('example-a.com', 'example-b.com', 'example-c.com');
|
|
125
192
|
|
|
126
193
|
catalog.setAllowedDomains(domains);
|
|
127
194
|
});
|
|
@@ -160,7 +227,7 @@ describe('webex-core', () => {
|
|
|
160
227
|
const domains = [];
|
|
161
228
|
|
|
162
229
|
beforeEach(() => {
|
|
163
|
-
domains.push('example-a', 'example-b', 'example-c');
|
|
230
|
+
domains.push('example-a.com', 'example-b.com', 'example-c.com');
|
|
164
231
|
|
|
165
232
|
catalog.setAllowedDomains(domains);
|
|
166
233
|
});
|
|
@@ -170,19 +237,31 @@ describe('webex-core', () => {
|
|
|
170
237
|
});
|
|
171
238
|
|
|
172
239
|
it('sets the allowed domain entries to new values', () => {
|
|
173
|
-
const newValues = ['example-d', 'example-e', 'example-f'];
|
|
240
|
+
const newValues = ['example-d.com', 'example-e.com', 'example-f.com'];
|
|
174
241
|
|
|
175
242
|
catalog.setAllowedDomains(newValues);
|
|
176
243
|
|
|
177
244
|
assert.notDeepInclude(domains, newValues);
|
|
178
245
|
});
|
|
246
|
+
|
|
247
|
+
it('canonicalizes entries and discards those that are not usable', () => {
|
|
248
|
+
catalog.setAllowedDomains([
|
|
249
|
+
'Example-D.COM',
|
|
250
|
+
'example-d.com',
|
|
251
|
+
'example-e.com.',
|
|
252
|
+
'',
|
|
253
|
+
undefined,
|
|
254
|
+
]);
|
|
255
|
+
|
|
256
|
+
assert.deepEqual(catalog.getAllowedDomains(), ['example-d.com', 'example-e.com']);
|
|
257
|
+
});
|
|
179
258
|
});
|
|
180
259
|
|
|
181
260
|
describe('#addAllowedDomains()', () => {
|
|
182
261
|
const domains = [];
|
|
183
262
|
|
|
184
263
|
beforeEach(() => {
|
|
185
|
-
domains.push('example-a', 'example-b', 'example-c');
|
|
264
|
+
domains.push('example-a.com', 'example-b.com', 'example-c.com');
|
|
186
265
|
|
|
187
266
|
catalog.setAllowedDomains(domains);
|
|
188
267
|
});
|
|
@@ -192,13 +271,16 @@ describe('webex-core', () => {
|
|
|
192
271
|
});
|
|
193
272
|
|
|
194
273
|
it('merge the allowed domain entries with new values', () => {
|
|
195
|
-
const newValues = ['example-c', 'example-e', 'example-f'];
|
|
274
|
+
const newValues = ['example-c.com', 'example-e.com', 'example-f.com'];
|
|
196
275
|
|
|
197
276
|
catalog.addAllowedDomains(newValues);
|
|
198
277
|
|
|
199
278
|
const list = catalog.getAllowedDomains();
|
|
200
279
|
|
|
201
|
-
assert.match(
|
|
280
|
+
assert.match(
|
|
281
|
+
['example-a.com', 'example-b.com', 'example-c.com', 'example-e.com', 'example-f.com'],
|
|
282
|
+
list
|
|
283
|
+
);
|
|
202
284
|
});
|
|
203
285
|
});
|
|
204
286
|
|
|
@@ -155,7 +155,7 @@ describe('webex-core', () => {
|
|
|
155
155
|
beforeEach(() => {
|
|
156
156
|
services.webex.config = {
|
|
157
157
|
...(services.webex.config || {}),
|
|
158
|
-
services: {waitForCatalogInit: true},
|
|
158
|
+
services: {waitForCatalogInit: true, catalogInitTimeout: 15000},
|
|
159
159
|
};
|
|
160
160
|
// Reset ready flag: the outer beforeEach constructs services which
|
|
161
161
|
// runs initialize() once with no config (ungated path, flips ready to
|
|
@@ -325,6 +325,11 @@ describe('webex-core', () => {
|
|
|
325
325
|
services.initServiceCatalogs.called,
|
|
326
326
|
'expected postauth catalog init after canAuthorize flips'
|
|
327
327
|
);
|
|
328
|
+
|
|
329
|
+
// `catalog.isReady` is now set inside initServiceCatalogs (after the
|
|
330
|
+
// postauth updateServices) rather than by this listener, so it is not
|
|
331
|
+
// asserted here where initServiceCatalogs is stubbed.
|
|
332
|
+
await waitForAsync();
|
|
328
333
|
});
|
|
329
334
|
|
|
330
335
|
it('does not re-init postauth catalog when canAuthorize fires but catalog is already ready', async () => {
|
|
@@ -101,7 +101,24 @@ describe('webex-core', () => {
|
|
|
101
101
|
const domains = [];
|
|
102
102
|
|
|
103
103
|
beforeEach(() => {
|
|
104
|
-
|
|
104
|
+
// Shaped like a real catalog rather than a tidy list: the commercial
|
|
105
|
+
// domains the sdk ships with, a multi-part suffix, sites added at
|
|
106
|
+
// runtime from meeting preferences, an entry that overlaps another,
|
|
107
|
+
// and an unset entry, which callers can add and which must match
|
|
108
|
+
// nothing.
|
|
109
|
+
domains.push(
|
|
110
|
+
'wbx2.com',
|
|
111
|
+
'ciscospark.com',
|
|
112
|
+
'webex.com',
|
|
113
|
+
'webexapis.com',
|
|
114
|
+
'broadcloud.com.au',
|
|
115
|
+
'webexgov.us',
|
|
116
|
+
'example-a.com',
|
|
117
|
+
'example-b.com',
|
|
118
|
+
'example-c.com',
|
|
119
|
+
'go.example-a.com',
|
|
120
|
+
''
|
|
121
|
+
);
|
|
105
122
|
|
|
106
123
|
catalog.setAllowedDomains(domains);
|
|
107
124
|
});
|
|
@@ -110,10 +127,60 @@ describe('webex-core', () => {
|
|
|
110
127
|
domains.length = 0;
|
|
111
128
|
});
|
|
112
129
|
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
130
|
+
[
|
|
131
|
+
// real service hosts resolve to the entry that covers them
|
|
132
|
+
['https://u2c-a.wbx2.com/u2c/api/v1/limited/catalog', 'wbx2.com'],
|
|
133
|
+
['https://conv-a.wbx2.com/conversation/api/v1/conversations', 'wbx2.com'],
|
|
134
|
+
['https://foobar.ciscospark.com/resource/id', 'ciscospark.com'],
|
|
135
|
+
['https://idbroker.webex.com/idb/token', 'webex.com'],
|
|
136
|
+
['https://webexapis.com/v1/people/me', 'webexapis.com'],
|
|
137
|
+
// an entry is not required to be a bare registrable domain
|
|
138
|
+
['https://foo.broadcloud.com.au/resource/id', 'broadcloud.com.au'],
|
|
139
|
+
['https://a.b.webexgov.us/resource/id', 'webexgov.us'],
|
|
140
|
+
// the domain itself and its subdomains match
|
|
141
|
+
['https://example-a.com/resource/id', 'example-a.com'],
|
|
142
|
+
['https://sub.example-b.com/resource/id', 'example-b.com'],
|
|
143
|
+
['https://deep.sub.example-c.com/resource/id', 'example-c.com'],
|
|
144
|
+
// overlapping entries resolve to the first covering entry in the list
|
|
145
|
+
['https://go.example-a.com/resource/id', 'example-a.com'],
|
|
146
|
+
// an explicit port must not defeat the match
|
|
147
|
+
['https://example-a.com:8443/resource/id', 'example-a.com'],
|
|
148
|
+
['https://u2c-a.wbx2.com:8000/resource/id', 'wbx2.com'],
|
|
149
|
+
// hostname comparison is case insensitive
|
|
150
|
+
['https://U2C-A.WBX2.COM/resource/id', 'wbx2.com'],
|
|
151
|
+
// a trailing dot is the same name
|
|
152
|
+
['https://u2c-a.wbx2.com./resource/id', 'wbx2.com'],
|
|
153
|
+
// a sibling registrable domain must not match
|
|
154
|
+
['https://notwebex.com/resource/id', undefined],
|
|
155
|
+
['https://mywebexgov.us/resource/id', undefined],
|
|
156
|
+
['https://webex.company/resource/id', undefined],
|
|
157
|
+
['https://webex.com-unrelated.example/resource/id', undefined],
|
|
158
|
+
['https://example-a.community/resource/id', undefined],
|
|
159
|
+
// a partial label must not match, even against a multi-part entry
|
|
160
|
+
['https://broadcloud.com/resource/id', undefined],
|
|
161
|
+
// the domain matches only as a suffix, on a label boundary
|
|
162
|
+
['https://webex.com.unrelated.example/resource/id', undefined],
|
|
163
|
+
['https://unrelated.example/webex.com/resource/id', undefined],
|
|
164
|
+
['https://unrelated.example/?next=https://webex.com', undefined],
|
|
165
|
+
// userinfo is not the host
|
|
166
|
+
['https://webex.com@unrelated.example/resource/id', undefined],
|
|
167
|
+
// an encoded or unusual separator is not a label boundary, and the url
|
|
168
|
+
// parsers used by the transports do not agree on where these end the
|
|
169
|
+
// host, so they must not resolve to an allowed domain
|
|
170
|
+
['https://webex.com%2eunrelated.example/resource/id', undefined],
|
|
171
|
+
['https://webex.com%2Eunrelated.example/resource/id', undefined],
|
|
172
|
+
['https://unrelated.example%2ewebex.com/resource/id', undefined],
|
|
173
|
+
['https://unrelated.example%2Ewebex.com/resource/id', undefined],
|
|
174
|
+
['https://unrelated.example;.webex.com/resource/id', undefined],
|
|
175
|
+
// an empty allowed domain entry matches nothing
|
|
176
|
+
['https://unrelated.example/resource/id', undefined],
|
|
177
|
+
// unparseable urls
|
|
178
|
+
['', undefined],
|
|
179
|
+
['not a url', undefined],
|
|
180
|
+
].forEach(([url, expected]) => {
|
|
181
|
+
it(`returns ${expected} for ${url || '<empty>'}`, () => {
|
|
182
|
+
assert.equal(catalog.findAllowedDomain(url), expected);
|
|
183
|
+
});
|
|
117
184
|
});
|
|
118
185
|
});
|
|
119
186
|
|
|
@@ -121,7 +188,7 @@ describe('webex-core', () => {
|
|
|
121
188
|
const domains = [];
|
|
122
189
|
|
|
123
190
|
beforeEach(() => {
|
|
124
|
-
domains.push('example-a', 'example-b', 'example-c');
|
|
191
|
+
domains.push('example-a.com', 'example-b.com', 'example-c.com');
|
|
125
192
|
|
|
126
193
|
catalog.setAllowedDomains(domains);
|
|
127
194
|
});
|
|
@@ -141,7 +208,7 @@ describe('webex-core', () => {
|
|
|
141
208
|
const domains = [];
|
|
142
209
|
|
|
143
210
|
beforeEach(() => {
|
|
144
|
-
domains.push('example-a', 'example-b', 'example-c');
|
|
211
|
+
domains.push('example-a.com', 'example-b.com', 'example-c.com');
|
|
145
212
|
|
|
146
213
|
catalog.setAllowedDomains(domains);
|
|
147
214
|
});
|
|
@@ -151,19 +218,31 @@ describe('webex-core', () => {
|
|
|
151
218
|
});
|
|
152
219
|
|
|
153
220
|
it('sets the allowed domain entries to new values', () => {
|
|
154
|
-
const newValues = ['example-d', 'example-e', 'example-f'];
|
|
221
|
+
const newValues = ['example-d.com', 'example-e.com', 'example-f.com'];
|
|
155
222
|
|
|
156
223
|
catalog.setAllowedDomains(newValues);
|
|
157
224
|
|
|
158
225
|
assert.notDeepInclude(domains, newValues);
|
|
159
226
|
});
|
|
227
|
+
|
|
228
|
+
it('canonicalizes entries and discards those that are not usable', () => {
|
|
229
|
+
catalog.setAllowedDomains([
|
|
230
|
+
'Example-D.COM',
|
|
231
|
+
'example-d.com',
|
|
232
|
+
'example-e.com.',
|
|
233
|
+
'',
|
|
234
|
+
undefined,
|
|
235
|
+
]);
|
|
236
|
+
|
|
237
|
+
assert.deepEqual(catalog.getAllowedDomains(), ['example-d.com', 'example-e.com']);
|
|
238
|
+
});
|
|
160
239
|
});
|
|
161
240
|
|
|
162
241
|
describe('#addAllowedDomains()', () => {
|
|
163
242
|
const domains = [];
|
|
164
243
|
|
|
165
244
|
beforeEach(() => {
|
|
166
|
-
domains.push('example-a', 'example-b', 'example-c');
|
|
245
|
+
domains.push('example-a.com', 'example-b.com', 'example-c.com');
|
|
167
246
|
|
|
168
247
|
catalog.setAllowedDomains(domains);
|
|
169
248
|
});
|
|
@@ -173,13 +252,16 @@ describe('webex-core', () => {
|
|
|
173
252
|
});
|
|
174
253
|
|
|
175
254
|
it('merge the allowed domain entries with new values', () => {
|
|
176
|
-
const newValues = ['example-c', 'example-e', 'example-f'];
|
|
255
|
+
const newValues = ['example-c.com', 'example-e.com', 'example-f.com'];
|
|
177
256
|
|
|
178
257
|
catalog.addAllowedDomains(newValues);
|
|
179
258
|
|
|
180
259
|
const list = catalog.getAllowedDomains();
|
|
181
260
|
|
|
182
|
-
assert.match(
|
|
261
|
+
assert.match(
|
|
262
|
+
['example-a.com', 'example-b.com', 'example-c.com', 'example-e.com', 'example-f.com'],
|
|
263
|
+
list
|
|
264
|
+
);
|
|
183
265
|
});
|
|
184
266
|
});
|
|
185
267
|
|
|
@@ -157,7 +157,7 @@ describe('webex-core', () => {
|
|
|
157
157
|
beforeEach(() => {
|
|
158
158
|
services.webex.config = {
|
|
159
159
|
...(services.webex.config || {}),
|
|
160
|
-
services: {waitForCatalogInit: true},
|
|
160
|
+
services: {waitForCatalogInit: true, catalogInitTimeout: 15000},
|
|
161
161
|
};
|
|
162
162
|
// Reset ready flag: the outer beforeEach constructs services which
|
|
163
163
|
// runs initialize() once with no config (ungated path, flips ready to
|
|
@@ -319,6 +319,11 @@ describe('webex-core', () => {
|
|
|
319
319
|
services.initServiceCatalogs.called,
|
|
320
320
|
'expected postauth catalog init after canAuthorize flips'
|
|
321
321
|
);
|
|
322
|
+
|
|
323
|
+
// `catalog.isReady` is now set inside initServiceCatalogs (after the
|
|
324
|
+
// postauth updateServices) rather than by this listener, so it is not
|
|
325
|
+
// asserted here where initServiceCatalogs is stubbed.
|
|
326
|
+
await waitForAsync();
|
|
322
327
|
});
|
|
323
328
|
|
|
324
329
|
it('does not re-init postauth catalog when canAuthorize fires but catalog is already ready', async () => {
|
|
@@ -670,6 +675,22 @@ describe('webex-core', () => {
|
|
|
670
675
|
);
|
|
671
676
|
});
|
|
672
677
|
|
|
678
|
+
it('includes the catalog override query when configured', async () => {
|
|
679
|
+
services.webex.config.services = {useCatalogOverride: true};
|
|
680
|
+
sinon.stub(services, '_formatReceivedHostmap').resolves('map response');
|
|
681
|
+
sinon.stub(services, 'request').resolves({});
|
|
682
|
+
|
|
683
|
+
await services._fetchNewServiceHostmap({from: 'limited'});
|
|
684
|
+
|
|
685
|
+
assert.calledOnceWithExactly(services.request, {
|
|
686
|
+
method: 'GET',
|
|
687
|
+
service: 'u2c',
|
|
688
|
+
resource: '/limited/catalog',
|
|
689
|
+
qs: {format: 'U2CV2', useCatalogOverride: true},
|
|
690
|
+
headers: {},
|
|
691
|
+
});
|
|
692
|
+
});
|
|
693
|
+
|
|
673
694
|
it('checks service request rejects', async () => {
|
|
674
695
|
const error = new Error('some error');
|
|
675
696
|
|
|
@@ -397,8 +397,6 @@ describe('Webex', () => {
|
|
|
397
397
|
return new Promise((resolve) => webex.once('loaded', resolve)).then(() => {
|
|
398
398
|
assert.isFalse(webex.ready);
|
|
399
399
|
assert.isFalse(webex.test.ready);
|
|
400
|
-
// Set services.ready to true since it now blocks webex.ready
|
|
401
|
-
webex.internal.services.ready = true;
|
|
402
400
|
webex.test.ready = true;
|
|
403
401
|
assert.isTrue(webex.test.ready);
|
|
404
402
|
assert.isTrue(webex.ready);
|
|
@@ -82,8 +82,6 @@ describe('Webex', () => {
|
|
|
82
82
|
assert.isFalse(webex.internal.test.ready);
|
|
83
83
|
assert.isFalse(webex.internal.ready);
|
|
84
84
|
assert.isFalse(webex.ready);
|
|
85
|
-
// Set services.ready to true since it now blocks webex.ready
|
|
86
|
-
webex.internal.services.ready = true;
|
|
87
85
|
webex.internal.test.ready = true;
|
|
88
86
|
assert.isTrue(webex.internal.ready);
|
|
89
87
|
assert.isTrue(webex.ready);
|